nwtgck
アカウントたち
※ここでの投稿は個人の意見であり所属先の公式見解ではありません。
UserScript
script.js/*
scrapbox.PopupMenu.addButton({
title: '適当タイトル',
onClick: (text) => {
const bracketRemoved = text.replace(/(^\[)|(\]$)/g, '');
return bracketRemoved;
}
});
*/
選択領域を #タグ
にする。
script.jsscrapbox.PopupMenu.addButton({
title: '#Tag',
onClick: (text) => {
return '#' + text.replace(/ /g, '_');
}
});
script.jssetTimeout(() => {
// チェックボックスとして使用する文字のリスト
// const checkBoxList = ['⬜', '☑️'];
const checkBoxList = ['⬜', '✅'];
// const checkBoxList = ['🔲', '☑️'];
const textArea = document.getElementById('text-input');
const keydownEvent = {
event: document.createEvent('Event'),
dispatch: function(keycode, withShift = false, withCommand = false) {
this.event.keyCode = keycode;
this.event.shiftKey = withShift;
this.event.metaKey = withCommand;
textArea.dispatchEvent(this.event);
}
};
keydownEvent.event.initEvent('keydown', true, true);
const inputEvent = {
event: document.createEvent('Event'),
dispatch: function(string) {
textArea.value = string;
textArea.dispatchEvent(this.event);
}
};
inputEvent.event.initEvent('input', true, true);
const isBoxCharSpan = (element) => {
if (element.tagName !== 'SPAN') return false;
const boxReg = new RegExp(`^(${checkBoxList.join('|')})$`);
for (const className of element.classList) {
if (/^c\-\d+$/.test(className)) {
return boxReg.test(element.textContent);
}
}
return false;
};
const startsWithBoxReg = new RegExp('^\\s*(' + checkBoxList.join('|') + ')');
// ボックスクリックでオンオフする
$('#app-container').off('click.toggleCheckBox', '.lines');
$('#app-container').on('click.toggleCheckBox', '.lines', event => {
const target = event.target;
if (!isFirstElementChild(target)||!isBoxCharSpan(target)) return;
setTimeout(() => {
let lineString;
try {
lineString = getCursorLineString();
} catch (err) {
console.log(err);
return;
}
if (!startsWithBoxReg.test(lineString)) return;
const targetX = target.getBoundingClientRect().left;
const cursorX = document.getElementsByClassName('cursor')[0].getBoundingClientRect().left;
if (cursorX <= targetX) {
keydownEvent.dispatch(39); // →
}
keydownEvent.dispatch(8); // Backspace
const newBox = (() => {
const trimmedLineString = lineString.trim();
for (let i = 0; i < checkBoxList.length; i++) {
if (trimmedLineString.startsWith(checkBoxList[i])) {
if (i + 1 < checkBoxList.length) {
return checkBoxList[i + 1];
} else {
return checkBoxList[0];
}
}
}
return checkBoxList[0];
})();
inputEvent.dispatch(newBox);
// この下のコメントアウトを解除すると、checked時に取消線を入れて時刻を追記します
// Mac、Porterでのみ動作します
/*
if (/Mobile/.test(navigator.userAgent) || newBox === checkBoxList[0]) return;
setTimeout(() => {
keydownEvent.dispatch(39, true, true); // shift + command + →
inputEvent.dispatch('-');
keydownEvent.dispatch(39, false, true); // command + →
const now = moment().format('HH:mm');
inputEvent.dispatch(` ${now}`);
}, 50);
*/
}, 50);
});
// ボックス行で改行すると次行にボックス自動挿入
$('#text-input').off('keydown.autoInsertCheckBox');
$('#text-input').on('keydown.autoInsertCheckBox', event => {
switch (event.key) {
case 'Enter': {
let lineString;
try {
lineString = getCursorLineString();
} catch (err) {
console.log(err);
return;
}
if (!startsWithBoxReg.test(lineString)) return;
setTimeout(() => {
let lineString;
try {
lineString = getCursorLineString();
} catch (err) {
console.log(err);
return;
}
if (!startsWithBoxReg.test(lineString)) {
inputEvent.dispatch(checkBoxList[0]);
}
}, 50);
return;
}
default: {
return;
}
}
});
function isFirstElementChild(element) {
return element.parentNode.firstElementChild === element;
}
function getCursorLineString() {
return document.querySelector('.lines div.line.cursor-line').textContent;
}
}, 1500);