Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
beda61b9f4 | ||
|
|
2c6e5f44df | ||
|
|
df4c956a0b | ||
|
|
ac087087c5 | ||
|
|
77eb4fa946 | ||
|
|
c9aa81af2e | ||
|
|
6871053810 | ||
|
|
73b7348eed
|
||
|
|
b71e822bb8
|
||
|
|
4c1025b1eb
|
||
|
|
b35c04a7d9
|
||
|
|
0612e9b6ec
|
||
|
|
42d6915b15 | ||
|
|
b646d24930
|
||
|
|
1533b5ccd4 | ||
|
|
2633b35f39
|
||
|
|
415029e0c3
|
||
|
|
091ec8c08a
|
||
|
|
ffd3356ab2
|
||
|
|
02e59c5d7a | ||
|
|
96dd9b0543
|
||
|
|
da9c2b568b
|
||
|
|
459892bb13
|
||
|
|
255eec7f35 | ||
|
|
536f5a075d
|
||
|
|
d73215c889 | ||
|
|
87643983ec | ||
|
|
94fef0a245 | ||
|
|
1a0a659ace | ||
|
|
f2ce91ec39 | ||
|
|
043bb339fe | ||
|
|
693676d61a | ||
|
|
94d5d6b854 | ||
|
|
71f128f6c9 | ||
|
|
ea8277ee5b | ||
|
|
c5e4f8039a | ||
|
|
8c91ccdd54 | ||
|
|
9966656e8b | ||
|
|
3ccb79c6c2 |
No files matched your search
@@ -3,7 +3,7 @@
|
|||||||
Circuiteria is a [Typst](https://typst.app) package for drawing block circuit diagrams using the [CeTZ](https://typst.app/universe/package/cetz) package.
|
Circuiteria is a [Typst](https://typst.app) package for drawing block circuit diagrams using the [CeTZ](https://typst.app/universe/package/cetz) package.
|
||||||
|
|
||||||
<p align="center">
|
<p align="center">
|
||||||
<img src="./gallery/platypus.png" alt="Perry the platypus">
|
<img src="./gallery/platypus.png" alt="A platypus / Perry the Platypus meme made with colored rounded rectangles">
|
||||||
</p>
|
</p>
|
||||||
|
|
||||||
## Examples
|
## Examples
|
||||||
@@ -11,17 +11,17 @@ Circuiteria is a [Typst](https://typst.app) package for drawing block circuit di
|
|||||||
<tr>
|
<tr>
|
||||||
<td colspan="2">
|
<td colspan="2">
|
||||||
<a href="./gallery/test.typ">
|
<a href="./gallery/test.typ">
|
||||||
<img src="./gallery/test.png" width="500px">
|
<img src="./gallery/test.png" width="500px" alt="Block diagram of a multi-cycle RISC-V FPGA processor">
|
||||||
</a>
|
</a>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td colspan="2">A bit of eveything</td>
|
<td colspan="2">A bit of everything</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td colspan="2">
|
<td colspan="2">
|
||||||
<a href="./gallery/test5.typ">
|
<a href="./gallery/test5.typ">
|
||||||
<img src="./gallery/test5.png" width="500px">
|
<img src="./gallery/test5.png" width="500px" alt="Block diagram of a single-cycle RISC-V processor">
|
||||||
</a>
|
</a>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
@@ -31,12 +31,12 @@ Circuiteria is a [Typst](https://typst.app) package for drawing block circuit di
|
|||||||
<tr>
|
<tr>
|
||||||
<td>
|
<td>
|
||||||
<a href="./gallery/test4.typ">
|
<a href="./gallery/test4.typ">
|
||||||
<img src="./gallery/test4.png" width="250px">
|
<img src="./gallery/test4.png" width="250px" alt="Top-level block diagram of a single-cycle RISC-V processor">
|
||||||
</a>
|
</a>
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<a href="./gallery/test6.typ">
|
<a href="./gallery/test6.typ">
|
||||||
<img src="./gallery/test6.png" width="250px">
|
<img src="./gallery/test6.png" width="250px" alt="Block diagram of a simple single-cycle RISC-V ALU">
|
||||||
</a>
|
</a>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
@@ -56,7 +56,7 @@ For more information, see the [manual](manual.pdf)
|
|||||||
|
|
||||||
To use this package, simply import [circuiteria](https://typst.app/universe/package/circuiteria) and call the `circuit` function:
|
To use this package, simply import [circuiteria](https://typst.app/universe/package/circuiteria) and call the `circuit` function:
|
||||||
```typ
|
```typ
|
||||||
#import "@preview/circuiteria:0.2.0"
|
#import "@preview/circuiteria:0.2.1"
|
||||||
#circuiteria.circuit({
|
#circuiteria.circuit({
|
||||||
import circuiteria: *
|
import circuiteria: *
|
||||||
...
|
...
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "../src/circuit.typ": circuit
|
#import "../src/circuit.typ": circuit
|
||||||
#import "../src/util.typ"
|
#import "../src/util.typ"
|
||||||
|
|
||||||
|
|||||||
@@ -56,7 +56,7 @@ for i in range(3) {
|
|||||||
```)
|
```)
|
||||||
|
|
||||||
#let wires = example(```
|
#let wires = example(```
|
||||||
for i in range(3) {
|
for i in range(4) {
|
||||||
draw.circle((i * 3, 0), radius: .1, name: "p" + str(i * 2))
|
draw.circle((i * 3, 0), radius: .1, name: "p" + str(i * 2))
|
||||||
draw.circle((i * 3 + 2, 1), radius: .1, name: "p" + str(i * 2 + 1))
|
draw.circle((i * 3 + 2, 1), radius: .1, name: "p" + str(i * 2 + 1))
|
||||||
draw.content((i * 3 + 1, -1), raw(wire.wire-styles.at(i)))
|
draw.content((i * 3 + 1, -1), raw(wire.wire-styles.at(i)))
|
||||||
@@ -65,8 +65,36 @@ wire.wire("w1", ("p0", "p1"), style: "direct")
|
|||||||
wire.wire("w2", ("p2", "p3"), style: "zigzag")
|
wire.wire("w2", ("p2", "p3"), style: "zigzag")
|
||||||
wire.wire("w3", ("p4", "p5"), style: "dodge",
|
wire.wire("w3", ("p4", "p5"), style: "dodge",
|
||||||
dodge-y: -0.5, dodge-margins: (0.5, 0.5))
|
dodge-y: -0.5, dodge-margins: (0.5, 0.5))
|
||||||
|
wire.wire("w4", ("p6","p7"), style: "guided",
|
||||||
|
guided-center:(20%, 40%), guided-margins: (90%,87%),
|
||||||
|
guided-sides: ("north","south"))
|
||||||
|
|
||||||
```, vertical: true)
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let zigzag-at = example(
|
||||||
|
```
|
||||||
|
// `zigzag-at` places the middle bend of a zigzag wire
|
||||||
|
// on the axis of a referenced anchor, overriding
|
||||||
|
// `zigzag-ratio`.
|
||||||
|
element.block(x: 0, y: 0, w: 1.5, h: 1.5, id: "src",
|
||||||
|
ports: (east: ((id: "o", name: "O"),),))
|
||||||
|
element.block(x: 3, y: -1.2, w: 1, h: 1, id: "ref",
|
||||||
|
fill: util.colors.pink,
|
||||||
|
ports: (west: ((id: "p", name: "R"),),))
|
||||||
|
element.block(x: 5.5, y: -2, w: 1.5, h: 1.5, id: "dst",
|
||||||
|
ports: (west: ((id: "i", name: "I"),),))
|
||||||
|
// String form: anchor name of a port.
|
||||||
|
wire.wire("w1", ("src-port-o", "dst-port-i"),
|
||||||
|
style: "zigzag",
|
||||||
|
zigzag-at: "ref-port-p")
|
||||||
|
// Ergonomic offset: shift 8pt right of ref.east.
|
||||||
|
wire.wire("w2", ("src-port-o", "dst-port-i"),
|
||||||
|
style: "zigzag",
|
||||||
|
zigzag-at: (rel: 8pt, to: "ref.east"))
|
||||||
|
```,
|
||||||
|
vertical: true,
|
||||||
|
)
|
||||||
|
|
||||||
#let stub = example(```
|
#let stub = example(```
|
||||||
draw.circle((0, 0), radius: .1, name: "p")
|
draw.circle((0, 0), radius: .1, name: "p")
|
||||||
wire.stub("p", "north", name: "north", length: 1)
|
wire.stub("p", "north", name: "north", length: 1)
|
||||||
@@ -115,6 +143,46 @@ gates.gate-xnor(x: 0, y: 0, w: 1.5, h: 1.5)
|
|||||||
gates.gate-xnor(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
gates.gate-xnor(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
```, vertical: true)
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-and = example(```
|
||||||
|
gates.iec-gate-and(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-and(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-nand = example(```
|
||||||
|
gates.iec-gate-nand(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-nand(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-or = example(```
|
||||||
|
gates.iec-gate-or(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-or(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-nor = example(```
|
||||||
|
gates.iec-gate-nor(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-nor(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-xor = example(```
|
||||||
|
gates.iec-gate-xor(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-xor(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-xnor = example(```
|
||||||
|
gates.iec-gate-xnor(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-xnor(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-buf = example(```
|
||||||
|
gates.iec-gate-buf(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-buf(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
|
#let iec-gate-not = example(```
|
||||||
|
gates.iec-gate-not(x: 0, y: 0, w: 1.5, h: 1.5)
|
||||||
|
gates.iec-gate-not(x: 3, y: 0, w: 1.5, h: 1.5, inverted: "all")
|
||||||
|
```, vertical: true)
|
||||||
|
|
||||||
#let group = example(```
|
#let group = example(```
|
||||||
element.group(
|
element.group(
|
||||||
id: "g1", name: "Group 1", stroke: (dash: "dashed"),
|
id: "g1", name: "Group 1", stroke: (dash: "dashed"),
|
||||||
@@ -147,4 +215,4 @@ wire.wire("w1", ((0, 0), (1, 1)), style: "zigzag")
|
|||||||
wire.wire("w2", ((0, 0), (1, -.5)),
|
wire.wire("w2", ((0, 0), (1, -.5)),
|
||||||
style: "zigzag", zigzag-ratio: 80%)
|
style: "zigzag", zigzag-ratio: 80%)
|
||||||
wire.intersection("w1.zig")
|
wire.intersection("w1.zig")
|
||||||
```)
|
```)
|
||||||
|
Before Width: | Height: | Size: 45 KiB After Width: | Height: | Size: 11 KiB |
@@ -1,4 +1,4 @@
|
|||||||
#import "../src/lib.typ": *
|
#import "@preview/circuiteria:0.2.1": *
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 142 KiB After Width: | Height: | Size: 53 KiB |
@@ -1,4 +1,4 @@
|
|||||||
#import "../src/lib.typ": circuit, element, util, wire
|
#import "@preview/circuiteria:0.2.1": circuit, element, util, wire
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 142 KiB After Width: | Height: | Size: 53 KiB |
@@ -1,4 +1,4 @@
|
|||||||
#import "../src/lib.typ": circuit, element, util, wire
|
#import "@preview/circuiteria:0.2.1": circuit, element, util, wire
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 66 KiB After Width: | Height: | Size: 23 KiB |
@@ -1,5 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "@preview/circuiteria:0.2.1": circuit, element, util, wire
|
||||||
#import "../src/lib.typ": circuit, element, util, wire
|
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 159 KiB After Width: | Height: | Size: 67 KiB |
@@ -1,5 +1,5 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "../src/lib.typ": *
|
#import "@preview/circuiteria:0.2.1": *
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 275 KiB After Width: | Height: | Size: 93 KiB |
@@ -1,5 +1,5 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "../src/lib.typ": *
|
#import "@preview/circuiteria:0.2.1": *
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
Before Width: | Height: | Size: 76 KiB After Width: | Height: | Size: 23 KiB |
@@ -1,5 +1,5 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw, vector
|
#import "/src/cetz.typ": draw
|
||||||
#import "../src/lib.typ": *
|
#import "@preview/circuiteria:0.2.1": *
|
||||||
|
|
||||||
#set page(width: auto, height: auto, margin: .5cm)
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
|||||||
|
After Width: | Height: | Size: 5.8 KiB |
@@ -0,0 +1,97 @@
|
|||||||
|
#import "@preview/circuiteria:0.2.1": circuit, element, util, wire
|
||||||
|
|
||||||
|
#set page(width: auto, height: auto, margin: .5cm)
|
||||||
|
|
||||||
|
#circuit({
|
||||||
|
element.iec-gate-buf(
|
||||||
|
x: 0,
|
||||||
|
y: 0,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
id: "iec-buf",
|
||||||
|
inputs: 1,
|
||||||
|
)
|
||||||
|
wire.stub("iec-buf-port-in0", "west")
|
||||||
|
|
||||||
|
element.iec-gate-not(
|
||||||
|
x: 3,
|
||||||
|
y: 0,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
id: "iec-not",
|
||||||
|
inputs: 1,
|
||||||
|
)
|
||||||
|
wire.stub("iec-not-port-in0", "west")
|
||||||
|
|
||||||
|
element.iec-gate-and(
|
||||||
|
id: "iec-and",
|
||||||
|
x: 0,
|
||||||
|
y: -3,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-and-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
|
||||||
|
element.iec-gate-nand(
|
||||||
|
id: "iec-nand",
|
||||||
|
x: 3,
|
||||||
|
y: -3,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-nand-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
|
||||||
|
element.iec-gate-or(
|
||||||
|
id: "iec-or",
|
||||||
|
x: 0,
|
||||||
|
y: -6,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-or-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
|
||||||
|
element.iec-gate-nor(
|
||||||
|
id: "iec-nor",
|
||||||
|
x: 3,
|
||||||
|
y: -6,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-nor-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
|
||||||
|
element.iec-gate-xor(
|
||||||
|
id: "iec-xor",
|
||||||
|
x: 0,
|
||||||
|
y: -9,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-xor-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
|
||||||
|
element.iec-gate-xnor(
|
||||||
|
id: "iec-nxor",
|
||||||
|
x: 3,
|
||||||
|
y: -9,
|
||||||
|
w: 2,
|
||||||
|
h: 2,
|
||||||
|
inputs: 2,
|
||||||
|
)
|
||||||
|
for i in range(2) {
|
||||||
|
wire.stub("iec-nxor-port-in" + str(i), "west")
|
||||||
|
}
|
||||||
|
})
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
#import "@preview/tidy:0.4.1"
|
#import "@preview/tidy:0.4.3"
|
||||||
#import "@preview/cetz:0.3.2": draw, canvas
|
#import "/src/cetz.typ": draw, canvas
|
||||||
#import "src/lib.typ"
|
#import "src/lib.typ"
|
||||||
#import "doc/examples.typ"
|
#import "doc/examples.typ"
|
||||||
#import "src/circuit.typ": circuit
|
#import "src/circuit.typ": circuit
|
||||||
@@ -105,7 +105,7 @@ This package provides a way to make beautiful block circuit diagrams using the C
|
|||||||
|
|
||||||
Simply import Circuiteria and call the `circuit` function:
|
Simply import Circuiteria and call the `circuit` function:
|
||||||
#pad(left: 1em)[```typ
|
#pad(left: 1em)[```typ
|
||||||
#import "@preview/circuiteria:0.2.0"
|
#import "@preview/circuiteria:0.2.1"
|
||||||
#circuiteria.circuit({
|
#circuiteria.circuit({
|
||||||
import circuiteria: *
|
import circuiteria: *
|
||||||
...
|
...
|
||||||
@@ -195,7 +195,12 @@ If you have installed Circuiteria directly in your project, import #link("src/li
|
|||||||
read("src/elements/logic/and.typ") + "\n" +
|
read("src/elements/logic/and.typ") + "\n" +
|
||||||
read("src/elements/logic/buf.typ") + "\n" +
|
read("src/elements/logic/buf.typ") + "\n" +
|
||||||
read("src/elements/logic/or.typ") + "\n" +
|
read("src/elements/logic/or.typ") + "\n" +
|
||||||
read("src/elements/logic/xor.typ"),
|
read("src/elements/logic/xor.typ") + "\n" +
|
||||||
|
read("src/elements/logic/iec_gate.typ") + "\n" +
|
||||||
|
read("src/elements/logic/iec_and.typ") + "\n" +
|
||||||
|
read("src/elements/logic/iec_buf.typ") + "\n" +
|
||||||
|
read("src/elements/logic/iec_or.typ") + "\n" +
|
||||||
|
read("src/elements/logic/iec_xor.typ"),
|
||||||
name: "gates",
|
name: "gates",
|
||||||
old-syntax: true,
|
old-syntax: true,
|
||||||
scope: (
|
scope: (
|
||||||
|
|||||||
@@ -0,0 +1 @@
|
|||||||
|
#import "@preview/cetz:0.5.2": *
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
#import "@preview/cetz:0.3.2": canvas
|
#import "/src/cetz.typ": canvas
|
||||||
#import "@preview/tidy:0.3.0"
|
#import "@preview/tidy:0.4.3"
|
||||||
|
|
||||||
/// Draws a block circuit diagram
|
/// Draws a block circuit diagram
|
||||||
///
|
///
|
||||||
@@ -9,6 +9,5 @@
|
|||||||
/// - length (length, ratio): Optional base unit
|
/// - length (length, ratio): Optional base unit
|
||||||
/// -> none
|
/// -> none
|
||||||
#let circuit(body, length: 2em) = {
|
#let circuit(body, length: 2em) = {
|
||||||
set text(font: "Source Sans 3")
|
|
||||||
canvas(length: length, body)
|
canvas(length: length, body)
|
||||||
}
|
}
|
||||||
@@ -11,5 +11,10 @@
|
|||||||
#import "elements/logic/or.typ": gate-or, gate-nor
|
#import "elements/logic/or.typ": gate-or, gate-nor
|
||||||
#import "elements/logic/xor.typ": gate-xor, gate-xnor
|
#import "elements/logic/xor.typ": gate-xor, gate-xnor
|
||||||
#import "elements/logic/buf.typ": gate-buf, gate-not
|
#import "elements/logic/buf.typ": gate-buf, gate-not
|
||||||
|
#import "elements/logic/iec_gate.typ": iec-gate
|
||||||
|
#import "elements/logic/iec_and.typ": iec-gate-and, iec-gate-nand
|
||||||
|
#import "elements/logic/iec_buf.typ": iec-gate-buf, iec-gate-not
|
||||||
|
#import "elements/logic/iec_or.typ": iec-gate-or, iec-gate-nor
|
||||||
|
#import "elements/logic/iec_xor.typ": iec-gate-xor, iec-gate-xnor
|
||||||
|
|
||||||
#import "elements/group.typ": group
|
#import "elements/group.typ": group
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "element.typ"
|
#import "element.typ"
|
||||||
#import "ports.typ": add-port
|
#import "ports.typ": add-port
|
||||||
|
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "element.typ"
|
#import "element.typ"
|
||||||
|
|
||||||
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
#let draw-shape(id, tl, tr, br, bl, fill, stroke, radius: 0.5em) = {
|
||||||
let f = draw.rect(
|
let f = draw.rect(
|
||||||
radius: 0.5em,
|
radius: radius,
|
||||||
inset: 0.5em,
|
inset: 0.5em,
|
||||||
fill: fill,
|
fill: fill,
|
||||||
stroke: stroke,
|
stroke: stroke,
|
||||||
@@ -16,7 +16,8 @@
|
|||||||
/// Draws a block element
|
/// Draws a block element
|
||||||
///
|
///
|
||||||
/// #examples.block
|
/// #examples.block
|
||||||
/// For parameters description, see #doc-ref("element.elmt")
|
/// For other parameters description, see #doc-ref("element.elmt")
|
||||||
|
/// - radius (number, length, ratio, dictionary): The corner radius of the block. See CeTZ documentation for more information
|
||||||
#let block(
|
#let block(
|
||||||
x: none,
|
x: none,
|
||||||
y: none,
|
y: none,
|
||||||
@@ -27,13 +28,14 @@
|
|||||||
ports: (),
|
ports: (),
|
||||||
ports-margins: (),
|
ports-margins: (),
|
||||||
fill: none,
|
fill: none,
|
||||||
|
radius: 0.5em,
|
||||||
stroke: black + 1pt,
|
stroke: black + 1pt,
|
||||||
id: "",
|
id: "",
|
||||||
debug: (
|
debug: (
|
||||||
ports: false
|
ports: false
|
||||||
)
|
)
|
||||||
) = element.elmt(
|
) = element.elmt(
|
||||||
draw-shape: draw-shape,
|
draw-shape: draw-shape.with(radius: radius),
|
||||||
x: x,
|
x: x,
|
||||||
y: y,
|
y: y,
|
||||||
w: w,
|
w: w,
|
||||||
@@ -46,4 +48,4 @@
|
|||||||
stroke: stroke,
|
stroke: stroke,
|
||||||
id: id,
|
id: id,
|
||||||
debug: debug
|
debug: debug
|
||||||
)
|
)
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw, coordinate
|
#import "/src/cetz.typ": draw, coordinate
|
||||||
#import "ports.typ": add-ports, add-port
|
#import "ports.typ": add-ports, add-port
|
||||||
#import "../util.typ"
|
#import "../util.typ"
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "element.typ"
|
#import "element.typ"
|
||||||
#import "ports.typ": add-port
|
#import "ports.typ": add-port
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw, coordinate
|
#import "/src/cetz.typ": draw, coordinate
|
||||||
#import "../util.typ"
|
#import "../util.typ"
|
||||||
|
|
||||||
/// Draws a group of elements
|
/// Draws a group of elements
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "gate.typ"
|
#import "gate.typ"
|
||||||
|
|
||||||
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "gate.typ"
|
#import "gate.typ"
|
||||||
|
|
||||||
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw, coordinate
|
#import "/src/cetz.typ": draw, coordinate
|
||||||
#import "../ports.typ": add-ports, add-port
|
#import "../ports.typ": add-ports, add-port
|
||||||
#import "../element.typ"
|
#import "../element.typ"
|
||||||
|
|
||||||
@@ -63,6 +63,12 @@
|
|||||||
if to == "out" {
|
if to == "out" {
|
||||||
dy = height / 2
|
dy = height / 2
|
||||||
} else {
|
} else {
|
||||||
|
let all-ports = range(inputs).map(i => "in" + str(i))
|
||||||
|
let i = all-ports.position(p => p == to)
|
||||||
|
assert(
|
||||||
|
i != none,
|
||||||
|
message: "Unknown port '" + y.to + "' must be one of " + repr(all-ports)
|
||||||
|
)
|
||||||
dy = height * (i + 0.5) / inputs
|
dy = height * (i + 0.5) / inputs
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,70 @@
|
|||||||
|
#import "/src/cetz.typ": draw
|
||||||
|
// #import "iec_gate.typ" as iec-gate
|
||||||
|
#import "iec_gate.typ" as iec-gate
|
||||||
|
|
||||||
|
|
||||||
|
/// Draws an IEC-AND gate. This function is also available as `element.iec-gate-and()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-and
|
||||||
|
#let iec-gate-and(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
),
|
||||||
|
) = {
|
||||||
|
iec-gate.iec-gate(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: inverted,
|
||||||
|
debug: debug,
|
||||||
|
symbol: $amp$,
|
||||||
|
)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Draws an IEC-NAND gate. This function is also available as `element.iec-gate-nand()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-nand
|
||||||
|
#let iec-gate-nand(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
),
|
||||||
|
) = {
|
||||||
|
iec-gate-and(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: if inverted != "all" {inverted + ("out",)} else {inverted},
|
||||||
|
debug: debug,
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -0,0 +1,68 @@
|
|||||||
|
#import "/src/cetz.typ": draw
|
||||||
|
#import "iec_gate.typ" as iec-gate
|
||||||
|
|
||||||
|
|
||||||
|
/// Draws an IEC buffer gate. This function is also available as `element.iec-gate-buf()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-buf
|
||||||
|
#let iec-gate-buf(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false,
|
||||||
|
),
|
||||||
|
) = {
|
||||||
|
iec-gate.iec-gate(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: inverted,
|
||||||
|
debug: debug,
|
||||||
|
symbol: "1",
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Draws an IEC NOT gate. This function is also available as `element.iec-gate-not()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-not
|
||||||
|
#let iec-gate-not(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false,
|
||||||
|
),
|
||||||
|
) = {
|
||||||
|
iec-gate-buf(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: if inverted != "all" { inverted + ("out",) } else { inverted },
|
||||||
|
debug: debug,
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -0,0 +1,125 @@
|
|||||||
|
#import "/src/cetz.typ": draw, coordinate
|
||||||
|
#import "../ports.typ": add-ports, add-port
|
||||||
|
#import "../element.typ"
|
||||||
|
|
||||||
|
#let default-draw-shape(id, tl, tr, br, bl, fill, stroke, symbol) = {
|
||||||
|
let shapes = draw.rect(
|
||||||
|
inset: 0.5em,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
name: id,
|
||||||
|
bl, tr
|
||||||
|
)
|
||||||
|
shapes += draw.content(
|
||||||
|
id + ".center",
|
||||||
|
[*$ symbol $*]
|
||||||
|
)
|
||||||
|
return (shapes, tl, tr, br, bl)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Draws a logic gate. This function is also available as `element.iec-gate()`
|
||||||
|
///
|
||||||
|
/// - draw-shape (function): see #doc-ref("element.elmt")
|
||||||
|
/// - x (number, dictionary): see #doc-ref("element.elmt")
|
||||||
|
/// - y (number, dictionary): see #doc-ref("element.elmt")
|
||||||
|
/// - w (number): see #doc-ref("element.elmt")
|
||||||
|
/// - h (number): see #doc-ref("element.elmt")
|
||||||
|
/// - inputs (int): The number of inputs
|
||||||
|
/// - fill (none, color): see #doc-ref("element.elmt")
|
||||||
|
/// - stroke (stroke): see #doc-ref("element.elmt")
|
||||||
|
/// - id (str): see #doc-ref("element.elmt")
|
||||||
|
/// - inverted (str, array): Either "all" or an array of port ids to display as inverted
|
||||||
|
/// - inverted-radius (number): The radius of inverted ports dot
|
||||||
|
/// - debug (dictionary): see #doc-ref("element.elmt")
|
||||||
|
/// - symbol (str): The symbol to display at the center of the gate
|
||||||
|
#let iec-gate(
|
||||||
|
draw-shape: default-draw-shape,
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
inverted-radius: 0.1,
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
),
|
||||||
|
symbol: "",
|
||||||
|
) = draw.get-ctx(ctx => {
|
||||||
|
let width = w
|
||||||
|
let height = h
|
||||||
|
|
||||||
|
let x = x
|
||||||
|
let y = y
|
||||||
|
if x == none { panic("Parameter x must be set") }
|
||||||
|
if y == none { panic("Parameter y must be set") }
|
||||||
|
if w == none { panic("Parameter w must be set") }
|
||||||
|
if h == none { panic("Parameter h must be set") }
|
||||||
|
|
||||||
|
if (type(x) == dictionary) {
|
||||||
|
let offset = x.rel
|
||||||
|
let to = x.to
|
||||||
|
let (ctx, to-pos) = coordinate.resolve(ctx, (rel: (offset, 0), to: to))
|
||||||
|
x = to-pos.at(0)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (type(y) == dictionary) {
|
||||||
|
let from = y.from
|
||||||
|
let to = y.to
|
||||||
|
|
||||||
|
let dy
|
||||||
|
if to == "out" {
|
||||||
|
dy = height / 2
|
||||||
|
} else {
|
||||||
|
dy = height * (i + 0.5) / inputs
|
||||||
|
}
|
||||||
|
|
||||||
|
let (ctx, from-pos) = coordinate.resolve(ctx, from)
|
||||||
|
y = from-pos.at(1) + dy - height
|
||||||
|
}
|
||||||
|
|
||||||
|
let tl = (x, y + height)
|
||||||
|
let tr = (x + width, y + height)
|
||||||
|
let br = (x + width, y)
|
||||||
|
let bl = (x, y)
|
||||||
|
|
||||||
|
// Workaround because CeTZ needs to have all draw functions in the body
|
||||||
|
let func = {}
|
||||||
|
(func, tl, tr, br, bl) = draw-shape(id, tl, tr, br, bl, fill, stroke, symbol)
|
||||||
|
func
|
||||||
|
|
||||||
|
let space = 100% / inputs
|
||||||
|
for i in range(inputs) {
|
||||||
|
let pct = (i + 0.5) * space
|
||||||
|
let port-pos = (tl, pct, bl)
|
||||||
|
let port-name = "in" + str(i)
|
||||||
|
if inverted == "all" or port-name in inverted {
|
||||||
|
draw.circle(
|
||||||
|
port-pos,
|
||||||
|
radius: inverted-radius,
|
||||||
|
anchor: "east",
|
||||||
|
stroke: stroke
|
||||||
|
)
|
||||||
|
port-pos = (rel: (-2 * inverted-radius, 0), to: port-pos)
|
||||||
|
}
|
||||||
|
add-port(
|
||||||
|
id, "west",
|
||||||
|
(id: port-name), port-pos,
|
||||||
|
debug: debug.ports
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
let out-pos = id + ".east"
|
||||||
|
if inverted == "all" or "out" in inverted {
|
||||||
|
draw.circle(out-pos, radius: inverted-radius, anchor: "west", stroke: stroke)
|
||||||
|
out-pos = (rel: (2 * inverted-radius, 0), to: out-pos)
|
||||||
|
}
|
||||||
|
add-port(
|
||||||
|
id, "east",
|
||||||
|
(id: "out"), out-pos,
|
||||||
|
debug: debug.ports
|
||||||
|
)
|
||||||
|
})
|
||||||
@@ -0,0 +1,67 @@
|
|||||||
|
#import "/src/cetz.typ": draw
|
||||||
|
#import "iec_gate.typ" as iec-gate
|
||||||
|
|
||||||
|
/// Draws an IEC-OR gate. This function is also available as `element.iec-gate-or()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-or
|
||||||
|
#let iec-gate-or(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
)
|
||||||
|
) = {
|
||||||
|
iec-gate.iec-gate(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: inverted,
|
||||||
|
debug: debug,
|
||||||
|
symbol: $>= 1$,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Draws an IEC-NOR gate. This function is also available as `element.iec-gate-nor()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-nor
|
||||||
|
#let iec-gate-nor(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
)
|
||||||
|
) = {
|
||||||
|
iec-gate-or(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: if inverted != "all" {inverted + ("out",)} else {inverted},
|
||||||
|
debug: debug
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -0,0 +1,67 @@
|
|||||||
|
#import "/src/cetz.typ": draw
|
||||||
|
#import "iec_gate.typ" as iec-gate
|
||||||
|
|
||||||
|
/// Draws an IEC-XOR gate. This function is also available as `element.iec-gate-xor()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-xor
|
||||||
|
#let iec-gate-xor(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
)
|
||||||
|
) = {
|
||||||
|
iec-gate.iec-gate(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: inverted,
|
||||||
|
debug: debug,
|
||||||
|
symbol: $= 1$,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Draws an IEC-XNOR gate. This function is also available as `element.iec-gate-xnor()`
|
||||||
|
///
|
||||||
|
/// For parameters, see #doc-ref("gates.iec-gate")
|
||||||
|
/// #examples.iec-gate-xnor
|
||||||
|
#let iec-gate-xnor(
|
||||||
|
x: none,
|
||||||
|
y: none,
|
||||||
|
w: none,
|
||||||
|
h: none,
|
||||||
|
inputs: 2,
|
||||||
|
fill: none,
|
||||||
|
stroke: black + 1pt,
|
||||||
|
id: "",
|
||||||
|
inverted: (),
|
||||||
|
debug: (
|
||||||
|
ports: false
|
||||||
|
)
|
||||||
|
) = {
|
||||||
|
iec-gate-xor(
|
||||||
|
x: x,
|
||||||
|
y: y,
|
||||||
|
w: w,
|
||||||
|
h: h,
|
||||||
|
inputs: inputs,
|
||||||
|
fill: fill,
|
||||||
|
stroke: stroke,
|
||||||
|
id: id,
|
||||||
|
inverted: if inverted != "all" {inverted + ("out",)} else {inverted},
|
||||||
|
debug: debug
|
||||||
|
)
|
||||||
|
}
|
||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "gate.typ"
|
#import "gate.typ"
|
||||||
|
|
||||||
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
#let draw-shape(id, tl, tr, br, bl, fill, stroke) = {
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "gate.typ"
|
#import "gate.typ"
|
||||||
|
|
||||||
#let space = 10%
|
#let space = 10%
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "../util.typ"
|
#import "../util.typ"
|
||||||
#import "element.typ"
|
#import "element.typ"
|
||||||
#import "ports.typ": add-port
|
#import "ports.typ": add-port
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw
|
#import "/src/cetz.typ": draw
|
||||||
#import "../util.typ": rotate-anchor
|
#import "../util.typ": rotate-anchor
|
||||||
|
|
||||||
#let add-port(
|
#let add-port(
|
||||||
|
|||||||
@@ -2,4 +2,9 @@
|
|||||||
#import "elements/logic/and.typ": gate-and, gate-nand
|
#import "elements/logic/and.typ": gate-and, gate-nand
|
||||||
#import "elements/logic/or.typ": gate-or, gate-nor
|
#import "elements/logic/or.typ": gate-or, gate-nor
|
||||||
#import "elements/logic/xor.typ": gate-xor, gate-xnor
|
#import "elements/logic/xor.typ": gate-xor, gate-xnor
|
||||||
#import "elements/logic/buf.typ": gate-buf, gate-not
|
#import "elements/logic/buf.typ": gate-buf, gate-not
|
||||||
|
#import "elements/logic/iec_gate.typ": iec-gate
|
||||||
|
#import "elements/logic/iec_and.typ": iec-gate-and, iec-gate-nand
|
||||||
|
#import "elements/logic/iec_or.typ": iec-gate-or, iec-gate-nor
|
||||||
|
#import "elements/logic/iec_buf.typ": iec-gate-buf, iec-gate-not
|
||||||
|
#import "elements/logic/iec_xor.typ": iec-gate-xor, iec-gate-xnor
|
||||||
@@ -1,4 +1,5 @@
|
|||||||
#let version = version(0, 2, 0)
|
#let version = version(0, 2, 1)
|
||||||
|
#let name = "circuiteria"
|
||||||
|
|
||||||
#import "circuit.typ": circuit
|
#import "circuit.typ": circuit
|
||||||
#import "element.typ"
|
#import "element.typ"
|
||||||
|
|||||||
@@ -73,4 +73,45 @@
|
|||||||
#let valid-anchors = (
|
#let valid-anchors = (
|
||||||
"center", "north", "east", "west", "south",
|
"center", "north", "east", "west", "south",
|
||||||
"north-east", "north-west", "south-east", "south-west"
|
"north-east", "north-west", "south-east", "south-west"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
/// Normalizes a coordinate so that 2D points (x, y) are padded
|
||||||
|
/// to (x, y, 0) as required by CeTZ's coordinate resolver.
|
||||||
|
/// Also handles function-based and dictionary-based coordinates
|
||||||
|
/// recursively.
|
||||||
|
///
|
||||||
|
/// - coord (any): A CeTZ-compatible coordinate
|
||||||
|
/// -> any
|
||||||
|
#let normalize-coord(coord) = {
|
||||||
|
if type(coord) == array {
|
||||||
|
if coord.len() == 2 {
|
||||||
|
let (a, b) = coord
|
||||||
|
// Raw 2D point: (x, y) -> (x, y, 0)
|
||||||
|
if type(a) in (int, float) and type(b) in (int, float) {
|
||||||
|
return (a, b, 0)
|
||||||
|
}
|
||||||
|
// Function-based coordinate: (fn, point)
|
||||||
|
if type(a) == function {
|
||||||
|
let orig = a
|
||||||
|
return (v => {
|
||||||
|
let result = orig(v)
|
||||||
|
if type(result) == array and result.len() == 2 {
|
||||||
|
let (rx, ry) = result
|
||||||
|
if type(rx) in (int, float) and type(ry) in (int, float) {
|
||||||
|
return (rx, ry, 0)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result
|
||||||
|
}, b)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if type(coord) == dictionary {
|
||||||
|
let result = (:)
|
||||||
|
for (key, value) in coord {
|
||||||
|
result.insert(key, normalize-coord(value))
|
||||||
|
}
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
return coord
|
||||||
|
}
|
||||||
@@ -1,9 +1,9 @@
|
|||||||
#import "@preview/cetz:0.3.2": draw, coordinate
|
#import "/src/cetz.typ": draw, coordinate
|
||||||
#import "util.typ": opposite-anchor
|
#import "util.typ": opposite-anchor, normalize-coord
|
||||||
|
|
||||||
/// List of valid wire styles
|
/// List of valid wire styles
|
||||||
/// #examples.wires
|
/// #examples.wires
|
||||||
#let wire-styles = ("direct", "zigzag", "dodge")
|
#let wire-styles = ("direct", "zigzag", "dodge", "guided")
|
||||||
#let signal-width = 1pt
|
#let signal-width = 1pt
|
||||||
#let bus-width = 1.5pt
|
#let bus-width = 1.5pt
|
||||||
|
|
||||||
@@ -24,29 +24,123 @@
|
|||||||
return (pts, anchors)
|
return (pts, anchors)
|
||||||
}
|
}
|
||||||
|
|
||||||
#let get-zigzag-wire(pts, ratio, dir) = {
|
// Normalize an anchor-based placement value used by `zigzag-at`, `u-at`, and
|
||||||
|
// the `s-at-*` family.
|
||||||
|
//
|
||||||
|
// `axis` selects which cartesian component the offset applies to:
|
||||||
|
// - `"x"` → offset in x (used when the placement fixes an x coordinate, e.g.
|
||||||
|
// a vertical bend line for horizontal wire flow).
|
||||||
|
// - `"y"` → offset in y (used when the placement fixes a y coordinate).
|
||||||
|
//
|
||||||
|
// Accepted forms:
|
||||||
|
// - `none` → unset; caller falls back to
|
||||||
|
// depth/ratio-based placement.
|
||||||
|
// - `str` / tuple / native CeTZ dict → passed through as a CeTZ coordinate.
|
||||||
|
// - `(rel: <length>, to: <coord>)` with a *scalar* `rel`
|
||||||
|
// → ergonomic axial offset, rewritten
|
||||||
|
// to `(rel: (rel, 0), to: to)` for
|
||||||
|
// `axis == "x"` or
|
||||||
|
// `(rel: (0, rel), to: to)` for
|
||||||
|
// `axis == "y"`. If `rel` is already
|
||||||
|
// an array/tuple, the value is
|
||||||
|
// passed through unchanged.
|
||||||
|
#let normalize-scalar-offset(at, axis) = {
|
||||||
|
if at == none { return none }
|
||||||
|
if type(at) == dictionary and "rel" in at and "to" in at and type(at.rel) != array {
|
||||||
|
let r = at.rel
|
||||||
|
if axis == "x" {
|
||||||
|
return (rel: (r, 0), to: at.to)
|
||||||
|
} else {
|
||||||
|
return (rel: (0, r), to: at.to)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return at
|
||||||
|
}
|
||||||
|
|
||||||
|
// Backwards-compatible wrapper: translates the old `dir` vocabulary
|
||||||
|
// (`"vertical"` / `"horizontal"`) to the `axis` vocabulary used by
|
||||||
|
// `normalize-scalar-offset`.
|
||||||
|
#let normalize-zigzag-at(at, dir) = {
|
||||||
|
let axis = if dir == "vertical" { "x" } else { "y" }
|
||||||
|
return normalize-scalar-offset(at, axis)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Try to deduce the cardinal side a port anchor faces by comparing its
|
||||||
|
// position to the center of the element it belongs to. Returns none if the
|
||||||
|
// anchor is not a port-style anchor (i.e. does not contain "-port-") or if
|
||||||
|
// resolution fails.
|
||||||
|
#let detect-port-side(anchor, ctx) = {
|
||||||
|
if type(anchor) != str { return none }
|
||||||
|
let sep = "-port-"
|
||||||
|
if not anchor.contains(sep) { return none }
|
||||||
|
let elmt-id = anchor.split(sep).first()
|
||||||
|
let port-pos = none
|
||||||
|
let center-pos = none
|
||||||
|
// coordinate.resolve panics on unknown anchors; there is no try/catch in
|
||||||
|
// Typst, so we assume port anchors created by add-port always come with a
|
||||||
|
// matching group of the same name. If not, the user must set the relevant side parameter
|
||||||
|
// explicitly.
|
||||||
|
let (_, p1) = coordinate.resolve(ctx, anchor)
|
||||||
|
let (_, p2) = coordinate.resolve(ctx, elmt-id + ".center")
|
||||||
|
port-pos = p1
|
||||||
|
center-pos = p2
|
||||||
|
let dx = port-pos.at(0) - center-pos.at(0)
|
||||||
|
let dy = port-pos.at(1) - center-pos.at(1)
|
||||||
|
if calc.abs(dx) >= calc.abs(dy) {
|
||||||
|
return if dx >= 0 { "east" } else { "west" }
|
||||||
|
} else {
|
||||||
|
return if dy >= 0 { "north" } else { "south" }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#let get-zigzag-wire(pts, ratio, dir, at: none) = {
|
||||||
let start = pts.first()
|
let start = pts.first()
|
||||||
let end = pts.last()
|
let end = pts.last()
|
||||||
let mid = if dir == "vertical" {
|
|
||||||
(start, ratio, (horizontal: end, vertical: ()))
|
|
||||||
} else {
|
|
||||||
(start, ratio, (horizontal: (), vertical: end))
|
|
||||||
}
|
|
||||||
|
|
||||||
let points = if dir == "vertical" {
|
let points
|
||||||
(
|
if at == none {
|
||||||
start,
|
// Ratio-based placement (default).
|
||||||
(horizontal: mid, vertical: ()),
|
let mid = if dir == "vertical" {
|
||||||
(horizontal: (), vertical: end),
|
(start, ratio, (horizontal: end, vertical: ()))
|
||||||
end
|
} else {
|
||||||
)
|
(start, ratio, (horizontal: (), vertical: end))
|
||||||
|
}
|
||||||
|
|
||||||
|
points = if dir == "vertical" {
|
||||||
|
(
|
||||||
|
start,
|
||||||
|
(horizontal: mid, vertical: ()),
|
||||||
|
(horizontal: (), vertical: end),
|
||||||
|
end
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
(
|
||||||
|
start,
|
||||||
|
(horizontal: (), vertical: mid),
|
||||||
|
(horizontal: end, vertical: ()),
|
||||||
|
end
|
||||||
|
)
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
(
|
// Anchor-based placement: the middle bend segment sits on the axis
|
||||||
start,
|
// extracted from `at` via CeTZ's perpendicular operator `|-`:
|
||||||
(horizontal: (), vertical: mid),
|
// - vertical: middle segment at x = at.x
|
||||||
(horizontal: end, vertical: ()),
|
// - horizontal: middle segment at y = at.y
|
||||||
end
|
points = if dir == "vertical" {
|
||||||
)
|
(
|
||||||
|
start,
|
||||||
|
(at, "|-", start),
|
||||||
|
(at, "|-", end),
|
||||||
|
end
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
(
|
||||||
|
start,
|
||||||
|
(start, "|-", at),
|
||||||
|
(end, "|-", at),
|
||||||
|
end
|
||||||
|
)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
let anchors = (
|
let anchors = (
|
||||||
"start": start,
|
"start": start,
|
||||||
@@ -68,8 +162,8 @@
|
|||||||
|
|
||||||
let (ctx, p0) = coordinate.resolve(ctx, start)
|
let (ctx, p0) = coordinate.resolve(ctx, start)
|
||||||
let (ctx, p3) = coordinate.resolve(ctx, end)
|
let (ctx, p3) = coordinate.resolve(ctx, end)
|
||||||
p0 = (x: p0.first(), y: p0.last())
|
p0 = (x: p0.first(), y: p0.at(1))
|
||||||
p3 = (x: p3.first(), y: p3.last())
|
p3 = (x: p3.first(), y: p3.at(1))
|
||||||
|
|
||||||
let dx1 = margin-start
|
let dx1 = margin-start
|
||||||
let dx2 = margin-end
|
let dx2 = margin-end
|
||||||
@@ -86,13 +180,13 @@
|
|||||||
if side-end == "east" {
|
if side-end == "east" {
|
||||||
dx2 *= -1
|
dx2 *= -1
|
||||||
}
|
}
|
||||||
p1 = (p0.x + dx1, p0.y)
|
p1 = (p0.x + dx1, p0.y, 0)
|
||||||
p2 = (p3.x - dx2, p0.y)
|
p2 = (p3.x - dx2, p0.y, 0)
|
||||||
|
|
||||||
let points = (
|
let points = (
|
||||||
start,
|
start,
|
||||||
(horizontal: p1, vertical: ()),
|
(horizontal: p1, vertical: ()),
|
||||||
(horizontal: (), vertical: (0, dodge-y)),
|
(horizontal: (), vertical: (0, dodge-y, 0)),
|
||||||
(horizontal: p2, vertical: ()),
|
(horizontal: p2, vertical: ()),
|
||||||
(horizontal: (), vertical: end),
|
(horizontal: (), vertical: end),
|
||||||
end
|
end
|
||||||
@@ -109,6 +203,88 @@
|
|||||||
return (points, anchors)
|
return (points, anchors)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#let get-guided-wire(pts, margins, sides, center-guides, ctx) = {
|
||||||
|
let start = pts.first()
|
||||||
|
let end = pts.last()
|
||||||
|
let (margin-start, margin-end) = margins
|
||||||
|
let (side-start, side-end) = sides
|
||||||
|
let (center_horizontal, center_vertical) = center-guides
|
||||||
|
|
||||||
|
let (ctx, p0) = coordinate.resolve(ctx, start)
|
||||||
|
let (ctx, p6) = coordinate.resolve(ctx, end)
|
||||||
|
p0 = (x: p0.first(), y: p0.at(1))
|
||||||
|
p6 = (x: p6.first(), y: p6.at(1))
|
||||||
|
|
||||||
|
let box_width = calc.abs(p6.x - p0.x)
|
||||||
|
let box_height = calc.abs(p6.y - p0.y)
|
||||||
|
|
||||||
|
// finding correct dx and dy
|
||||||
|
let dx1 = box_width * margin-start / 100%
|
||||||
|
if side-start == "west" {
|
||||||
|
dx1 *= -1
|
||||||
|
} else if side-start == "north" or side-start == "south" { dx1 = 0}
|
||||||
|
|
||||||
|
let dx2 = box_width * margin-end / 100%
|
||||||
|
if side-end == "west" {
|
||||||
|
dx2 *= -1
|
||||||
|
} else if side-end == "north" or side-end == "south" { dx2 = 0}
|
||||||
|
|
||||||
|
let dy1 = box_height * margin-start / 100%
|
||||||
|
if side-start == "south" {
|
||||||
|
dy1 *= -1
|
||||||
|
} else if side-start == "west" or side-start == "east" { dy1 = 0}
|
||||||
|
|
||||||
|
let dy2 = box_height * margin-end / 100%
|
||||||
|
if side-end == "south" {
|
||||||
|
dy2 *= -1
|
||||||
|
} else if side-end == "west" or side-end == "east" { dy2 = 0}
|
||||||
|
|
||||||
|
|
||||||
|
// points that are closest to the edge points
|
||||||
|
let p1 = (p0.x + dx1, p0.y + dy1, 0)
|
||||||
|
let p5 = (p6.x + dx2, p6.y + dy2, 0)
|
||||||
|
|
||||||
|
|
||||||
|
// middle point
|
||||||
|
let center_x = p0.x + box_width * center_horizontal / 100%
|
||||||
|
let center_y = p0.y + box_height * center_vertical / 100%
|
||||||
|
let p3 = (center_x, center_y, 0)
|
||||||
|
|
||||||
|
// setting up the points for that touch the guides
|
||||||
|
let p2 = (0, 0, 0)
|
||||||
|
let p4 = (0, 0, 0)
|
||||||
|
if side-start in ("north", "south") {
|
||||||
|
p2 = (horizontal: p3, vertical: p1)
|
||||||
|
} else {
|
||||||
|
p2 = (horizontal: p1, vertical: p3)
|
||||||
|
}
|
||||||
|
if side-end in ("north", "south") {
|
||||||
|
p4 = (horizontal: p3, vertical: p5)
|
||||||
|
} else if side-end in ("east", "west") {
|
||||||
|
p4 = (horizontal: p5, vertical: p3)
|
||||||
|
}
|
||||||
|
|
||||||
|
// returning
|
||||||
|
let points = (
|
||||||
|
start,
|
||||||
|
p1,
|
||||||
|
p2,
|
||||||
|
p3,
|
||||||
|
p4,
|
||||||
|
p5,
|
||||||
|
end
|
||||||
|
)
|
||||||
|
let anchors = (
|
||||||
|
"start": start,
|
||||||
|
"start2": points.at(1),
|
||||||
|
"guide-start": points.at(2),
|
||||||
|
"center": points.at(3),
|
||||||
|
"guide-end": points.at(4),
|
||||||
|
"end2": points.at(5),
|
||||||
|
"end": end
|
||||||
|
)
|
||||||
|
return (points, anchors)
|
||||||
|
}
|
||||||
/// Draws a wire between two points
|
/// Draws a wire between two points
|
||||||
/// - id (str): The wire's id, for future reference (anchors)
|
/// - id (str): The wire's id, for future reference (anchors)
|
||||||
/// - pts (array): The two points (as CeTZ compatible coordinates, i.e. XY, relative positions, ids, etc.)
|
/// - pts (array): The two points (as CeTZ compatible coordinates, i.e. XY, relative positions, ids, etc.)
|
||||||
@@ -122,11 +298,15 @@
|
|||||||
/// - reverse (bool): If true, the start and end points will be swapped (useful in cases where the start point depends on the end point, for example with perpendiculars)
|
/// - reverse (bool): If true, the start and end points will be swapped (useful in cases where the start point depends on the end point, for example with perpendiculars)
|
||||||
/// - directed (bool): If true, the wire will be directed, meaning an arrow will be drawn at the endpoint
|
/// - directed (bool): If true, the wire will be directed, meaning an arrow will be drawn at the endpoint
|
||||||
/// - rotate-name (bool): If true, the name will be rotated according to the wire's slope
|
/// - rotate-name (bool): If true, the name will be rotated according to the wire's slope
|
||||||
/// - zigzag-ratio (ratio): Position of the zigzag vertical relative to the horizontal span (only with style "zigzag")
|
/// - zigzag-ratio (auto, ratio): Position of the zigzag middle bend segment relative to the horizontal (or vertical) span, as a fraction between the two endpoints (only with style "zigzag"). Defaults to `auto`, which resolves to `50%`. Panics if combined with an explicitly set `zigzag-at`.
|
||||||
/// - zigzag-dir (str): The zigzag's direction. As either "vertical" or "horizontal" (only with dstyle "zigzag")
|
/// - zigzag-dir (auto, str): The zigzag's direction, as either "vertical" or "horizontal" (only with style "zigzag"). If `auto`, it is deduced from the endpoints when they are port anchors of the form `<elmt-id>-port-<port-id>` by comparing each port's position with its element's `.center` anchor: east/west-facing ports yield `"vertical"` (wire exits horizontally) and north/south-facing ports yield `"horizontal"`. If the direction cannot be deduced (no port anchor on either endpoint, or conflicting directions), it falls back to `"vertical"`.
|
||||||
|
/// - zigzag-at (none, str, array, dictionary): Optional. Anchor-based placement of the zigzag middle bend segment (only with style "zigzag"). When set, overrides `zigzag-ratio` (which must be left at its default `auto`). The middle segment sits on the axis extracted from the given coordinate: `x` for `zigzag-dir: "vertical"`, `y` for `"horizontal"`. Accepted forms: a raw CeTZ anchor name string (e.g. `"elmt.center"` or `"elmt-port-a"`); any native CeTZ coordinate (tuple, dict such as `(rel: (dx, dy), to: anchor)`); or the ergonomic scalar-offset form `(rel: <length>, to: <coord>)`, which is rewritten to a `(dx, 0)` offset for `"vertical"` and `(0, dy)` for `"horizontal"`. See #examples.zigzag-at
|
||||||
/// - dodge-y (number): Y position to dodge the wire to (only with style "dodge")
|
/// - dodge-y (number): Y position to dodge the wire to (only with style "dodge")
|
||||||
/// - dodge-sides (array): The start and end sides (going out of the connected element) of the wire (only with style "dodge")
|
/// - dodge-sides (array): The start and end sides (going out of the connected element) of the wire (only with style "dodge")
|
||||||
/// - dodge-margins (array): The start and end margins (i.e. space before dodging) of the wire (only with style "dodge")
|
/// - dodge-margins (array): The start and end margins (i.e. space before dodging) of the wire (only with style "dodge")
|
||||||
|
/// - guided-center (array): the horizontal and vertical guides of the center guides (only with style "guided")
|
||||||
|
/// - guided-margins (array): the start and end of guided margins of the wire (only with style "guided")
|
||||||
|
/// - guided-sides (array): the side of start and end array (must be either "north", "south", "west", "east") (only work with style "guided")
|
||||||
#let wire(
|
#let wire(
|
||||||
id, pts,
|
id, pts,
|
||||||
bus: false,
|
bus: false,
|
||||||
@@ -137,10 +317,14 @@
|
|||||||
dashed: false,
|
dashed: false,
|
||||||
style: "direct",
|
style: "direct",
|
||||||
reverse: false,
|
reverse: false,
|
||||||
|
guided-center: (50%, 50%),
|
||||||
|
guided-margins: (5%, 5%),
|
||||||
|
guided-sides: ("east", "west"),
|
||||||
directed: false,
|
directed: false,
|
||||||
rotate-name: true,
|
rotate-name: true,
|
||||||
zigzag-ratio: 50%,
|
zigzag-ratio: auto,
|
||||||
zigzag-dir: "vertical",
|
zigzag-dir: auto,
|
||||||
|
zigzag-at: none,
|
||||||
dodge-y: 0,
|
dodge-y: 0,
|
||||||
dodge-sides: ("east", "west"),
|
dodge-sides: ("east", "west"),
|
||||||
dodge-margins: (5%, 5%)
|
dodge-margins: (5%, 5%)
|
||||||
@@ -152,6 +336,22 @@
|
|||||||
if pts.len() != 2 {
|
if pts.len() != 2 {
|
||||||
panic("Wrong number of points (got " + str(pts.len()) + " instead of 2)")
|
panic("Wrong number of points (got " + str(pts.len()) + " instead of 2)")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// `zigzag-at` validation.
|
||||||
|
if zigzag-at != none {
|
||||||
|
if style != "zigzag" {
|
||||||
|
panic("wire '" + id + "': `zigzag-at` requires style: \"zigzag\" (got \""
|
||||||
|
+ style + "\")")
|
||||||
|
}
|
||||||
|
if zigzag-ratio != auto {
|
||||||
|
panic("wire '" + id
|
||||||
|
+ "': cannot combine `zigzag-at` with an explicit `zigzag-ratio`")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
let zigzag-ratio-effective = if zigzag-ratio == auto { 50% } else { zigzag-ratio }
|
||||||
|
|
||||||
|
// Normalize user-provided coordinates: (x, y) -> (x, y, 0)
|
||||||
|
let pts = pts.map(normalize-coord)
|
||||||
|
|
||||||
let stroke = (
|
let stroke = (
|
||||||
paint: color,
|
paint: color,
|
||||||
@@ -168,7 +368,26 @@
|
|||||||
(points, anchors) = get-direct-wire(pts)
|
(points, anchors) = get-direct-wire(pts)
|
||||||
|
|
||||||
} else if style == "zigzag" {
|
} else if style == "zigzag" {
|
||||||
(points, anchors) = get-zigzag-wire(pts, zigzag-ratio, zigzag-dir)
|
let zz-dir = zigzag-dir
|
||||||
|
if zz-dir == auto {
|
||||||
|
let side-start = detect-port-side(pts.first(), ctx)
|
||||||
|
let side-end = detect-port-side(pts.last(), ctx)
|
||||||
|
let dir-from-side(s) = if s == none { none } else if s == "east" or s == "west" { "vertical" } else { "horizontal" }
|
||||||
|
let d-start = dir-from-side(side-start)
|
||||||
|
let d-end = dir-from-side(side-end)
|
||||||
|
// Fall back to "vertical" (the previous default) when the direction
|
||||||
|
// cannot be deduced (no port anchors, or conflicting endpoints).
|
||||||
|
if d-start != none and d-end != none and d-start != d-end { zz-dir = "vertical" }
|
||||||
|
else if d-start != none { zz-dir = d-start }
|
||||||
|
else if d-end != none { zz-dir = d-end }
|
||||||
|
else { zz-dir = "vertical" }
|
||||||
|
}
|
||||||
|
(points, anchors) = get-zigzag-wire(
|
||||||
|
pts,
|
||||||
|
zigzag-ratio-effective,
|
||||||
|
zz-dir,
|
||||||
|
at: normalize-zigzag-at(zigzag-at, zz-dir),
|
||||||
|
)
|
||||||
|
|
||||||
} else if style == "dodge" {
|
} else if style == "dodge" {
|
||||||
(points, anchors) = get-dodge-wire(
|
(points, anchors) = get-dodge-wire(
|
||||||
@@ -178,6 +397,14 @@
|
|||||||
dodge-sides,
|
dodge-sides,
|
||||||
ctx
|
ctx
|
||||||
)
|
)
|
||||||
|
} else if style == "guided" {
|
||||||
|
(points, anchors) = get-guided-wire(
|
||||||
|
pts,
|
||||||
|
guided-margins,
|
||||||
|
guided-sides,
|
||||||
|
guided-center,
|
||||||
|
ctx
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
let mark = (fill: color)
|
let mark = (fill: color)
|
||||||
@@ -303,4 +530,4 @@
|
|||||||
name
|
name
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
[package]
|
[package]
|
||||||
name = "circuiteria"
|
name = "circuiteria"
|
||||||
version = "0.2.0"
|
version = "0.2.1"
|
||||||
compiler = "0.13.0"
|
compiler = "0.15.0"
|
||||||
repository = "https://git.kb28.ch/HEL/circuiteria"
|
repository = "https://git.kb28.ch/HEL/circuiteria"
|
||||||
entrypoint = "src/lib.typ"
|
entrypoint = "src/lib.typ"
|
||||||
authors = [
|
authors = [
|
||||||
@@ -9,6 +9,6 @@ authors = [
|
|||||||
]
|
]
|
||||||
categories = [ "visualization" ]
|
categories = [ "visualization" ]
|
||||||
license = "Apache-2.0"
|
license = "Apache-2.0"
|
||||||
description = "Drawing block circuits with Typst made easy, using CeTZ"
|
description = "Drawing block circuits made easy, using CeTZ"
|
||||||
keywords = [ "circuit", "block", "draw" ]
|
keywords = [ "circuit", "block", "draw" ]
|
||||||
exclude = [ "gallery", "justfile", "doc" ]
|
exclude = [ "gallery", "justfile", "doc" ]
|
||||||