Skip to content

Commit a463c79

Browse files
committed
layers preset
1 parent 199eb57 commit a463c79

File tree

8 files changed

+219
-17
lines changed

8 files changed

+219
-17
lines changed

README.md

+6
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,12 @@ I'm working on more examples.
3939
<td>
4040
<img src="./examples/neon.svg" width="300"/>
4141
</td>
42+
<td>
43+
<img src="./examples/layers1.svg" width="300"/>
44+
</td>
45+
<td>
46+
<img src="./examples/layers2.svg" width="300"/>
47+
</td>
4248
</tr>
4349
<tr>
4450
<th colspan="3">Import external libs, fetch external files, etc </th>

examples/layers1.svg

+1
Loading

examples/layers2.svg

+1
Loading

pnpm-lock.yaml

-15
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

presets/Layers.js

+103
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,103 @@
1+
export const paramsSchema = {
2+
Margin: {
3+
type: "number",
4+
min: 0,
5+
max: 10,
6+
step: 0.1,
7+
default: 2,
8+
},
9+
Background: {
10+
type: "color",
11+
default: "#163157",
12+
},
13+
// See browser compatibility issues here
14+
// https://developer.mozilla.org/en-US/docs/Web/CSS/mix-blend-mode
15+
"Mix blend mode": {
16+
type: "select",
17+
options: [
18+
"normal",
19+
"multiply",
20+
"screen",
21+
"overlay",
22+
"darken",
23+
"lighten",
24+
"color-dodge",
25+
"color-burn",
26+
"hard-light",
27+
"soft-light",
28+
"difference",
29+
"exclusion",
30+
"hue",
31+
"saturation",
32+
"color",
33+
"luminosity",
34+
"plus-darker",
35+
"plus-lighter",
36+
],
37+
default: "difference",
38+
},
39+
Foreground: {
40+
type: "array",
41+
resizable: true,
42+
props: {
43+
type: "color",
44+
},
45+
default: ["#e80004", "#000000", "#ca70cf", "#000000", "#ffffff"],
46+
},
47+
"Offset x": {
48+
type: "array",
49+
resizable: true,
50+
props: {
51+
type: "number",
52+
min: -1,
53+
step: 0.1,
54+
max: 1,
55+
},
56+
default: [0.6, 0.4, 0.2, 0, -0.2],
57+
},
58+
"Offset y": {
59+
type: "array",
60+
resizable: true,
61+
props: {
62+
type: "number",
63+
min: -1,
64+
step: 0.1,
65+
max: 1,
66+
},
67+
default: [0.6, 0.4, 0.2, 0, -0.2],
68+
},
69+
};
70+
71+
export function renderSVG(qr, params) {
72+
const matrixWidth = qr.version * 4 + 17;
73+
const margin = params["Margin"];
74+
const colors = params["Foreground"];
75+
const offsetX = params["Offset x"];
76+
const offsetY = params["Offset y"];
77+
const bg = params["Background"];
78+
79+
const size = matrixWidth + 2 * margin;
80+
let svg = `<svg xmlns="http://www.w3.org/2000/svg" viewBox="${-margin} ${-margin} ${size} ${size}">`;
81+
svg += `<rect x="${-margin}" y="${-margin}" width="${size}" height="${size}" fill="${bg}"/>`;
82+
83+
svg += `<defs>`;
84+
svg += `<path id="base" d="`;
85+
for (let y = 0; y < matrixWidth; y++) {
86+
for (let x = 0; x < matrixWidth; x++) {
87+
const module = qr.matrix[y * matrixWidth + x];
88+
if (module & 1) {
89+
svg += `M${x},${y}h1v1h-1z`;
90+
}
91+
}
92+
}
93+
svg += `"/>`;
94+
svg += `</defs>`;
95+
96+
svg += `<g style="mix-blend-mode:${params["Mix blend mode"]}">`;
97+
colors.forEach((color, i) => {
98+
svg += `<use fill="${color}" transform="translate(${offsetX[i]},${offsetY[i]})" href="#base"/>`;
99+
});
100+
svg += `</g>`;
101+
svg += `</svg>`;
102+
return svg;
103+
}

src/lib/presets.ts

