show config for usercss vars in installer (#1302)

* simplify messageBox code
* also bind events correctly in case messageBox is called when a messageBox was already shown
This commit is contained in:
tophf 2021-08-12 14:40:03 +03:00 committed by GitHub
parent 91324a4a48
commit 50717465b9
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 77 additions and 44 deletions

View File

@ -35,6 +35,9 @@
<div class="actions">
<h2 class="installed" i18n-text="installButtonInstalled"></h2>
<button class="install" i18n-text="installButton"></button>
<a class="configure-usercss" i18n-title="configureStyle" tabindex="0">
<svg class="svg-icon config"><use xlink:href="#svg-icon-config"></use></svg>
</a>
<p id="live-reload-install-hint" hidden></p>
<label class="set-update-url">
<input type="checkbox">
@ -74,6 +77,12 @@
<symbol id="svg-icon-checked" viewBox="0 0 1000 1000">
<path fill-rule="evenodd" d="M983.2,184.3L853,69.8c-4-3.5-9.3-5.3-14.5-5c-5.3,0.4-10.3,2.8-13.8,6.8L352.3,609.2L184.4,386.9c-3.2-4.2-8-7-13.2-7.8c-5.3-0.8-10.6,0.6-14.9,3.9L18,487.5c-8.8,6.7-10.6,19.3-3.9,28.1L325,927.2c3.6,4.8,9.3,7.7,15.3,8c0.2,0,0.5,0,0.7,0c5.8,0,11.3-2.5,15.1-6.8L985,212.6C992.3,204.3,991.5,191.6,983.2,184.3z"/>
</symbol>
<symbol id="svg-icon-select-arrow" viewBox="0 0 1792 1792">
<path fill-rule="evenodd" d="M1408 704q0 26-19 45l-448 448q-19 19-45 19t-45-19l-448-448q-19-19-19-45t19-45 45-19h896q26 0 45 19t19 45z"/>
</symbol>
<symbol id="svg-icon-config" viewBox="0 0 16 16">
<path d="M13.3,12.8l1.5-2.6l-2.2-1.5c0-0.2,0.1-0.5,0.1-0.7c0-0.2,0-0.5-0.1-0.7l2.2-1.5l-1.5-2.6l-2.4,1.2 c-0.4-0.3-0.8-0.5-1.2-0.7L9.5,1h-3L6.3,3.7C5.9,3.8,5.5,4.1,5.1,4.4L2.7,3.2L1.2,5.8l2.2,1.5c0,0.2-0.1,0.5-0.1,0.7 c0,0.2,0,0.5,0.1,0.7l-2.2,1.5l1.5,2.6l2.4-1.2c0.4,0.3,0.8,0.5,1.2,0.7L6.5,15h3l0.2-2.7c0.4-0.2,0.8-0.4,1.2-0.7L13.3,12.8z M8,10.3c-1.3,0-2.3-1-2.3-2.3c0-1.3,1-2.3,2.3-2.3c1.3,0,2.3,1,2.3,2.3C10.3,9.3,9.3,10.3,8,10.3z"/>
</symbol>
</svg>
<script src="js/dlg/message-box.js"></script>

View File

@ -305,6 +305,20 @@ label {
animation: none;
}
.configure-usercss .svg-icon.config {
width: 20px;
height: 20px;
margin-top: -3px;
}
#message-box.config-dialog {
width: 0;
height: 0;
background: none;
}
#message-box.config-dialog > div {
box-shadow: 5px 5px 50px rgba(0, 0, 0, 0.75); /* copied from message-box.css + darkened the color */
}
/************ reponsive layouts ************/
@media (max-width: 850px) {
@ -417,6 +431,10 @@ label {
flex-shrink: 0;
margin-right: 1em;
}
#message-box.config-dialog > div {
top: auto;
bottom: 3rem;
}
}
/* Retina-specific stuff here */

View File

@ -1,6 +1,6 @@
/* global $ $create $createLink $$remove */
/* global $ $create $createLink $$remove showSpinner */// dom.js
/* global API */// msg.js
/* global closeCurrentTab */// toolbox.js
/* global closeCurrentTab deepEqual */// toolbox.js
/* global messageBox */
/* global prefs */
/* global preinit */
@ -13,20 +13,16 @@ let installed;
let installedDup;
let liveReload;
let tabId;
let vars;
// "History back" in Firefox (for now) restores the old DOM including the messagebox,
// which stays after installing since we don't want to wait for the fadeout animation before resolving.
document.on('visibilitychange', () => {
if (messageBox.element) messageBox.element.remove();
$$remove('#message-box:not(.config-dialog)');
if (installed) liveReload.onToggled();
});
setTimeout(() => {
if (!cm) {
$('#header').appendChild($create('.lds-spinner',
new Array(12).fill($create('div')).map(e => e.cloneNode())));
}
}, 200);
setTimeout(() => !cm && showSpinner($('#header')), 200);
/*
* Preinit starts to download as early as possible,
@ -187,11 +183,29 @@ function updateMeta(style, dup = installedDup) {
$('.external-link').appendChild(externalLink);
}
Object.assign($('.configure-usercss'), {
hidden: !data.vars,
onclick: openConfigDialog,
});
if (!data.vars) {
$$remove('#message-box.config-dialog');
} else if (!deepEqual(data.vars, vars)) {
vars = data.vars;
// Use the user-customized vars from the installed style
for (const [dk, dv] of Object.entries(dup && dupData.vars || {})) {
const v = vars[dk];
if (v && v.type === dv.type) {
v.value = dv.value;
}
}
openConfigDialog();
}
$('#header').dataset.arrivedFast = performance.now() < 500;
$('#header').classList.add('meta-init');
$('#header').classList.remove('meta-init-error');
setTimeout(() => $$remove('.lds-spinner'), 1000);
setTimeout(() => $$remove('.lds-spinner'), 1000);
showError('');
requestAnimationFrame(adjustCodeHeight);
@ -233,6 +247,11 @@ function updateMeta(style, dup = installedDup) {
)),
]));
}
async function openConfigDialog() {
await require(['/js/dlg/config-dialog']); /* global configDialog */
configDialog(style);
}
}
function showError(err) {

View File

@ -2,12 +2,12 @@
--onoffswitch-width: 60px;
}
#stylus-manage .config-dialog #message-box-contents {
padding: 2em 16px;
.config-dialog {
--pad: 16px;
}
#stylus-popup .config-dialog #message-box-contents {
padding: 8px 16px;
.config-dialog #message-box-contents {
padding: var(--pad);
}
#stylus-popup .config-dialog > div {
@ -33,7 +33,7 @@
display: flex;
padding: .75em 0;
align-items: center;
margin-right: -16px; /* for .config-reset-icon */
margin-right: calc(-1 * var(--pad)); /* for .config-reset-icon */
}
.config-body .select-resizer {
@ -120,14 +120,14 @@
}
.config-reset-icon {
height: 16px;
height: var(--pad);
}
.config-reset-icon .svg-icon {
cursor: pointer;
fill: #aaa;
width: 16px;
height: 16px;
width: var(--pad);
height: var(--pad);
padding: 0 1px;
box-sizing: border-box;
flex-shrink: 0;
@ -139,7 +139,7 @@
#config-autosave-wrapper {
position: relative;
padding: 0 0 0 16px;
padding: 0 0 0 var(--pad);
display: inline-flex;
}

View File

