//============================================================================= // NRP_OptionCustomize.js //============================================================================= /*: * @target MZ * @plugindesc v1.001 Customize the display of the options scene. * @author Takeshi Sunagawa (http://newrpg.seesaa.net/) * @url https://newrpg.seesaa.net/article/502777639.html * * @help Customize the display of the options scene. * * ◆Main functions * - Insert a separator. * - Change window width. * - Change the number of items displayed. * - Change the amount of volume increase/decrease. (Default:20) * * ------------------------------------------------------------------- * [Notice] * ------------------------------------------------------------------- * Separators are also counted internally as items. * Note that if multiple separators are inserted, * the other separators will also affect the insertion position. * * In the list of plugins, * it would be better to place them below the plugins * that add items to the options to reduce the effect of conflicts. * * ------------------------------------------------------------------- * [Terms] * ------------------------------------------------------------------- * There are no restrictions. * Modification, redistribution freedom, commercial availability, * and rights indication are also optional. * The author is not responsible, * but will deal with defects to the extent possible. * * @------------------------------------------------------------------ * @ [Plugin Parameters] * @------------------------------------------------------------------ * * @param SeparateList * @type struct[] * @desc Defines a separator. * * @param SeparateCenter * @type boolean * @default false * @desc Center the separator. * * @param MaxVisibleCommands * @type number * @desc The number of optional commands to be displayed in the window. Default value is 12 * * @param WindowWidth * @type number * @desc Width of the options window. * Default value is 400. * * @param WindowBackgroundType * @type select * @option Normal @value 0 * @option Dimmer @value 1 * @option Transparency @value 2 * @default 0 * @desc The background of the options window. * * @param VolumeOffset * @type number @min 1 @max 100 @decimals 2 * @desc The amount by which the volume item is to be increased or decreased at one time. Default is 20. * * @param MagnifiedVolume * @type number @min 1 @max 100 * @desc Multiply the volume display only; at 5, 100% will be displayed as 500%. */ /*~struct~Separate: * @param SeparateText * @type string * @desc The content to be displayed as a separator. Control characters are also valid. (e.g.: \c[1]Separate) * * @param Position * @type number * @default 0 * @desc The position at which the separator is to be inserted. * Set 0 as the beginning. */ /*:ja * @target MZ * @plugindesc v1.001 オプション画面の表示をカスタマイズ * @author 砂川赳(http://newrpg.seesaa.net/) * @url https://newrpg.seesaa.net/article/502777639.html * * @help オプション画面の表示をカスタマイズします。 * * ◆主な機能 * ・区切りを挿入 * ・ウィンドウのサイズを変更 * ・表示項目数を変更 * ・音量の増減量(標準は20)を変更 * * ------------------------------------------------------------------- * ■注意点 * ------------------------------------------------------------------- * 区切りも内部的には項目としてカウントされます。 * 複数の区切りを挿入した場合は、 * 他の区切りも挿入位置に影響するのでご注意ください。 * * プラグイン一覧では、オプションに項目を追加するプラグインよりも、 * 下に配置したほうが競合の影響を抑えられると思います。 * * ------------------------------------------------------------------- * ■利用規約 * ------------------------------------------------------------------- * 特に制約はありません。 * 改変、再配布自由、商用可、権利表示も任意です。 * 作者は責任を負いませんが、不具合については可能な範囲で対応します。 * * @------------------------------------------------------------------ * @ プラグインパラメータ * @------------------------------------------------------------------ * * @param SeparateList * @text 区切りリスト * @type struct[] * @desc 区切りを定義します。 * * @param SeparateCenter * @text 区切りを中央寄せ * @type boolean * @default false * @desc 区切りを中央寄せします。 * * @param MaxVisibleCommands * @text 表示項目数 * @type number * @desc ウィンドウ内に表示するオプションのコマンド数です。 * 初期値は12 * * @param WindowWidth * @text ウィンドウの横幅 * @type number * @desc オプションウィンドウの横幅です。 * 初期値は400 * * @param WindowBackgroundType * @text ウィンドウ背景 * @type select * @option 0:ウィンドウ @value 0 * @option 1:暗くする @value 1 * @option 2:透明 @value 2 * @default 0 * @desc オプションウィンドウの背景です。 * * @param VolumeOffset * @text 音量の増減量 * @type number @min 1 @max 100 @decimals 2 * @desc 音量項目を一度に増減させる量です。デフォルトは20です。 * * @param MagnifiedVolume * @text 音量表示を倍増 * @type number @min 1 @max 100 * @desc 音量の表示だけを倍増させます。5にすると100%が500%として表示されるようになります。 */ /*~struct~Separate:ja * @param SeparateText * @text 区切りの文字 * @type string * @desc 区切りとして表示する内容です。 * 制御文字も有効です。(例:\c[1]区切り) * * @param Position * @text 挿入位置 * @type number * @default 0 * @desc 区切りを挿入する位置です。 * 0を先頭として設定してください。 */ (function() { "use strict"; /** * ●構造体(二重配列)をJSで扱えるように変換 */ function parseStruct2(arg) { const ret = []; if (arg) { for (const str of JSON.parse(arg)) { ret.push(JSON.parse(str)); } } return ret; } function toBoolean(str, def) { if (str === true || str === "true") { return true; } else if (str === false || str === "false") { return false; } return def; } function toNumber(str, def) { if (str == undefined || str == "") { return def; } return isNaN(str) ? def : +(str || def); } function setDefault(str, def) { if (str == undefined || str == "") { return def; } return str; } const PLUGIN_NAME = "NRP_OptionCustomize"; const parameters = PluginManager.parameters(PLUGIN_NAME); const pSeparateList = parseStruct2(parameters["SeparateList"]); const pSeparateCenter = toBoolean(parameters["SeparateCenter"], false); const pMaxVisibleCommands = toNumber(parameters["MaxVisibleCommands"]); const pWindowWidth = toNumber(parameters["WindowWidth"]); const pWindowBackgroundType = toNumber(parameters["WindowBackgroundType"], 0); const pVolumeOffset = toNumber(parameters["VolumeOffset"]); const pMagnifiedVolume = toNumber(parameters["MagnifiedVolume"]); // 区切り識別用のキー const SYMBOL_SEPARATE = "separate"; //----------------------------------------------------------------------------- // Scene_Options //----------------------------------------------------------------------------- if (pWindowWidth) { /** * ●オプションウィンドウの表示領域 */ const _Scene_Options_optionsWindowRect = Scene_Options.prototype.optionsWindowRect; Scene_Options.prototype.optionsWindowRect = function() { const ret = _Scene_Options_optionsWindowRect.apply(this, arguments); ret.width = pWindowWidth; ret.x = (Graphics.boxWidth - ret.width) / 2; return ret; }; } /** * ●コマンド数を設定 */ const _Scene_Options_maxCommands = Scene_Options.prototype.maxCommands; Scene_Options.prototype.maxCommands = function() { // 表示項目数の指定があれば優先 if (pMaxVisibleCommands) { return pMaxVisibleCommands; } // 追加した区切りの数を加算 let count = 0; if (pSeparateList) { count += pSeparateList.length; } return _Scene_Options_maxCommands.apply(this, arguments) + count; }; /** * ●最大表示数を設定 */ const _Scene_Options_maxVisibleCommands = Scene_Options.prototype.maxVisibleCommands; Scene_Options.prototype.maxVisibleCommands = function() { // 表示項目数の指定があれば優先 if (pMaxVisibleCommands) { return pMaxVisibleCommands; } return _Scene_Options_maxVisibleCommands.apply(this, arguments); }; //----------------------------------------------------------------------------- // Window_Options //----------------------------------------------------------------------------- const _Window_Options_initialize = Window_Options.prototype.initialize; Window_Options.prototype.initialize = function(rect) { _Window_Options_initialize.apply(this, arguments); const symbol = this.commandSymbol(this.index()); // 区切りの場合は次の行を設定 if (this.isSeparateSymbol(symbol)) { this.smoothSelect(this._index + 1); } // ウィンドウの背景を変更。 this.setBackgroundType(pWindowBackgroundType); }; /** * ●コマンドの生成 */ const _Window_Options_makeCommandList = Window_Options.prototype.makeCommandList; Window_Options.prototype.makeCommandList = function() { _Window_Options_makeCommandList.apply(this, arguments); // 区切りを追加 for (const separate of pSeparateList) { this._list.splice(separate.Position, 0, { name: separate.SeparateText, symbol: SYMBOL_SEPARATE, enabled: true, ext: null}); } }; /** * 【独自】シンボルが区切りかどうか? */ Window_Options.prototype.isSeparateSymbol = function(symbol) { return symbol == SYMBOL_SEPARATE; }; const _Window_Options_statusText = Window_Options.prototype.statusText; Window_Options.prototype.statusText = function(index) { const symbol = this.commandSymbol(index); // 区切りの場合は空白 if (this.isSeparateSymbol(symbol)) { return ""; } return _Window_Options_statusText.apply(this, arguments); }; const _Window_Options_drawItem = Window_Options.prototype.drawItem; Window_Options.prototype.drawItem = function(index) { const symbol = this.commandSymbol(index); // 区切りの場合 if (this.isSeparateSymbol(symbol)) { const title = this.commandName(index); const rect = this.itemLineRect(index); this.resetTextColor(); this.changePaintOpacity(this.isCommandEnabled(index)); let x = rect.x; // 中央寄せの場合はX座標を調整 if (pSeparateCenter) { const textWidth = this.textSizeEx(title).width; x += (rect.width - textWidth) / 2; } // drawTextExによってタイトルを描画(制御文字を使用可能に) this.drawTextEx(title, x, rect.y, rect.width); return; } _Window_Options_drawItem.apply(this, arguments); }; const _Window_Options_processOk = Window_Options.prototype.processOk; Window_Options.prototype.processOk = function() { const symbol = this.commandSymbol(this.index()); // 区切りの場合は何もしない if (this.isSeparateSymbol(symbol)) { return; } _Window_Options_processOk.apply(this, arguments); }; const _Window_Options_cursorRight = Window_Options.prototype.cursorRight; Window_Options.prototype.cursorRight = function() { const symbol = this.commandSymbol(this.index()); // 区切りの場合は何もしない if (this.isSeparateSymbol(symbol)) { return; } _Window_Options_cursorRight.apply(this, arguments); }; const _Window_Options_cursorLeft = Window_Options.prototype.cursorLeft; Window_Options.prototype.cursorLeft = function() { const symbol = this.commandSymbol(this.index()); // 区切りの場合は何もしない if (this.isSeparateSymbol(symbol)) { return; } _Window_Options_cursorLeft.apply(this, arguments); }; /* * メソッドが未定義の場合は事前に定義 * ※これをしておかないと以後の親クラスへの追記が反映されない。 */ if (Window_Options.prototype.cursorDown == Window_Selectable.prototype.cursorDown) { Window_Options.prototype.cursorDown = function(wrap) { return Window_Selectable.prototype.cursorDown.apply(this, arguments); } } if (Window_Options.prototype.cursorUp == Window_Selectable.prototype.cursorUp) { Window_Options.prototype.cursorUp = function(wrap) { return Window_Selectable.prototype.cursorUp.apply(this, arguments); } } const _Window_Options_cursorDown = Window_Options.prototype.cursorDown; Window_Options.prototype.cursorDown = function(wrap) { const keepIndex = this.index(); _Window_Options_cursorDown.apply(this, arguments); const symbol = this.commandSymbol(this.index()); // 区切りの場合はスルーして次へ if (this.isSeparateSymbol(symbol)) { // 先頭の場合はスクロールも先頭に。 // ※下からループしてきた場合を想定 if (this.index() == 0) { this.scrollTo(this._scrollX, 0); } let index = this.index() + 1; // 一番下へ到達した場合はループ if (index >= this._list.length) { // 端で停止する場合はインデックスを戻す。 if (!wrap) { this.smoothSelect(keepIndex); return; } index = 0; } this.smoothSelect(index); return; } }; const _Window_Options_cursorUp = Window_Options.prototype.cursorUp; Window_Options.prototype.cursorUp = function(wrap) { const keepIndex = this.index(); _Window_Options_cursorUp.apply(this, arguments); const symbol = this.commandSymbol(this.index()); // 区切りの場合はスルーして前へ if (this.isSeparateSymbol(symbol)) { let index = this.index() - 1; // 一番上へ到達した場合はループ if (index < 0) { // 端で停止する場合はインデックスを戻す。 if (!wrap) { this.smoothSelect(keepIndex); return; } index = this._list.length - 1; } this.smoothSelect(index); return; } }; /* * メソッドが未定義の場合は事前に定義 * ※これをしておかないと以後の親クラスへの追記が反映されない。 */ if (Window_Options.prototype.drawItemBackground == Window_Selectable.prototype.drawItemBackground) { Window_Options.prototype.drawItemBackground = function(index) { return Window_Selectable.prototype.drawItemBackground.apply(this, arguments); } } /** * ●黒背景の描画 */ const _Window_Options_drawItemBackground = Window_Options.prototype.drawItemBackground; Window_Options.prototype.drawItemBackground = function(index) { const symbol = this.commandSymbol(index); // 区切りの場合は無視 if (this.isSeparateSymbol(symbol)) { return; } _Window_Options_drawItemBackground.apply(this, arguments); }; /* * メソッドが未定義の場合は事前に定義 * ※これをしておかないと以後の親クラスへの追記が反映されない。 */ if (Window_Options.prototype.refreshCursor == Window_Selectable.prototype.refreshCursor) { Window_Options.prototype.refreshCursor = function() { return Window_Selectable.prototype.refreshCursor.apply(this, arguments); } } /** * ●選択行のカーソル更新 */ const _Window_Options_refreshCursor = Window_Options.prototype.refreshCursor; Window_Options.prototype.refreshCursor = function() { if (this.index() >= 0) { const symbol = this.commandSymbol(this.index()); // 区切りの場合はクリア if (this.isSeparateSymbol(symbol)) { this.setCursorRect(0, 0, 0, 0); return; } } _Window_Options_refreshCursor.apply(this, arguments); }; if (pVolumeOffset) { /** * 【上書】音量の増減単位 */ Window_Options.prototype.volumeOffset = function() { return pVolumeOffset; }; } if (pMagnifiedVolume) { /** * 【上書】音量表示の倍増 */ Window_Options.prototype.volumeStatusText = function(value) { return value * pMagnifiedVolume + "%"; }; } })();