Subversion Repositories Scribus

Rev

Rev 16746 | Rev 16764 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
16729 fschmid 1
#include "slaoutput.h"
2
#include <GlobalParams.h>
3
#include <QFile>
4
#include "commonstrings.h"
5
#include "loadsaveplugin.h"
6
#include "sccolorengine.h"
7
#include "util.h"
8
#include "util_math.h"
9
 
10
 
11
SlaOutputDev::SlaOutputDev(ScribusDoc* doc, QList<PageItem*> *Elements, QStringList *importedColors, int flags)
12
{
13
        m_doc = doc;
14
        m_Elements = Elements;
15
        m_groupStack.clear();
16732 fschmid 16
        pushGroup();
16729 fschmid 17
        m_clipStack.clear();
18
        m_currentMask = "";
19
        m_importedColors = importedColors;
20
        CurrColorStroke = "Black";
21
        CurrColorFill = "Black";
22
        Coords = "";
23
        pathIsClosed = false;
24
        tmpSel = new Selection(m_doc, false);
25
        grStackDepth = 0;
26
        firstLayer = true;
27
        layerNum = 1;
28
        importerFlags = flags;
29
        currentLayer = m_doc->activeLayer();
30
        xref = NULL;
31
        m_fontEngine = 0;
32
        m_font = 0;
33
        firstPage = true;
34
        pagecount = 1;
35
}
36
 
37
SlaOutputDev::~SlaOutputDev()
38
{
39
        m_groupStack.clear();
40
        tmpSel->clear();
41
        delete tmpSel;
42
        delete m_fontEngine;
43
}
44
 
45
 
46
void SlaOutputDev::startDoc(XRef *xrefA, Catalog *catA)
47
{
48
        xref = xrefA;
49
        catalog = catA;
50
        firstPage = true;
51
        pagecount = 1;
52
        m_fontEngine = new SplashFontEngine(
53
#if HAVE_T1LIB_H
54
        globalParams->getEnableT1lib(),
55
#endif
56
#if HAVE_FREETYPE_H
57
        globalParams->getEnableFreeType(),
58
        true,
59
        true,
60
#endif
61
        true);
62
}
63
 
64
void SlaOutputDev::startPage(int pageNum, GfxState *state)
65
{
66
//    qDebug() << "starting page" << pageNum;
67
        if (firstPage)
68
                firstPage = false;
69
        else
70
        {
71
                if (importerFlags & LoadSavePlugin::lfCreateDoc)
72
                {
73
                        m_doc->addPage(pagecount);
74
                        m_doc->view()->addPage(pagecount, true);
75
                        pagecount++;
76
                }
77
        }
78
 //   qDebug() << "page size =" << pageSize;
79
}
80
 
81
void SlaOutputDev::endPage()
82
{
83
//      qDebug() << "ending page";
84
}
85
 
86
void SlaOutputDev::saveState(GfxState *state)
87
{
88
//      qDebug() << "saveState" << grStackDepth;
89
        grStackDepth++;
90
}
91
 
92
void SlaOutputDev::restoreState(GfxState *state)
93
{
94
//      qDebug() << "restoreState" << grStackDepth;
95
        grStackDepth--;
96
        if (m_groupStack.count() != 0)
97
                m_groupStack.top().maskName = "";
98
        if (m_clipStack.count() != 0)
99
        {
100
                while (m_clipStack.top().grStackDepth > grStackDepth)
101
                {
102
                        clipEntry clp = m_clipStack.pop();
103
                        PageItem *ite = clp.ClipItem;
104
                        if (m_groupStack.count() != 0)
105
                        {
106
                                groupEntry gElements = m_groupStack.pop();
107
                                if (gElements.Items.count() > 0)
108
                                {
109
                                        for (int d = 0; d < gElements.Items.count(); d++)
110
                                        {
111
                                                m_Elements->removeAll(gElements.Items.at(d));
112
                                        }
113
                                        m_doc->groupObjectsToItem(ite, gElements.Items);
114
                                        ite->setFillTransparency(1.0 - state->getFillOpacity());
115
                                        ite->setFillBlendmode(getBlendMode(state));
116
                                }
117
                                else
118
                                {
119
                                        m_Elements->removeAll(ite);
120
                                        m_doc->Items->removeAll(ite);
121
                                        m_groupStack.top().Items.removeAll(ite);
122
                                }
123
                        }
124
                        if (m_clipStack.count() == 0)
125
                                break;
126
                }
127
        }
128
}
129
 
130
void SlaOutputDev::updateFillColor(GfxState *state)
131
{
16746 fschmid 132
        int shade = 100;
133
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 134
}
135
 
136
void SlaOutputDev::beginTransparencyGroup(GfxState *state, double *bbox, GfxColorSpace * /*blendingColorSpace*/, GBool /*isolated*/, GBool /*knockout*/, GBool forSoftMask)
137
{
138
//      qDebug() << "Start Group";
16732 fschmid 139
        pushGroup("", forSoftMask);
16729 fschmid 140
}
141
 
142
void SlaOutputDev::endTransparencyGroup(GfxState *state)
143
{
144
//      qDebug() << "End Group";
145
        if (m_groupStack.count() != 0)
146
        {
147
                groupEntry gElements = m_groupStack.pop();
148
                tmpSel->clear();
149
                if (gElements.Items.count() > 0)
150
                {
151
                        for (int dre = 0; dre < gElements.Items.count(); ++dre)
152
                        {
153
                                tmpSel->addItem(gElements.Items.at(dre), true);
154
                                m_Elements->removeAll(gElements.Items.at(dre));
155
                        }
156
                        PageItem *ite = m_doc->groupObjectsSelection(tmpSel);
157
                        ite->setFillTransparency(1.0 - state->getFillOpacity());
158
                        ite->setFillBlendmode(getBlendMode(state));
159
                        if (gElements.forSoftMask)
160
                        {
161
                                ScPattern pat = ScPattern();
162
                                pat.setDoc(m_doc);
163
                                m_doc->DoDrawing = true;
164
                                pat.pattern = ite->DrawObj_toImage(qMax(ite->width(), ite->height()));
165
                                pat.xoffset = 0;
166
                                pat.yoffset = 0;
167
                                m_doc->DoDrawing = false;
168
                                pat.width = ite->width();
169
                                pat.height = ite->height();
170
                                pat.items.append(ite);
171
                                m_doc->Items->removeAll(ite);
172
                                QString id = QString("Pattern_from_PDF_%1S").arg(m_doc->docPatterns.count() + 1);
173
                                m_doc->addPattern(id, pat);
174
                                m_currentMask = id;
175
                                tmpSel->clear();
176
                                return;
177
                        }
178
                        else
179
                        {
180
                                for (int as = 0; as < tmpSel->count(); ++as)
181
                                {
182
                                        m_Elements->append(tmpSel->itemAt(as));
183
                                }
184
                        }
185
                        if (m_groupStack.count() != 0)
16732 fschmid 186
                                applyMask(ite);
16729 fschmid 187
                }
188
                if (m_groupStack.count() != 0)
189
                {
190
                        for (int as = 0; as < tmpSel->count(); ++as)
191
                        {
192
                                m_groupStack.top().Items.append(tmpSel->itemAt(as));
193
                        }
194
                }
195
                tmpSel->clear();
196
        }
197
}
198
 
16732 fschmid 199
void SlaOutputDev::setSoftMask(GfxState * /*state*/, double * /*bbox*/, GBool alpha, Function *transferFunc, GfxColor * /*backdropColor*/)
16729 fschmid 200
{
201
        if (m_groupStack.count() != 0)
202
        {
16732 fschmid 203
                double lum = 0;
204
                double lum2 = 0;
205
                if (transferFunc)
206
                        transferFunc->transform(&lum, &lum2);
207
                else
208
                        lum2 = lum;
209
                if (lum == lum2)
210
                        m_groupStack.top().inverted = false;
211
                else
212
                        m_groupStack.top().inverted = true;
213
//              qDebug() << "Inverted Softmask" << m_groupStack.top().inverted;
16729 fschmid 214
                m_groupStack.top().maskName = m_currentMask;
215
                m_groupStack.top().alpha = alpha;
216
        }
217
}
218
 
219
void SlaOutputDev::clearSoftMask(GfxState * /*state*/)
220
{
221
        if (m_groupStack.count() != 0)
222
        {
223
                m_groupStack.top().maskName = "";
224
        }
225
}
226
 
227
void SlaOutputDev::clip(GfxState *state)
228
{
229
//      qDebug() << "Clip";
230
        double *ctm;
231
        ctm = state->getCTM();
232
        QString output = convertPath(state->getPath());
233
        FPointArray out;
234
        out.parseSVG(output);
235
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
236
        out.map(m_ctm);
237
        double xmin, ymin, xmax, ymax;
238
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
239
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
240
        crect = crect.normalized();
241
        int z = m_doc->itemAdd(PageItem::Group, PageItem::Rectangle, crect.x() + m_doc->currentPage()->xOffset(), crect.y() + m_doc->currentPage()->yOffset(), crect.width(), crect.height(), 0, CommonStrings::None, CommonStrings::None, true);
242
        PageItem *ite = m_doc->Items->at(z);
243
        FPoint wh(getMinClipF(&out));
244
        out.translate(-wh.x(), -wh.y());
245
        ite->PoLine = out.copy();  //FIXME: try to avoid copy if FPointArray when properly shared
246
        ite->ClipEdited = true;
247
        ite->FrameType = 3;
16744 fschmid 248
        ite->setFillEvenOdd(false);
16729 fschmid 249
        ite->Clip = FlattenPath(ite->PoLine, ite->Segments);
250
        ite->ContourLine = ite->PoLine.copy();
251
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
252
        m_doc->AdjustItemSize(ite);
253
        m_Elements->append(ite);
254
        if (m_groupStack.count() != 0)
255
        {
256
                m_groupStack.top().Items.append(ite);
16732 fschmid 257
                applyMask(ite);
16729 fschmid 258
        }
259
        clipEntry clp;
260
        clp.ClipCoords = out.copy();
261
        clp.ClipItem = ite;
262
        clp.grStackDepth = grStackDepth;
263
        m_clipStack.push(clp);
264
        m_doc->GroupCounter++;
16732 fschmid 265
        pushGroup();
16729 fschmid 266
}
267
 
268
void SlaOutputDev::eoClip(GfxState *state)
269
{
270
//      qDebug() << "EoClip";
271
        double *ctm;
272
        ctm = state->getCTM();
273
        QString output = convertPath(state->getPath());
274
        FPointArray out;
275
        out.parseSVG(output);
276
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
277
        out.map(m_ctm);
278
        double xmin, ymin, xmax, ymax;
279
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
280
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
281
        crect = crect.normalized();
282
        int z = m_doc->itemAdd(PageItem::Group, PageItem::Rectangle, crect.x() + m_doc->currentPage()->xOffset(), crect.y() + m_doc->currentPage()->yOffset(), crect.width(), crect.height(), 0, CommonStrings::None, CommonStrings::None, true);
283
        PageItem *ite = m_doc->Items->at(z);
284
        FPoint wh(getMinClipF(&out));
285
        out.translate(-wh.x(), -wh.y());
286
        ite->PoLine = out.copy();  //FIXME: try to avoid copy if FPointArray when properly shared
287
        ite->ClipEdited = true;
288
        ite->FrameType = 3;
16744 fschmid 289
        ite->setFillEvenOdd(true);
16729 fschmid 290
        ite->Clip = FlattenPath(ite->PoLine, ite->Segments);
291
        ite->ContourLine = ite->PoLine.copy();
292
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
293
        m_doc->AdjustItemSize(ite);
294
        m_Elements->append(ite);
295
        if (m_groupStack.count() != 0)
296
        {
297
                m_groupStack.top().Items.append(ite);
16732 fschmid 298
                applyMask(ite);
16729 fschmid 299
        }
300
        clipEntry clp;
301
        clp.ClipCoords = out.copy();
302
        clp.ClipItem = ite;
303
        clp.grStackDepth = grStackDepth;
304
        m_clipStack.push(clp);
305
        m_doc->GroupCounter++;
16732 fschmid 306
        pushGroup();
16729 fschmid 307
}
308
 
309
void SlaOutputDev::stroke(GfxState *state)
310
{
311
//      qDebug() << "Stroke";
312
        double *ctm;
313
        ctm = state->getCTM();
314
        double xCoor = m_doc->currentPage()->xOffset();
315
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 316
        int shade = 100;
317
        CurrColorStroke = getColor(state->getStrokeColorSpace(), state->getStrokeColor(), &shade);
16729 fschmid 318
        QString output = convertPath(state->getPath());
319
        getPenState(state);
320
        if ((m_Elements->count() != 0) && (output == Coords))                   // Path is the same as in last fill
321
        {
322
                PageItem* ite = m_Elements->at(m_Elements->count()-1);
323
                ite->setLineColor(CurrColorStroke);
16746 fschmid 324
                ite->setLineShade(shade);
16729 fschmid 325
                ite->setLineEnd(PLineEnd);
326
                ite->setLineJoin(PLineJoin);
327
                ite->setLineWidth(state->getTransformedLineWidth());
328
                ite->setDashes(DashValues);
329
                ite->setDashOffset(DashOffset);
330
                ite->setLineTransparency(1.0 - state->getStrokeOpacity());
331
        }
332
        else
333
        {
334
                FPointArray out;
335
                out.parseSVG(output);
336
                m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
337
                out.map(m_ctm);
338
                FPoint wh = out.WidthHeight();
339
                if ((out.size() > 3) && ((wh.x() != 0.0) || (wh.y() != 0.0)))
340
                {
341
                        int z;
342
                        if (pathIsClosed)
343
                                z = m_doc->itemAdd(PageItem::Polygon, PageItem::Unspecified, xCoor, yCoor, 10, 10, state->getTransformedLineWidth(), CommonStrings::None, CurrColorStroke, true);
344
                        else
345
                                z = m_doc->itemAdd(PageItem::PolyLine, PageItem::Unspecified, xCoor, yCoor, 10, 10, state->getTransformedLineWidth(), CommonStrings::None, CurrColorStroke, true);
346
                        PageItem* ite = m_doc->Items->at(z);
347
                        ite->PoLine = out.copy();
348
                        ite->ClipEdited = true;
349
                        ite->FrameType = 3;
16746 fschmid 350
                        ite->setLineShade(shade);
16729 fschmid 351
                        ite->setLineTransparency(1.0 - state->getStrokeOpacity());
352
                        ite->setLineBlendmode(getBlendMode(state));
353
                        ite->setLineEnd(PLineEnd);
354
                        ite->setLineJoin(PLineJoin);
355
                        ite->setDashes(DashValues);
356
                        ite->setDashOffset(DashOffset);
357
                        ite->setWidthHeight(wh.x(),wh.y());
358
                        ite->setTextFlowMode(PageItem::TextFlowDisabled);
359
                        m_doc->AdjustItemSize(ite);
360
                        m_Elements->append(ite);
361
                        if (m_groupStack.count() != 0)
362
                                m_groupStack.top().Items.append(ite);
363
                }
364
        }
365
}
366
 
367
void SlaOutputDev::fill(GfxState *state)
368
{
369
//      qDebug() << "Fill";
370
        double *ctm;
371
        ctm = state->getCTM();
372
        double xCoor = m_doc->currentPage()->xOffset();
373
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 374
        int shade = 100;
375
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 376
        FPointArray out;
377
        QString output = convertPath(state->getPath());
378
        out.parseSVG(output);
379
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
380
        out.map(m_ctm);
381
        Coords = output;
382
        FPoint wh = out.WidthHeight();
383
        if ((out.size() > 3) && ((wh.x() != 0.0) || (wh.y() != 0.0)))
384
        {
385
                int z;
386
                if (pathIsClosed)
387
                        z = m_doc->itemAdd(PageItem::Polygon, PageItem::Unspecified, xCoor, yCoor, 10, 10, 0, CurrColorFill, CommonStrings::None, true);
388
                else
389
                        z = m_doc->itemAdd(PageItem::PolyLine, PageItem::Unspecified, xCoor, yCoor, 10, 10, 0, CurrColorFill, CommonStrings::None, true);
390
                PageItem* ite = m_doc->Items->at(z);
391
                ite->PoLine = out.copy();
392
                ite->ClipEdited = true;
393
                ite->FrameType = 3;
16746 fschmid 394
                ite->setFillShade(shade);
16729 fschmid 395
                ite->setLineShade(100);
396
                ite->setFillEvenOdd(false);
397
                ite->setFillTransparency(1.0 - state->getFillOpacity());
398
                ite->setFillBlendmode(getBlendMode(state));
399
                ite->setLineEnd(PLineEnd);
400
                ite->setLineJoin(PLineJoin);
401
                ite->setWidthHeight(wh.x(),wh.y());
402
                ite->setTextFlowMode(PageItem::TextFlowDisabled);
403
                m_doc->AdjustItemSize(ite);
404
                m_Elements->append(ite);
405
                if (m_groupStack.count() != 0)
406
                {
407
                        m_groupStack.top().Items.append(ite);
16732 fschmid 408
                        applyMask(ite);
16729 fschmid 409
                }
410
        }
411
}
412
 
413
void SlaOutputDev::eoFill(GfxState *state)
414
{
415
//      qDebug() << "EoFill";
416
        double *ctm;
417
        ctm = state->getCTM();
418
        double xCoor = m_doc->currentPage()->xOffset();
419
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 420
        int shade = 100;
421
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 422
        FPointArray out;
423
        QString output = convertPath(state->getPath());
424
        out.parseSVG(output);
425
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
426
        out.map(m_ctm);
427
        Coords = output;
428
        FPoint wh = out.WidthHeight();
429
        if ((out.size() > 3) && ((wh.x() != 0.0) || (wh.y() != 0.0)))
430
        {
431
                int z;
432
                if (pathIsClosed)
433
                        z = m_doc->itemAdd(PageItem::Polygon, PageItem::Unspecified, xCoor, yCoor, 10, 10, 0, CurrColorFill, CommonStrings::None, true);
434
                else
435
                        z = m_doc->itemAdd(PageItem::PolyLine, PageItem::Unspecified, xCoor, yCoor, 10, 10, 0, CurrColorFill, CommonStrings::None, true);
436
                PageItem* ite = m_doc->Items->at(z);
437
                ite->PoLine = out.copy();
438
                ite->ClipEdited = true;
439
                ite->FrameType = 3;
16746 fschmid 440
                ite->setFillShade(shade);
16729 fschmid 441
                ite->setLineShade(100);
442
                ite->setFillEvenOdd(true);
443
                ite->setFillTransparency(1.0 - state->getFillOpacity());
444
                ite->setFillBlendmode(getBlendMode(state));
445
                ite->setLineEnd(PLineEnd);
446
                ite->setLineJoin(PLineJoin);
447
                ite->setWidthHeight(wh.x(),wh.y());
448
                ite->setTextFlowMode(PageItem::TextFlowDisabled);
449
                m_doc->AdjustItemSize(ite);
450
                m_Elements->append(ite);
451
                if (m_groupStack.count() != 0)
452
                {
453
                        m_groupStack.top().Items.append(ite);
16732 fschmid 454
                        applyMask(ite);
16729 fschmid 455
                }
456
        }
457
}
458
 
459
GBool SlaOutputDev::axialShadedFill(GfxState *state, GfxAxialShading *shading, double tMin, double tMax)
460
{
461
        double GrStartX;
462
        double GrStartY;
463
        double GrEndX;
464
        double GrEndY;
16746 fschmid 465
        int shade = 100;
16729 fschmid 466
        Function *func = shading->getFunc(0);
467
        VGradient FillGradient = VGradient(VGradient::linear);
468
        FillGradient.clearStops();
469
        GfxColorSpace *color_space = shading->getColorSpace();
470
        if (func->getType() == 3)
471
        {
472
                StitchingFunction *stitchingFunc = (StitchingFunction*)func;
473
                double *bounds = stitchingFunc->getBounds();
474
                int num_funcs = stitchingFunc->getNumFuncs();
475
                // Add stops from all the stitched functions
476
                for ( int i = 0 ; i < num_funcs ; i++ )
477
                {
478
                        GfxColor temp;
479
                        ((GfxAxialShading*)shading)->getColor(bounds[i], &temp);
16746 fschmid 480
                        QString stopColor = getColor(color_space, &temp, &shade);
481
                        FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor], m_doc), bounds[i], 0.5, 1.0, stopColor, shade );
16729 fschmid 482
                        if (i == num_funcs - 1)
483
                        {
484
                                ((GfxAxialShading*)shading)->getColor(bounds[i+1], &temp);
16746 fschmid 485
                                QString stopColor = getColor(color_space, &temp, &shade);
486
                                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor], m_doc), bounds[i+1], 0.5, 1.0, stopColor, shade );
16729 fschmid 487
                        }
488
                }
489
        }
490
        else if (func->getType() == 2)
491
        {
492
                GfxColor stop1;
493
                ((GfxAxialShading*)shading)->getColor(0.0, &stop1);
16746 fschmid 494
                QString stopColor1 = getColor(color_space, &stop1, &shade);
495
                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor1], m_doc), 0.0, 0.5, 1.0, stopColor1, shade );
16729 fschmid 496
                GfxColor stop2;
497
                ((GfxAxialShading*)shading)->getColor(1.0, &stop2);
16746 fschmid 498
                QString stopColor2 = getColor(color_space, &stop2, &shade);
499
                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor2], m_doc), 1.0, 0.5, 1.0, stopColor2, shade );
16729 fschmid 500
        }
501
        ((GfxAxialShading*)shading)->getCoords(&GrStartX, &GrStartY, &GrEndX, &GrEndY);
502
        double xmin, ymin, xmax, ymax;
503
        // get the clip region bbox
504
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
505
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
506
        crect = crect.normalized();
507
        double *ctm;
508
        ctm = state->getCTM();
509
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
510
        FPointArray gr;
511
        gr.addPoint(GrStartX, GrStartY);
512
        gr.addPoint(GrEndX, GrEndY);
513
        gr.map(m_ctm);
514
        GrStartX = gr.point(0).x() - crect.x();
515
        GrStartY = gr.point(0).y() - crect.y();
516
        GrEndX = gr.point(1).x() - crect.x();
517
        GrEndY = gr.point(1).y() - crect.y();
518
        double xCoor = m_doc->currentPage()->xOffset();
