src/LDConfig.cc

changeset 655
b376645315ab
parent 654
a74f2ff353b8
child 656
2a1c204df14d
child 706
d79083b9f74d
equal deleted inserted replaced
654:a74f2ff353b8 655:b376645315ab
1 /*
2 * LDForge: LDraw parts authoring CAD
3 * Copyright (C) 2013, 2014 Santeri Piippo
4 *
5 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
17 */
18
19 #include <QFile>
20 #include "Document.h"
21 #include "LDConfig.h"
22 #include "MainWindow.h"
23 #include "Misc.h"
24 #include "Colors.h"
25
26 // =============================================================================
27 //
28 // Helper function for parseLDConfig
29 //
30 static bool parseLDConfigTag (LDConfigParser& pars, char const* tag, QString& val)
31 {
32 int pos;
33
34 // Try find the token and get its position
35 if (!pars.findToken (pos, tag, 1))
36 return false;
37
38 // Get the token after it and store it into val
39 return pars.getToken (val, pos + 1);
40 }
41
42 // =============================================================================
43 //
44 void parseLDConfig()
45 {
46 QFile* fp = openLDrawFile ("LDConfig.ldr", false);
47
48 if (!fp)
49 {
50 critical (QObject::tr ("Unable to open LDConfig.ldr for parsing."));
51 return;
52 }
53
54 // Read in the lines
55 while (fp->atEnd() == false)
56 {
57 QString line = QString::fromUtf8 (fp->readLine());
58
59 if (line.isEmpty() || line[0] != '0')
60 continue; // empty or illogical
61
62 line.remove ('\r');
63 line.remove ('\n');
64
65 // Parse the line
66 LDConfigParser pars (line, ' ');
67
68 int code = 0, alpha = 255;
69 QString name, facename, edgename, valuestr;
70
71 // Check 0 !COLOUR, parse the name
72 if (!pars.tokenCompare (0, "0") || !pars.tokenCompare (1, "!COLOUR") || !pars.getToken (name, 2))
73 continue;
74
75 // Replace underscores in the name with spaces for readability
76 name.replace ("_", " ");
77
78 // Get the CODE tag
79 if (!parseLDConfigTag (pars, "CODE", valuestr))
80 continue;
81
82 if (!numeric (valuestr))
83 continue; // not a number
84
85 // Ensure that the code is within [0 - 511]
86 bool ok;
87 code = valuestr.toShort (&ok);
88
89 if (!ok || code < 0 || code >= 512)
90 continue;
91
92 // VALUE and EDGE tags
93 if (!parseLDConfigTag (pars, "VALUE", facename) || !parseLDConfigTag (pars, "EDGE", edgename))
94 continue;
95
96 // Ensure that our colors are correct
97 QColor faceColor (facename),
98 edgeColor (edgename);
99
100 if (!faceColor.isValid() || !edgeColor.isValid())
101 continue;
102
103 // Parse alpha if given.
104 if (parseLDConfigTag (pars, "ALPHA", valuestr))
105 alpha = clamp (valuestr.toInt(), 0, 255);
106
107 LDColor* col = new LDColor;
108 col->name = name;
109 col->faceColor = faceColor;
110 col->edgeColor = edgeColor;
111 col->hexcode = facename;
112 col->faceColor.setAlpha (alpha);
113 col->index = code;
114 setColor (code, col);
115 }
116
117 fp->close();
118 fp->deleteLater();
119 }
120
121 // =============================================================================
122 //
123 LDConfigParser::LDConfigParser (QString inText, char sep)
124 {
125 m_tokens = inText.split (sep, QString::SkipEmptyParts);
126 m_pos = -1;
127 }
128
129 // =============================================================================
130 //
131 bool LDConfigParser::isAtBeginning()
132 {
133 return m_pos == -1;
134 }
135
136 // =============================================================================
137 //
138 bool LDConfigParser::isAtEnd()
139 {
140 return m_pos == m_tokens.size() - 1;
141 }
142
143 // =============================================================================
144 //
145 bool LDConfigParser::getToken (QString& val, const int pos)
146 {
147 if (pos >= m_tokens.size())
148 return false;
149
150 val = m_tokens[pos];
151 return true;
152 }
153
154 // =============================================================================
155 //
156 bool LDConfigParser::getNextToken (QString& val)
157 {
158 return getToken (val, ++m_pos);
159 }
160
161 // =============================================================================
162 //
163 bool LDConfigParser::peekNextToken (QString& val)
164 {
165 return getToken (val, m_pos + 1);
166 }
167
168 // =============================================================================
169 //
170 bool LDConfigParser::findToken (int& result, char const* needle, int args)
171 {
172 for (int i = 0; i < (m_tokens.size() - args); ++i)
173 {
174 if (m_tokens[i] == needle)
175 {
176 result = i;
177 return true;
178 }
179 }
180
181 return false;
182 }
183
184 // =============================================================================
185 //
186 void LDConfigParser::rewind()
187 {
188 m_pos = -1;
189 }
190
191 // =============================================================================
192 //
193 void LDConfigParser::seek (int amount, bool rel)
194 {
195 m_pos = (rel ? m_pos : 0) + amount;
196 }
197
198 // =============================================================================
199 //
200 int LDConfigParser::getSize()
201 {
202 return m_tokens.size();
203 }
204
205 // =============================================================================
206 //
207 bool LDConfigParser::tokenCompare (int inPos, const char* sOther)
208 {
209 QString tok;
210
211 if (!getToken (tok, inPos))
212 return false;
213
214 return (tok == sOther);
215 }

mercurial