103 lines
3.2 KiB
TypeScript
103 lines
3.2 KiB
TypeScript
import { v4 as uuidv4 } from "uuid";
|
|
import { useGetSetting, useSetSetting } from "../../utils/querySettings";
|
|
import { ISpool } from "../spools/model";
|
|
|
|
export interface PrintSettings {
|
|
id: string;
|
|
name?: string;
|
|
margin?: { top: number; bottom: number; left: number; right: number };
|
|
printerMargin?: { top: number; bottom: number; left: number; right: number };
|
|
spacing?: { horizontal: number; vertical: number };
|
|
columns?: number;
|
|
rows?: number;
|
|
skipItems?: number;
|
|
itemCopies?: number;
|
|
paperSize?: string;
|
|
customPaperSize?: { width: number; height: number };
|
|
borderShowMode?: "none" | "border" | "grid";
|
|
}
|
|
|
|
export interface QRCodePrintSettings {
|
|
showContent?: boolean;
|
|
showQRCodeMode?: "no" | "simple" | "withIcon";
|
|
textSize?: number;
|
|
printSettings: PrintSettings;
|
|
}
|
|
|
|
export interface SpoolQRCodePrintSettings {
|
|
template?: string;
|
|
labelSettings: QRCodePrintSettings;
|
|
}
|
|
|
|
export function useGetPrintSettings(): SpoolQRCodePrintSettings[] | undefined {
|
|
const { data } = useGetSetting("print_presets");
|
|
if (!data) return;
|
|
const parsed: SpoolQRCodePrintSettings[] =
|
|
data && data.value ? JSON.parse(data.value) : ([] as SpoolQRCodePrintSettings[]);
|
|
// Loop through all parsed and generate a new ID field if it's not set
|
|
return parsed.map((settings) => {
|
|
if (!settings.labelSettings.printSettings.id) {
|
|
settings.labelSettings.printSettings.id = uuidv4();
|
|
}
|
|
return settings;
|
|
});
|
|
}
|
|
|
|
export function useSetPrintSettings(): (spoolQRCodePrintSettings: SpoolQRCodePrintSettings[]) => void {
|
|
const mut = useSetSetting("print_presets");
|
|
|
|
return (spoolQRCodePrintSettings: SpoolQRCodePrintSettings[]) => {
|
|
mut.mutate(spoolQRCodePrintSettings);
|
|
};
|
|
}
|
|
|
|
interface GenericObject {
|
|
[key: string]: any;
|
|
extra: { [key: string]: string };
|
|
}
|
|
|
|
function getTagValue(tag: string, obj: GenericObject): any {
|
|
// Split tag by .
|
|
const tagParts = tag.split(".");
|
|
if (tagParts[0] === "extra") {
|
|
return JSON.parse(obj.extra[tagParts[1]]);
|
|
}
|
|
|
|
const value = obj[tagParts[0]] ?? "?";
|
|
// check if value is itself an object. If so, recursively call this and remove the first part of the tag
|
|
if (typeof value === "object") {
|
|
return getTagValue(tagParts.slice(1).join("."), value);
|
|
}
|
|
return value;
|
|
}
|
|
|
|
function applyNewline(text: string): JSX.Element[] {
|
|
return text.split("\n").map((line, idx, arr) => (
|
|
<span key={idx}>
|
|
{line}
|
|
{idx < arr.length - 1 && <br />}
|
|
</span>
|
|
));
|
|
}
|
|
|
|
function applyTextFormatting(text: string): JSX.Element[] {
|
|
const regex = /\*\*([\w\W]*?)\*\*/g;
|
|
const parts = text.split(regex);
|
|
// Map over the parts and wrap matched text with <b> tags
|
|
const elements = parts.map((part, index) => {
|
|
// Even index: outside asterisks, odd index: inside asterisks (to be bolded)
|
|
const node = applyNewline(part);
|
|
return index % 2 === 0 ? <span key={index}>{node}</span> : <b key={index}>{node}</b>;
|
|
});
|
|
return elements;
|
|
}
|
|
export function renderLabelContents(template: string, spool: ISpool): JSX.Element {
|
|
// Find all {tags} in the template string and loop over them
|
|
let result = template.replace(/\{(.*?)\}/g, function (_, tag) {
|
|
return getTagValue(tag, spool);
|
|
});
|
|
|
|
// Split string on \n into individual lines
|
|
return <>{applyTextFormatting(result)}</>;
|
|
}
|