+2
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import { Dots } from "./presets/Dots";
88
import { Drawing } from "./presets/Drawing";
99
import { Glass } from "./presets/Glass";
1010
import { Halftone } from "./presets/Halftone";
11+
import { Layers } from "./presets/Layers";
1112
import { Minimal } from "./presets/Minimal";
1213
import { Mondrian } from "./presets/Mondrian";
1314
import { Neon } from "./presets/Neon";
@@ -25,6 +26,7 @@ export const PRESET_CODE = {
2526
Tile,
2627
Drawing,
2728
Halftone,
29+
Layers,
2830
Dots,
2931
Minimal,
3032
Blocks,

src/lib/presets/Blocks.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ export function renderSVG(qr, params) {
139139
if (
140140
!visited(x + 1, y) &&
141141
!visited(x + 2, y) &&
142-
!visited(x + 1, y + 1) &&
142+
!visited(x, y + 1) &&
143143
!visited(x + 2, y + 1)
144144
) {
145145
crossLayer += \`<g>\`;
@@ -159,7 +159,7 @@ export function renderSVG(qr, params) {
159159
x < matrixWidth - 1 &&
160160
matrix(x + 1, y) & matrix(x, y + 1) & matrix(x + 1, y + 1) & 1
161161
) {
162-
if (!visited(x + 1, y) && !visited(x + 1, y + 1)) {
162+
if (!visited(x + 1, y) && !visited(x + 1, y + 1) && !visited(x, y + 1)) {
163163
crossLayer += \`<g>\`;
164164
crossLayer += \`<line x1="\${x + co}" y1="\${y + co}" x2="\${x + 2 - co}" y2="\${y + 2 - co}"/>\`;
165165
crossLayer += \`<line x1="\${x + 2 - co}" y1="\${y + co}" x2="\${x + co}" y2="\${y + 2 - co}"/>\`;

src/lib/presets/Layers.ts

+104
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
export const Layers = `export const paramsSchema = {
2+
Margin: {
3+
type: "number",
4+
min: 0,
5+
max: 10,
6+
step: 0.1,
7+
default: 2,
8+
},
9+
Background: {
10+
type: "color",
11+
default: "#163157",
12+
},
13+
// See browser compatibility issues here
14+
// https://developer.mozilla.org/en-US/docs/Web/CSS/mix-blend-mode
15+
"Mix blend mode": {
16+
type: "select",
17+
options: [
18+
"normal",
19+
"multiply",
20+
"screen",
21+
"overlay",
22+
"darken",
23+
"lighten",
24+
"color-dodge",
25+
"color-burn",
26+
"hard-light",
27+
"soft-light",
28+
"difference",
29+
"exclusion",
30+
"hue",
31+
"saturation",
32+
"color",
33+
"luminosity",
34+
"plus-darker",
35+
"plus-lighter",
36+
],
37+
default: "difference",
38+
},
39+
Foreground: {
40+
type: "array",
41+
resizable: true,
42+
props: {
43+
type: "color",
44+
},
45+
default: ["#e80004", "#000000", "#ca70cf", "#000000", "#ffffff"],
46+
},
47+
"Offset x": {
48+
type: "array",
49+
resizable: true,
50+
props: {
51+
type: "number",
52+
min: -1,
53+
step: 0.1,
54+
max: 1,
55+
},
56+
default: [0.6, 0.4, 0.2, 0, -0.2],
57+
},
58+
"Offset y": {
59+
type: "array",
60+
resizable: true,
61+
props: {
62+
type: "number",
63+
min: -1,
64+
step: 0.1,
65+
max: 1,
66+
},
67+
default: [0.6, 0.4, 0.2, 0, -0.2],
68+
},
69+
};
70+
71+
export function renderSVG(qr, params) {
72+
const matrixWidth = qr.version * 4 + 17;
73+
const margin = params["Margin"];
74+
const colors = params["Foreground"];
75+
const offsetX = params["Offset x"];
76+
const offsetY = params["Offset y"];
77+
const bg = params["Background"];
78+
79+
const size = matrixWidth + 2 * margin;
80+
let svg = \`<svg xmlns="http://www.w3.org/2000/svg" viewBox="\${-margin} \${-margin} \${size} \${size}">\`;
81+
svg += \`<rect x="\${-margin}" y="\${-margin}" width="\${size}" height="\${size}" fill="\${bg}"/>\`;
82+
83+
svg += \`<defs>\`;
84+
svg += \`<path id="base" d="\`;
85+
for (let y = 0; y < matrixWidth; y++) {
86+
for (let x = 0; x < matrixWidth; x++) {
87+
const module = qr.matrix[y * matrixWidth + x];
88+
if (module & 1) {
89+
svg += \`M\${x},\${y}h1v1h-1z\`;
90+
}
91+
}
92+
}
93+
svg += \`"/>\`;
94+
svg += \`</defs>\`;
95+
96+
svg += \`<g style="mix-blend-mode:\${params["Mix blend mode"]}">\`;
97+
colors.forEach((color, i) => {
98+
svg += \`<use fill="\${color}" transform="translate(\${offsetX[i]},\${offsetY[i]})" href="#base"/>\`;
99+
});
100+
svg += \`</g>\`;
101+
svg += \`</svg>\`;
102+
return svg;
103+
}
104+
`

0 commit comments

Comments
 (0)