519
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 520
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 521
        QString output = QString("M %1 %2").arg(0.0).arg(0.0);
522
        output += QString("L %1 %2").arg(crect.width()).arg(0.0);
523
        output += QString("L %1 %2").arg(crect.width()).arg(crect.height());
524
        output += QString("L %1 %2").arg(0.0).arg(crect.height());
525
        output += QString("L %1 %2").arg(0.0).arg(0.0);
526
        output += QString("Z");
527
        pathIsClosed = true;
528
        Coords = output;
529
        int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + crect.x(), yCoor + crect.y(), crect.width(), crect.height(), 0, CurrColorFill, CommonStrings::None, true);
530
        PageItem* ite = m_doc->Items->at(z);
531
        ite->ClipEdited = true;
532
        ite->FrameType = 3;
16746 fschmid 533
        ite->setFillShade(shade);
16729 fschmid 534
        ite->setLineShade(100);
535
        ite->setFillEvenOdd(false);
536
        ite->setFillTransparency(1.0 - state->getFillOpacity());
537
        ite->setFillBlendmode(getBlendMode(state));
538
        ite->setLineEnd(PLineEnd);
539
        ite->setLineJoin(PLineJoin);
540
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
541
        ite->GrType = 6;
542
        ite->fill_gradient = FillGradient;
543
        ite->setGradientVector(GrStartX, GrStartY, GrEndX, GrEndY, 0, 0, 1, 0);
544
        m_doc->AdjustItemSize(ite);
545
        m_Elements->append(ite);
546
        if (m_groupStack.count() != 0)
547
        {
548
                m_groupStack.top().Items.append(ite);
16732 fschmid 549
                applyMask(ite);
16729 fschmid 550
        }
551
        return gTrue;
552
}
553
 
554
GBool SlaOutputDev::radialShadedFill(GfxState *state, GfxRadialShading *shading, double sMin, double sMax)
555
{
556
        double GrStartX;
557
        double GrStartY;
558
        double GrEndX;
559
        double GrEndY;
16746 fschmid 560
        int shade = 100;
16729 fschmid 561
        Function *func = shading->getFunc(0);
562
        VGradient FillGradient = VGradient(VGradient::linear);
563
        FillGradient.clearStops();
564
        GfxColorSpace *color_space = shading->getColorSpace();
565
        if (func->getType() == 3)
566
        {
567
                StitchingFunction *stitchingFunc = (StitchingFunction*)func;
568
                double *bounds = stitchingFunc->getBounds();
569
                int num_funcs = stitchingFunc->getNumFuncs();
570
                // Add stops from all the stitched functions
571
                for ( int i = 0 ; i < num_funcs ; i++ )
572
                {
573
                        GfxColor temp;
574
                        ((GfxRadialShading*)shading)->getColor(bounds[i], &temp);
16746 fschmid 575
                        QString stopColor = getColor(color_space, &temp, &shade);
576
                        FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor], m_doc), bounds[i], 0.5, 1.0, stopColor, shade );
16729 fschmid 577
                        if (i == num_funcs - 1)
578
                        {
579
                                ((GfxRadialShading*)shading)->getColor(bounds[i+1], &temp);
16746 fschmid 580
                                QString stopColor = getColor(color_space, &temp, &shade);
581
                                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor], m_doc), bounds[i+1], 0.5, 1.0, stopColor, shade );
16729 fschmid 582
                        }
583
                }
584
        }
585
        else if (func->getType() == 2)
586
        {
587
                GfxColor stop1;
588
                ((GfxRadialShading*)shading)->getColor(0.0, &stop1);
16746 fschmid 589
                QString stopColor1 = getColor(color_space, &stop1, &shade);
590
                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor1], m_doc), 0.0, 0.5, 1.0, stopColor1, shade );
16729 fschmid 591
                GfxColor stop2;
592
                ((GfxRadialShading*)shading)->getColor(1.0, &stop2);
16746 fschmid 593
                QString stopColor2 = getColor(color_space, &stop2, &shade);
594
                FillGradient.addStop( ScColorEngine::getRGBColor(m_doc->PageColors[stopColor2], m_doc), 1.0, 0.5, 1.0, stopColor2, shade );
16729 fschmid 595
        }
596
        double r0, x1, y1, r1;
597
        ((GfxRadialShading*)shading)->getCoords(&GrStartX, &GrStartY, &r0, &x1, &y1, &r1);
598
        double xmin, ymin, xmax, ymax;
599
        // get the clip region bbox
600
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
601
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
602
        crect = crect.normalized();
603
        double GrFocalX = x1;
604
        double GrFocalY = y1;
605
        GrEndX = GrFocalX + r1;
606
        GrEndY = GrFocalY;
607
        double *ctm;
608
        ctm = state->getCTM();
609
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
610
        FPointArray gr;
611
        gr.addPoint(GrStartX, GrStartY);
612
        gr.addPoint(GrEndX, GrEndY);
613
        gr.addPoint(GrFocalX, GrFocalY);
614
        gr.map(m_ctm);
615
        GrStartX = gr.point(0).x() - crect.x();
616
        GrStartY = gr.point(0).y() - crect.y();
617
        GrEndX = gr.point(1).x() - crect.x();
618
        GrEndY = gr.point(1).y() - crect.y();
619
        GrFocalX = gr.point(2).x() - crect.x();
620
        GrFocalY = gr.point(2).y() - crect.y();
621
        double xCoor = m_doc->currentPage()->xOffset();
622
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 623
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 624
        QString output = QString("M %1 %2").arg(0.0).arg(0.0);
625
        output += QString("L %1 %2").arg(crect.width()).arg(0.0);
626
        output += QString("L %1 %2").arg(crect.width()).arg(crect.height());
627
        output += QString("L %1 %2").arg(0.0).arg(crect.height());
628
        output += QString("L %1 %2").arg(0.0).arg(0.0);
629
        output += QString("Z");
630
        pathIsClosed = true;
631
        Coords = output;
632
        int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + crect.x(), yCoor + crect.y(), crect.width(), crect.height(), 0, CurrColorFill, CommonStrings::None, true);
633
        PageItem* ite = m_doc->Items->at(z);
634
        ite->ClipEdited = true;
635
        ite->FrameType = 3;
16746 fschmid 636
        ite->setFillShade(shade);
16729 fschmid 637
        ite->setLineShade(100);
638
        ite->setFillEvenOdd(false);
639
        ite->setFillTransparency(1.0 - state->getFillOpacity());
640
        ite->setFillBlendmode(getBlendMode(state));
641
        ite->setLineEnd(PLineEnd);
642
        ite->setLineJoin(PLineJoin);
643
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
644
        ite->GrType = 7;
645
        ite->fill_gradient = FillGradient;
646
        ite->setGradientVector(GrStartX, GrStartY, GrEndX, GrEndY, GrFocalX, GrFocalY, 1, 0);
647
        m_doc->AdjustItemSize(ite);
648
        m_Elements->append(ite);
649
        if (m_groupStack.count() != 0)
650
        {
651
                m_groupStack.top().Items.append(ite);
16732 fschmid 652
                applyMask(ite);
16729 fschmid 653
        }
654
        return gTrue;
655
}
656
 
16745 fschmid 657
GBool SlaOutputDev::gouraudTriangleShadedFill(GfxState *state, GfxGouraudTriangleShading *shading)
658
{
659
        double xCoor = m_doc->currentPage()->xOffset();
660
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 661
        int shade = 100;
662
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16745 fschmid 663
        double xmin, ymin, xmax, ymax;
664
        // get the clip region bbox
665
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
666
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
667
        crect = crect.normalized();
668
        QString output = QString("M %1 %2").arg(0.0).arg(0.0);
669
        output += QString("L %1 %2").arg(crect.width()).arg(0.0);
670
        output += QString("L %1 %2").arg(crect.width()).arg(crect.height());
671
        output += QString("L %1 %2").arg(0.0).arg(crect.height());
672
        output += QString("L %1 %2").arg(0.0).arg(0.0);
673
        output += QString("Z");
674
        pathIsClosed = true;
675
        Coords = output;
676
        double *ctm;
677
        ctm = state->getCTM();
678
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
679
        int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + crect.x(), yCoor + crect.y(), crect.width(), crect.height(), 0, CurrColorFill, CommonStrings::None, true);
680
        PageItem* ite = m_doc->Items->at(z);
681
        ite->ClipEdited = true;
682
        ite->FrameType = 3;
683
        ite->setFillShade(100);
684
        ite->setLineShade(100);
685
        ite->setFillEvenOdd(false);
686
        ite->setFillTransparency(1.0 - state->getFillOpacity());
687
        ite->setFillBlendmode(getBlendMode(state));
688
        ite->setLineEnd(PLineEnd);
689
        ite->setLineJoin(PLineJoin);
690
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
691
        m_doc->AdjustItemSize(ite);
692
        m_Elements->append(ite);
693
        if (m_groupStack.count() != 0)
694
        {
695
                m_groupStack.top().Items.append(ite);
696
                applyMask(ite);
697
        }
698
        GfxColor color[3];
699
        double x0, y0, x1, y1, x2, y2;
700
        for (int i = 0; i < shading->getNTriangles(); i++)
701
        {
702
                meshGradientPatch patchM;
703
                shading->getTriangle(i, &x0, &y0, &color[0],  &x1, &y1, &color[1],  &x2, &y2, &color[2]);
704
                patchM.BL.resetTo(FPoint(x0, y0));
705
                patchM.BL.shade = 100;
706
                patchM.BL.transparency = 1.0;
16746 fschmid 707
                patchM.BL.colorName = getColor(shading->getColorSpace(), &color[0], &shade);
708
                patchM.BL.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.BL.colorName], m_doc, shade);
16745 fschmid 709
                patchM.TL.resetTo(FPoint(x1, y1));
710
                patchM.TL.shade = 100;
711
                patchM.TL.transparency = 1.0;
16746 fschmid 712
                patchM.TL.colorName = getColor(shading->getColorSpace(), &color[1], &shade);
713
                patchM.TL.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.TL.colorName], m_doc, shade);
16745 fschmid 714
                patchM.TR.resetTo(FPoint(x2, y2));
715
                patchM.TR.shade = 100;
716
                patchM.TR.transparency = 1.0;
16746 fschmid 717
                patchM.TR.colorName = getColor(shading->getColorSpace(), &color[2], &shade);
718
                patchM.TR.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.TR.colorName], m_doc, shade);
16745 fschmid 719
                patchM.BR.resetTo(FPoint(x0, y0));
720
                patchM.BR.shade = 100;
721
                patchM.BR.transparency = 1.0;
16746 fschmid 722
                patchM.BR.colorName = getColor(shading->getColorSpace(), &color[0], &shade);
723
                patchM.BR.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.BR.colorName], m_doc, shade);
16745 fschmid 724
                patchM.TL.transform(m_ctm);
725
                patchM.TL.moveRel(-crect.x(), -crect.y());
726
                patchM.TR.transform(m_ctm);
727
                patchM.TR.moveRel(-crect.x(), -crect.y());
728
                patchM.BR.transform(m_ctm);
729
                patchM.BR.moveRel(-crect.x(), -crect.y());
730
                patchM.BL.transform(m_ctm);
731
                patchM.BL.moveRel(-crect.x(), -crect.y());
732
                ite->meshGradientPatches.append(patchM);
733
        }