@ -28,8 +28,9 @@ async function configDialog(style) {
let varsInitial = getInitialValues(varsHash);
const elements = [];
const colorpicker = window.colorpicker();
const isPopup = location.href.includes('popup.html');
const isInstaller = location.pathname.startsWith('/install-usercss.html');
const isPopup = location.pathname.startsWith('/popup.html');
const colorpicker = ((window.CodeMirror || {}).prototype || window).colorpicker();
const buttons = {};
buildConfigForm();
@ -122,7 +123,7 @@ async function configDialog(style) {
buttons.close.textContent = t(someDirty ? 'confirmCancel' : 'confirmClose');
}
async function save({anyChangeIsDirty = false} = {}, bgStyle) {
async function save({anyChangeIsDirty = false} = {}) {
for (let delay = 1; saving && delay < 1000; delay *= 2) {
await new Promise(resolve => setTimeout(resolve, delay));
}
@ -132,15 +133,13 @@ async function configDialog(style) {
if (!vars.some(va => va.dirty || anyChangeIsDirty && va.value !== va.savedValue)) {
return;
}
if (!bgStyle) {
bgStyle = await API.styles.get(style.id).catch(() => ({}));
}
const bgStyle = !isInstaller && await API.styles.get(style.id).catch(() => ({}));
style = style.sections ? Object.assign({}, style) : style;
style.enabled = true;
style.sourceCode = null;
style.sections = null;
const styleVars = style.usercssData.vars;
const bgVars = (bgStyle.usercssData || {}).vars || {};
const bgVars = isInstaller ? styleVars : (bgStyle.usercssData || {}).vars || {};
const invalid = [];
let numValid = 0;
for (const va of vars) {
@ -184,7 +183,7 @@ async function configDialog(style) {
}
saving = true;
try {
const newVars = await API.usercss.configVars(style.id, style.usercssData.vars);
const newVars = isInstaller ? styleVars : await API.usercss.configVars(style.id, styleVars);
varsInitial = getInitialValues(newVars);
vars.forEach(va => onchange({target: va.input, justSaved: true}));
renderValues();

View File

@ -40,10 +40,9 @@ messageBox.show = async ({
}) => {
await require(['/js/dlg/message-box.css']);
if (!messageBox.listeners) initOwnListeners();
bindGlobalListeners();
createElement();
bindGlobalListeners();
document.body.appendChild(messageBox.element);
bindElementLiseners();
messageBox._originalFocus = document.activeElement;
// focus the first focusable child but skip the first external link which is usually `feedback`
@ -132,15 +131,9 @@ messageBox.show = async ({
listening = false;
},
mouseMove(event) {
const x = clamp(event.clientX, 30, innerWidth - 30) - clickX;
const y = clamp(event.clientY, 30, innerHeight - 30) - clickY;
offsetX = x;
offsetY = y;
$('#message-box > div').style.transform =
`translateX(${x}px)
translateY(${y}px)`;
offsetX = clamp(event.clientX, 30, innerWidth - 30) - clickX;
offsetY = clamp(event.clientY, 30, innerHeight - 30) - clickY;
messageBox.element.firstChild.style.transform = `translate(${offsetX}px,${offsetY}px)`;
},
};
}
@ -164,7 +157,7 @@ messageBox.show = async ({
messageBox.element =
$create({id, className}, [
$create([
$create(`#${id}-title`, title),
$create(`#${id}-title`, {onmousedown: messageBox.listeners.mouseDown}, title),
$create(`#${id}-close-icon`, {onclick: messageBox.listeners.closeIcon},
$create('SVG:svg.svg-icon', {viewBox: '0 0 20 20'},
$create('SVG:path', {d: 'M11.69,10l4.55,4.55-1.69,1.69L10,11.69,' +
@ -191,16 +184,11 @@ messageBox.show = async ({
window.on('keydown', messageBox.listeners.key, true);
}
function bindElementLiseners() {
$('#message-box-title').on('mousedown', messageBox.listeners.mouseDown, {passive: true});
}
function unbindGlobalListeners() {
window.off('keydown', messageBox.listeners.key, true);
window.off('scroll', messageBox.listeners.scroll);
window.off('mouseup', messageBox.listeners.mouseUp);
window.off('mousemove', messageBox.listeners.mouseMove);
$('#message-box-title').off('mousedown', messageBox.listeners.mouseDown);
}
function removeSelf() {