GNU Octave 7.1.0
A high-level interpreted language, primarily intended for numerical computations, mostly compatible with Matlab
octave-qsvghandler.h
Go to the documentation of this file.
1/****************************************************************************
2**
3** Copyright (C) 2016 The Qt Company Ltd.
4** Contact: https://www.qt.io/licensing/
5**
6** This file is part of the Qt SVG module of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:LGPL$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and The Qt Company. For licensing terms
14** and conditions see https://www.qt.io/terms-conditions. For further
15** information use the contact form at https://www.qt.io/contact-us.
16**
17** GNU Lesser General Public License Usage
18** Alternatively, this file may be used under the terms of the GNU Lesser
19** General Public License version 3 as published by the Free Software
20** Foundation and appearing in the file LICENSE.LGPL3 included in the
21** packaging of this file. Please review the following information to
22** ensure the GNU Lesser General Public License version 3 requirements
23** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
24**
25** GNU General Public License Usage
26** Alternatively, this file may be used under the terms of the GNU
27** General Public License version 2.0 or (at your option) the GNU General
28** Public license version 3 or any later version approved by the KDE Free
29** Qt Foundation. The licenses are as published by the Free Software
30** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
31** included in the packaging of this file. Please review the following
32** information to ensure the GNU General Public License requirements will
33** be met: https://www.gnu.org/licenses/gpl-2.0.html and
34** https://www.gnu.org/licenses/gpl-3.0.html.
35**
36** $QT_END_LICENSE$
37**
38****************************************************************************/
39
40// --------------------------------------------------------------------------
41// Build a QPainterPath from the "d" attribute of a path element
42// These functions are extracted from Qt-5.12 sources (qtsvghandler.cpp)
43// Modifications:
44// * use static_cast<qreal> to avoid old style cast warning.
45// --------------------------------------------------------------------------
46
47#include <QPainterPath>
48
49static inline bool isDigit(ushort ch)
50{
51 static quint16 magic = 0x3ff;
52 return ((ch >> 4) == 3) && (magic >> (ch & 15));
53}
54
55static qreal toDouble(const QChar *&str)
56{
57 const int maxLen = 255;//technically doubles can go til 308+ but whatever
58 char temp[maxLen+1];
59 int pos = 0;
60
61 if (*str == QLatin1Char('-')) {
62 temp[pos++] = '-';
63 ++str;
64 } else if (*str == QLatin1Char('+')) {
65 ++str;
66 }
67 while (isDigit(str->unicode()) && pos < maxLen) {
68 temp[pos++] = str->toLatin1();
69 ++str;
70 }
71 if (*str == QLatin1Char('.') && pos < maxLen) {
72 temp[pos++] = '.';
73 ++str;
74 }
75 while (isDigit(str->unicode()) && pos < maxLen) {
76 temp[pos++] = str->toLatin1();
77 ++str;
78 }
79 bool exponent = false;
80 if ((*str == QLatin1Char('e') || *str == QLatin1Char('E')) && pos < maxLen) {
81 exponent = true;
82 temp[pos++] = 'e';
83 ++str;
84 if ((*str == QLatin1Char('-') || *str == QLatin1Char('+')) && pos < maxLen) {
85 temp[pos++] = str->toLatin1();
86 ++str;
87 }
88 while (isDigit(str->unicode()) && pos < maxLen) {
89 temp[pos++] = str->toLatin1();
90 ++str;
91 }
92 }
93
94 temp[pos] = '\0';
95
96 qreal val;
97 if (!exponent && pos < 10) {
98 int ival = 0;
99 const char *t = temp;
100 bool neg = false;
101 if(*t == '-') {
102 neg = true;
103 ++t;
104 }
105 while(*t && *t != '.') {
106 ival *= 10;
107 ival += (*t) - '0';
108 ++t;
109 }
110 if(*t == '.') {
111 ++t;
112 int div = 1;
113 while(*t) {
114 ival *= 10;
115 ival += (*t) - '0';
116 div *= 10;
117 ++t;
118 }
119 val = static_cast<qreal> (ival)/static_cast<qreal> (div);
120 } else {
121 val = ival;
122 }
123 if (neg)
124 val = -val;
125 } else {
126 val = QByteArray::fromRawData(temp, pos).toDouble();
127 }
128 return val;
129
130}
131
132static inline void parseNumbersArray(const QChar *&str, QVarLengthArray<qreal, 8> &points)
133{
134 while (str->isSpace())
135 ++str;
136 while (isDigit(str->unicode()) ||
137 *str == QLatin1Char('-') || *str == QLatin1Char('+') ||
138 *str == QLatin1Char('.')) {
139
140 points.append(toDouble(str));
141
142 while (str->isSpace())
143 ++str;
144 if (*str == QLatin1Char(','))
145 ++str;
146
147 //eat the rest of space
148 while (str->isSpace())
149 ++str;
150 }
151}
152static void pathArcSegment(QPainterPath &path,
153 qreal xc, qreal yc,
154 qreal th0, qreal th1,
155 qreal rx, qreal ry, qreal xAxisRotation)
156{
157 qreal sinTh, cosTh;
158 qreal a00, a01, a10, a11;
159 qreal x1, y1, x2, y2, x3, y3;
160 qreal t;
161 qreal thHalf;
162
163 sinTh = qSin(xAxisRotation * (3.141592653589793 / 180.0));
164 cosTh = qCos(xAxisRotation * (3.141592653589793 / 180.0));
165
166 a00 = cosTh * rx;
167 a01 = -sinTh * ry;
168 a10 = sinTh * rx;
169 a11 = cosTh * ry;
170
171 thHalf = 0.5 * (th1 - th0);
172 t = (8.0 / 3.0) * qSin(thHalf * 0.5) * qSin(thHalf * 0.5) / qSin(thHalf);
173 x1 = xc + qCos(th0) - t * qSin(th0);
174 y1 = yc + qSin(th0) + t * qCos(th0);
175 x3 = xc + qCos(th1);
176 y3 = yc + qSin(th1);
177 x2 = x3 + t * qSin(th1);
178 y2 = y3 - t * qCos(th1);
179
180 path.cubicTo(a00 * x1 + a01 * y1, a10 * x1 + a11 * y1,
181 a00 * x2 + a01 * y2, a10 * x2 + a11 * y2,
182 a00 * x3 + a01 * y3, a10 * x3 + a11 * y3);
183}
184
185// the arc handling code underneath is from XSVG (BSD license)
186/*
187 * Copyright 2002 USC/Information Sciences Institute
188 *
189 * Permission to use, copy, modify, distribute, and sell this software
190 * and its documentation for any purpose is hereby granted without
191 * fee, provided that the above copyright notice appear in all copies
192 * and that both that copyright notice and this permission notice
193 * appear in supporting documentation, and that the name of
194 * Information Sciences Institute not be used in advertising or
195 * publicity pertaining to distribution of the software without
196 * specific, written prior permission. Information Sciences Institute
197 * makes no representations about the suitability of this software for
198 * any purpose. It is provided "as is" without express or implied
199 * warranty.
200 *
201 * INFORMATION SCIENCES INSTITUTE DISCLAIMS ALL WARRANTIES WITH REGARD
202 * TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
203 * MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL INFORMATION SCIENCES
204 * INSTITUTE BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
205 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA
206 * OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
207 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
208 * PERFORMANCE OF THIS SOFTWARE.
209 *
210 */
211static void pathArc(QPainterPath &path,
212 qreal rx,
213 qreal ry,
214 qreal x_axis_rotation,
215 int large_arc_flag,
216 int sweep_flag,
217 qreal x,
218 qreal y,
219 qreal curx, qreal cury)
220{
221 qreal sin_th, cos_th;
222 qreal a00, a01, a10, a11;
223 qreal x0, y0, x1, y1, xc, yc;
224 qreal d, sfactor, sfactor_sq;
225 qreal th0, th1, th_arc;
226 int i, n_segs;
227 qreal dx, dy, dx1, dy1, Pr1, Pr2, Px, Py, check;
228
229 rx = qAbs(rx);
230 ry = qAbs(ry);
231
232 sin_th = qSin(x_axis_rotation * (3.141592653589793 / 180.0));
233 cos_th = qCos(x_axis_rotation * (3.141592653589793 / 180.0));
234
235 dx = (curx - x) / 2.0;
236 dy = (cury - y) / 2.0;
237 dx1 = cos_th * dx + sin_th * dy;
238 dy1 = -sin_th * dx + cos_th * dy;
239 Pr1 = rx * rx;
240 Pr2 = ry * ry;
241 Px = dx1 * dx1;
242 Py = dy1 * dy1;
243 /* Spec : check if radii are large enough */
244 check = Px / Pr1 + Py / Pr2;
245 if (check > 1) {
246 rx = rx * qSqrt(check);
247 ry = ry * qSqrt(check);
248 }
249
250 a00 = cos_th / rx;
251 a01 = sin_th / rx;
252 a10 = -sin_th / ry;
253 a11 = cos_th / ry;
254 x0 = a00 * curx + a01 * cury;
255 y0 = a10 * curx + a11 * cury;
256 x1 = a00 * x + a01 * y;
257 y1 = a10 * x + a11 * y;
258 /* (x0, y0) is current point in transformed coordinate space.
259 (x1, y1) is new point in transformed coordinate space.
260
261 The arc fits a unit-radius circle in this space.
262 */
263 d = (x1 - x0) * (x1 - x0) + (y1 - y0) * (y1 - y0);
264 sfactor_sq = 1.0 / d - 0.25;
265 if (sfactor_sq < 0) sfactor_sq = 0;
266 sfactor = qSqrt(sfactor_sq);
267 if (sweep_flag == large_arc_flag) sfactor = -sfactor;
268 xc = 0.5 * (x0 + x1) - sfactor * (y1 - y0);
269 yc = 0.5 * (y0 + y1) + sfactor * (x1 - x0);
270 /* (xc, yc) is center of the circle. */
271
272 th0 = qAtan2(y0 - yc, x0 - xc);
273 th1 = qAtan2(y1 - yc, x1 - xc);
274
275 th_arc = th1 - th0;
276 if (th_arc < 0 && sweep_flag)
277 th_arc += 2 * 3.141592653589793;
278 else if (th_arc > 0 && !sweep_flag)
279 th_arc -= 2 * 3.141592653589793;
280
281 n_segs = qCeil(qAbs(th_arc / (3.141592653589793 * 0.5 + 0.001)));
282
283 for (i = 0; i < n_segs; i++) {
284 pathArcSegment(path, xc, yc,
285 th0 + i * th_arc / n_segs,
286 th0 + (i + 1) * th_arc / n_segs,
287 rx, ry, x_axis_rotation);
288 }
289}
290
291static QTransform parseTransformationMatrix(const QStringRef &value)
292{
293 if (value.isEmpty())
294 return QTransform();
295
296 QTransform matrix;
297 const QChar *str = value.constData();
298 const QChar *end = str + value.length();
299
300 while (str < end) {
301 if (str->isSpace() || *str == QLatin1Char(',')) {
302 ++str;
303 continue;
304 }
305 enum State {
306 Matrix,
307 Translate,
308 Rotate,
309 Scale,
310 SkewX,
311 SkewY
312 };
313 State state = Matrix;
314 if (*str == QLatin1Char('m')) { //matrix
315 const char *ident = "atrix";
316 for (int i = 0; i < 5; ++i)
317 if (*(++str) != QLatin1Char(ident[i]))
318 goto error;
319 ++str;
320 state = Matrix;
321 } else if (*str == QLatin1Char('t')) { //translate
322 const char *ident = "ranslate";
323 for (int i = 0; i < 8; ++i)
324 if (*(++str) != QLatin1Char(ident[i]))
325 goto error;
326 ++str;
327 state = Translate;
328 } else if (*str == QLatin1Char('r')) { //rotate
329 const char *ident = "otate";
330 for (int i = 0; i < 5; ++i)
331 if (*(++str) != QLatin1Char(ident[i]))
332 goto error;
333 ++str;
334 state = Rotate;
335 } else if (*str == QLatin1Char('s')) { //scale, skewX, skewY
336 ++str;
337 if (*str == QLatin1Char('c')) {
338 const char *ident = "ale";
339 for (int i = 0; i < 3; ++i)
340 if (*(++str) != QLatin1Char(ident[i]))
341 goto error;
342 ++str;
343 state = Scale;
344 } else if (*str == QLatin1Char('k')) {
345 if (*(++str) != QLatin1Char('e'))
346 goto error;
347 if (*(++str) != QLatin1Char('w'))
348 goto error;
349 ++str;
350 if (*str == QLatin1Char('X'))
351 state = SkewX;
352 else if (*str == QLatin1Char('Y'))
353 state = SkewY;
354 else
355 goto error;
356 ++str;
357 } else {
358 goto error;
359 }
360 } else {
361 goto error;
362 }
363
364
365 while (str < end && str->isSpace())
366 ++str;
367 if (*str != QLatin1Char('('))
368 goto error;
369 ++str;
370 QVarLengthArray<qreal, 8> points;
371 parseNumbersArray(str, points);
372 if (*str != QLatin1Char(')'))
373 goto error;
374 ++str;
375
376 if(state == Matrix) {
377 if(points.count() != 6)
378 goto error;
379 matrix = QTransform(points[0], points[1],
380 points[2], points[3],
381 points[4], points[5]) * matrix;
382 } else if (state == Translate) {
383 if (points.count() == 1)
384 matrix.translate(points[0], 0);
385 else if (points.count() == 2)
386 matrix.translate(points[0], points[1]);
387 else
388 goto error;
389 } else if (state == Rotate) {
390 if(points.count() == 1) {
391 matrix.rotate(points[0]);
392 } else if (points.count() == 3) {
393 matrix.translate(points[1], points[2]);
394 matrix.rotate(points[0]);
395 matrix.translate(-points[1], -points[2]);
396 } else {
397 goto error;
398 }
399 } else if (state == Scale) {
400 if (points.count() < 1 || points.count() > 2)
401 goto error;
402 qreal sx = points[0];
403 qreal sy = sx;
404 if(points.count() == 2)
405 sy = points[1];
406 matrix.scale(sx, sy);
407 } else if (state == SkewX) {
408 if (points.count() != 1)
409 goto error;
410 const qreal deg2rad = qreal(0.017453292519943295769);
411 matrix.shear(qTan(points[0]*deg2rad), 0);
412 } else if (state == SkewY) {
413 if (points.count() != 1)
414 goto error;
415 const qreal deg2rad = qreal(0.017453292519943295769);
416 matrix.shear(0, qTan(points[0]*deg2rad));
417 }
418 }
419 error:
420 return matrix;
421}
422
423static bool parsePathDataFast(const QStringRef &dataStr, QPainterPath &path)
424{
425 qreal x0 = 0, y0 = 0; // starting point
426 qreal x = 0, y = 0; // current point
427 char lastMode = 0;
428 QPointF ctrlPt;
429 const QChar *str = dataStr.constData();
430 const QChar *end = str + dataStr.size();
431
432 while (str != end) {
433 while (str->isSpace() && (str + 1) != end)
434 ++str;
435 QChar pathElem = *str;
436 ++str;
437 QChar endc = *end;
438 *const_cast<QChar *>(end) = 0; // parseNumbersArray requires 0-termination that QStringRef cannot guarantee
439 QVarLengthArray<qreal, 8> arg;
440 parseNumbersArray(str, arg);
441 *const_cast<QChar *>(end) = endc;
442 if (pathElem == QLatin1Char('z') || pathElem == QLatin1Char('Z'))
443 arg.append(0);//dummy
444 const qreal *num = arg.constData();
445 int count = arg.count();
446 while (count > 0) {
447 qreal offsetX = x; // correction offsets
448 qreal offsetY = y; // for relative commands
449 switch (pathElem.unicode()) {
450 case 'm': {
451 if (count < 2) {
452 num++;
453 count--;
454 break;
455 }
456 x = x0 = num[0] + offsetX;
457 y = y0 = num[1] + offsetY;
458 num += 2;
459 count -= 2;
460 path.moveTo(x0, y0);
461
462 // As per 1.2 spec 8.3.2 The "moveto" commands
463 // If a 'moveto' is followed by multiple pairs of coordinates without explicit commands,
464 // the subsequent pairs shall be treated as implicit 'lineto' commands.
465 pathElem = QLatin1Char('l');
466 }
467 break;
468 case 'M': {
469 if (count < 2) {
470 num++;
471 count--;
472 break;
473 }
474 x = x0 = num[0];
475 y = y0 = num[1];
476 num += 2;
477 count -= 2;
478 path.moveTo(x0, y0);
479
480 // As per 1.2 spec 8.3.2 The "moveto" commands
481 // If a 'moveto' is followed by multiple pairs of coordinates without explicit commands,
482 // the subsequent pairs shall be treated as implicit 'lineto' commands.
483 pathElem = QLatin1Char('L');
484 }
485 break;
486 case 'z':
487 case 'Z': {
488 x = x0;
489 y = y0;
490 count--; // skip dummy
491 num++;
492 path.closeSubpath();
493 }
494 break;
495 case 'l': {
496 if (count < 2) {
497 num++;
498 count--;
499 break;
500 }
501 x = num[0] + offsetX;
502 y = num[1] + offsetY;
503 num += 2;
504 count -= 2;
505 path.lineTo(x, y);
506
507 }
508 break;
509 case 'L': {
510 if (count < 2) {
511 num++;
512 count--;
513 break;
514 }
515 x = num[0];
516 y = num[1];
517 num += 2;
518 count -= 2;
519 path.lineTo(x, y);
520 }
521 break;
522 case 'h': {
523 x = num[0] + offsetX;
524 num++;
525 count--;
526 path.lineTo(x, y);
527 }
528 break;
529 case 'H': {
530 x = num[0];
531 num++;
532 count--;
533 path.lineTo(x, y);
534 }
535 break;
536 case 'v': {
537 y = num[0] + offsetY;
538 num++;
539 count--;
540 path.lineTo(x, y);
541 }
542 break;
543 case 'V': {
544 y = num[0];
545 num++;
546 count--;
547 path.lineTo(x, y);
548 }
549 break;
550 case 'c': {
551 if (count < 6) {
552 num += count;
553 count = 0;
554 break;
555 }
556 QPointF c1(num[0] + offsetX, num[1] + offsetY);
557 QPointF c2(num[2] + offsetX, num[3] + offsetY);
558 QPointF e(num[4] + offsetX, num[5] + offsetY);
559 num += 6;
560 count -= 6;
561 path.cubicTo(c1, c2, e);
562 ctrlPt = c2;
563 x = e.x();
564 y = e.y();
565 break;
566 }
567 case 'C': {
568 if (count < 6) {
569 num += count;
570 count = 0;
571 break;
572 }
573 QPointF c1(num[0], num[1]);
574 QPointF c2(num[2], num[3]);
575 QPointF e(num[4], num[5]);
576 num += 6;
577 count -= 6;
578 path.cubicTo(c1, c2, e);
579 ctrlPt = c2;
580 x = e.x();
581 y = e.y();
582 break;
583 }
584 case 's': {
585 if (count < 4) {
586 num += count;
587 count = 0;
588 break;
589 }
590 QPointF c1;
591 if (lastMode == 'c' || lastMode == 'C' ||
592 lastMode == 's' || lastMode == 'S')
593 c1 = QPointF(2*x-ctrlPt.x(), 2*y-ctrlPt.y());
594 else
595 c1 = QPointF(x, y);
596 QPointF c2(num[0] + offsetX, num[1] + offsetY);
597 QPointF e(num[2] + offsetX, num[3] + offsetY);
598 num += 4;
599 count -= 4;
600 path.cubicTo(c1, c2, e);
601 ctrlPt = c2;
602 x = e.x();
603 y = e.y();
604 break;
605 }
606 case 'S': {
607 if (count < 4) {
608 num += count;
609 count = 0;
610 break;
611 }
612 QPointF c1;
613 if (lastMode == 'c' || lastMode == 'C' ||
614 lastMode == 's' || lastMode == 'S')
615 c1 = QPointF(2*x-ctrlPt.x(), 2*y-ctrlPt.y());
616 else
617 c1 = QPointF(x, y);
618 QPointF c2(num[0], num[1]);
619 QPointF e(num[2], num[3]);
620 num += 4;
621 count -= 4;
622 path.cubicTo(c1, c2, e);
623 ctrlPt = c2;
624 x = e.x();
625 y = e.y();
626 break;
627 }
628 case 'q': {
629 if (count < 4) {
630 num += count;
631 count = 0;
632 break;
633 }
634 QPointF c(num[0] + offsetX, num[1] + offsetY);
635 QPointF e(num[2] + offsetX, num[3] + offsetY);
636 num += 4;
637 count -= 4;
638 path.quadTo(c, e);
639 ctrlPt = c;
640 x = e.x();
641 y = e.y();
642 break;
643 }
644 case 'Q': {
645 if (count < 4) {
646 num += count;
647 count = 0;
648 break;
649 }
650 QPointF c(num[0], num[1]);
651 QPointF e(num[2], num[3]);
652 num += 4;
653 count -= 4;
654 path.quadTo(c, e);
655 ctrlPt = c;
656 x = e.x();
657 y = e.y();
658 break;
659 }
660 case 't': {
661 if (count < 2) {
662 num += count;
663 count = 0;
664 break;
665 }
666 QPointF e(num[0] + offsetX, num[1] + offsetY);
667 num += 2;
668 count -= 2;
669 QPointF c;
670 if (lastMode == 'q' || lastMode == 'Q' ||
671 lastMode == 't' || lastMode == 'T')
672 c = QPointF(2*x-ctrlPt.x(), 2*y-ctrlPt.y());
673 else
674 c = QPointF(x, y);
675 path.quadTo(c, e);
676 ctrlPt = c;
677 x = e.x();
678 y = e.y();
679 break;
680 }
681 case 'T': {
682 if (count < 2) {
683 num += count;
684 count = 0;
685 break;
686 }
687 QPointF e(num[0], num[1]);
688 num += 2;
689 count -= 2;
690 QPointF c;
691 if (lastMode == 'q' || lastMode == 'Q' ||
692 lastMode == 't' || lastMode == 'T')
693 c = QPointF(2*x-ctrlPt.x(), 2*y-ctrlPt.y());
694 else
695 c = QPointF(x, y);
696 path.quadTo(c, e);
697 ctrlPt = c;
698 x = e.x();
699 y = e.y();
700 break;
701 }
702 case 'a': {
703 if (count < 7) {
704 num += count;
705 count = 0;
706 break;
707 }
708 qreal rx = (*num++);
709 qreal ry = (*num++);
710 qreal xAxisRotation = (*num++);
711 qreal largeArcFlag = (*num++);
712 qreal sweepFlag = (*num++);
713 qreal ex = (*num++) + offsetX;
714 qreal ey = (*num++) + offsetY;
715 count -= 7;
716 qreal curx = x;
717 qreal cury = y;
718 pathArc(path, rx, ry, xAxisRotation, int(largeArcFlag),
719 int(sweepFlag), ex, ey, curx, cury);
720
721 x = ex;
722 y = ey;
723 }
724 break;
725 case 'A': {
726 if (count < 7) {
727 num += count;
728 count = 0;
729 break;
730 }
731 qreal rx = (*num++);
732 qreal ry = (*num++);
733 qreal xAxisRotation = (*num++);
734 qreal largeArcFlag = (*num++);
735 qreal sweepFlag = (*num++);
736 qreal ex = (*num++);
737 qreal ey = (*num++);
738 count -= 7;
739 qreal curx = x;
740 qreal cury = y;
741 pathArc(path, rx, ry, xAxisRotation, int(largeArcFlag),
742 int(sweepFlag), ex, ey, curx, cury);
743
744 x = ex;
745 y = ey;
746 }
747 break;
748 default:
749 return false;
750 }
751 lastMode = pathElem.toLatin1();
752 }
753 }
754 return true;
755}
Definition: dMatrix.h:42
void error(const char *fmt,...)
Definition: error.cc:980
QString path
F77_RET_T const F77_DBLE const F77_DBLE F77_DBLE * d
F77_RET_T const F77_DBLE * x
class OCTAVE_API Matrix
Definition: mx-fwd.h:31
static uint32_t state[624]
Definition: randmtzig.cc:192
static bool isDigit(ushort ch)
static void pathArc(QPainterPath &path, qreal rx, qreal ry, qreal x_axis_rotation, int large_arc_flag, int sweep_flag, qreal x, qreal y, qreal curx, qreal cury)
static qreal toDouble(const QChar *&str)
static void pathArcSegment(QPainterPath &path, qreal xc, qreal yc, qreal th0, qreal th1, qreal rx, qreal ry, qreal xAxisRotation)
static bool parsePathDataFast(const QStringRef &dataStr, QPainterPath &path)
static QTransform parseTransformationMatrix(const QStringRef &value)
static void parseNumbersArray(const QChar *&str, QVarLengthArray< qreal, 8 > &points)