734
        ite->GrType = 12;
735
        return gTrue;
736
}
737
 
16729 fschmid 738
GBool SlaOutputDev::patchMeshShadedFill(GfxState *state, GfxPatchMeshShading *shading)
739
{
740
//      qDebug() << "mesh shaded fill";
741
        double xCoor = m_doc->currentPage()->xOffset();
742
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 743
        int shade = 100;
744
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 745
        double xmin, ymin, xmax, ymax;
746
        // get the clip region bbox
747
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
748
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
749
        crect = crect.normalized();
750
        QString output = QString("M %1 %2").arg(0.0).arg(0.0);
751
        output += QString("L %1 %2").arg(crect.width()).arg(0.0);
752
        output += QString("L %1 %2").arg(crect.width()).arg(crect.height());
753
        output += QString("L %1 %2").arg(0.0).arg(crect.height());
754
        output += QString("L %1 %2").arg(0.0).arg(0.0);
755
        output += QString("Z");
756
        pathIsClosed = true;
757
        Coords = output;
758
        double *ctm;
759
        ctm = state->getCTM();
760
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
761
        int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + crect.x(), yCoor + crect.y(), crect.width(), crect.height(), 0, CurrColorFill, CommonStrings::None, true);
762
        PageItem* ite = m_doc->Items->at(z);
763
        ite->ClipEdited = true;
764
        ite->FrameType = 3;
16746 fschmid 765
        ite->setFillShade(shade);
16729 fschmid 766
        ite->setLineShade(100);
767
        ite->setFillEvenOdd(false);
768
        ite->setFillTransparency(1.0 - state->getFillOpacity());
769
        ite->setFillBlendmode(getBlendMode(state));
770
        ite->setLineEnd(PLineEnd);
771
        ite->setLineJoin(PLineJoin);
772
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
773
        m_doc->AdjustItemSize(ite);
774
        m_Elements->append(ite);
775
        if (m_groupStack.count() != 0)
776
        {
777
                m_groupStack.top().Items.append(ite);
16732 fschmid 778
                applyMask(ite);
16729 fschmid 779
        }
780
//      qDebug() << "Mesh of" << shading->getNPatches() << "Patches";
781
        for (int i = 0; i < shading->getNPatches(); i++)
782
        {
783
                GfxPatch *patch = shading->getPatch(i);
784
                GfxColor color;
785
                meshGradientPatch patchM;
786
                int u, v;
787
                patchM.BL.resetTo(FPoint(patch->x[0][0], patch->y[0][0]));
788
                patchM.BL.controlTop = FPoint(patch->x[0][1], patch->y[0][1]);
789
                patchM.BL.controlRight = FPoint(patch->x[1][0], patch->y[1][0]);
790
                u = 0;
791
                v = 0;
792
                if (shading->isParameterized())
793
                {
794
                        shading->getParameterizedColor (patch->color[u][v].c[0], &color);
795
                }
796
                else
797
                {
798
                        for (int k = 0; k < shading->getColorSpace()->getNComps(); k++)
799
                        {
800
                                color.c[k] = GfxColorComp (patch->color[u][v].c[k]);
801
                        }
802
                }
16746 fschmid 803
                patchM.BL.colorName = getColor(shading->getColorSpace(), &color, &shade);
16729 fschmid 804
                patchM.BL.shade = 100;
805
                patchM.BL.transparency = 1.0;
16746 fschmid 806
                patchM.BL.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.BL.colorName], m_doc, shade);
16729 fschmid 807
 
808
                u = 0;
809
                v = 1;
810
                patchM.TL.resetTo(FPoint(patch->x[0][3], patch->y[0][3]));
811
                patchM.TL.controlRight = FPoint(patch->x[1][3], patch->y[1][3]);
812
                patchM.TL.controlBottom = FPoint(patch->x[0][2], patch->y[0][2]);
813
                if (shading->isParameterized())
814
                {
815
                        shading->getParameterizedColor (patch->color[u][v].c[0], &color);
816
                }
817
                else
818
                {
819
                        for (int k = 0; k < shading->getColorSpace()->getNComps(); k++)
820
                        {
821
                                color.c[k] = GfxColorComp (patch->color[u][v].c[k]);
822
                        }
823
                }
16746 fschmid 824
                patchM.TL.colorName = getColor(shading->getColorSpace(), &color, &shade);
16729 fschmid 825
                patchM.TL.shade = 100;
826
                patchM.TL.transparency = 1.0;
16746 fschmid 827
                patchM.TL.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.TL.colorName], m_doc, shade);
16729 fschmid 828
 
829
                u = 1;
830
                v = 1;
831
                patchM.TR.resetTo(FPoint(patch->x[3][3], patch->y[3][3]));
832
                patchM.TR.controlBottom = FPoint(patch->x[3][2], patch->y[3][2]);
833
                patchM.TR.controlLeft = FPoint(patch->x[2][3], patch->y[2][3]);
834
                if (shading->isParameterized())
835
                {
836
                        shading->getParameterizedColor (patch->color[u][v].c[0], &color);
837
                }
838
                else
839
                {
840
                        for (int k = 0; k < shading->getColorSpace()->getNComps(); k++)
841
                        {
842
                                color.c[k] = GfxColorComp (patch->color[u][v].c[k]);
843
                        }
844
                }
16746 fschmid 845
                patchM.TR.colorName = getColor(shading->getColorSpace(), &color, &shade);
16729 fschmid 846
                patchM.TR.shade = 100;
847
                patchM.TR.transparency = 1.0;
16746 fschmid 848
                patchM.TR.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.TR.colorName], m_doc, shade);
16729 fschmid 849
 
850
                u = 1;
851
                v = 0;
852
                patchM.BR.resetTo(FPoint(patch->x[3][0], patch->y[3][0]));
853
                patchM.BR.controlLeft = FPoint(patch->x[2][0], patch->y[2][0]);
854
                patchM.BR.controlTop = FPoint(patch->x[3][1], patch->y[3][1]);
855
                if (shading->isParameterized())
856
                {
857
                        shading->getParameterizedColor (patch->color[u][v].c[0], &color);
858
                }
859
                else
860
                {
861
                        for (int k = 0; k < shading->getColorSpace()->getNComps(); k++)
862
                        {
863
                                color.c[k] = GfxColorComp (patch->color[u][v].c[k]);
864
                        }
865
                }
16746 fschmid 866
                patchM.BR.colorName = getColor(shading->getColorSpace(), &color, &shade);
16729 fschmid 867
                patchM.BR.shade = 100;
868
                patchM.BR.transparency = 1.0;
16746 fschmid 869
                patchM.BR.color = ScColorEngine::getShadeColorProof(m_doc->PageColors[patchM.BR.colorName], m_doc, shade);
16729 fschmid 870
 
871
                patchM.TL.transform(m_ctm);
872
                patchM.TL.moveRel(-crect.x(), -crect.y());
873
                patchM.TR.transform(m_ctm);
874
                patchM.TR.moveRel(-crect.x(), -crect.y());
875
                patchM.BR.transform(m_ctm);
876
                patchM.BR.moveRel(-crect.x(), -crect.y());
877
                patchM.BL.transform(m_ctm);
878
                patchM.BL.moveRel(-crect.x(), -crect.y());
879
                ite->meshGradientPatches.append(patchM);
880
        }
881
        ite->GrType = 12;
882
        return gTrue;
883
}
884
 
885
GBool SlaOutputDev::tilingPatternFill(GfxState *state, Catalog *cat, Object *str, double *pmat, int paintType, Dict *resDict, double *mat, double *bbox, int x0, int y0, int x1, int y1, double xStep, double yStep)
886
{
887
        PDFRectangle box;
888
        Gfx *gfx;
889
        QString id;
890
        PageItem *ite;
891
        groupEntry gElements;
892
        gElements.forSoftMask = gFalse;
893
        gElements.alpha = gFalse;
16732 fschmid 894
        gElements.inverted = false;
16729 fschmid 895
        gElements.maskName = "";
896
        gElements.Items.clear();
897
        m_groupStack.push(gElements);
898
        double width, height;
899
        width = bbox[2] - bbox[0];
900
        height = bbox[3] - bbox[1];
901
        if (xStep != width || yStep != height)
902
                return gFalse;
903
        box.x1 = bbox[0];
904
        box.y1 = bbox[1];
905
        box.x2 = bbox[2];
906
        box.y2 = bbox[3];
907
        double *ctm;
908
        ctm = state->getCTM();
909
        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
910
        QTransform mm = QTransform(mat[0], mat[1], mat[2], mat[3], mat[4], mat[5]);
911
        QTransform mmx = mm * m_ctm;
912
        gfx = new Gfx(xref, this, resDict, catalog, &box, NULL);
913
        gfx->display(str);
914
        gElements = m_groupStack.pop();
915
        tmpSel->clear();
916
        double pwidth = 0;
917
        double pheight = 0;
918
        if (gElements.Items.count() > 0)
919
        {
920
                for (int dre = 0; dre < gElements.Items.count(); ++dre)
921
                {
922
                        tmpSel->addItem(gElements.Items.at(dre), true);
923
                        m_Elements->removeAll(gElements.Items.at(dre));
924
                }
925
                ite = m_doc->groupObjectsSelection(tmpSel);
926
                ite->setFillTransparency(1.0 - state->getFillOpacity());
927
                ite->setFillBlendmode(getBlendMode(state));
928
                m_doc->m_Selection->addItem(ite, true);
929
                m_doc->itemSelection_FlipV();
930
                m_doc->m_Selection->clear();
931
                ScPattern pat = ScPattern();
932
                pat.setDoc(m_doc);
933
                m_doc->DoDrawing = true;
934
                pat.pattern = ite->DrawObj_toImage(qMax(ite->width(), ite->height()));
935
                pat.xoffset = 0;
936
                pat.yoffset = 0;
937
                m_doc->DoDrawing = false;
938
                pat.width = ite->width();
939
                pat.height = ite->height();
940
                pwidth = ite->width();
941
                pheight = ite->height();
942
                pat.items.append(ite);
943
                m_doc->Items->removeAll(ite);
944
                id = QString("Pattern_from_PDF_%1").arg(m_doc->docPatterns.count() + 1);
945
                m_doc->addPattern(id, pat);
946
                tmpSel->clear();
947
        }
948
        double xCoor = m_doc->currentPage()->xOffset();
949
        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 950
        int shade = 100;
951
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 952
        double xmin, ymin, xmax, ymax;
953
        // get the clip region bbox
954
        state->getClipBBox(&xmin, &ymin, &xmax, &ymax);
955
        QRectF crect = QRectF(QPointF(xmin, ymin), QPointF(xmax, ymax));
956
        crect = crect.normalized();
957
        QString output = QString("M %1 %2").arg(0.0).arg(0.0);
958
        output += QString("L %1 %2").arg(crect.width()).arg(0.0);
959
        output += QString("L %1 %2").arg(crect.width()).arg(crect.height());
960
        output += QString("L %1 %2").arg(0.0).arg(crect.height());
961
        output += QString("L %1 %2").arg(0.0).arg(0.0);
962
        output += QString("Z");
963
        pathIsClosed = true;
964
        Coords = output;
965
        int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + crect.x(), yCoor + crect.y(), crect.width(), crect.height(), 0, CurrColorFill, CommonStrings::None, true);
