Newer
Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
/*
* Copyright (c) 2015 Tricoire Sebastien 3dsman@free.fr
*
* This software is provided 'as-is', without any express or implied
* warranty. In no event will the authors be held liable for any damages
* arising from the use of this software.
*
* Permission is granted to anyone to use this software for any purpose,
* including commercial applications, and to alter it and redistribute it
* freely, subject to the following restrictions:
*
* 1. The origin of this software must not be misrepresented; you must not
* claim that you wrote the original software. If you use this software
* in a product, an acknowledgment in the product documentation would be
* appreciated but is not required.
* 2. Altered source versions must be plainly marked as such, and must not be
* misrepresented as being the original software.
* 3. This notice may not be removed or altered from any source distribution.
*
*/
#include "OE_io.h"
#include "OE_document.h"
#include "stitchs/OE_staticstitch.h"
#include "stitchs/OE_linkstitch.h"
#include <iostream>
#include <fstream>
static bool loadFromPES(std::string path, OE_document* document);
//static bool saveToPES(const OE_document* document, std::string path);
extern const OE_io ioPes;
const OE_io ioPes = {"pes", "Brother PES format", loadFromPES, 0};
static const int pecThreadCount = 65;
struct PESCol
{
unsigned char rgb[3];
const char* name;
const char* dummy;
};
static const PESCol pecThreads[] = {
{{ 0, 0, 0}, "Unknown", ""}, /* Index 0 */
{{ 14, 31, 124}, "Prussian Blue", ""}, /* Index 1 */
{{ 10, 85, 163}, "Blue", ""}, /* Index 2 */
{{ 0, 135, 119}, "Teal Green", ""}, /* Index 3 */ /* TODO: Verify RGB value is correct */
{{ 75, 107, 175}, "Cornflower Blue", ""}, /* Index 4 */
{{237, 23, 31}, "Red", ""}, /* Index 5 */
{{209, 92, 0}, "Reddish Brown", ""}, /* Index 6 */
{{145, 54, 151}, "Magenta", ""}, /* Index 7 */
{{228, 154, 203}, "Light Lilac", ""}, /* Index 8 */
{{145, 95, 172}, "Lilac", ""}, /* Index 9 */
{{158, 214, 125}, "Mint Green", ""}, /* Index 10 */ /* TODO: Verify RGB value is correct */
{{232, 169, 0}, "Deep Gold", ""}, /* Index 11 */
{{254, 186, 53}, "Orange", ""}, /* Index 12 */
{{255, 255, 0}, "Yellow", ""}, /* Index 13 */
{{112, 188, 31}, "Lime Green", ""}, /* Index 14 */
{{186, 152, 0}, "Brass", ""}, /* Index 15 */
{{168, 168, 168}, "Silver", ""}, /* Index 16 */
{{125, 111, 0}, "Russet Brown", ""}, /* Index 17 */ /* TODO: Verify RGB value is correct */
{{255, 255, 179}, "Cream Brown", ""}, /* Index 18 */
{{ 79, 85, 86}, "Pewter", ""}, /* Index 19 */
{{ 0, 0, 0}, "Black", ""}, /* Index 20 */
{{ 11, 61, 145}, "Ultramarine", ""}, /* Index 21 */
{{119, 1, 118}, "Royal Purple", ""}, /* Index 22 */
{{ 41, 49, 51}, "Dark Gray", ""}, /* Index 23 */
{{ 42, 19, 1}, "Dark Brown", ""}, /* Index 24 */
{{246, 74, 138}, "Deep Rose", ""}, /* Index 25 */
{{178, 118, 36}, "Light Brown", ""}, /* Index 26 */
{{252, 187, 197}, "Salmon Pink", ""}, /* Index 27 */ /* TODO: Verify RGB value is correct */
{{254, 55, 15}, "Vermillion", ""}, /* Index 28 */
{{240, 240, 240}, "White", ""}, /* Index 29 */
{{106, 28, 138}, "Violet", ""}, /* Index 30 */
{{168, 221, 196}, "Seacrest", ""}, /* Index 31 */
{{ 37, 132, 187}, "Sky Blue", ""}, /* Index 32 */
{{254, 179, 67}, "Pumpkin", ""}, /* Index 33 */
{{255, 243, 107}, "Cream Yellow", ""}, /* Index 34 */
{{208, 166, 96}, "Khaki", ""}, /* Index 35 */
{{209, 84, 0}, "Clay Brown", ""}, /* Index 36 */
{{102, 186, 73}, "Leaf Green", ""}, /* Index 37 */
{{ 19, 74, 70}, "Peacock Blue", ""}, /* Index 38 */
{{135, 135, 135}, "Gray", ""}, /* Index 39 */
{{216, 204, 198}, "Warm Gray", ""}, /* Index 40 */ /* TODO: Verify RGB value is correct */
{{ 67, 86, 7}, "Dark Olive", ""}, /* Index 41 */
{{253, 217, 222}, "Flesh Pink", ""}, /* Index 42 */ /* TODO: Verify RGB value is correct */
{{249, 147, 188}, "Pink", ""}, /* Index 43 */
{{ 0, 56, 34}, "Deep Green", ""}, /* Index 44 */
{{178, 175, 212}, "Lavender", ""}, /* Index 45 */
{{104, 106, 176}, "Wisteria Violet", ""}, /* Index 46 */
{{239, 227, 185}, "Beige", ""}, /* Index 47 */
{{247, 56, 102}, "Carmine", ""}, /* Index 48 */
{{181, 75, 100}, "Amber Red", ""}, /* Index 49 */ /* TODO: Verify RGB value is correct */
{{ 19, 43, 26}, "Olive Green", ""}, /* Index 50 */
{{199, 1, 86}, "Dark Fuschia", ""}, /* Index 51 */ /* TODO: Verify RGB value is correct */
{{254, 158, 50}, "Tangerine", ""}, /* Index 52 */
{{168, 222, 235}, "Light Blue", ""}, /* Index 53 */
{{ 0, 103, 62}, "Emerald Green", ""}, /* Index 54 */ /* TODO: Verify RGB value is correct */
{{ 78, 41, 144}, "Purple", ""}, /* Index 55 */
{{ 47, 126, 32}, "Moss Green", ""}, /* Index 56 */
{{255, 204, 204}, "Flesh Pink", ""}, /* Index 57 */ /* TODO: Verify RGB value is correct */ /* TODO: Flesh Pink is Index 42, is this Index incorrect? */
{{255, 217, 17}, "Harvest Gold", ""}, /* Index 58 */
{{ 9, 91, 166}, "Electric Blue", ""}, /* Index 59 */
{{240, 249, 112}, "Lemon Yellow", ""}, /* Index 60 */
{{227, 243, 91}, "Fresh Green", ""}, /* Index 61 */
{{255, 153, 0}, "Orange", ""}, /* Index 62 */ /* TODO: Verify RGB value is correct */ /* TODO: Orange is Index 12, is this Index incorrect? */
{{255, 240, 141}, "Cream Yellow", ""}, /* Index 63 */ /* TODO: Verify RGB value is correct */ /* TODO: Cream Yellow is Index 34, is this Index incorrect? */
{{255, 200, 200}, "Applique", ""} /* Index 64 */
};
static int getU8(std::ifstream& in)
{
unsigned char u = 0;
if (in.good())
in.read((char*)&u, 1);
return u;
}
static bool loadFromPES(std::string path, OE_document* document)
{
std::ifstream in(path);
if (!in.is_open())
return false;
in.seekg(8);
int pecstart = getU8(in);
pecstart |= getU8(in)<<8;
pecstart |= getU8(in)<<16;
pecstart |= getU8(in)<<24;
std::cout << "PES: " << "pecstart=" << pecstart << std::endl;
std::cout << "PES: " << "jumping to " << (pecstart+48) << std::endl;
in.seekg(pecstart+48);
int nThreads = getU8(in)+1;
std::cout << "PES: " << nThreads << " threads" << std::endl;
for (int thread=0; thread<nThreads; thread++) {
int iCol = getU8(in);
if (iCol >= pecThreadCount) {
std::cout << "PES: " << "thread " << thread << " unmanaged color " << iCol << ". Fallbacking." << std::endl;
iCol = 0;
}
const PESCol* col = &pecThreads[iCol];
std::cout << "PES: " << "thread " << thread << " col (" <<
(int)col->rgb[0] << ", " <<
(int)col->rgb[1] << ", " <<
(int)col->rgb[2] << ")" << std::endl;
document->threads.push_back(new OE_thread(col->rgb[0], col->rgb[1], col->rgb[2], OE_thread::defaultWidth));
}
OE_staticstitch* stitch = 0;
std::cout << "PES: " << "jumping to " << (pecstart+532) << std::endl;
in.seekg(pecstart+532);
int iCol = 0;
auto itThread = document->threads.begin();
int nstitchs = 0; // TODO remove
int ntrims = 0; // TODO remove
int njumps = 0; // TODO remove
long long x=0;
long long y=0;
while(in.good()) {
int val1 = getU8(in);
int val2 = getU8(in);
if (val1 == 0xFF && val2 == 0x00) {
std::cout << "PES: " << "end of program" << std::endl;
break;
} else if (val1 == 0xFE && val2 == 0xB0) {
std::cout << "PES: " << "stitch end, thread change" << std::endl;
getU8(in);
iCol++;
itThread++;
continue;
}
int stitchType = 0;
/* High bit set means 12-bit offset, otherwise 7-bit signed delta */
if(val1 & 0x80)
{
if(val1 & 0x20) stitchType = 1; // trim + move to
if(val1 & 0x10) stitchType = 2; // move to
val1 = ((val1 & 0x0F) << 8) + val2;
/* Signed 12-bit arithmetic */
if(val1 & 0x800)
{
val1 -= 0x1000;
}
val2 = getU8(in);
}
else if(val1 >= 0x40)
{
val1 -= 0x80;
}
if(val2 & 0x80)
{
if(val2 & 0x20) stitchType = 1; // trim + move to
if(val2 & 0x10) stitchType = 2; // move to
val2 = ((val2 & 0x0F) << 8) + getU8(in);
/* Signed 12-bit arithmetic */
if(val2 & 0x800)
{
val2 -= 0x1000;
}
}
else if(val2 >= 0x40)
{
val2 -= 0x80;
}
x += val1;
y += val2;
if ((stitchType == 0 && !stitch) || stitchType)
{
OE_staticstitch* newStitch = new OE_staticstitch(*itThread);
if (stitch)
document->addStitch(new OE_linkstitch(stitch, newStitch));
stitch = newStitch;
}
stitch->addPoint(x/10.0, y/10.0);
if (stitchType == 1)
ntrims++;
if (stitchType == 1 || stitchType == 2)
njumps++;
nstitchs++;
}
std::cout << "PES: " << iCol << "threads parsed" << std::endl;
std::cout << "PES: " << nstitchs << "points parsed" << std::endl;
std::cout << "PES: " << ntrims << "trims parsed" << std::endl;
std::cout << "PES: " << njumps << "jumps parsed" << std::endl;
in.close();
return true;
}