gyazoにテキストを埋め込んで表示するTamperMonkeyUserScript
code:gyazo.user.js
// ==UserScript==
// @name gyazo-text-layer
// @version 0.1.0
// @description gyazoにテキストを埋め込んで表示するTamperMonkeyUserScript
// @author takker
// @license MIT
// @copyright Copyright (c) 2023 takker
// ==/UserScript==
const makeStyle = () => {
const id = "gyazo-layer-style";
const styleEl = document.getElementById(id);
if (styleEl) return styleEl;
const style = document.createElement("style");
style.id = id;
style.textContent = '.image-box-component picture{position:relative}#textLayer{position:absolute;height:var(--image-height);line-height:1.0;}#textLayer span{color: transparent;position:absolute;white-space:pre;cursor:text;transform-origin:0% 0%;}';
document.head.append(style);
return style;
};
const render = ({ metadata, scale }) => {
const id = "textLayer";
document.getElementById(id)?.remove?.();
const image = document.querySelector("img.image-viewer");
const textLayer = document.createElement("div");
textLayer.id = id;
textLayer.addEventListener("click", (e) => {
if (globalThis.getSelection().getRangeAt(0).commonAncestorContainer === textLayer) return;
e.stopPropagation();
e.preventDefault();
image.click();
});
const pageWidth = scale.width * scale.scale;
const pageHeight = scale.height * scale.scale;
for (const { description, boundingPoly: { vertices } } of metadata.ocrAnnotations) {
const span = document.createElement("span");
span.style.top = ${100 * vertices[0].y / pageHeight}%;
span.style.left = ${100 * vertices[0].x / pageWidth}%;
const width = (vertices1.x - vertices0.x + vertices2.x - vertices3.x) / 2; const height = (vertices3.y - vertices0.y + vertices2.y - vertices1.y) / 2; span.style.width = ${100 * width / pageWidth}%;
span.style.height = ${100 * height / pageHeight}%;
span.style.fontSize = calc(${height / pageHeight)} * var(--image-height));
span.textContent = description;
textLayer.append(span);
}
const handleResize = (rect) => {
textLayer.style.width = ${rect.width}px;
};
const observer = new ResizeObserver(
(contentRect }) => handleResize(contentRect),
);
handleResize(image.getBoundingClientRect());
observer.observe(image);
image.insertAdjacentElement("afterend", textLayer);
};
const callback = async () => {
if (!/\/0-9a-f{32}/.test(location.pathname)) return; makeStyle();
const res = await fetch(${location.origin}${location.pathname}.json);
const json = await res.json();
// 画像が表示されるまで待機
await new Promise((res) => {
const timer = setInterval(() => {
if (!document.querySelector("img.image-viewer")) return;
clearInterval(timer);
res();
}, 100);
});
render(json);
};
globalThis.addEventListener("load", () => {
callback();
let prevURL = location.href;
setInterval(() => {
if (prevURL === location.href) return;
prevURL = location.href;
callback();
}, 1000);
});
文字が画像と一致していないのが微妙
フォントの食い違いは仕方ないけど
https://gyazo.com/3325de927b34fcaff820403ffd40ece9
矩形を射影変換してverticesの各頂点にあわせる 改行を入れたい