From 8d2bc9b84f711978ddbab60de57148c0ebcf98c5 Mon Sep 17 00:00:00 2001 From: syuilo <4439005+syuilo@users.noreply.github.com> Date: Thu, 30 Oct 2025 18:14:41 +0900 Subject: [PATCH] wip --- locales/index.d.ts | 6 +- locales/ja-JP.yml | 3 +- .../components/MkImageLabelEditorDialog.vue | 5 ++ .../src/utility/image-label-renderer.ts | 55 ++++++++++--------- 4 files changed, 40 insertions(+), 29 deletions(-) diff --git a/locales/index.d.ts b/locales/index.d.ts index 8871a67178..4d8c86b110 100644 --- a/locales/index.d.ts +++ b/locales/index.d.ts @@ -5611,9 +5611,13 @@ export interface Locale extends ILocale { */ "title": string; /** - * フレーム + * フレームの幅 */ "frameThickness": string; + /** + * ラベルの幅 + */ + "labelThickness": string; /** * 中央揃え */ diff --git a/locales/ja-JP.yml b/locales/ja-JP.yml index 5d4e5f7a6f..d6a1dff2b6 100644 --- a/locales/ja-JP.yml +++ b/locales/ja-JP.yml @@ -1399,7 +1399,8 @@ deviceInfoDescription: "技術的なお問い合わせの際に、以下の情 _imageLabelEditor: title: "ラベルの編集" - frameThickness: "フレーム" + frameThickness: "フレームの幅" + labelThickness: "ラベルの幅" centered: "中央揃え" captionMain: "キャプション(大)" captionSub: "キャプション(小)" diff --git a/packages/frontend/src/components/MkImageLabelEditorDialog.vue b/packages/frontend/src/components/MkImageLabelEditorDialog.vue index e48321766a..81e1438d86 100644 --- a/packages/frontend/src/components/MkImageLabelEditorDialog.vue +++ b/packages/frontend/src/components/MkImageLabelEditorDialog.vue @@ -34,6 +34,10 @@ SPDX-License-Identifier: AGPL-3.0-only + + + + @@ -109,6 +113,7 @@ const props = defineProps<{ const frame = reactive(deepClone(props.frame) ?? { style: 'frame', frameThickness: 0.05, + labelThickness: 0.2, title: 'Untitled by @syuilo', text: '{mm}mm f/{f} {s}s ISO{iso}', centered: false, diff --git a/packages/frontend/src/utility/image-label-renderer.ts b/packages/frontend/src/utility/image-label-renderer.ts index b7a25f22f3..fc6627f56b 100644 --- a/packages/frontend/src/utility/image-label-renderer.ts +++ b/packages/frontend/src/utility/image-label-renderer.ts @@ -18,6 +18,7 @@ const FXS = [ export type ImageLabelParams = { style: 'frame' | 'frameLess'; frameThickness: number; + labelThickness: number; title: string; text: string; centered: boolean; @@ -26,11 +27,9 @@ export type ImageLabelParams = { export class ImageLabelRenderer { private effector: ImageEffector; - private renderWidth: number; - private renderHeight: number; private image: HTMLImageElement | ImageBitmap; - private paddingBottom = 0; private exif: ExifReader.Tags; + private renderAsPreview = false; constructor(options: { canvas: HTMLCanvasElement, @@ -40,30 +39,13 @@ export class ImageLabelRenderer { }) { this.image = options.image; this.exif = options.exif; + this.renderAsPreview = options.renderAsPreview ?? false; console.log(this.exif); - let w = this.image.width; - let h = this.image.height; - - if (options.renderAsPreview) { - const MAX_W = 1000; - const MAX_H = 1000; - - if (w > MAX_W || h > MAX_H) { - const scale = Math.min(MAX_W / w, MAX_H / h); - w = Math.floor(w * scale); - h = Math.floor(h * scale); - } - } - - this.paddingBottom = Math.floor(h * 0.2); - this.renderWidth = w; - this.renderHeight = h + this.paddingBottom; - this.effector = new ImageEffector({ canvas: options.canvas, - renderWidth: this.renderWidth, - renderHeight: this.renderHeight, + renderWidth: 1, + renderHeight: 1, image: null, fxs: FXS, }); @@ -89,10 +71,28 @@ export class ImageLabelRenderer { } public async update(params: ImageLabelParams): Promise { - const aspectRatio = this.renderWidth / this.renderHeight; + let w = this.image.width; + let h = this.image.height; + + if (this.renderAsPreview) { + const MAX_W = 1000; + const MAX_H = 1000; + + if (w > MAX_W || h > MAX_H) { + const scale = Math.min(MAX_W / w, MAX_H / h); + w = Math.floor(w * scale); + h = Math.floor(h * scale); + } + } + + const paddingBottom = Math.floor(h * params.labelThickness); + const renderWidth = w; + const renderHeight = h + paddingBottom; + + const aspectRatio = renderWidth / renderHeight; const ctx = window.document.createElement('canvas').getContext('2d')!; - ctx.canvas.width = this.renderWidth; - ctx.canvas.height = this.paddingBottom; + ctx.canvas.width = renderWidth; + ctx.canvas.height = paddingBottom; const fontSize = ctx.canvas.height / 6; const marginX = Math.max(fontSize * 2, (ctx.canvas.width * params.frameThickness) / aspectRatio); const withQrCode = params.withQrCode; @@ -184,6 +184,8 @@ export class ImageLabelRenderer { await this.effector.registerTexture('label', data); + this.effector.changeResolution(renderWidth, renderHeight); + await this.effector.setLayers([{ fxId: 'label', id: 'a', @@ -194,7 +196,6 @@ export class ImageLabelRenderer { imageMarginY: paddingY, }, }]); - this.render(); } public render(): void {