You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
82 lines
1.8 KiB
JavaScript
82 lines
1.8 KiB
JavaScript
class Builder {
|
|
constructor(files) {
|
|
this.files = files
|
|
}
|
|
|
|
buildModule(file) {
|
|
const script = document.createElement('script')
|
|
script.setAttribute('type', 'module')
|
|
let initAppend = ""
|
|
let append = ""
|
|
const data = file.data.replaceAll(
|
|
/^\s*export\s+(?:class|function|async\s+function|const)\s+(\S+)/gms,
|
|
(match, p1) => {
|
|
const path = JSON.stringify(file.name)
|
|
const mref = `Macchiato.modules[${path}]`
|
|
const pref = `[${JSON.stringify(p1)}]`
|
|
initAppend = `\n\n${mref} = {}`
|
|
const s = `${mref}${pref} = ${p1}`
|
|
append += "\n" + s
|
|
return `// append: ${s}\n${match}`
|
|
}
|
|
).replaceAll(
|
|
/^\s*import\s+(\{[^}]+\})\s+from\s+("[^"]+"|')/gms,
|
|
(match, p1, p2) => {
|
|
const vars = p1.replaceAll(' as ', ': ')
|
|
const importPath = p2.slice(1, -1)
|
|
const path = JSON.stringify(
|
|
importPath.slice(
|
|
importPath.indexOf('/') + 1
|
|
)
|
|
)
|
|
const ref = `Macchiato.modules[${path}]`
|
|
return `const ${vars} = ${ref}`
|
|
}
|
|
)
|
|
script.textContent = (
|
|
"\n" + data + initAppend + append + "\n"
|
|
)
|
|
return script.outerHTML
|
|
}
|
|
|
|
build() {
|
|
const modules = this.files.map(file => {
|
|
return this.buildModule(file)
|
|
})
|
|
return `
|
|
<!doctype html>
|
|
<html>
|
|
<head>
|
|
<title>Editor</title>
|
|
<style>
|
|
html, body, iframe {
|
|
margin: 0;
|
|
padding: 0;
|
|
width: 100%;
|
|
height: 100%;
|
|
}
|
|
iframe {
|
|
border: none;
|
|
display: block;
|
|
}
|
|
html {
|
|
box-sizing: border-box;
|
|
}
|
|
*, *:before, *:after {
|
|
box-sizing: inherit;
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
${'<'}script type="module">
|
|
window.Macchiato = {modules: {}}
|
|
${'</'}script>
|
|
${modules.join("\n")}
|
|
${'<'}script type="module">
|
|
|
|
${'</'}script>
|
|
</body>
|
|
</html>
|
|
`.trim()
|
|
}
|
|
} |