966
        ite = m_doc->Items->at(z);
967
        ite->ClipEdited = true;
968
        ite->FrameType = 3;
16746 fschmid 969
        ite->setFillShade(shade);
16729 fschmid 970
        ite->setLineShade(100);
971
        ite->setFillEvenOdd(false);
972
        ite->setFillTransparency(1.0 - state->getFillOpacity());
973
        ite->setFillBlendmode(getBlendMode(state));
974
        ite->setLineEnd(PLineEnd);
975
        ite->setLineJoin(PLineJoin);
976
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
977
        ite->GrType = 8;
978
        ite->setPattern(id);
979
        ite->setPatternTransform(fabs(pmat[0]) * 100, fabs(pmat[3]) * 100, mmx.dx() - ctm[4], mmx.dy() - ctm[5], 0, -1 * pmat[1], pmat[2]);
980
        m_doc->AdjustItemSize(ite);
981
        m_Elements->append(ite);
982
        if (m_groupStack.count() != 0)
983
        {
984
                m_groupStack.top().Items.append(ite);
16732 fschmid 985
                applyMask(ite);
16729 fschmid 986
        }
987
        delete gfx;
988
        return gTrue;
989
}
990
 
16751 fschmid 991
void SlaOutputDev::drawImageMask(GfxState *state, Object *ref, Stream *str, int width, int height, GBool invert, GBool interpolate, GBool inlineImg)
992
{
993
//      qDebug() << "Draw Image Mask";
994
        QImage * image = 0;
995
        int invert_bit;
996
        int row_stride;
997
        int x, y, i, bit;
998
        unsigned char *dest = 0;
999
        unsigned char *buffer;
1000
        Guchar *pix;
1001
        ImageStream * imgStr = new ImageStream(str, width, 1, 1);
1002
        imgStr->reset();
1003
#ifdef WORDS_BIGENDIAN
1004
        image = new QImage(width, height, QImage::Format_Mono);
1005
#else
1006
        image = new QImage(width, height, QImage::Format_MonoLSB);
1007
#endif
1008
        invert_bit = invert ? 1 : 0;
1009
        buffer = image->bits();
1010
        row_stride = image->bytesPerLine();
1011
        for (y = 0; y < height; y++)
1012
        {
1013
                pix = imgStr->getLine();
1014
                dest = buffer + y * row_stride;
1015
                i = 0;
1016
                bit = 0;
1017
                for (x = 0; x < width; x++)
1018
                {
1019
                        if (bit == 0)
1020
                                dest[i] = 0;
1021
                        if (!(pix[x] ^ invert_bit))
1022
                        {
1023
#ifdef WORDS_BIGENDIAN
1024
                                dest[i] |= (1 << (7 - bit));
1025
#else
1026
                                dest[i] |= (1 << bit);
1027
#endif
1028
                        }
1029
                        bit++;
1030
                        if (bit > 7)
1031
                        {
1032
                                bit = 0;
1033
                                i++;
1034
                        }
1035
                }
1036
        }
1037
        QImage res = image->convertToFormat(QImage::Format_ARGB32);
1038
        double *ctm;
1039
        ctm = state->getCTM();
1040
        double xCoor = m_doc->currentPage()->xOffset();
1041
        double yCoor = m_doc->currentPage()->yOffset();
1042
        QRectF crect = QRectF(0, 0, width, height);
1043
        m_ctm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, ctm[2] + ctm[4], ctm[3] + ctm[5]);
1044
        QLineF cline = QLineF(0, 0, width, 0);
1045
        QLineF tline = m_ctm.map(cline);
1046
        QRectF trect = m_ctm.mapRect(crect);
1047
        double sx = m_ctm.m11();
1048
        double sy = m_ctm.m22();
1049
        QTransform mm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, 0, 0);
1050
        if ((mm.type() == QTransform::TxShear) || (mm.type() == QTransform::TxRotate))
1051
        {
1052
                mm.reset();
1053
                mm.rotate(-tline.angle());
1054
        }
1055
        else
1056
        {
1057
                mm.reset();
1058
                if (sx < 0)
1059
                        mm.scale(-1, 1);
1060
                if (sy < 0)
1061
                        mm.scale(1, -1);
1062
        }
1063
        QImage img = res.transformed(mm);
1064
        int z = m_doc->itemAdd(PageItem::ImageFrame, PageItem::Unspecified, xCoor + trect.x(), yCoor + trect.y(), trect.width(), trect.height(), 0, CommonStrings::None, CommonStrings::None, true);
1065
        PageItem* ite = m_doc->Items->at(z);
1066
        ite->SetRectFrame();
1067
        m_doc->setRedrawBounding(ite);
1068
        ite->Clip = FlattenPath(ite->PoLine, ite->Segments);
1069
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
1070
        ite->setFillShade(100);
1071
        ite->setLineShade(100);
1072
        ite->setFillEvenOdd(false);
1073
        ite->tempImageFile = new QTemporaryFile(QDir::tempPath() + "/scribus_temp_pdf_XXXXXX.png");
1074
        ite->tempImageFile->open();
1075
        QString fileName = getLongPathName(ite->tempImageFile->fileName());
1076
        ite->tempImageFile->close();
1077
        ite->isInlineImage = true;
1078
        img.save(fileName, "PNG");
1079
        m_doc->LoadPict(fileName, z);
1080
        ite->setImageScalingMode(false, true);
1081
        m_doc->AdjustItemSize(ite);
1082
        // Now creating patttern out of the image;
1083
        ScPattern pat = ScPattern();
1084
        pat.setDoc(m_doc);
1085
        m_doc->DoDrawing = true;
1086
        pat.pattern = ite->DrawObj_toImage(qMax(ite->width(), ite->height()));
1087
        pat.xoffset = 0;
1088
        pat.yoffset = 0;
1089
        m_doc->DoDrawing = false;
1090
        pat.width = pat.pattern.width();
1091
        pat.height = pat.pattern.height();
1092
        pat.items.append(ite);
1093
        m_doc->Items->removeAll(ite);
1094
        QString id = QString("Pattern_from_PDF_%1M").arg(m_doc->docPatterns.count() + 1);
1095
        m_doc->addPattern(id, pat);
1096
        // create the real item
1097
        int shade = 100;
1098
        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
1099
        z = m_doc->itemAdd(PageItem::Polygon, PageItem::Rectangle, xCoor + trect.x(), yCoor + trect.y(), trect.width(), trect.height(), 0, CurrColorFill, CommonStrings::None, true);
1100
        ite = m_doc->Items->at(z);
1101
        ite->ClipEdited = true;
1102
        ite->FrameType = 3;
1103
        ite->setFillShade(shade);
1104
        ite->setLineShade(100);
1105
        ite->setFillEvenOdd(false);
1106
        ite->setFillTransparency(1.0 - state->getFillOpacity());
1107
        ite->setFillBlendmode(getBlendMode(state));
1108
        ite->setLineEnd(PLineEnd);
1109
        ite->setLineJoin(PLineJoin);
1110
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
1111
        ite->setPatternMask(id);
1112
        ite->setMaskTransform(ite->width() / pat.width * 100, ite->height() / pat.height * 100, 0, 0, 0, 0, 0);
1113
        ite->setMaskType(6);
1114
        m_Elements->append(ite);
1115
        if (m_groupStack.count() != 0)
1116
                m_groupStack.top().Items.append(ite);
1117
        imgStr->close();
1118
        delete imgStr;
1119
        delete image;
1120
}
1121
 
16729 fschmid 1122
void SlaOutputDev::drawSoftMaskedImage(GfxState *state, Object *ref, Stream *str, int width, int height, GfxImageColorMap *colorMap, GBool interpolate, Stream *maskStr, int maskWidth, int maskHeight,
1123
                                   GfxImageColorMap *maskColorMap, GBool maskInterpolate)
1124
{
1125
        ImageStream * imgStr = new ImageStream(str, width, colorMap->getNumPixelComps(), colorMap->getBits());
1126
        imgStr->reset();
1127
        unsigned int *dest = 0;
1128
        unsigned char * buffer = new unsigned char[width * height * 4];
1129
        QImage * image = 0;
1130
        for (int y = 0; y < height; y++)
1131
        {
1132
                dest = (unsigned int *)(buffer + y * 4 * width);
1133
                Guchar * pix = imgStr->getLine();
1134
                colorMap->getRGBLine(pix, dest, width);
1135
        }
1136
        image = new QImage(buffer, width, height, QImage::Format_RGB32);
1137
        if (image == NULL || image->isNull())
1138
        {
1139
                delete imgStr;
1140
                delete[] buffer;
1141
                delete image;
1142
                return;
1143
        }
1144
        ImageStream *mskStr = new ImageStream(maskStr, maskWidth, maskColorMap->getNumPixelComps(), maskColorMap->getBits());
1145
        mskStr->reset();
1146
        Guchar *mdest = 0;
1147
        unsigned char * mbuffer = new unsigned char[maskWidth * maskHeight];
1148
        for (int y = 0; y < maskHeight; y++)
1149
        {
1150
                mdest = (Guchar *)(mbuffer + y * maskWidth);
1151
                Guchar * pix = mskStr->getLine();
1152
                maskColorMap->getGrayLine(pix, mdest, maskWidth);
1153
        }
1154
        if ((maskWidth != width) || (maskHeight != height))
1155
        {
1156
                delete imgStr;
1157
                delete[] buffer;
1158
                delete image;
1159
                delete mskStr;
1160
                delete[] mbuffer;
1161
                return;
1162
        }
1163
        QImage res = image->convertToFormat(QImage::Format_ARGB32);
1164
        unsigned char cc, cm, cy, ck;
1165
        int s = 0;
1166
        for( int yi=0; yi < res.height(); ++yi )
1167
        {
1168
                QRgb *t = (QRgb*)(res.scanLine( yi ));
1169
                for(int xi=0; xi < res.width(); ++xi )
1170
                {
1171
                        cc = qRed(*t);
1172
                        cm = qGreen(*t);
1173
                        cy = qBlue(*t);
1174
                        ck = mbuffer[s];
1175
                        (*t) = qRgba(cc, cm, cy, ck);
1176
                        s++;
1177
                        t++;
1178
                }
1179
        }
16751 fschmid 1180
        double *ctm;
1181
        ctm = state->getCTM();
16729 fschmid 1182
        double xCoor = m_doc->currentPage()->xOffset();
1183
        double yCoor = m_doc->currentPage()->yOffset();
16751 fschmid 1184
        QRectF crect = QRectF(0, 0, width, height);
1185
        m_ctm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, ctm[2] + ctm[4], ctm[3] + ctm[5]);
1186
        QLineF cline = QLineF(0, 0, width, 0);
1187
        QLineF tline = m_ctm.map(cline);
1188
        QRectF trect = m_ctm.mapRect(crect);
1189
        double sx = m_ctm.m11();
1190
        double sy = m_ctm.m22();
1191
        QTransform mm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, 0, 0);
1192
        if ((mm.type() == QTransform::TxShear) || (mm.type() == QTransform::TxRotate))
1193
        {
1194
                mm.reset();
1195
                mm.rotate(-tline.angle());
1196
        }
16729 fschmid 1197
        else
16751 fschmid 1198
        {
1199
                mm.reset();
1200
                if (sx < 0)
1201
                        mm.scale(-1, 1);
1202
                if (sy < 0)
1203
                        mm.scale(1, -1);
1204
        }
1205
        QImage img = res.transformed(mm);
1206
        int z = m_doc->itemAdd(PageItem::ImageFrame, PageItem::Unspecified, xCoor + trect.x(), yCoor + trect.y(), trect.width(), trect.height(), 0, CommonStrings::None, CommonStrings::None, true);
16729 fschmid 1207
        PageItem* ite = m_doc->Items->at(z);
1208
        ite->SetRectFrame();
1209
        m_doc->setRedrawBounding(ite);
1210
        ite->Clip = FlattenPath(ite->PoLine, ite->Segments);
1211
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
1212
        ite->setFillShade(100);
1213
        ite->setLineShade(100);
1214
        ite->setFillEvenOdd(false);
1215
        ite->setFillTransparency(1.0 - state->getFillOpacity());
1216
        ite->setFillBlendmode(getBlendMode(state));
1217
        ite->tempImageFile = new QTemporaryFile(QDir::tempPath() + "/scribus_temp_pdf_XXXXXX.png");
1218
        ite->tempImageFile->open();
1219
        QString fileName = getLongPathName(ite->tempImageFile->fileName());
1220
        ite->tempImageFile->close();
1221
        ite->isInlineImage = true;
16751 fschmid 1222
        img.save(fileName, "PNG");
16729 fschmid 1223
        m_doc->LoadPict(fileName, z);
1224
        ite->setImageScalingMode(false, true);
1225
        m_doc->AdjustItemSize(ite);
1226
        m_Elements->append(ite);
1227
        if (m_groupStack.count() != 0)
1228
        {
1229
                m_groupStack.top().Items.append(ite);
16732 fschmid 1230
                applyMask(ite);
16729 fschmid 1231
        }
1232
        delete imgStr;
1233
        delete[] buffer;
1234
        delete image;
1235
        delete mskStr;
1236
        delete[] mbuffer;
1237
}
1238
 
1239
void SlaOutputDev::drawImage(GfxState *state, Object *ref, Stream *str, int width, int height, GfxImageColorMap *colorMap, GBool interpolate, int *maskColors, GBool inlineImg)
1240
{
1241
        ImageStream * imgStr = new ImageStream(str, width, colorMap->getNumPixelComps(), colorMap->getBits());
1242
        imgStr->reset();
1243
        unsigned int *dest = 0;
1244
        unsigned char * buffer = new unsigned char[width * height * 4];
1245
        QImage * image = 0;
1246
        if (maskColors)
1247
        {
1248
                for (int y = 0; y < height; y++)
1249
                {
1250
                        dest = (unsigned int *)(buffer + y * 4 * width);
1251
                        Guchar * pix = imgStr->getLine();
1252
                        colorMap->getRGBLine(pix, dest, width);
1253
                        for (int x = 0; x < width; x++)
1254
                        {
1255
                                for (int i = 0; i < colorMap->getNumPixelComps(); ++i)
1256
                                {
1257
                                        if (pix[i] < maskColors[2*i] * 255 || pix[i] > maskColors[2*i+1] * 255)
1258
                                        {
1259
                                                *dest = *dest | 0xff000000;
1260
                                                break;
1261
                                        }
1262
                                }
1263
                                pix += colorMap->getNumPixelComps();
1264
                                dest++;
1265
                        }
1266
                }
1267
                image = new QImage(buffer, width, height, QImage::Format_ARGB32);
1268
        }
1269
        else
1270
        {
1271
                for (int y = 0; y < height; y++)
1272
                {
1273
                        dest = (unsigned int *)(buffer + y * 4 * width);
1274
                        Guchar * pix = imgStr->getLine();
1275
                        colorMap->getRGBLine(pix, dest, width);
1276
                }
1277
                image = new QImage(buffer, width, height, QImage::Format_RGB32);
1278
        }
1279
        if (image == NULL || image->isNull())
1280
        {
1281
                delete imgStr;
1282
                delete[] buffer;
1283
                delete image;
1284
                return;
1285
        }
16751 fschmid 1286
        double *ctm;
1287
        ctm = state->getCTM();
16729 fschmid 1288
        double xCoor = m_doc->currentPage()->xOffset();
1289
        double yCoor = m_doc->currentPage()->yOffset();
16751 fschmid 1290
        QRectF crect = QRectF(0, 0, width, height);
1291
        m_ctm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, ctm[2] + ctm[4], ctm[3] + ctm[5]);
1292
        QLineF cline = QLineF(0, 0, width, 0);
1293
        QLineF tline = m_ctm.map(cline);
1294
        QRectF trect = m_ctm.mapRect(crect);
1295
        double sx = m_ctm.m11();
1296
        double sy = m_ctm.m22();
1297
        QTransform mm = QTransform(ctm[0] / width, ctm[1] / width, -ctm[2] / height, -ctm[3] / height, 0, 0);
1298
        if ((mm.type() == QTransform::TxShear) || (mm.type() == QTransform::TxRotate))
1299
        {
1300
                mm.reset();
1301
                mm.rotate(-tline.angle());
1302
        }
16729 fschmid 1303
        else
16751 fschmid 1304
        {
1305
                mm.reset();
1306
                if (sx < 0)
1307
                        mm.scale(-1, 1);
1308
                if (sy < 0)
1309
                        mm.scale(1, -1);
1310
        }
1311
        QImage img = image->transformed(mm);
1312
        int z = m_doc->itemAdd(PageItem::ImageFrame, PageItem::Unspecified, xCoor + trect.x(), yCoor + trect.y(), trect.width(), trect.height(), 0, CommonStrings::None, CommonStrings::None, true);
16729 fschmid 1313
        PageItem* ite = m_doc->Items->at(z);
1314
        ite->SetRectFrame();
1315
        m_doc->setRedrawBounding(ite);
1316
        ite->Clip = FlattenPath(ite->PoLine, ite->Segments);
1317
        ite->setTextFlowMode(PageItem::TextFlowDisabled);
1318
        ite->setFillShade(100);
1319
        ite->setLineShade(100);
1320
        ite->setFillEvenOdd(false);
1321
        ite->setFillTransparency(1.0 - state->getFillOpacity());
1322
        ite->setFillBlendmode(getBlendMode(state));
1323
        ite->tempImageFile = new QTemporaryFile(QDir::tempPath() + "/scribus_temp_pdf_XXXXXX.png");
1324
        ite->tempImageFile->open();
1325
        QString fileName = getLongPathName(ite->tempImageFile->fileName());
1326
        ite->tempImageFile->close();
1327
        ite->isInlineImage = true;
16751 fschmid 1328
        img.save(fileName, "PNG");
16729 fschmid 1329
        m_doc->LoadPict(fileName, z);
1330
        ite->setImageScalingMode(false, true);
1331
        m_doc->AdjustItemSize(ite);
1332
        m_Elements->append(ite);
1333
        if (m_groupStack.count() != 0)
1334
        {
1335
                m_groupStack.top().Items.append(ite);
16732 fschmid 1336
                applyMask(ite);
16729 fschmid 1337
        }
1338
        delete imgStr;
1339
        delete[] buffer;
1340
        delete image;
1341
}
1342
 
1343
void SlaOutputDev::beginMarkedContent(char *name, Dict *properties)
1344
{
1345
//      qDebug() << "Begin Marked Content with Name " << QString(name);
1346
        if (importerFlags & LoadSavePlugin::lfCreateDoc)
1347
        {
1348
                if (QString(name) == "Layer")           // Handle Adobe Illustrator Layer command
1349
                {
1350
                        layerNum++;
1351
                        if (!firstLayer)
1352
                                currentLayer = m_doc->addLayer(QString("Layer_%1").arg(layerNum), true);
1353
                        firstLayer = false;
1354
                        Object obj;
1355
                        if (properties->lookup((char*)"Title", &obj))
1356
                        {
1357
                                if (obj.isString())
1358
                                {
1359
                                        QString lName =  QString(obj.getString()->getCString());
1360
                                        m_doc->changeLayerName(currentLayer, lName);
1361
                                }
1362
                                obj.free();
1363
                        }
1364
                        if (properties->lookup((char*)"Visible", &obj))
1365
                        {
1366
                                if (obj.isBool())
1367
                                        m_doc->setLayerVisible(currentLayer, obj.getBool());
1368
                                obj.free();
1369
                        }
1370
                        if (properties->lookup((char*)"Editable", &obj))
1371
                        {
1372
                                if (obj.isBool())
1373
                                        m_doc->setLayerLocked(currentLayer, !obj.getBool());
1374
                                obj.free();
1375
                        }
1376
                        if (properties->lookup((char*)"Printed", &obj))
1377
                        {
1378
                                if (obj.isBool())
1379
                                        m_doc->setLayerPrintable(currentLayer, obj.getBool());
1380
                                obj.free();
1381
                        }
1382
                        if (properties->lookup((char*)"Color", &obj))
1383
                        {
1384
                                if (obj.isArray())
1385
                                {
1386
                                        Object obj1;
1387
                                        obj.arrayGet(0, &obj1);
1388
                                        int r = obj1.getNum() / 256;
1389
                                        obj1.free();
1390
                                        obj.arrayGet(1, &obj1);
1391
                                        int g = obj1.getNum() / 256;
1392
                                        obj1.free();
1393
                                        obj.arrayGet(2, &obj1);
1394
                                        int b = obj1.getNum() / 256;
1395
                                        obj1.free();
1396
                                        m_doc->setLayerMarker(currentLayer, QColor(r, g, b));
1397
                                }
1398
                                obj.free();
1399
                        }
1400
                }
1401
        }
1402
}
1403
 
1404
void SlaOutputDev::endMarkedContent(GfxState *state)
1405
{
1406
//      qDebug() << "End Marked Content";
1407
}
1408
 
