Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions api/modal.css
Original file line number Diff line number Diff line change
Expand Up @@ -75,4 +75,17 @@

.st-modal button:hover {
top: .4rem !important;
}

.st-modal button.ste-modal-cancel-btn {
background-color: #c9c9c9 !important;
}

.st-modal input {
padding: 0.5rem !important;
outline: none !important;
border-radius: 0.25rem !important;
border: 0px !important;
background-color: #e3e3e3;
margin-right: .5rem;
}
3 changes: 2 additions & 1 deletion api/modals.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,8 @@ ScratchTools.modals = {
});

var closeButton = document.createElement("button");
closeButton.textContent = "Close";
closeButton.textContent = data.cancel ? "Cancel" : "Close";
closeButton.className = data.cancel ? "ste-modal-cancel-btn" : ""
closeButton.onclick = function () {
div.remove();
};
Expand Down
17 changes: 5 additions & 12 deletions features/features.json
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
[
{
"version": 2,
"id": "more-editor-fonts",
"versionAdded": "v4.0.0"
},
{
"version": 2,
"id": "upload-thumbnail",
Expand Down Expand Up @@ -706,18 +711,6 @@
"type": ["Website"],
"dynamic": true
},
{
"title": "More Editor Fonts",
"description": "Adds more fonts to choose from in the paint editor. They look nicer and are more modern.",
"credits": ["rgantzos", "Lasted10"],
"urls": [
"https://scratch.mit.edu/users/rgantzos/",
"https://scratch.mit.edu/users/Lasted10_Forever/"
],
"file": "special-editor-fonts",
"tags": ["Recommended", "Beta"],
"type": ["Editor"]
},
{
"title": "Display Project Tags",
"description": "Lists all of the tags used in the project description right below the project notes and credits.",
Expand Down
16 changes: 16 additions & 0 deletions features/more-editor-fonts/data.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
{
"title": "More Paint Editor Fonts",
"description": "Allows you to use dozens of extra fonts in the paint editor.",
"credits": [
{
"username": "Sanjang_Beta",
"url": "https://scratch.mit.edu/users/Sanjang_Beta/"
},
{ "username": "rgantzos", "url": "https://scratch.mit.edu/users/rgantzos/" }
],
"type": ["Editor"],
"tags": ["New", "Featured"],
"scripts": [{ "file": "script.js", "runOn": "/projects/*" }],
"styles": [{ "file": "style.css", "runOn": "/projects/*" }],
"resources": [{ "name": "more-text-icon", "path": "/text.svg" }]
}
178 changes: 178 additions & 0 deletions features/more-editor-fonts/script.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,178 @@
export default async function ({ feature, console }) {
let { default: openTypeDefault } = await import(
"../../libraries/opentype.js"
);
openTypeDefault();

let fonts = await (await fetch(feature.server.endpoint("/fonts/"))).json();

feature.page.waitForElements(
"div[class^='asset-panel_wrapper_'] div[class^='action-menu_more-buttons_']",
function (menu) {
if (menu.querySelector(".ste-more-fonts")) return;

let div = document.createElement("div");
div.className = "ste-more-fonts";
feature.self.hideOnDisable(div);

let original =
menu.parentElement.previousElementSibling.previousElementSibling;
let id = original.getAttribute("aria-label").replace(/\s+/g, "_");

let button = document.createElement("button");
button.dataset.tip = "Add Font";
button.dataset.for = `ste-${id}-Add Font`;
button.currentitem = false;
button.ariaLabel = "Add Font";
button.className =
"action-menu_button_1qbot action-menu_more-button_1fMGZ ste-more-fonts-btn";
div.appendChild(button);

let img = Object.assign(document.createElement("img"), {
src: feature.self.getResource("more-text-icon"),
draggable: false,
className: "action-menu_more-icon_TJUQ7",
width: 10,
});
button.appendChild(img);

let tooltip = Object.assign(document.createElement("div"), {
className:
"__react_component_tooltip place-right type-dark action-menu_tooltip_3Bkh5",
id: `ste-${id}-Add Font`,
textContent: "Add Font",
});
tooltip.dataset.id = "tooltip";
div.appendChild(tooltip);

menu.prepend(div);

button.addEventListener("click", function () {
let div = document.createElement("div");
div.className = "ste-font-options";

let modal = ScratchTools.modals.create({
title: "Pick Font",
description:
"You can pick a font from the list below to add to the project.",
components: [
{
type: "html",
content: div,
},
],
cancel: true,
});

for (var i in fonts) {
let span = document.createElement("span");
span.className = "ste-font-option";
span.dataset.font = fonts[i];

let img = document.createElement("img");
img.src = feature.server.endpoint(`/font/image/${fonts[i]}/`);
span.appendChild(img);

span.addEventListener("click", function () {
let font = this.dataset.font;
modal.close();

let button = document.createElement("button");
button.textContent = "Continue";

let typeModal = ScratchTools.modals.create({
title: "Type Text",
description: "Type the text you would like to add.",
cancel: true,
components: [
{
type: "html",
content: Object.assign(document.createElement("input"), {
className: "ste-font-input",
}),
},
{
type: "html",
content: button,
},
{
type: "html",
content: document.createElement("br"),
},
],
});

button.addEventListener("click", function () {
let text = document.querySelector(".ste-font-input").value;
typeModal.close();

setFont(font, text);
});
});

div.appendChild(span);
}
});

let observer = new MutationObserver(doresize);
observer.observe(menu, { attributes: true, subtree: true });

function doresize() {
let rect = div.getBoundingClientRect();
tooltip.style.top = rect.top + 2 + "px";
tooltip.style.left = rect.left + rect.width + "px";
}
}
);

function setFont(font, text) {
async function fetchFont(url) {
const response = await fetch(url);
if (!response.ok) throw new Error("Failed to fetch font");
const arrayBuffer = await response.arrayBuffer();
return arrayBuffer;
}

function createSVGFromText(font, text) {
let width = font.getAdvanceWidth(text, 72);
const path = font.getPath(text, 0, 150, 72);
const svgPath = path.toSVG();
const svg = `
<svg xmlns="http://www.w3.org/2000/svg" width="${width.toString()}" height="200">
${svgPath}
</svg>
`;
return svg;
}

async function generateSVGText(url, text) {
try {
const fontArrayBuffer = await fetchFont(url);
const font = opentype.parse(fontArrayBuffer);
const svgText = createSVGFromText(font, text);
addCostume(svgText);
} catch (error) {
console.error("Error:" + error);
}
}

generateSVGText(feature.server.endpoint(`/font/${font}.ttf`), text);
}

window.setFont = setFont;

function addCostume(svg) {
let fileInput = document.querySelector("input[type=file]");

const blob = new Blob([svg], { type: "image/svg+xml" });
const url = URL.createObjectURL(blob);

const file = new File([blob], "text.svg", { type: "image/svg+xml" });

const dataTransfer = new DataTransfer();
dataTransfer.items.add(file);
fileInput.files = dataTransfer.files;

fileInput.dispatchEvent(new Event("change", { bubbles: true }));
}
}
35 changes: 35 additions & 0 deletions features/more-editor-fonts/style.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
[data-for*="Add Font"]:hover + .__react_component_tooltip {
visibility: visible;
}

.ste-more-fonts-btn + .__react_component_tooltip {
left: auto;
}

span.ste-font-option:nth-child(even) {
background-color: #e9e9e9;
}

span.ste-font-option {
display: block;
padding-left: .5rem;
border-radius: .5rem;
cursor: pointer;
}

span.ste-font-option:hover {
background-color: #ff9f00;
}

span.ste-font-option:hover img {
filter: invert(1);
}

span.ste-font-option img {
height: 3rem;
}

.ste-font-options {
height: 11rem;
overflow: auto;
}
24 changes: 24 additions & 0 deletions features/more-editor-fonts/text.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
47 changes: 0 additions & 47 deletions features/special-editor-fonts.js

This file was deleted.

Loading