Commit d8405e3e authored by Jean-Charles BRAUN's avatar Jean-Charles BRAUN

Initial commit

parents
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import os
import shutil
import dbf
import colorama
from colorama import Fore
# Réinitialisation de la couleur après chaque 'print'
colorama.init(autoreset=True)
# Choix d'un préfixe pour les nouveaux fichiers
prefix = input(Fore.CYAN + '\nPréfixe pour les nouveaux fichiers : ' + Fore.RESET)
if not prefix:
print(Fore.RED + '======================')
print(Fore.RED + 'Programme interrompu !')
print(Fore.RED + '======================')
exit(0)
# Copie et renommage des fichiers
list_files = []
for filename in os.listdir():
if os.path.isfile(filename) and 'entities' in filename:
limit = filename.find('-')
shortname = prefix + '_' + filename[(limit + 1):]
shutil.copy(filename, shortname)
list_files.append(shortname)
# Modification des fichiers DBF
for element in list_files:
if element.endswith('.dbf'):
(filename, extension) = os.path.splitext(element)
with dbf.Table(element) as document:
document.codepage = dbf.CodePage('utf8')
# Création d'un fichier CPG 'utf8'
with open(filename + '.cpg', 'w') as cpgfile:
cpgfile.write('UTF-8\n')
# Affichage des propriétés du fichier DBF courant
print(document)
# Si le fichier est vide, tous les éléments sont effacés
if 'Record count: 0' in str(document):
print(Fore.RED + 'Fichier vide !')
print(Fore.RED + '----')
for ext in ['.cpg', '.dbf', '.prj', '.qpj', '.shp', '.shx']:
if os.path.exists(filename + ext):
os.remove(filename + ext)
print(Fore.RED + filename + ext + ' effacé !')
continue
# Si le fichier ne contient ni XDATA ni texte, tous les éléments sont effacés
if document[0][2].count(' ') == 254 and document[0][5].count(' ') == 254:
print(Fore.RED + 'XDATA vide / Texte vide !')
print(Fore.RED + '----')
for ext in ['.cpg', '.dbf', '.prj', '.qpj', '.shp', '.shx']:
if os.path.exists(filename + ext):
os.remove(filename + ext)
print(Fore.RED + filename + ext + ' effacé !')
continue
# Si le fichier ne contient pas de XDATA mais du texte, tous les éléments sont conservés
if document[0][2].count(' ') == 254 and document[0][5].count(' ') != 254:
print(Fore.YELLOW + 'XDATA vide / Texte OK -> Fichier non traité !')
continue
# Traitement du fichier contenant les XDATA (pas de texte ici)
for field in ['layer', 'subclasses', 'linetype', 'entityhand', 'text']:
document.delete_fields(field)
document.add_fields('UE C(50); TYPE C(20); OP C(12); DATE C(8); COMMUNE C(45); INSEE C(5)')
# Préparation des nouvelles données
table = []
for record in document:
xdata = record['extendeden'].split(' ')
liste = []
for datum in xdata:
if datum != '' and datum != '{' and datum != '}':
liste.append(str(datum))
table.append(liste)
document.delete_fields('extendeden')
# Écriture des nouvelles données
for index, record in enumerate(dbf.Process(document)):
data = table[index]
for num in range(len(data)):
record[num] = data[num]
print(Fore.GREEN + 'XDATA OK / Texte vide -> Fichier traité !')
# Suppression du backup
if os.path.exists(filename + '_backup.dbf'):
os.remove(filename + '_backup.dbf')
# dbfconvert.py
Ce script permet de réorganiser le contenu de fichiers DBF.
## Prérequis
* python3-colorama
* python3-dbf
## Utilisation
Placez le fichier `dbfconvert.py` dans le dossier contenant vos fichiers DBF, puis faites :
```
$ python3 dbfconvert.py
```
## Fonctionnement
Ce script fonctionne dans un cadre bien précis : il permet de manipuler le contenu de fichiers DBF créés avec QGIS, quand celui-ci importe un fichier DXF contenant des XDATA (*Extended Entity Data*).
Exemple avec un fichier DXF contenant des données étendues (XDATA) sur les tracés, les points et les blocs :
Dans un logiciel de type CAD, les XDATA ne sont pas directement visibles à l'écran. Selon les possibilités du logiciel, en sélectionnant une entité, la commande `XDLIST` retourne :
```
* Registered Application Name: TABLE_UE
* Code 1002, Starting or ending brace: {
* Code 1000, ASCII string: 28
* Code 1000, ASCII string: Structure
* Code 1000, ASCII string: 094268
* Code 1000, ASCII string: 20160222
* Code 1000, ASCII string: Saulx
* Code 1000, ASCII string: 70478
* Code 1002, Starting or ending brace: }
```
Lorsque QGIS importe ce fichier DXF, ce dernier est alors décomposé en différentes couches :
* entities LineString
* entities Point
En utilisant la fonction `Séparer une couche vecteur` et en choisissant `Layer` pour chacune des couches, on obtient une série de fichiers du type CPG, DBF, PRJ, QPJ, SHP et SHX.
Lorsqu'on charge les fichiers SHP ainsi obtenus dans un nouveau projet QGIS, on obtient des couches qui correspondent aux anciens calques du fichier DXF. Chacune des couches contient des entités graphiques ainsi qu'une table attributaire à 6 colonnes. L'une de ces colonnes est nommée **ExtendedEn**, elle contient les données étendues (XDATA) associées à chaque entité.
Le script `dbfconvert.py` crée une copie des fichiers CPG, DBF, PRJ, QPJ, SHP et SHX. Puis, il va modifier les fichiers DBF selon leur contenu :
**Cas n°1** : le fichier DBF est vide
-> tous les fichiers liés à la couche sont effacés
**Cas n°2** : le fichier DBF ne contient ni XDATA ni texte
-> tous les fichiers liés à la couche sont effacés
**Cas n°3** : le fichier DBF ne contient pas de XDATA mais du texte
-> tous les fichiers liés à la couche sont conservés, sans modifications
**Cas n°4** : le fichier DBF contient des XDATA (pas de texte ici)
-> traitement du fichier DBF avec réorganisation des colonnes
Exemple de contenu d'un fichier DBF avec *Extended Entity Data* :
| Layer | SubClasses | ExtendedEn | Linetype | EntityHand | Text |
|--------------|---------------------------|------------------------------------------------|----------|------------|------|
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 13 Structure 094268 20160222 Saulx 70478 }` | | 25E | |
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 14 Structure 094268 20160222 Saulx 70478 }` | | 269 | |
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 16 Structure 094268 20160222 Saulx 70478 }` | | 27F | |
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 21 Structure 094268 20160222 Saulx 70478 }` | | 2EA | |
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 22 Structure 094268 20160222 Saulx 70478 }` | | 2FB | |
| 2-Structures | AcDbEntity:AcDb2dPolyline | `{ 28 Structure 094268 20160222 Saulx 70478 }` | | 33E | |
Après traitement, seule la colonne **ExtendedEn** est conservée et les informations sont séparées :
| UE | TYPE | OP | DATE | COMMUNE | INSEE |
|----|-----------|--------|----------|---------|-------|
| 13 | Structure | 094268 | 20160222 | Saulx | 70478 |
| 14 | Structure | 094268 | 20160222 | Saulx | 70478 |
| 16 | Structure | 094268 | 20160222 | Saulx | 70478 |
| 21 | Structure | 094268 | 20160222 | Saulx | 70478 |
| 22 | Structure | 094268 | 20160222 | Saulx | 70478 |
| 28 | Structure | 094268 | 20160222 | Saulx | 70478 |
Le fichier DBF est prêt !
## Licence
Le programme ci-joint est publié sous licence GPLv3.
[www.gnu.org/licenses/gpl-3.0.fr.html](https://www.gnu.org/licenses/gpl-3.0.fr.html)
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment