@liquid-js/qr-code-styling 2.4.2 → 3.0.0-1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -6,13 +6,21 @@ export declare class QRSVG {
6
6
  /** @ignore */
7
7
  _defs: SVGElement;
8
8
  /** @ignore */
9
- _backgroundClipPath?: SVGElement;
9
+ _backgroundMask?: SVGElement;
10
10
  /** @ignore */
11
- _dotsClipPath?: SVGElement;
11
+ _backgroundMaskGroup?: SVGElement;
12
12
  /** @ignore */
13
- _cornersSquareClipPath?: SVGElement;
13
+ _dotsMask?: SVGElement;
14
14
  /** @ignore */
15
- _cornersDotClipPath?: SVGElement;
15
+ _dotsMaskGroup?: SVGElement;
16
+ /** @ignore */
17
+ _cornersSquareMask?: SVGElement;
18
+ /** @ignore */
19
+ _cornersSquareMaskGroup?: SVGElement;
20
+ /** @ignore */
21
+ _cornersDotMask?: SVGElement;
22
+ /** @ignore */
23
+ _cornersDotMaskGroup?: SVGElement;
16
24
  /** @ignore */
17
25
  _options: RequiredOptions;
18
26
  /** @ignore */
@@ -46,4 +54,5 @@ export declare class QRSVG {
46
54
  width: number;
47
55
  name: string;
48
56
  }): void;
57
+ _createMask(id: string): (SVGGElement | SVGMaskElement)[];
49
58
  }
@@ -1240,15 +1240,14 @@ class QRSVG {
1240
1240
  });
1241
1241
  const size = Math.min(options.width, options.height);
1242
1242
  const element = this._document.createElementNS("http://www.w3.org/2000/svg", "rect");
1243
- this._backgroundClipPath = this._document.createElementNS("http://www.w3.org/2000/svg", "clipPath");
1244
- this._backgroundClipPath.setAttribute("id", "clip-path-background-color");
1245
- this._defs.appendChild(this._backgroundClipPath);
1243
+ [this._backgroundMask, this._backgroundMaskGroup] = this._createMask("mask-background-color");
1244
+ this._defs.appendChild(this._backgroundMask);
1246
1245
  element.setAttribute("x", String((options.width - size) / 2));
1247
1246
  element.setAttribute("y", String((options.height - size) / 2));
1248
1247
  element.setAttribute("width", String(size));
1249
1248
  element.setAttribute("height", String(size));
1250
1249
  element.setAttribute("rx", String((size / 2) * (options.backgroundOptions.round || 0)));
1251
- this._backgroundClipPath.appendChild(element);
1250
+ this._backgroundMaskGroup.appendChild(element);
1252
1251
  }
1253
1252
  }
