/*: * @target MZ * @plugindesc (v1.0) MPPステートアイコンを横並び表示し、ステート変化に応じてリアルタイム更新するパッチ(先頭アクター専用・アニメなし固定式) * @author * * @base BlockClearState * @base MPP_StateLevel * @orderAfter BlockClearState * @orderAfter MPP_StateLevel * * @help * ------------------------------------------------------------------------------ * ■ 前提 * ------------------------------------------------------------------------------ * - RPGツクールMZ * * ------------------------------------------------------------------------------ * ■ 概要 * ------------------------------------------------------------------------------ * - 先頭アクターのステートを横並び表示 * - アニメ切り替えなし(ABがあれば A と B を同時に表示) * - ステート付与/解除があったら即座に再配置(都度リフレッシュ) * - レベル数値表示はMPPの仕組みに従い、レベル1~などがそのまま描画 * - ツクール標準ステート描画は無効化 * * ------------------------------------------------------------------------------ */ (() => { "use strict"; const BaseX = 1300; // 初期値(お好みで変更) const BaseY = 920; // 初期値(お好みで変更) const SpacingX = 36; // アイコン間のスペース const SortById = true; // true ならステートID順, falseなら付与順 // ★ アニメではなく固定IDでアイコンを表示するSprite class Sprite_MppStateIconFixed extends Sprite_StateIcon { initialize() { super.initialize(); this._fixedStateId = 0; } setFixedStateId(stateId) { this._fixedStateId = stateId; this._iconIndex = 0; this._level = 0; } updateIcon() { // 特定ステートIDだけを表示(アニメ切り替えなし) if (!this._battler || !this._fixedStateId) { this._iconIndex = 0; this._level = 0; return; } const st = $dataStates[this._fixedStateId]; if (!st || !this._battler.isStateAffected(this._fixedStateId) || st.iconIndex <= 0) { this._iconIndex = 0; this._level = 0; return; } // アイコン番号 this._iconIndex = st.iconIndex; // MPPで拡張されたレベル値を取得 const idx = this._battler.displayedStates().indexOf(st); if (idx >= 0) { this._level = this._battler.allLevels()[idx] || 0; } else { this._level = 0; } } } // ステートを横並びに並べ、都度リフレッシュする管理スプライト class Sprite_MppIconRow extends Sprite { constructor() { super(); this._actor = null; this._stateIdList = []; } setup(actor) { this._actor = actor; } update() { super.update(); if (!this._actor) return; const states = this._actor.displayedStates(); if (!states || states.length === 0) { if (this._stateIdList.length > 0) { this.refresh([]); } return; } let sorted = states.slice(); if (SortById) { sorted.sort((a, b) => a.id - b.id); } const currentIds = sorted.map(st => st.id); if (!this.isDifferentList(currentIds, this._stateIdList)) { return; } this.refresh(currentIds); } refresh(stateIds) { this.removeChildren(); this._stateIdList = stateIds; let drawX = 0; for (const id of stateIds) { // ★ ここがポイント: Sprite_MppStateIconFixed を使って // 特定ステートIDに固定し、アニメしない const iconSprite = new Sprite_MppStateIconFixed(); iconSprite.setup(this._actor); iconSprite.setFixedStateId(id); iconSprite.x = drawX; iconSprite.y = 0; this.addChild(iconSprite); drawX += SpacingX; } } isDifferentList(listA, listB) { if (listA.length !== listB.length) return true; for (let i = 0; i < listA.length; i++) { if (listA[i] !== listB[i]) return true; } return false; } } // ツクール標準のステート表示を無効化 Sprite_Actor.prototype.createStateSprite = function() { // 空処理にして競合防止 }; // 永続ステートは表示しないように(元定義はMPP_StateLevel) const _Game_Actor_prototype_displayedStates = Game_Actor.prototype.displayedStates; Game_Actor.prototype.displayedStates = function() { return this.states() .filter(state => state.iconIndex > 0) .filter(state => !this.isStickyState(state.id)); }; // 対象ステートのレベル取得 Game_BattlerBase.prototype.stateLevel = function(stateId) { return this._stateLevels[stateId] ?? 0; }; const _Game_BattlerBase_prototype_eraseState = Game_BattlerBase.prototype.eraseState; Game_BattlerBase.prototype.eraseState = function(stateId) { _Game_BattlerBase_prototype_eraseState.apply(this, arguments); this._stateLevels[stateId] = undefined; this._stateMaxTurns[stateId] = undefined; }; })();