aboutsummaryrefslogtreecommitdiffstats
path: root/app/svg.js
diff options
context:
space:
mode:
authorPetri Hienonen <petri.hienonen@gmail.com>2025-11-14 13:23:58 +0200
committerPetri Hienonen <petri.hienonen@gmail.com>2025-11-14 13:23:58 +0200
commita92ad2b817b2c28b26e869897e03c14d30d0f991 (patch)
tree702b4b63e2dc7cc544949cd76b444445e6c12ae5 /app/svg.js
parentd41ac3c094f733a8038885de3400ed7558b2b878 (diff)
downloadhousing-a92ad2b817b2c28b26e869897e03c14d30d0f991.tar.zst
Add histogram
Diffstat (limited to 'app/svg.js')
-rw-r--r--app/svg.js79
1 files changed, 79 insertions, 0 deletions
diff --git a/app/svg.js b/app/svg.js
index 92bd825..d977ead 100644
--- a/app/svg.js
+++ b/app/svg.js
@@ -26,6 +26,85 @@ export class SvgOptions {
export class Svg {
/**
+ * Create a rectangle with explicit coordinates
+ * @param {number} x
+ * @param {number} y
+ * @param {number} width
+ * @param {number} height
+ * @param {SvgOptions} [options=new SvgOptions()]
+ * @returns {SVGRectElement}
+ */
+ static rectXY(x, y, width, height, options = new SvgOptions()) {
+ const element = document.createElementNS("http://www.w3.org/2000/svg", "rect");
+ for (const [key, value] of Object.entries({
+ height: String(height),
+ width: String(width),
+ x: String(x),
+ y: String(y),
+ ...options.attributes,
+ })) {
+ element.setAttribute(key, value);
+ }
+ Object.assign(element.style, options.styles);
+ if (options.id) element.id = options.id;
+ if (options.classes.length) element.classList.add(...options.classes.filter(Boolean));
+ element.append(...options.children.filter(Boolean));
+ return element;
+ }
+
+ /**
+ * Create a text element at specific coordinates
+ * @param {number} x
+ * @param {number} y
+ * @param {string} text
+ * @param {SvgOptions} [options=new SvgOptions()]
+ * @returns {SVGTextElement}
+ */
+ static textXY(x, y, text, options = new SvgOptions()) {
+ const element = document.createElementNS("http://www.w3.org/2000/svg", "text");
+ element.textContent = text;
+ for (const [key, value] of Object.entries({
+ x: String(x),
+ y: String(y),
+ ...options.attributes,
+ })) {
+ element.setAttribute(key, value);
+ }
+ Object.assign(element.style, options.styles);
+ if (options.id) element.id = options.id;
+ if (options.classes.length) element.classList.add(...options.classes.filter(Boolean));
+ element.append(...options.children.filter(Boolean));
+ return element;
+ }
+
+ /**
+ * Create a line element
+ * @param {number} x1
+ * @param {number} y1
+ * @param {number} x2
+ * @param {number} y2
+ * @param {SvgOptions} [options=new SvgOptions()]
+ * @returns {SVGLineElement}
+ */
+ static line(x1, y1, x2, y2, options = new SvgOptions()) {
+ const element = document.createElementNS("http://www.w3.org/2000/svg", "line");
+ for (const [key, value] of Object.entries({
+ x1: String(x1),
+ x2: String(x2),
+ y1: String(y1),
+ y2: String(y2),
+ ...options.attributes,
+ })) {
+ element.setAttribute(key, value);
+ }
+ Object.assign(element.style, options.styles);
+ if (options.id) element.id = options.id;
+ if (options.classes.length) element.classList.add(...options.classes.filter(Boolean));
+ element.append(...options.children.filter(Boolean));
+ return element;
+ }
+
+ /**
* Create an SVG element
* @param {SvgOptions} [options=new SvgOptions()]
* @returns {SVGSVGElement}