Skip to content

Instantly share code, notes, and snippets.

@whiteball
Last active June 24, 2023 17:27
Show Gist options
  • Select an option

  • Save whiteball/fb39e820addeaa8468762f5f29878868 to your computer and use it in GitHub Desktop.

Select an option

Save whiteball/fb39e820addeaa8468762f5f29878868 to your computer and use it in GitHub Desktop.
// ==UserScript==
// @name AIのべりすと スライダーをボタンに置き換え
// @namespace https://ai-novelist-share.geo.jp/
// @version 0.2.0
// @description AIのべりすとの詳細オプションにあるスライダーを、増減ボタンに変更できるようにする設定を追加します。設定は環境設定のその他にあります。
// @author しらたま
// @match https://ai-novel.com/novel.php
// @icon https://www.google.com/s2/favicons?sz=64&domain=ai-novel.com
// @updateURL https://gist.github.com/whiteball/fb39e820addeaa8468762f5f29878868/raw/ai_novelist_range2button.user.js
// @downloadURL https://gist.github.com/whiteball/fb39e820addeaa8468762f5f29878868/raw/ai_novelist_range2button.user.js
// @supportURL https://gist.github.com/whiteball/fb39e820addeaa8468762f5f29878868
// @grant none
// ==/UserScript==
/*
2023/06/24
スーパーとりんさま対応。
*/
(function() {
'use strict';
// 設定
if (localStorage.hasOwnProperty('mod_slider2button')) {
// 保存キー名を間違ってリリースしたので修正
localStorage.mod_range2button = localStorage.mod_slider2button
localStorage.removeItem('mod_slider2button')
}
const init = localStorage.mod_range2button ? localStorage.mod_range2button : '0'
document.head.insertAdjacentHTML('beforeend',`<style>
.mod_range2button_box {max-width:400px;}
.mod_range2button_box .btn-param {width: 2rem;height: 2rem;}
.mod_range2button_box span {display: inline-block;}
</style>`)
// 環境設定に選択肢を追加
const gui_disp_docinfo = document.getElementById('gui_disp_docinfo')
if (gui_disp_docinfo) {
gui_disp_docinfo.parentElement.insertAdjacentHTML('afterend', `<div style="margin-top:0.5rem" id="mod_range2button_area"><div style="font-size: 16px;" class="options_title">詳細オプションのUIの形状(ユーザースクリプト)</div>
<label><input type="radio" style="font-size: 18px; transform:scale(1.5);" id="mod_range2button_0" name="mod_range2button" value="0" ${init === '0' ? 'checked' : ''}> スライダー</label>
<label><input type="radio" style="font-size: 18px; transform:scale(1.5);margin-left:1.5rem;" id="mod_range2button_1" name="mod_range2button" value="1" ${init === '1' ? 'checked' : ''}> スライダー&ボタン</label>
<label><input type="radio" style="font-size: 18px; transform:scale(1.5);margin-left:1.5rem;" id="mod_range2button_2" name="mod_range2button" value="2" ${init === '2' ? 'checked' : ''}> ボタン</label>
</div>`)
for (const radio of document.querySelectorAll('#mod_range2button_area input[name="mod_range2button"]')) {
radio.addEventListener('change', function (event) {
changeShow(event.target.value)
if (/[0-2]/.test(event.target.value)) {
localStorage.mod_range2button = event.target.value
}
})
}
}
// ボタンUIを準備
for (const range of document.querySelectorAll('#optionsMenu input[type="range"]')) {
range.nextElementSibling.insertAdjacentHTML('afterend', `<div style="display:none;" class="mod_range2button_box">
<button id="${range.id}_dec2" class="btn-param">≪</button>
<button id="${range.id}_dec" class="btn-param" data-show="0"><</button>
<button id="${range.id}_inc" class="btn-param">></button>
<button id="${range.id}_inc2" class="btn-param">≫</button>
</div>`)
const dec = document.getElementById(range.id + '_dec')
dec.addEventListener('click', function () {
range.stepDown()
range.dispatchEvent(new Event('input'))
TempChange2()
})
const inc = document.getElementById(range.id + '_inc')
inc.addEventListener('click', function () {
range.stepUp()
range.dispatchEvent(new Event('input'))
TempChange2()
})
const dec2 = document.getElementById(range.id + '_dec2')
dec2.addEventListener('click', function () {
range.stepDown(5)
range.dispatchEvent(new Event('input'))
TempChange2()
})
const inc2 = document.getElementById(range.id + '_inc2')
inc2.addEventListener('click', function () {
range.stepUp(5)
range.dispatchEvent(new Event('input'))
TempChange2()
})
range.addEventListener('input', function () {
TempChange2()
})
}
const changeShow = function (value) {
if (value === '1') {
showButton(true)
} else if (value === '2') {
showButton(false)
} else {
hideButton()
}
}
const showButton = function (withSlider) {
for (const range of document.querySelectorAll('#optionsMenu input[type="range"]')) {
const dec = document.getElementById(range.id + '_dec')
if (dec.parentElement.nextElementSibling.tagName === 'BR') {
dec.parentElement.nextElementSibling.style.display = 'none'
}
if (dec.getAttribute('data-show') !== '1') {
const label = range.nextElementSibling
label.style.width = 'calc(100% - 10rem)'
label.style['text-align'] = 'center'
dec.insertAdjacentElement('afterend', label)
dec.setAttribute('data-show', '1')
}
if (range.previousElementSibling.style.display !== 'none') {
dec.parentElement.style.display = ''
} else {
dec.parentElement.style.display = 'none'
}
if (withSlider && range.previousElementSibling.style.display !== 'none') {
range.style.display = ''
} else {
range.style.display = 'none'
}
}
}
const hideButton = function () {
for (const range of document.querySelectorAll('#optionsMenu input[type="range"]')) {
const dec = document.getElementById(range.id + '_dec')
if (dec.parentElement.nextElementSibling.tagName === 'BR') {
dec.parentElement.nextElementSibling.style.display = ''
}
if (dec.getAttribute('data-show') !== '0') {
const label = dec.nextElementSibling
label.style.width = ''
label.style['text-align'] = ''
range.insertAdjacentElement('afterend', label)
dec.parentElement.style.display = 'none'
dec.setAttribute('data-show', '0')
}
if (range.previousElementSibling.style.display !== 'none') {
range.style.display = ''
} else {
range.style.display = 'none'
}
}
}
// 各パラメータが上限/下限のときに、その方向のボタンを非表示にする
const TempChange2 = function () {
for (const range of document.querySelectorAll('#optionsMenu input[type="range"]')) {
const dec = document.getElementById(range.id + '_dec'),
dec2 = document.getElementById(range.id + '_dec2')
if (dec && dec2) {
if (range.value === range.min) {
dec.style.visibility = 'hidden'
dec2.style.visibility = 'hidden'
} else {
dec.style.visibility = ''
dec2.style.visibility = ''
}
}
const inc = document.getElementById(range.id + '_inc'),
inc2 = document.getElementById(range.id + '_inc2')
if (inc && inc2) {
if (range.value === range.max) {
inc.style.visibility = 'hidden'
inc2.style.visibility = 'hidden'
} else {
inc.style.visibility = ''
inc2.style.visibility = ''
}
}
}
}
// TempChangeが変数であるためオーバーライドできないので、TempChangeが呼ばれた後に呼ばれる関数をオーバーライドする
const originalChangePreset = window.ChangePreset
window.ChangePreset = function (data) {
originalChangePreset(data)
TempChange2()
}
const originalChangeAutoSum = window.ChangeAutoSum
window.ChangeAutoSum = function (data) {
originalChangeAutoSum(data)
TempChange2()
}
const originalLoadScriptsFromStorage = window.LoadScriptsFromStorage
window.LoadScriptsFromStorage = function () {
originalLoadScriptsFromStorage()
TempChange2()
}
// OnLoadイベントへの追加が間に合わないので、オプション表示前に必ず呼ばれる関数をオーバーライドする
const originalToggleOptions = window.ToggleOptions
window.ToggleOptions = function (id, dontclose = false) {
originalToggleOptions(id, dontclose)
TempChange2()
}
//モデル変更でスライドの有無が変わるので監視
const model_options = document.getElementById('model-options')
if (model_options) {
model_options.addEventListener('input', function () {
setTimeout(function () {
changeShow(localStorage.mod_range2button ? localStorage.mod_range2button : '0')
}, 500)
})
}
//初期値反映
changeShow(init)
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment