/src/assimp/code/AssetLib/DXF/DXFHelper.h
Line | Count | Source |
1 | | /* |
2 | | Open Asset Import Library (assimp) |
3 | | ---------------------------------------------------------------------- |
4 | | |
5 | | Copyright (c) 2006-2025, assimp team |
6 | | |
7 | | All rights reserved. |
8 | | |
9 | | Redistribution and use of this software in source and binary forms, |
10 | | with or without modification, are permitted provided that the |
11 | | following conditions are met: |
12 | | |
13 | | * Redistributions of source code must retain the above |
14 | | copyright notice, this list of conditions and the |
15 | | following disclaimer. |
16 | | |
17 | | * Redistributions in binary form must reproduce the above |
18 | | copyright notice, this list of conditions and the |
19 | | following disclaimer in the documentation and/or other |
20 | | materials provided with the distribution. |
21 | | |
22 | | * Neither the name of the assimp team, nor the names of its |
23 | | contributors may be used to endorse or promote products |
24 | | derived from this software without specific prior |
25 | | written permission of the assimp team. |
26 | | |
27 | | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
28 | | "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
29 | | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
30 | | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
31 | | OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
32 | | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
33 | | LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
34 | | DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
35 | | THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
36 | | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
37 | | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
38 | | |
39 | | ---------------------------------------------------------------------- |
40 | | */ |
41 | | |
42 | | /** @file DXFHelper.h |
43 | | * @brief Internal utilities for the DXF loader. |
44 | | */ |
45 | | |
46 | | #ifndef INCLUDED_DXFHELPER_H |
47 | | #define INCLUDED_DXFHELPER_H |
48 | | |
49 | | #include <assimp/LineSplitter.h> |
50 | | #include <assimp/TinyFormatter.h> |
51 | | #include <assimp/StreamReader.h> |
52 | | #include <assimp/fast_atof.h> |
53 | | #include <vector> |
54 | | #include <assimp/DefaultLogger.hpp> |
55 | | |
56 | | namespace Assimp { |
57 | | namespace DXF { |
58 | | |
59 | | // read pairs of lines, parse group code and value and provide utilities |
60 | | // to convert the data to the target data type. |
61 | | // do NOT skip empty lines. In DXF files, they count as valid data. |
62 | | class LineReader { |
63 | | public: |
64 | 29 | LineReader(StreamReaderLE& reader) : splitter(reader,false,true), groupcode( 0 ), end() { |
65 | | // empty |
66 | 29 | } |
67 | | |
68 | | // ----------------------------------------- |
69 | 148k | bool Is(int gc, const char* what) const { |
70 | 148k | return groupcode == gc && !strcmp(what,value.c_str()); |
71 | 148k | } |
72 | | |
73 | | // ----------------------------------------- |
74 | 5.90k | bool Is(int gc) const { |
75 | 5.90k | return groupcode == gc; |
76 | 5.90k | } |
77 | | |
78 | | // ----------------------------------------- |
79 | 47.5k | int GroupCode() const { |
80 | 47.5k | return groupcode; |
81 | 47.5k | } |
82 | | |
83 | | // ----------------------------------------- |
84 | 1.12k | const std::string& Value() const { |
85 | 1.12k | return value; |
86 | 1.12k | } |
87 | | |
88 | | // ----------------------------------------- |
89 | 57.7k | bool End() const { |
90 | 57.7k | return !((bool)*this); |
91 | 57.7k | } |
92 | | |
93 | | // ----------------------------------------- |
94 | 882 | unsigned int ValueAsUnsignedInt() const { |
95 | 882 | return strtoul10(value.c_str()); |
96 | 882 | } |
97 | | |
98 | | // ----------------------------------------- |
99 | 573 | int ValueAsSignedInt() const { |
100 | 573 | return strtol10(value.c_str()); |
101 | 573 | } |
102 | | |
103 | | // ----------------------------------------- |
104 | 7.18k | float ValueAsFloat() const { |
105 | 7.18k | return fast_atof(value.c_str()); |
106 | 7.18k | } |
107 | | |
108 | | // ----------------------------------------- |
109 | | /** pseudo-iterator increment to advance to the next (groupcode/value) pair */ |
110 | 52.8k | LineReader& operator++() { |
111 | 52.8k | if (end) { |
112 | 27 | if (end == 1) { |
113 | 27 | ++end; |
114 | 27 | } |
115 | 27 | return *this; |
116 | 27 | } |
117 | | |
118 | 52.8k | try { |
119 | 52.8k | groupcode = strtol10(splitter->c_str()); |
120 | 52.8k | splitter++; |
121 | | |
122 | 52.8k | value = *splitter; |
123 | 52.8k | splitter++; |
124 | | |
125 | | // automatically skip over {} meta blocks (these are for application use |
126 | | // and currently not relevant for Assimp). |
127 | 52.8k | if (value.length() && value[0] == '{') { |
128 | | |
129 | 8 | size_t cnt = 0; |
130 | 16 | for(;splitter->length() && splitter->at(0) != '}'; splitter++, cnt++); |
131 | | |
132 | 8 | splitter++; |
133 | 8 | ASSIMP_LOG_VERBOSE_DEBUG("DXF: skipped over control group (",cnt," lines)"); |
134 | 8 | } |
135 | 52.8k | } catch(std::logic_error&) { |
136 | 16 | ai_assert(!splitter); |
137 | 16 | } |
138 | 52.8k | if (!splitter) { |
139 | 27 | end = 1; |
140 | 27 | } |
141 | 52.8k | return *this; |
142 | 52.8k | } |
143 | | |
144 | | // ----------------------------------------- |
145 | 24.1k | LineReader& operator++(int) { |
146 | 24.1k | return ++(*this); |
147 | 24.1k | } |
148 | | |
149 | | |
150 | | // ----------------------------------------- |
151 | 57.7k | operator bool() const { |
152 | 57.7k | return end <= 1; |
153 | 57.7k | } |
154 | | |
155 | | private: |
156 | | LineSplitter splitter; |
157 | | int groupcode; |
158 | | std::string value; |
159 | | int end; |
160 | | }; |
161 | | |
162 | | // represents a POLYLINE or a LWPOLYLINE. or even a 3DFACE The data is converted as needed. |
163 | | struct PolyLine { |
164 | 2.10k | PolyLine() : flags() { |
165 | | // empty |
166 | 2.10k | } |
167 | | |
168 | | std::vector<aiVector3D> positions; |
169 | | std::vector<aiColor4D> colors; |
170 | | std::vector<unsigned int> indices; |
171 | | std::vector<unsigned int> counts; |
172 | | unsigned int flags; |
173 | | |
174 | | std::string layer; |
175 | | std::string desc; |
176 | | }; |
177 | | |
178 | | // reference to a BLOCK. Specifies its own coordinate system. |
179 | | struct InsertBlock { |
180 | 1.27k | InsertBlock() : pos(0.f, 0.f, 0.f), scale(1.f,1.f,1.f), angle(0.0f) { |
181 | | // empty |
182 | 1.27k | } |
183 | | |
184 | | aiVector3D pos; |
185 | | aiVector3D scale; |
186 | | float angle; |
187 | | |
188 | | std::string name; |
189 | | }; |
190 | | |
191 | | |
192 | | // keeps track of all geometry in a single BLOCK. |
193 | | struct Block { |
194 | | std::vector< std::shared_ptr<PolyLine> > lines; |
195 | | std::vector<InsertBlock> insertions; |
196 | | |
197 | | std::string name; |
198 | | aiVector3D base; |
199 | | }; |
200 | | |
201 | | struct FileData { |
202 | | // note: the LAST block always contains the stuff from ENTITIES. |
203 | | std::vector<Block> blocks; |
204 | | }; |
205 | | |
206 | | } // namespace DXF |
207 | | } // namespace Assimp |
208 | | |
209 | | #endif // INCLUDED_DXFHELPER_H |