Thu, 26 Aug 2021 19:37:00 +0300
Update license year
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
1 | import datetime |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
2 | import parse |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
3 | import os |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
4 | from pathlib import Path |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
5 | import linetypes |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
6 | import math |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
7 | |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
8 | def find_ldraw_file(filename, libraries): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
9 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
10 | Searches the LDraw libraries for the specified file. |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
11 | `libraries` must be an iterable of LDraw library root paths. |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
12 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
13 | if os.path.sep != "\\": |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
14 | filename = filename.replace("\\", os.path.sep) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
15 | for library in libraries: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
16 | for path in [ |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
17 | Path(library) / filename, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
18 | Path(library) / "parts" / filename, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
19 | Path(library) / "p" / filename, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
20 | ]: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
21 | if path.exists(): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
22 | return path |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
23 | raise FileNotFoundError(str.format( |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
24 | '"{}" not found in the LDraw libraries', |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
25 | filename, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
26 | )) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
27 | |
92
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
28 | def is_logo_stud_name(name): |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
29 | return name in ['stud.dat', 'stud3.dat'] |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
30 | |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
31 | class CyclicalReferenceError(Exception): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
32 | pass |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
33 | |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
34 | class SubfileCache: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
35 | class Subfile: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
36 | def __init__(self): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
37 | self.valid = None |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
38 | self.flatness = None |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
39 | self.description = None |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
40 | self.problem = None |
92
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
41 | self.has_studs = None # Whether or not it contains studs |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
42 | self.vertices = set() |
145
fde18c4d6784
refactoring: moved context-dependant data to new class LDrawContext. ldcheck no longer writes the config file, and looks for it in sensible locations like ~/.config and /etc. LDraw libraries can now be specified on the command line.
Teemu Piippo <teemu@hecknology.net>
parents:
95
diff
changeset
|
43 | def __init__(self, context): |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
44 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
45 | Initializes a new subfile cache |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
46 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
47 | self.cache = dict() |
145
fde18c4d6784
refactoring: moved context-dependant data to new class LDrawContext. ldcheck no longer writes the config file, and looks for it in sensible locations like ~/.config and /etc. LDraw libraries can now be specified on the command line.
Teemu Piippo <teemu@hecknology.net>
parents:
95
diff
changeset
|
48 | self.context = context |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
49 | self.reference_stack = [] |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
50 | def flatness_of(self, filename): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
51 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
52 | Returns the set of all directiones the specified file is flat in. |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
53 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
54 | self.prepare_file(filename) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
55 | return self.cache[filename].flatness |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
56 | def description_of(self, filename): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
57 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
58 | Returns the description of the specified file |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
59 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
60 | self.prepare_file(filename) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
61 | return self.cache[filename].description |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
62 | def find_file(self, filename): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
63 | return find_ldraw_file( |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
64 | filename = filename, |
145
fde18c4d6784
refactoring: moved context-dependant data to new class LDrawContext. ldcheck no longer writes the config file, and looks for it in sensible locations like ~/.config and /etc. LDraw libraries can now be specified on the command line.
Teemu Piippo <teemu@hecknology.net>
parents:
95
diff
changeset
|
65 | libraries = self.context.libraries, |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
66 | ) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
67 | def prepare_file(self, filename): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
68 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
69 | Loads the file if not loaded yet. |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
70 | ''' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
71 | if filename not in self.cache: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
72 | self._load_subfile(filename) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
73 | return self.cache[filename] |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
74 | def _load_subfile(self, filename): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
75 | # ward against cyclical dependencies |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
76 | if filename in self.reference_stack: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
77 | raise CyclicalReferenceError( |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
78 | ' -> '.join(self.reference_stack + [filename]), |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
79 | ) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
80 | self.reference_stack.append(filename) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
81 | subfile = SubfileCache.Subfile() |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
82 | self.cache[filename] = subfile |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
83 | try: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
84 | path = self.find_file(filename) |
94
109fb7cf658f
added a check for non-DOS line endings
Teemu Piippo <teemu@hecknology.net>
parents:
92
diff
changeset
|
85 | with path.open('rb') as file: |
145
fde18c4d6784
refactoring: moved context-dependant data to new class LDrawContext. ldcheck no longer writes the config file, and looks for it in sensible locations like ~/.config and /etc. LDraw libraries can now be specified on the command line.
Teemu Piippo <teemu@hecknology.net>
parents:
95
diff
changeset
|
86 | model = parse.read_ldraw(file, context = self.context) |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
87 | except (FileNotFoundError, IOError, PermissionError) as error: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
88 | subfile.valid = False |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
89 | subfile.problem = str(error) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
90 | else: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
91 | if isinstance(model.body[0], linetypes.MetaCommand): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
92 | subfile.valid = True |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
93 | subfile.description = model.body[0].text |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
94 | else: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
95 | subfile.valid = False |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
96 | subfile.problem = 'Description not found' |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
97 | if subfile.valid: |
95
a3536e51f6bc
fixed the cyclical dependency handling
Teemu Piippo <teemu@hecknology.net>
parents:
94
diff
changeset
|
98 | subfile.vertices = set(parse.model_vertices(model, file_cache = self)) |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
99 | subfile.flatness = {'x', 'y', 'z'} |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
100 | for vertex in subfile.vertices: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
101 | # Use list(subfile.flatness) for iteration because the |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
102 | # actual set may be modified during the loop |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
103 | for dimension in list(subfile.flatness): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
104 | if not math.isclose( |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
105 | getattr(vertex, dimension), |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
106 | 0.0, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
107 | abs_tol = 1e-05, |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
108 | ): |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
109 | subfile.flatness.remove(dimension) |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
110 | if not subfile.flatness: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
111 | break |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
112 | for subfile_reference in model.subfile_references: |
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
113 | # Go through all the subfile references so that we catch any |
92
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
114 | # cyclical references and to get studs |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
115 | self.prepare_file(subfile_reference.subfile_path) |
92
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
116 | subfile.has_studs = any( |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
117 | self.cache[subfile_reference.subfile_path].has_studs |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
118 | or is_logo_stud_name(subfile_reference.subfile_path) |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
119 | for subfile_reference in model.subfile_references |
b8d72909d593
improved the mirrored stud check to catch cases where a subfile that contains studs is mirrored
Teemu Piippo <teemu@hecknology.net>
parents:
58
diff
changeset
|
120 | ) |
54
0c686d10eb49
added tests for moved-to files and scaling in flat dimensions
Teemu Piippo <teemu@hecknology.net>
parents:
diff
changeset
|
121 | self.reference_stack.pop() |