1409
void SlaOutputDev::updateFont(GfxState *state)
1410
{
1411
        GfxFont *gfxFont;
1412
        GfxFontType fontType;
1413
        SplashOutFontFileID *id;
1414
        SplashFontFile *fontFile;
1415
        SplashFontSrc *fontsrc = NULL;
1416
        FoFiTrueType *ff;
1417
        Ref embRef;
1418
        Object refObj, strObj;
1419
        GooString *fileName;
1420
        char *tmpBuf;
1421
        int tmpBufLen;
1422
        Gushort *codeToGID;
1423
        DisplayFontParam *dfp;
1424
        double *textMat;
1425
        double m11, m12, m21, m22, fontSize;
1426
        SplashCoord mat[4];
1427
        int n;
1428
        int faceIndex = 0;
1429
        SplashCoord matrix[6];
1430
 
1431
        m_font = NULL;
1432
        fileName = NULL;
1433
        tmpBuf = NULL;
1434
 
1435
        if (!(gfxFont = state->getFont()))
1436
                goto err1;
1437
        fontType = gfxFont->getType();
1438
        if (fontType == fontType3)
1439
                goto err1;
1440
 
1441
  // check the font file cache
1442
        id = new SplashOutFontFileID(gfxFont->getID());
1443
        if ((fontFile = m_fontEngine->getFontFile(id)))
1444
        {
1445
                delete id;
1446
        }
1447
        else
1448
        {
1449
                // if there is an embedded font, write it to disk
1450
                if (gfxFont->getEmbeddedFontID(&embRef))
1451
                {
1452
                        tmpBuf = gfxFont->readEmbFontFile(xref, &tmpBufLen);
1453
                        if (!tmpBuf)
1454
                                goto err2;
1455
                // if there is an external font file, use it
1456
                }
1457
                else if (!(fileName = gfxFont->getExtFontFile()))
1458
                {
1459
          // look for a display font mapping or a substitute font
1460
                        dfp = NULL;
1461
                        if (gfxFont->getName())
1462
                        {
1463
                                dfp = globalParams->getDisplayFont(gfxFont);
1464
                        }
1465
                        if (!dfp)
1466
                        {
1467
                //              error(-1, "Couldn't find a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1468
                                goto err2;
1469
                        }
1470
                        switch (dfp->kind)
1471
                        {
1472
                                case displayFontT1:
1473
                                        fileName = dfp->t1.fileName;
1474
                                        fontType = gfxFont->isCIDFont() ? fontCIDType0 : fontType1;
1475
                                        break;
1476
                                case displayFontTT:
1477
                                        fileName = dfp->tt.fileName;
1478
                                        fontType = gfxFont->isCIDFont() ? fontCIDType2 : fontTrueType;
1479
                                        faceIndex = dfp->tt.faceIndex;
1480
                                        break;
1481
                        }
1482
                }
1483
                fontsrc = new SplashFontSrc;
1484
                if (fileName)
1485
                        fontsrc->setFile(fileName, gFalse);
1486
                else
1487
                        fontsrc->setBuf(tmpBuf, tmpBufLen, gTrue);
1488
        // load the font file
1489
                switch (fontType)
1490
                {
1491
                        case fontType1:
1492
                                if (!(fontFile = m_fontEngine->loadType1Font( id, fontsrc, ((Gfx8BitFont *)gfxFont)->getEncoding())))
1493
                                {
1494
                        //              error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1495
                                        goto err2;
1496
                                }
1497
                                break;
1498
                        case fontType1C:
1499
                                if (!(fontFile = m_fontEngine->loadType1CFont( id, fontsrc, ((Gfx8BitFont *)gfxFont)->getEncoding())))
1500
                                {
1501
                //                      error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1502
                                        goto err2;
1503
                                }
1504
                                break;
1505
                        case fontType1COT:
1506
                                if (!(fontFile = m_fontEngine->loadOpenTypeT1CFont( id, fontsrc, ((Gfx8BitFont *)gfxFont)->getEncoding())))
1507
                                {
1508
                //                      error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1509
                                        goto err2;
1510
                                }
1511
                                break;
1512
                        case fontTrueType:
1513
                        case fontTrueTypeOT:
1514
                                if (fileName)
1515
                                        ff = FoFiTrueType::load(fileName->getCString());
1516
                                else
1517
                                        ff = FoFiTrueType::make(tmpBuf, tmpBufLen);
1518
                                if (ff)
1519
                                {
1520
                                        codeToGID = ((Gfx8BitFont *)gfxFont)->getCodeToGIDMap(ff);
1521
                                        n = 256;
1522
                                        delete ff;
1523
                                }
1524
                                else
1525
                                {
1526
                                        codeToGID = NULL;
1527
                                        n = 0;
1528
                                }
1529
                                if (!(fontFile = m_fontEngine->loadTrueTypeFont( id, fontsrc, codeToGID, n)))
1530
                                {
1531
        //                              error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1532
                                        goto err2;
1533
                                }
1534
                        break;
1535
                case fontCIDType0:
1536
                case fontCIDType0C:
1537
                        if (!(fontFile = m_fontEngine->loadCIDFont( id, fontsrc)))
1538
                        {
1539
        //                      error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1540
                                goto err2;
1541
                        }
1542
                        break;
1543
                case fontCIDType0COT:
1544
                        if (!(fontFile = m_fontEngine->loadOpenTypeCFFFont( id, fontsrc)))
1545
                        {
1546
        //                      error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1547
                                goto err2;
1548
                        }
1549
                        break;
1550
                case fontCIDType2:
1551
                case fontCIDType2OT:
1552
                        codeToGID = NULL;
1553
                        n = 0;
1554
                        if (((GfxCIDFont *)gfxFont)->getCIDToGID())
1555
                        {
1556
                                n = ((GfxCIDFont *)gfxFont)->getCIDToGIDLen();
1557
                                if (n)
1558
                                {
1559
                                        codeToGID = (Gushort *)gmallocn(n, sizeof(Gushort));
1560
                                        memcpy(codeToGID, ((GfxCIDFont *)gfxFont)->getCIDToGID(), n * sizeof(Gushort));
1561
                                }
1562
                        }
1563
                        else
1564
                        {
1565
                                if (fileName)
1566
                                        ff = FoFiTrueType::load(fileName->getCString());
1567
                                else
1568
                                        ff = FoFiTrueType::make(tmpBuf, tmpBufLen);
1569
                                if (!ff)
1570
                                        goto err2;
1571
                                codeToGID = ((GfxCIDFont *)gfxFont)->getCodeToGIDMap(ff, &n);
1572
                                delete ff;
1573
                        }
1574
                        if (!(fontFile = m_fontEngine->loadTrueTypeFont( id, fontsrc, codeToGID, n, faceIndex)))
1575
                        {
1576
        //                      error(-1, "Couldn't create a font for '%s'", gfxFont->getName() ? gfxFont->getName()->getCString() : "(unnamed)");
1577
                                goto err2;
1578
                        }
1579
                        break;
1580
                default:
1581
          // this shouldn't happen
1582
                        goto err2;
1583
                }
1584
        }
1585
        // get the font matrix
1586
        textMat = state->getTextMat();
1587
        fontSize = state->getFontSize();
1588
        m11 = textMat[0] * fontSize * state->getHorizScaling();
1589
        m12 = textMat[1] * fontSize * state->getHorizScaling();
1590
        m21 = textMat[2] * fontSize;
1591
        m22 = textMat[3] * fontSize;
1592
        matrix[0] = 1;
1593
        matrix[1] = 0;
1594
        matrix[2] = 0;
1595
        matrix[3] = 1;
1596
        matrix[4] = 0;
1597
        matrix[5] = 0;
1598
  // create the scaled font
1599
        mat[0] = m11;
1600
        mat[1] = -m12;
1601
        mat[2] = m21;
1602
        mat[3] = -m22;
1603
        m_font = m_fontEngine->getFont(fontFile, mat, matrix);
1604
        if (fontsrc && !fontsrc->isFile)
1605
                fontsrc->unref();
1606
        return;
1607
 
1608
err2:
1609
        delete id;
1610
err1:
1611
        if (fontsrc && !fontsrc->isFile)
1612
                fontsrc->unref();
1613
        return;
1614
}
1615
 
1616
void SlaOutputDev::drawChar(GfxState *state, double x, double y, double dx, double dy, double originX, double originY, CharCode code, int nBytes, Unicode *u, int uLen)
1617
{
1618
        double x1, y1, x2, y2;
1619
        int render;
1620
        updateFont(state);
1621
        if (!m_font)
1622
                return;
1623
  // check for invisible text -- this is used by Acrobat Capture
1624
        render = state->getRender();
1625
        if (render == 3)
1626
                return;
1627
        if (!(render & 1))
1628
        {
1629
                SplashPath * fontPath;
1630
                fontPath = m_font->getGlyphPath(code);
1631
                if (fontPath)
1632
                {
1633
                        QPainterPath qPath;
1634
                        qPath.setFillRule(Qt::WindingFill);
1635
                        for (int i = 0; i < fontPath->getLength(); ++i)
1636
                        {
1637
                                Guchar f;
1638
                                fontPath->getPoint(i, &x1, &y1, &f);
1639
                                if (f & splashPathFirst)
1640
                                        qPath.moveTo(x1,y1);
1641
                                else if (f & splashPathCurve)
1642
                                {
1643
                                        double x3, y3;
1644
                                        ++i;
1645
                                        fontPath->getPoint(i, &x2, &y2, &f);
1646
                                        ++i;
1647
                                        fontPath->getPoint(i, &x3, &y3, &f);
1648
                                        qPath.cubicTo(x1,y1,x2,y2,x3,y3);
1649
                                }
1650
                                else
1651
                                        qPath.lineTo(x1,y1);
1652
                                if (f & splashPathLast)
1653
                                        qPath.closeSubpath();
1654
                        }
1655
                        double *ctm;
1656
                        ctm = state->getCTM();
1657
                        m_ctm = QTransform(ctm[0], ctm[1], ctm[2], ctm[3], ctm[4], ctm[5]);
1658
                        double xCoor = m_doc->currentPage()->xOffset();
1659
                        double yCoor = m_doc->currentPage()->yOffset();
16746 fschmid 1660
                        int shade = 100;
1661
                        CurrColorFill = getColor(state->getFillColorSpace(), state->getFillColor(), &shade);
16729 fschmid 1662
                        FPointArray textPath;
1663
                        textPath.fromQPainterPath(qPath);
1664
                        FPoint wh = textPath.WidthHeight();
1665
                        if ((textPath.size() > 3) && ((wh.x() != 0.0) || (wh.y() != 0.0)))
1666
                        {
1667
                                int z = m_doc->itemAdd(PageItem::Polygon, PageItem::Unspecified, xCoor, yCoor, 10, 10, 0, CurrColorFill, CommonStrings::None, true);
1668
                                PageItem* ite = m_doc->Items->at(z);
1669
                                FPoint tp2(getMinClipF(&textPath));
1670
                                QTransform mm;
1671
                                mm.scale(1, -1);
1672
                                mm.translate(x, -y);
1673
                                textPath.map(mm);
1674
                                textPath.map(m_ctm);
1675
                                ite->PoLine = textPath.copy();
1676
                                ite->ClipEdited = true;
1677
                                ite->FrameType = 3;
16746 fschmid 1678
                                ite->setFillShade(shade);
16729 fschmid 1679
                                ite->setFillEvenOdd(false);
1680
                                ite->setFillTransparency(1.0 - state->getFillOpacity());
1681
                                ite->setFillBlendmode(getBlendMode(state));
1682
                                ite->setLineEnd(PLineEnd);
1683
                                ite->setLineJoin(PLineJoin);
1684
                                ite->setTextFlowMode(PageItem::TextFlowDisabled);
1685
                                m_doc->AdjustItemSize(ite);
1686
                                if ((render & 3) == 1 || (render & 3) == 2)
1687
                                {
16746 fschmid 1688
                                        CurrColorStroke = getColor(state->getStrokeColorSpace(), state->getStrokeColor(), &shade);
16729 fschmid 1689
                                        ite->setLineColor(CurrColorStroke);
1690
                                        ite->setLineWidth(state->getTransformedLineWidth());
1691
                                        ite->setLineTransparency(1.0 - state->getStrokeOpacity());
1692
                                        ite->setLineBlendmode(getBlendMode(state));
16746 fschmid 1693
                                        ite->setLineShade(shade);
16729 fschmid 1694
                                }
1695
                                m_Elements->append(ite);
1696
                                if (m_groupStack.count() != 0)
1697
                                {
1698
                                        m_groupStack.top().Items.append(ite);
16732 fschmid 1699
                                        applyMask(ite);
16729 fschmid 1700
                                }
1701
                                delete fontPath;
1702
                        }
1703
                }
1704
        }
1705
}
1706
 
