Change app layout
parent
a162b8001a
commit
d13021baec
|
|
@ -10,14 +10,12 @@ As a result, there is no risk of data being lost or deleted. Nobody will ever be
|
|||
|
||||
> **Note:** This project is a clone of [Topaz's paste service][topaz-example], with a reworked design and additional features such as syntax highlighting, line numbers, and more
|
||||
|
||||
|
||||
## How it works
|
||||
|
||||
When you click on "Generate Link", the whole text is compressed using the [LZMA algorithm](https://en.wikipedia.org/wiki/Lempel%E2%80%93Ziv%E2%80%93Markov_chain_algorithm), encoded in [Base64](https://en.wikipedia.org/wiki/Base64), and put in the optional fragment at the end of the URL: `bokub.github.io/paste/#<data is here>`
|
||||
|
||||
When you open a link which contains data, the fragment is decoded, decompressed, and displayed in the editor
|
||||
|
||||
|
||||
## Embedded Paste snippets
|
||||
|
||||
You can include code snippets into your own website by clicking the _Embed_ button and using the generated HTML code
|
||||
|
|
|
|||
13
index.html
13
index.html
|
|
@ -34,17 +34,18 @@ npm/codemirror@5.52.0/theme/dracula.min.css
|
|||
<link href="favicon.ico" rel="icon" type="image/x-icon" />
|
||||
</head>
|
||||
<body>
|
||||
<div id="progress"></div>
|
||||
<div id="editor"></div>
|
||||
<div id="footer">
|
||||
<label for="language"></label
|
||||
><select id="language"></select>
|
||||
<div id="controls">
|
||||
<div class="title">{ Paste }</div>
|
||||
<span class="grow"></span>
|
||||
<select id="language"></select>
|
||||
|
||||
<button onclick="generateLink('url')" type="button">Generate link</button>
|
||||
<button onclick="generateLink('markdown')" type="button">Generate markdown</button>
|
||||
<button onclick="generateLink('iframe')" type="button">Embed</button>
|
||||
</div>
|
||||
<div id="copy" style="display: none">
|
||||
<div id="progress"></div>
|
||||
<div id="editor"></div>
|
||||
<div id="copy" style="display: none;">
|
||||
<input
|
||||
type="text"
|
||||
value="copy me"
|
||||
|
|
|
|||
26
index.js
26
index.js
|
|
@ -19,7 +19,7 @@ const initCodeEditor = () => {
|
|||
lineNumbers: true,
|
||||
theme: 'dracula',
|
||||
readOnly: readOnly,
|
||||
scrollbarStyle: 'simple'
|
||||
scrollbarStyle: 'simple',
|
||||
});
|
||||
if (readOnly) {
|
||||
document.body.classList.add('readonly');
|
||||
|
|
@ -29,17 +29,17 @@ const initCodeEditor = () => {
|
|||
const initLangSelector = () => {
|
||||
select = new SlimSelect({
|
||||
select: '#language',
|
||||
data: CodeMirror.modeInfo.map(e => ({
|
||||
data: CodeMirror.modeInfo.map((e) => ({
|
||||
text: e.name,
|
||||
value: slugify(e.name),
|
||||
data: { mime: e.mime, mode: e.mode }
|
||||
data: { mime: e.mime, mode: e.mode },
|
||||
})),
|
||||
showContent: 'up',
|
||||
onChange: e => {
|
||||
showContent: 'down',
|
||||
onChange: (e) => {
|
||||
const language = e.data || { mime: null, mode: null };
|
||||
editor.setOption('mode', language.mime);
|
||||
CodeMirror.autoLoadMode(editor, language.mode);
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
select.set(decodeURIComponent(new URLSearchParams(window.location.search).get('lang') || 'plain-text'));
|
||||
|
|
@ -66,7 +66,7 @@ const initClipboard = () => {
|
|||
});
|
||||
};
|
||||
|
||||
const generateLink = mode => {
|
||||
const generateLink = (mode) => {
|
||||
compress(editor.getValue(), (base64, err) => {
|
||||
if (err) {
|
||||
alert('Failed to compress data: ' + err);
|
||||
|
|
@ -78,7 +78,7 @@ const generateLink = mode => {
|
|||
};
|
||||
|
||||
// Open the "Copy" bar and select the content
|
||||
const showCopyBar = dataToCopy => {
|
||||
const showCopyBar = (dataToCopy) => {
|
||||
const linkInput = document.getElementById('copy-link');
|
||||
linkInput.value = dataToCopy;
|
||||
linkInput.setSelectionRange(0, dataToCopy.length);
|
||||
|
|
@ -86,7 +86,7 @@ const showCopyBar = dataToCopy => {
|
|||
};
|
||||
|
||||
// Close the "Copy" bar
|
||||
const hideCopyBar = success => {
|
||||
const hideCopyBar = (success) => {
|
||||
const copyButton = document.getElementById('copy-btn');
|
||||
const copyBar = document.getElementById('copy');
|
||||
if (!success) {
|
||||
|
|
@ -124,14 +124,14 @@ const decompress = (base64, cb) => {
|
|||
const req = new XMLHttpRequest();
|
||||
req.open('GET', 'data:application/octet;base64,' + base64);
|
||||
req.responseType = 'arraybuffer';
|
||||
req.onload = e => {
|
||||
req.onload = (e) => {
|
||||
lzma.decompress(
|
||||
new Uint8Array(e.target.response),
|
||||
(result, err) => {
|
||||
progressBar.style.width = '0';
|
||||
cb(result, err);
|
||||
},
|
||||
progress => {
|
||||
(progress) => {
|
||||
progressBar.style.width = 100 * progress + '%';
|
||||
}
|
||||
);
|
||||
|
|
@ -159,13 +159,13 @@ const compress = (str, cb) => {
|
|||
};
|
||||
reader.readAsDataURL(new Blob([new Uint8Array(compressed)]));
|
||||
},
|
||||
progress => {
|
||||
(progress) => {
|
||||
progressBar.style.width = 100 * progress + '%';
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
const slugify = str =>
|
||||
const slugify = (str) =>
|
||||
str
|
||||
.toString()
|
||||
.toLowerCase()
|
||||
|
|
|
|||
52
style.css
52
style.css
|
|
@ -1,7 +1,7 @@
|
|||
/* App layout */
|
||||
|
||||
#editor,
|
||||
#footer,
|
||||
#controls,
|
||||
#copy,
|
||||
#progress {
|
||||
position: absolute;
|
||||
|
|
@ -10,11 +10,21 @@
|
|||
}
|
||||
|
||||
#editor {
|
||||
top: 0;
|
||||
bottom: 46px;
|
||||
top: 44px;
|
||||
bottom: 0;
|
||||
}
|
||||
.readonly #editor {
|
||||
bottom: 0;
|
||||
top: 0;
|
||||
}
|
||||
|
||||
#controls {
|
||||
box-shadow: rgba(0, 0, 0, 0.15) 0 3px 10px;
|
||||
}
|
||||
#controls .title {
|
||||
color: #fff;
|
||||
font-family: JetBrainsMono, sans-serif;
|
||||
font-size: 24px;
|
||||
line-height: 30px;
|
||||
}
|
||||
|
||||
.CodeMirror {
|
||||
|
|
@ -23,21 +33,22 @@
|
|||
font-family: JetBrainsMono, sans-serif;
|
||||
}
|
||||
|
||||
#footer,
|
||||
#controls,
|
||||
#copy {
|
||||
bottom: 0;
|
||||
height: 38px;
|
||||
top: 0;
|
||||
height: 36px;
|
||||
padding: 8px 8px 0;
|
||||
background-color: #3b3b47;
|
||||
display: flex;
|
||||
flex-wrap: wrap;
|
||||
z-index: 10;
|
||||
}
|
||||
#footer > *,
|
||||
#controls > *,
|
||||
#copy > * {
|
||||
margin: 0 6px;
|
||||
}
|
||||
|
||||
.readonly #footer {
|
||||
.readonly #controls {
|
||||
display: none;
|
||||
}
|
||||
|
||||
|
|
@ -59,10 +70,11 @@
|
|||
|
||||
/* Form elements */
|
||||
|
||||
.ss-main {
|
||||
max-width: 300px;
|
||||
#controls .ss-main {
|
||||
max-width: 230px;
|
||||
width: calc(100% - 150px);
|
||||
font-family: sans-serif;
|
||||
font-family: Roboto, sans-serif;
|
||||
margin-right: 30px;
|
||||
}
|
||||
|
||||
.ss-main .ss-single-selected,
|
||||
|
|
@ -75,12 +87,17 @@ input[type='search'] {
|
|||
border-radius: 2px !important;
|
||||
border: 1px solid #ccc !important;
|
||||
font-size: 14px !important;
|
||||
font-family: Roboto, sans-serif;
|
||||
}
|
||||
input[type='text'],
|
||||
input[type='search'] {
|
||||
height: 26px !important;
|
||||
padding: 0 5px;
|
||||
}
|
||||
|
||||
input::-webkit-search-cancel-button {
|
||||
display: none;
|
||||
}
|
||||
input::-moz-selection {
|
||||
background-color: rgba(90, 95, 128, 0.99);
|
||||
}
|
||||
|
|
@ -113,3 +130,14 @@ button:hover {
|
|||
font-weight: 400;
|
||||
font-style: normal;
|
||||
}
|
||||
|
||||
@font-face {
|
||||
font-family: 'Roboto';
|
||||
font-style: normal;
|
||||
font-weight: 400;
|
||||
font-display: swap;
|
||||
src: local('Roboto'), local('Roboto-Regular'),
|
||||
url(https://fonts.gstatic.com/s/roboto/v20/KFOmCnqEu92Fr1Mu4mxK.woff2) format('woff2');
|
||||
unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC,
|
||||
U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue