mirror of
https://github.com/slint-ui/slint.git
synced 2025-07-18 18:45:25 +00:00
201 lines
5.8 KiB
JavaScript
201 lines
5.8 KiB
JavaScript
// Copyright © SixtyFPS GmbH <info@slint.dev>
|
|
// SPDX-License-Identifier: MIT
|
|
import { definePlugin } from "@expressive-code/core";
|
|
import { h } from "@expressive-code/core/hast";
|
|
import fs from "node:fs";
|
|
import { pluginLineNumbers } from "@expressive-code/plugin-line-numbers";
|
|
|
|
function sideBorder() {
|
|
return definePlugin({
|
|
name: "Adds side border to slint code blocks",
|
|
baseStyles: `
|
|
|
|
.sideBar {
|
|
position: absolute;
|
|
top: calc(var(--button-spacing) - 6px);
|
|
bottom: 0;
|
|
left: 0;
|
|
width: 100px;
|
|
border-left-width: 2px;
|
|
border-left-style: solid;
|
|
border-color: #2479f4;
|
|
border-top-left-radius: 0.4rem;
|
|
border-bottom-left-radius: 0.4rem;
|
|
pointer-events: none;
|
|
}
|
|
`,
|
|
hooks: {
|
|
postprocessRenderedBlock: (context) => {
|
|
if (
|
|
context.renderData.blockAst.children[1].properties
|
|
.dataLanguage !== "slint"
|
|
) {
|
|
return;
|
|
}
|
|
const side = h("div.sideBar");
|
|
|
|
const ast = context.renderData.blockAst;
|
|
ast.children.push(side);
|
|
|
|
context.renderData.blockAst = ast;
|
|
},
|
|
},
|
|
});
|
|
}
|
|
|
|
function remapLanguageIdentifiers(lang) {
|
|
switch (lang) {
|
|
case "cpp": {
|
|
return "C++";
|
|
}
|
|
case "sh": {
|
|
return "bash";
|
|
}
|
|
default: {
|
|
return lang;
|
|
}
|
|
}
|
|
}
|
|
|
|
function languageLabel() {
|
|
return definePlugin({
|
|
name: "Adds language label to code blocks",
|
|
baseStyles: `
|
|
.language-label {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
position: absolute;
|
|
inset-block-start: calc(var(--ec-brdWd) + var(--button-spacing));
|
|
inset-inline-end: calc(var(--ec-brdWd) + var(--ec-uiPadInl) );
|
|
direction: ltr;
|
|
font-size: 0.8rem;
|
|
color:rgb(169, 169, 169);
|
|
opacity: 1;
|
|
transition: opacity 0.3s;
|
|
}
|
|
div.expressive-code:hover .language-label,
|
|
.expressive-code:hover .language-label {
|
|
opacity: 0;
|
|
}
|
|
`,
|
|
hooks: {
|
|
postprocessRenderedBlock: (context) => {
|
|
const language =
|
|
context.renderData.blockAst.children[1].properties
|
|
.dataLanguage;
|
|
|
|
const label = h("div.language-label", {}, [
|
|
remapLanguageIdentifiers(language),
|
|
]);
|
|
|
|
const ast = context.renderData.blockAst;
|
|
ast.children.push(label);
|
|
|
|
context.renderData.blockAst = ast;
|
|
},
|
|
},
|
|
});
|
|
}
|
|
|
|
function workersPlaygroundButton() {
|
|
return definePlugin({
|
|
name: "Adds 'Run in SlintPad' button to slint codeblocks",
|
|
baseStyles: `
|
|
.run {
|
|
display: flex;
|
|
align-items: center;
|
|
justify-content: center;
|
|
position: absolute;
|
|
inset-block-start: calc(var(--ec-brdWd) + var(--button-spacing));
|
|
inset-inline-end: calc(var(--ec-brdWd) + var(--ec-uiPadInl) * 3);
|
|
direction: ltr;
|
|
unicode-bidi: isolate;
|
|
|
|
background-color: color-mix(in srgb, var(--sl-color-accent) 50%, transparent);
|
|
color: var(--sl-color-white);
|
|
text-decoration: none;
|
|
width: 2rem;
|
|
height: 2rem;
|
|
border-radius: 50%;
|
|
opacity: 0;
|
|
font-size: 0;
|
|
transition: opacity 0.3s, background-color 0.3s;
|
|
|
|
&:hover {
|
|
background-color: color-mix(in srgb, var(--sl-color-accent) 90%, transparent);
|
|
}
|
|
|
|
&::before {
|
|
content: '';
|
|
display: inline-block;
|
|
margin-left: 0.25rem;
|
|
border-style: solid;
|
|
border-width: 0.5rem 0 0.5rem 0.75rem;
|
|
border-color: transparent transparent transparent white;
|
|
}
|
|
}
|
|
div.expressive-code:hover .run,
|
|
.expressive-code:hover .run {
|
|
opacity: 1;
|
|
}
|
|
`,
|
|
hooks: {
|
|
postprocessRenderedBlock: (context) => {
|
|
if (!context.codeBlock.meta.includes("playground")) {
|
|
return;
|
|
}
|
|
|
|
const content = context.codeBlock.code;
|
|
const url = `https://slintpad.com?snippet=${encodeURIComponent(content)}`;
|
|
|
|
const runButton = h(
|
|
"a.run",
|
|
{
|
|
href: url,
|
|
target: "__blank",
|
|
title: "Open in SlintPad",
|
|
},
|
|
[],
|
|
);
|
|
|
|
const ast = context.renderData.blockAst;
|
|
ast.children.push(runButton);
|
|
|
|
context.renderData.blockAst = ast;
|
|
},
|
|
},
|
|
});
|
|
}
|
|
|
|
export default {
|
|
plugins: [
|
|
workersPlaygroundButton(),
|
|
sideBorder(),
|
|
languageLabel(),
|
|
pluginLineNumbers(),
|
|
],
|
|
defaultProps: {
|
|
showLineNumbers: false,
|
|
},
|
|
themes: ["dark-plus", "light-plus"],
|
|
styleOverrides: {
|
|
borderRadius: "0.4rem",
|
|
borderColor: "var(--slint-code-background)",
|
|
frames: { shadowColor: "transparent" },
|
|
codeBackground: "var(--slint-code-background)",
|
|
},
|
|
shiki: {
|
|
langs: [
|
|
JSON.parse(
|
|
fs.readFileSync(
|
|
"../../editors/vscode/slint.tmLanguage.json",
|
|
"utf-8",
|
|
),
|
|
),
|
|
],
|
|
},
|
|
frames: {
|
|
extractFileNameFromCode: false,
|
|
},
|
|
};
|