1707
void SlaOutputDev::beginTextObject(GfxState *state)
1708
{
1709
//      qDebug() << "Begin Text Object";
16732 fschmid 1710
        pushGroup();
16729 fschmid 1711
}
1712
 
1713
void SlaOutputDev::endTextObject(GfxState *state)
1714
{
1715
//      qDebug() << "End Text Object";
1716
        if (m_groupStack.count() != 0)
1717
        {
1718
                groupEntry gElements = m_groupStack.pop();
1719
                tmpSel->clear();
1720
                if (gElements.Items.count() > 0)
1721
                {
1722
                        for (int dre = 0; dre < gElements.Items.count(); ++dre)
1723
                        {
1724
                                tmpSel->addItem(gElements.Items.at(dre), true);
1725
                                m_Elements->removeAll(gElements.Items.at(dre));
1726
                        }
1727
                        PageItem *ite = m_doc->groupObjectsSelection(tmpSel);
1728
                        ite->setFillTransparency(1.0 - state->getFillOpacity());
1729
                        ite->setFillBlendmode(getBlendMode(state));
1730
                        for (int as = 0; as < tmpSel->count(); ++as)
1731
                        {
1732
                                m_Elements->append(tmpSel->itemAt(as));
1733
                        }
1734
                        if (m_groupStack.count() != 0)
16732 fschmid 1735
                                applyMask(ite);
16729 fschmid 1736
                }
1737
                if (m_groupStack.count() != 0)
1738
                {
1739
                        for (int as = 0; as < tmpSel->count(); ++as)
1740
                        {
1741
                                m_groupStack.top().Items.append(tmpSel->itemAt(as));
1742
                        }
1743
                }
1744
                tmpSel->clear();
1745
        }
1746
}
1747
 
16746 fschmid 1748
QString SlaOutputDev::getColor(GfxColorSpace *color_space, GfxColor *color, int *shade)
16729 fschmid 1749
{
1750
        QString fNam;
1751
        QString namPrefix = "FromPDF";
1752
        ScColor tmp;
1753
        tmp.setSpotColor(false);
1754
        tmp.setRegistrationColor(false);
16746 fschmid 1755
        *shade = 100;
16729 fschmid 1756
        if ((color_space->getMode() == csDeviceRGB) || (color_space->getMode() == csCalRGB))
1757
        {
1758
                GfxRGB rgb;
1759
                color_space->getRGB(color, &rgb);
1760
                int Rc = qRound(colToDbl(rgb.r) * 255);
1761
                int Gc = qRound(colToDbl(rgb.g) * 255);
1762
                int Bc = qRound(colToDbl(rgb.b) * 255);
1763
                tmp.setColorRGB(Rc, Gc, Bc);
1764
                fNam = m_doc->PageColors.tryAddColor(namPrefix+tmp.name(), tmp);
1765
        }
1766
        else if (color_space->getMode() == csDeviceCMYK)
1767
        {
1768
                GfxCMYK cmyk;
1769
                color_space->getCMYK(color, &cmyk);
1770
                int Cc = qRound(colToDbl(cmyk.c) * 255);
1771
                int Mc = qRound(colToDbl(cmyk.m) * 255);
1772
                int Yc = qRound(colToDbl(cmyk.y) * 255);
1773
                int Kc = qRound(colToDbl(cmyk.k) * 255);
1774
                tmp.setColor(Cc, Mc, Yc, Kc);
1775
                fNam = m_doc->PageColors.tryAddColor(namPrefix+tmp.name(), tmp);
1776
        }
1777
        else if ((color_space->getMode() == csCalGray) || (color_space->getMode() == csDeviceGray))
1778
        {
1779
                GfxGray gray;
1780
                color_space->getGray(color, &gray);
1781
                int Kc = 255 - qRound(colToDbl(gray) * 255);
1782
                tmp.setColor(0, 0, 0, Kc);
1783
                fNam = m_doc->PageColors.tryAddColor(namPrefix+tmp.name(), tmp);
1784
        }
1785
        else if (color_space->getMode() == csSeparation)
1786
        {
1787
                GfxCMYK cmyk;
1788
                color_space->getCMYK(color, &cmyk);
1789
                int Cc = qRound(colToDbl(cmyk.c) * 255);
1790
                int Mc = qRound(colToDbl(cmyk.m) * 255);
1791
                int Yc = qRound(colToDbl(cmyk.y) * 255);
1792
                int Kc = qRound(colToDbl(cmyk.k) * 255);
1793
                tmp.setColor(Cc, Mc, Yc, Kc);
1794
                tmp.setSpotColor(true);
1795
                QString nam = QString(((GfxSeparationColorSpace*)color_space)->getName()->getCString());
1796
                fNam = m_doc->PageColors.tryAddColor(nam, tmp);
16746 fschmid 1797
                *shade = qRound(colToDbl(color->c[0]) * 100);
16729 fschmid 1798
        }
1799
        else
1800
        {
1801
                GfxRGB rgb;
1802
                color_space->getRGB(color, &rgb);
1803
                int Rc = qRound(colToDbl(rgb.r) * 255);
1804
                int Gc = qRound(colToDbl(rgb.g) * 255);
1805
                int Bc = qRound(colToDbl(rgb.b) * 255);
1806
                tmp.setColorRGB(Rc, Gc, Bc);
1807
                fNam = m_doc->PageColors.tryAddColor(namPrefix+tmp.name(), tmp);
1808
        //      qDebug() << "update fill color other colorspace" << color_space->getMode() << "treating as rgb" << Rc << Gc << Bc;
1809
        }
1810
        if (fNam == namPrefix+tmp.name())
1811
                m_importedColors->append(fNam);
1812
        return fNam;
1813
}
1814
 
1815
QString SlaOutputDev::convertPath(GfxPath *path)
1816
{
1817
    if (! path)
1818
                return QString();
1819
 
1820
    QString output;
1821
        pathIsClosed = false;
1822
 
1823
        for (int i = 0; i < path->getNumSubpaths(); ++i)
1824
        {
1825
        GfxSubpath * subpath = path->getSubpath(i);
1826
                if (subpath->getNumPoints() > 0)
1827
                {
1828
                        output += QString("M %1 %2").arg(subpath->getX(0)).arg(subpath->getY(0));
1829
            int j = 1;
1830
                        while (j < subpath->getNumPoints())
1831
                        {
1832
                                if (subpath->getCurve(j))
1833
                                {
1834
                                        output += QString("C %1 %2 %3 %4 %5 %6")
1835
                              .arg(subpath->getX(j)).arg(subpath->getY(j))
1836
                              .arg(subpath->getX(j + 1)).arg(subpath->getY(j + 1))
1837
                              .arg(subpath->getX(j + 2)).arg(subpath->getY(j + 2));
1838
                    j += 3;
1839
                                }
1840
                                else
1841
                                {
1842
                                        output += QString("L %1 %2").arg(subpath->getX(j)).arg(subpath->getY(j));
1843
                    ++j;
1844
                }
1845
            }
1846
                        if (subpath->isClosed())
1847
                        {
1848
                output += QString("Z");
1849
                                pathIsClosed = true;
1850
            }
1851
        }
1852
        }
1853
        return output;
1854
}
1855
 
1856
void SlaOutputDev::getPenState(GfxState *state)
1857
{
1858
        switch (state->getLineCap())
1859
        {
1860
                case 0:
1861
                        PLineEnd = Qt::FlatCap;
1862
                        break;
1863
                case 1:
1864
                        PLineEnd = Qt::RoundCap;
1865
                        break;
1866
                case 2:
1867
                        PLineEnd = Qt::SquareCap;
1868
                        break;
1869
        }
1870
        switch (state->getLineJoin())
1871
        {
1872
                case 0:
1873
                        PLineJoin = Qt::MiterJoin;
1874
                        break;
1875
                case 1:
1876
                        PLineJoin = Qt::RoundJoin;
1877
                        break;
1878
                case 2:
1879
                        PLineJoin = Qt::BevelJoin;
1880
                        break;
1881
        }
1882
        double *dashPattern;
1883
        int dashLength;
1884
        state->getLineDash(&dashPattern, &dashLength, &DashOffset);
1885
        QVector<double> pattern(dashLength);
1886
        for (int i = 0; i < dashLength; ++i)
1887
        {
1888
                pattern[i] = dashPattern[i];
1889
        }
1890
        DashValues = pattern;
1891
}
1892
 
1893
int SlaOutputDev::getBlendMode(GfxState *state)
1894
{
1895
        int mode = 0;
1896
        switch (state->getBlendMode())
1897
        {
1898
                default:
1899
                case gfxBlendNormal:
1900
                        mode = 0;
1901
                        break;
1902
                case gfxBlendDarken:
1903
                        mode = 1;
1904
                        break;
1905
                case gfxBlendLighten:
1906
                        mode = 2;
1907
                        break;
1908
                case gfxBlendMultiply:
1909
                        mode = 3;
1910
                        break;
1911
                case gfxBlendScreen:
1912
                        mode = 4;
1913
                        break;
1914
                case gfxBlendOverlay:
1915
                        mode = 5;
1916
                        break;
1917
                case gfxBlendHardLight:
1918
                        mode = 6;
1919
                        break;
1920
                case gfxBlendSoftLight:
1921
                        mode = 7;
1922
                        break;
1923
                case gfxBlendDifference:
1924
                        mode = 8;
1925
                        break;
1926
                case gfxBlendExclusion:
1927
                        mode = 9;
1928
                        break;
1929
                case gfxBlendColorDodge:
1930
                        mode = 10;
1931
                        break;
1932
                case gfxBlendColorBurn:
1933
                        mode = 11;
1934
                        break;
1935
                case gfxBlendHue:
1936
                        mode = 12;
1937
                        break;
1938
                case gfxBlendSaturation:
1939
                        mode = 13;
1940
                        break;
1941
                case gfxBlendColor:
1942
                        mode = 14;
1943
                        break;
1944
                case gfxBlendLuminosity:
1945
                        mode = 15;
1946
                        break;
1947
        }
1948
        return mode;
1949
}
1950
 
16732 fschmid 1951
void SlaOutputDev::applyMask(PageItem *ite)
1952
{
1953
        if (m_groupStack.count() != 0)
1954
        {
1955
                if (!m_groupStack.top().maskName.isEmpty())
1956
                {
1957
                        ite->setPatternMask(m_groupStack.top().maskName);
1958
                        if (m_groupStack.top().alpha)
1959
                        {
1960
                                if (m_groupStack.top().inverted)
1961
                                        ite->setMaskType(8);
1962
                                else
1963
                                        ite->setMaskType(3);
1964
                        }
1965
                        else
1966
                        {
1967
                                if (m_groupStack.top().inverted)
1968
                                        ite->setMaskType(7);
1969
                                else
1970
                                        ite->setMaskType(6);
1971
                        }
1972
                }
1973
        }
1974
}
1975
 
1976
void SlaOutputDev::pushGroup(QString maskName, GBool forSoftMask, GBool alpha, bool inverted)
1977
{
1978
        groupEntry gElements;
1979
        gElements.forSoftMask = forSoftMask;
1980
        gElements.alpha = alpha;
1981
        gElements.inverted = inverted;
1982
        gElements.maskName = maskName;
1983
        m_groupStack.push(gElements);
1984
}