1254
1253
  drawDots(filter) {
@@ -1265,19 +1264,8 @@ class QRSVG {
1265
1264
  const xBeginning = Math.floor((options.width - count * dotSize) / 2);
1266
1265
  const yBeginning = Math.floor((options.height - count * dotSize) / 2);
1267
1266
  const dot = new QRDot({ svg: this._element, type: options.dotsOptions.type, document: this._document });
1268
- this._dotsClipPath = this._document.createElementNS("http://www.w3.org/2000/svg", "clipPath");
1269
- this._dotsClipPath.setAttribute("id", "clip-path-dot-color");
1270
- this._defs.appendChild(this._dotsClipPath);
1271
- this._createColor({
1272
- options: options.dotsOptions?.gradient,
1273
- color: options.dotsOptions.color,
1274
- additionalRotation: 0,
1275
- x: 0,
1276
- y: 0,
1277
- height: options.height,
1278
- width: options.width,
1279
- name: "dot-color"
1280
- });
1267
+ [this._dotsMask, this._dotsMaskGroup] = this._createMask("mask-dot-color");
1268
+ this._defs.appendChild(this._dotsMask);
1281
1269
  for (let i = 0; i < count; i++) {
1282
1270
  for (let j = 0; j < count; j++) {
1283
1271
  if (filter && !filter(i, j)) {
@@ -1293,17 +1281,23 @@ class QRSVG {
1293
1281
  return false;
1294
1282
  return !!this._qr && this._qr.isDark(j + yOffset, i + xOffset);
1295
1283
  });
1296
- if (dot._element && this._dotsClipPath) {
1297
- this._dotsClipPath.appendChild(dot._element);
1284
+ if (dot._element && this._dotsMask) {
1285
+ this._dotsMaskGroup.appendChild(dot._element);
1298
1286
  }
1299
1287
  }
1300
1288
  }
1289
+ let colorX = xBeginning;
1290
+ let colorY = yBeginning;
1291
+ let colorCount = count;
1301
1292
  if (options.shape === ShapeType.circle) {
1302
1293
  const margin = (this._options.backgroundOptions && this._options.backgroundOptions.margin) || 0;
1303
1294
  const additionalDots = Math.floor((minSize / dotSize - count - 2 * margin) / 2);
1304
1295
  const fakeCount = count + additionalDots * 2;
1305
1296
  const xFakeBeginning = xBeginning - additionalDots * dotSize;
1306
1297
  const yFakeBeginning = yBeginning - additionalDots * dotSize;
1298
+ colorX = xFakeBeginning;
1299
+ colorY = yFakeBeginning;
1300
+ colorCount = count + additionalDots * 2;
1307
1301
  const fakeMatrix = [];
1308
1302
  const center = Math.floor(fakeCount / 2);
1309
1303
  for (let i = 0; i < fakeCount; i++) {
@@ -1333,12 +1327,22 @@ class QRSVG {
1333
1327
  dot.draw(xFakeBeginning + i * dotSize, yFakeBeginning + j * dotSize, dotSize, (xOffset, yOffset) => {
1334
1328
  return !!fakeMatrix[i + xOffset]?.[j + yOffset];
1335
1329
  });
1336
- if (dot._element && this._dotsClipPath) {
1337
- this._dotsClipPath.appendChild(dot._element);
1330
+ if (dot._element && this._dotsMask) {
1331
+ this._dotsMaskGroup.appendChild(dot._element);
1338
1332
  }
1339
1333
  }
1340
1334
  }
1341
1335
  }
1336
+ this._createColor({
1337
+ options: options.dotsOptions?.gradient,
1338
+ color: options.dotsOptions.color,
1339
+ additionalRotation: 0,
1340
+ x: colorX,
1341
+ y: colorY,
1342
+ height: colorCount * dotSize,
1343
+ width: colorCount * dotSize,
1344
+ name: "dot-color"
1345
+ });
1342
1346
  }
1343
1347
  drawCorners() {
1344
1348
  if (!this._qr) {
@@ -1362,13 +1366,15 @@ class QRSVG {
1362
1366
  ].forEach(([column, row, rotation]) => {
1363
1367
  const x = xBeginning + column * dotSize * (count - 7);
1364
1368
  const y = yBeginning + row * dotSize * (count - 7);
1365
- let cornersSquareClipPath = this._dotsClipPath;
1366
- let cornersDotClipPath = this._dotsClipPath;
1369
+ let cornersSquareMask = this._dotsMask;
1370
+ let cornersSquareMaskGroup = this._dotsMaskGroup;
1371
+ let cornersDotMask = this._dotsMask;
1372
+ let cornersDotMaskGroup = this._dotsMaskGroup;
1367
1373
  if (options.cornersSquareOptions?.gradient || options.cornersSquareOptions?.color) {
1368
- cornersSquareClipPath = this._document.createElementNS("http://www.w3.org/2000/svg", "clipPath");
1369
- cornersSquareClipPath.setAttribute("id", `clip-path-corners-square-color-${column}-${row}`);
1370
- this._defs.appendChild(cornersSquareClipPath);
1371
- this._cornersSquareClipPath = this._cornersDotClipPath = cornersDotClipPath = cornersSquareClipPath;
1374
+ [cornersSquareMask, cornersSquareMaskGroup] = this._createMask(`mask-corners-square-color-${column}-${row}`);
1375
+ this._defs.appendChild(cornersSquareMask);
1376
+ this._cornersSquareMask = this._cornersDotMask = cornersDotMask = cornersSquareMask;
1377
+ this._cornersSquareMaskGroup = this._cornersDotMaskGroup = cornersDotMaskGroup = cornersSquareMaskGroup;
1372
1378
  this._createColor({
1373
1379
  options: options.cornersSquareOptions?.gradient,
1374
1380
  color: options.cornersSquareOptions?.color,
@@ -1387,8 +1393,8 @@ class QRSVG {
1387
1393
  document: this._document
1388
1394
  });
1389
1395
  cornersSquare.draw(x, y, cornersSquareSize, rotation);
1390
- if (cornersSquare._element && cornersSquareClipPath) {
1391
- cornersSquareClipPath.appendChild(cornersSquare._element);
1396
+ if (cornersSquare._element && cornersSquareMaskGroup) {
1397
+ cornersSquareMaskGroup.appendChild(cornersSquare._element);
1392
1398
  }
1393
1399
  }
1394
1400
  else {
@@ -1399,17 +1405,17 @@ class QRSVG {
1399
1405
  continue;
1400
1406
  }
1401
1407
  dot.draw(x + i * dotSize, y + j * dotSize, dotSize, (xOffset, yOffset) => !!squareMask[i + xOffset]?.[j + yOffset]);
1402
- if (dot._element && cornersSquareClipPath) {
1403
- cornersSquareClipPath.appendChild(dot._element);
1408
+ if (dot._element && cornersSquareMaskGroup) {
1409
+ cornersSquareMaskGroup.appendChild(dot._element);
1404
1410
  }
1405
1411
  }
1406
1412
  }
1407
1413
  }
1408
1414
  if (options.cornersDotOptions?.gradient || options.cornersDotOptions?.color) {
1409
- cornersDotClipPath = this._document.createElementNS("http://www.w3.org/2000/svg", "clipPath");
1410
- cornersDotClipPath.setAttribute("id", `clip-path-corners-dot-color-${column}-${row}`);
1411
- this._defs.appendChild(cornersDotClipPath);
1412
- this._cornersDotClipPath = cornersDotClipPath;
1415
+ [cornersDotMask, cornersDotMaskGroup] = this._createMask(`mask-corners-dot-color-${column}-${row}`);
1416
+ this._defs.appendChild(cornersDotMask);
1417
+ this._cornersDotMask = cornersDotMask;
1418
+ this._cornersDotMaskGroup = cornersDotMaskGroup;
1413
1419
  this._createColor({
1414
1420
  options: options.cornersDotOptions?.gradient,
1415
1421
  color: options.cornersDotOptions?.color,
@@ -1428,8 +1434,8 @@ class QRSVG {
1428
1434
  document: this._document
1429
1435
  });
1430
1436
  cornersDot.draw(x + dotSize * 2, y + dotSize * 2, cornersDotSize, rotation);
1431
- if (cornersDot._element && cornersDotClipPath) {
1432
- cornersDotClipPath.appendChild(cornersDot._element);
1437
+ if (cornersDot._element && cornersDotMaskGroup) {
1438
+ cornersDotMaskGroup.appendChild(cornersDot._element);
1433
1439
  }
1434
1440
  }
1435
1441
  else {
@@ -1440,8 +1446,8 @@ class QRSVG {
1440
1446
  continue;
1441
1447
  }
1442
1448
  dot.draw(x + i * dotSize, y + j * dotSize, dotSize, (xOffset, yOffset) => !!dotMask[i + xOffset]?.[j + yOffset]);
1443
- if (dot._element && cornersDotClipPath) {
1444
- cornersDotClipPath.appendChild(dot._element);
1449
+ if (dot._element && cornersDotMaskGroup) {
1450
+ cornersDotMaskGroup.appendChild(dot._element);
1445
1451
  }
1446
1452
  }
1447
1453
  }
@@ -1459,7 +1465,7 @@ class QRSVG {
1459
1465
  const dh = height - margin * 2;
1460
1466
  const imageUrl = await this._imageTools.toDataURL(options.image || "");
1461
1467
  let image = this._document.createElementNS("http://www.w3.org/2000/svg", "image");
1462
- image.setAttribute("href", imageUrl || "");
1468
+ image.setAttributeNS("http://www.w3.org/1999/xlink", "xlink:href", imageUrl || "");
1463
1469
  if (imageUrl.startsWith("data:image/svg+xml;")) {
1464
1470
  let data = imageUrl.substring(19);
1465
1471
  const i = data.indexOf(",");
@@ -1494,7 +1500,7 @@ class QRSVG {
1494
1500
  rect.setAttribute("y", String(y));
1495
1501
  rect.setAttribute("height", String(height));
1496
1502
  rect.setAttribute("width", String(width));
1497
- rect.setAttribute("clip-path", `url('#clip-path-${name}')`);
1503
+ rect.setAttribute("style", `mask:url(#mask-${name})`);
1498
1504
  if (options) {
1499
1505
  let gradient;
1500
1506
  if (options.type === GradientType.radial) {
@@ -1553,7 +1559,7 @@ class QRSVG {
1553
1559
  stop.setAttribute("stop-color", color);
1554
1560
  gradient.appendChild(stop);
1555
1561
  });
1556
- rect.setAttribute("fill", `url('#${name}')`);
1562
+ rect.setAttribute("fill", `url(#${name})`);
1557
1563
  this._defs.appendChild(gradient);
1558
1564
  }
1559
1565
  else if (color) {
@@ -1561,6 +1567,20 @@ class QRSVG {
1561
1567
  }
1562
1568
  this._element.appendChild(rect);
1563
1569
  }
1570
+ _createMask(id) {
1571
+ const options = this._options;
1572
+ const mask = this._document.createElementNS("http://www.w3.org/2000/svg", "mask");
1573
+ mask.setAttribute("id", id);
1574
+ mask.setAttribute("maskUnits", "userSpaceOnUse");
1575
+ mask.setAttribute("x", "0");
1576
+ mask.setAttribute("y", "0");
1577
+ mask.setAttribute("width", String(options.width));
1578
+ mask.setAttribute("height", String(options.height));
1579
+ const group = this._document.createElementNS("http://www.w3.org/2000/svg", "g");
1580
+ group.setAttribute("fill", "#fff");
1581
+ mask.appendChild(group);
1582
+ return [mask, group];
1583
+ }
1564
1584
  }
1565
1585
 
1566
1586
  let QRCodeStyling$1 = class QRCodeStyling {