DoubleX RMMV Confusion Edit
#1
DoubleX RMMV Confusion Edit

Version: v1.00e

Introduction

* Lets you set some states to reverse the ally/foe identification

Prerequisites

* Little Javascript coding proficiency to fully utilize this plugin

Script

Code:
/*============================================================================
*    ## Plugin Info
*----------------------------------------------------------------------------
*    # Plugin Name
*      DoubleX RMMV Confusion Edit
*----------------------------------------------------------------------------
*    # Terms Of Use
*      You shall keep this plugin's Plugin Info part's contents intact
*      You shalln't claim that this plugin's written by anyone other than
*      DoubleX or his aliases
*      None of the above applies to DoubleX or his aliases
*----------------------------------------------------------------------------
*    # Prerequisites
*      Abilities:
*      1. Little Javascript coding proficiency to fully utilize this plugin
*----------------------------------------------------------------------------
*    # Links
*      This plugin:
*      1. http://pastebin.com/LX7qJ74P
*      Video:
*      1. https://www.youtube.com/watch?v=NCVMdR7HFls
*      Mentioned Patreon Supporters:
*      https://www.patreon.com/posts/71738797
*----------------------------------------------------------------------------
*    # Author
*      DoubleX
*----------------------------------------------------------------------------
*    # Changelog
*      v1.00e(GMT 1100 9-9-2022):
*      1. Fixed infinite loop in targetsForReversedExcludeSelf due to typo
*      v1.00d(GMT 0200 6-6-2020):
*      1. Fixed actions having no targets not executing bug
*      v1.00c(GMT 0300 9-3-2020):
*      1. Fixed undefined subject in hasValidOriginalTargets
*      v1.00b(GMT 0800 30-1-2016):
*      1. Fixed missing return in targetsForOpponents and targetsForFriends
*      2. Fixed undefined target in targetsForReversedExcludeSelf due to typo
*      3. Fixed infinite loop with excludeSelf when subject's always selected
*      v1.00a(GMT 0800 3-1-2016):
*      1. 1st version of this plugin finished
*============================================================================*/
/*:
* @plugindesc Lets you set some states to reverse the ally/foe identification
* @author DoubleX
*
* @help
*============================================================================
*    ## Notetag Info
*----------------------------------------------------------------------------
*    # State Notetags:
*      1. <confusion edit: reverse, excludeSelf>
*         - Sets the confusion state to reverse the ally/foe identification
*           only instead of restricting the battler to be merely using the
*           1st skill in the database if reverse is true and the actions
*           aren't forced
*         - Reversal will never take place for state Restriction as Attack an
*           Enemy nor skill/item scope as The User
*         - Reversal will have 50% chance to take place for state Restriction
*           as Attack Anyone
*         - Reversal will always take place for state Restriction as Attack
*           an Ally
*         - Sets the confusion state to make the battler never targeting self
*           if excludeSelf is true and the actions aren't forced
*         - Only the effective notetag with the highest priority will be used
*============================================================================
*    ## Plugin Call Info
*----------------------------------------------------------------------------
*    # State manipulations
*      1. meta.confusionEdit
*         - Returns the confusion edit reverse and excludeSelf flag in the
*           form of { reverse: reverse, excludeSelf: excludeSelf }
*      2. meta.confusionEdit = { reverse: reverse, excludeSelf: excludeSelf }
*         - Sets the confusion edit reverse and excludeSelf flag in the form
*           of { reverse: reverse, excludeSelf: excludeSelf }
*         - All meta.confusionEdit changes can be saved if
*           DoubleX RMMV Dynamic Data is used
*============================================================================
*/

"use strict";
var DoubleX_RMMV = DoubleX_RMMV || {};
DoubleX_RMMV["Confusion Edit"] = "v1.00e";

/*============================================================================
*    ## Plugin Implementations
*       You need not edit this part as it's about how this plugin works
*----------------------------------------------------------------------------
*    # Plugin Support Info:
*      1. Prerequisites
*         - Some Javascript coding proficiency to fully comprehend this
*           plugin
*      2. Function documentation
*         - The 1st part describes why this function's rewritten/extended for
*           rewritten/extended functions or what the function does for new
*           functions
*         - The 2nd part describes what the arguments of the function are
*         - The 3rd part informs which version rewritten, extended or created
*           this function
*         - The 4th part informs whether the function's rewritten or new
*         - The 5th part informs whether the function's a real or potential
*           hotspot
*         - The 6th part describes how this function works for new functions
*           only, and describes the parts added, removed or rewritten for
*           rewritten or extended functions only
*         Example:
* /*----------------------------------------------------------------------
*  *    Why rewrite/extended/What this function does
*  *----------------------------------------------------------------------*/
/* // arguments: What these arguments are
* functionName = function(arguments) { // Version X+; Hotspot
*     // Added/Removed/Rewritten to do something/How this function works
*     functionContents
*     //
* } // functionName
*----------------------------------------------------------------------------*/

DoubleX_RMMV.Confusion_Edit = {};
(function(CE) {

    CE.DataManager = {};
    var DM = CE.DataManager;

    DM.isDatabaseLoaded = DataManager.isDatabaseLoaded;
    DataManager.isDatabaseLoaded = function() {
        // Rewritten
        return DM.isDatabaseLoaded.apply(this, arguments) && DM.loadAllNotes();
        //
    }; // DataManager.isDatabaseLoaded

    DM.loadAllNotes = function() {
        $dataStates.forEach(function(data) {
            if (data) { DM.loadDataNotes(data); }
        });
        return true;
    }; // DM.loadAllNotes

    // data: The data to have its notetags read
    DM.loadDataNotes = function(data) {
        data.meta.confusionEdit = {};
        var lines = data.note.split(/[\r\n]+/);
        var regex = /< *confusion +edit *: *(\w+) *, *(\w+) *>/i;
        for (var index = 0, length = lines.length; index < length; index++) {
            if (!lines[index].match(regex)) { continue; }
            data.meta.confusionEdit.reverse = RegExp.$1 === "true";
            return data.meta.confusionEdit.excludeSelf = RegExp.$2 === "true";
        }
    }; // DM.loadDataNotes

    CE.Game_Action = {};
    var GA = CE.Game_Action;

    GA.friendsUnit = Game_Action.prototype.friendsUnit;
    Game_Action.prototype.friendsUnit = function() {
        // Rewritten to reverse the ally/foe identification with reverse flag
        return GA.originalReversedUnit.call(this, "friends", "opponents");
        //
    }; // Game_Action.prototype.friendsUnit

    GA.opponentsUnit = Game_Action.prototype.opponentsUnit;
    Game_Action.prototype.opponentsUnit = function() {
        // Rewritten to reverse the ally/foe identification with reverse flag
        return GA.originalReversedUnit.call(this, "opponents", "friends");
        //
    }; // Game_Action.prototype.opponentsUnit

    GA.setConfusion = Game_Action.prototype.setConfusion;
    Game_Action.prototype.setConfusion = function() {
        // Added to let battlers with reverse flag to use all available skills
        if (GBB.isConfusionEdit.call(this.subject(), "reverse")) { return; }
        //
        GA.setConfusion.apply(this, arguments);
    }; // Game_Action.prototype.setConfusion

    GA.isValid = Game_Action.prototype.isValid;
    Game_Action.prototype.isValid = function() {
        // Rewritten to ensure the target list won't be empty due to excludeSelf
        if (!GA.isValid.apply(this, arguments)) { return false; }
        if (!this.isForOpponent() && !this.isForFriend()) return true;
        return this.makeTargets().length > 0;
        //
    }; // Game_Action.prototype.isValid

    GA.makeTargets = Game_Action.prototype.makeTargets;
    Game_Action.prototype.makeTargets = function() {
        // Rewritten
        if (GBB.isConfusionEdit.call(this.subject(), "reverse")) {
            return this.repeatTargets(GA.makeReversedTargets.call(this));
        } else if (GA.hasValidOriginalTargets.call(this)) {
            return GA.makeTargets.apply(this, arguments);
        }
        return [];
        //
    }; // Game_Action.prototype.makeTargets

    GA.confusionTarget = Game_Action.prototype.confusionTarget;
    Game_Action.prototype.confusionTarget = function() {
        // Rewritten to exclude the subject itself with the excludeSelf flag
        var subject = this.subject();
        var target = GA.confusionTarget.apply(this, arguments);
        if (GBB.isConfusionEdit.call(subject, "excludeSelf")) {
            while (subject === target) {
                target = GA.confusionTarget.apply(this, arguments);
            }
        }
        return target;
        //
    }; // Game_Action.prototype.confusionTarget

    GA.targetsForOpponents = Game_Action.prototype.targetsForOpponents;
    Game_Action.prototype.targetsForOpponents = function() {
        // Rewritten
        return GA.confusionEditTargets.call(this, "targetsForOpponents");
        //
    }; // Game_Action.prototype.targetsForOpponents

    GA.targetsForFriends = Game_Action.prototype.targetsForFriends;
    Game_Action.prototype.targetsForFriends = function() {
        // Rewritten
        return GA.confusionEditTargets.call(this, "targetsForFriends");
        //
    }; // Game_Action.prototype.targetsForFriends
    /*------------------------------------------------------------------------
     *    Returns the reversed allies/foes for reverse flag
     *------------------------------------------------------------------------*/
    /* original: The original units to be returned
     * reversed: The units with the reverse flag to the returned
     */
    GA.originalReversedUnit = function(original, reversed) {
        var subject = this.subject();
        if (!this._forcing && GBB.isConfusionEdit.call(subject, "reverse")) {
            switch (subject.confusionLevel()) {
            case 1: return GA[original + "Unit"].apply(this, arguments);
            case 2:
                var side = Math.random() < 0.5 ? original : reversed;
                return GA[side + "Unit"].apply(this, arguments);
            default: return GA[reversed + "Unit"].apply(this, arguments);
            }
        }
        return GA[original + "Unit"].apply(this, arguments);
    }; // GA.originalReversedUnit

    /*------------------------------------------------------------------------
     *    Uses Autobattle with reversed ally/foe definition to mimic confusion
     *------------------------------------------------------------------------*/
    GA.makeReversedTargets = function() {
        if (this.isForOpponent()) { return this.targetsForOpponents(); }
        if (this.isForFriend()) { return this.targetsForFriends(); }
        return [];
    }; // GA.makeReversedTargets

    /*------------------------------------------------------------------------
     *    Returns if excludeSelf is false or self isn't the only valid target
     *------------------------------------------------------------------------*/
    GA.hasValidOriginalTargets = function() {
        if (this._forcing) { return true; }
        var subject = this.subject();
        if (!GBB.isConfusionEdit.call(subject, "excludeSelf")) { return true; }
        if (this.isForUser()) { return false; }
        if (subject.confusionLevel() !== 3) { return true; }
        return this.friendsUnit().aliveMembers().length > 1;
    }; // GA.hasValidOriginalTargets

    // functionName: The targetsForOpponents/targetsForFriends function name
    GA.confusionEditTargets = function(functionName) {
        if (!GBB.isConfusionEdit.call(this.subject(), "excludeSelf")) {
            return GA[functionName].apply(this, arguments);
        }
        // Prevents inifinite loops by checking for cases having no valid target
        if (!GA.canTargetReversed.call(this)) { return []; }
        //
        return GA.targetsForReversedExcludeSelf.call(this, functionName);
    }; // GA.confusionEditTargets

    /*------------------------------------------------------------------------
     *    Checks if there are targets other than self with the reverse flag
     *------------------------------------------------------------------------*/
    GA.canTargetReversed = function() {
        // User's always equal to self for both original and reversed cases
        if (this.isForUser()) { return false; }
        //
        var level = this.subject().confusionLevel();
        if (level === 1 && this.isForFriend()) {
            return this.friendsUnit().aliveMembers().length > 1;
        } else if (level === 3 && this.isForOpponent()) {
            return this.opponentsUnit().aliveMembers().length > 1;
        }
        return true;
    }; // GA.canTargetReversed

    /*------------------------------------------------------------------------
     *    Returns the target list with both reverse and excludeSelf flags
     *------------------------------------------------------------------------*/
    // functionName: The targetsForOpponents/targetsForFriends function name
    GA.targetsForReversedExcludeSelf = function(functionName) {
        var subject = this.subject();
        var index, num = this.isForRandom() ? this.numTargets() : 1, targets;
        do {
            // Prevents infinite loop by ensuring the subject won't be selected
            if (this._targetIndex === subject.index() && this.isForOne()) {
                this._targetIndex -= 1;
            }
            //
            targets = GA[functionName].apply(this, arguments);
            index = targets.indexOf(subject);
            if (index >= 0) { targets.splice(index, 1); }
        } while (targets.length < num);
        return targets;
    }; // GA.targetsForReversedExcludeSelf

    CE.Game_BattlerBase = {};
    var GBB = CE.Game_BattlerBase;

    /*------------------------------------------------------------------------
     *    Returns the queried notetag value of the 1st found effective notetag
     *------------------------------------------------------------------------*/
    // flag: The reverse/excludeSelf notetag value
    GBB.isConfusionEdit = function(flag) {
        if (!this.isConfused() || !this._states) { return false; }
        var state = this.states().filter(function(state) {
            return state.meta.confusionEdit !== undefined;
        })[0];
        return state && state.meta.confusionEdit[flag];
    }; // GBB.isConfusionEdit

    CE.Game_Actor = {};

    CE.Game_Actor.makeActions = Game_Actor.prototype.makeActions;
    Game_Actor.prototype.makeActions = function() {
        // Added to let actors with the reverse flag to use all available skills
        if (GBB.isConfusionEdit.call(this, "reverse")) {
            Game_Battler.prototype.makeActions.call(this);
            return this.makeAutoBattleActions();
        }
        //
        CE.Game_Actor.makeActions.apply(this, arguments);
    }; // Game_Actor.prototype.makeActions

})(DoubleX_RMMV.Confusion_Edit);

/*============================================================================*/

Video



FAQ

* None so far

Credits and Thanks

* None

Author's Notes

* None so far

Terms and Conditions

* You shall keep this plugin's Plugin Info part's contents intact
* You shalln't claim that this plugin's written by anyone other than DoubleX or his aliases
* None of the above applies to DoubleX or his aliases

Changelog

v1.00e(GMT 1100 9-9-2022):
1. Fixed infinite loop in targetsForReversedExcludeSelf due to typo
v1.00d(GMT 0200 6-6-2020):
1. Fixed actions having no targets not executing bug
v1.00c(GMT 0300 9-3-2020):
1. Fixed undefined subject in hasValidOriginalTargets
v1.00b(GMT 0800 30-1-2016):
1. Fixed missing return in targetsForOpponents and targetsForFriends
2. Fixed undefined target in targetsForReversedExcludeSelf due to typo
3. Fixed infinite loop with excludeSelf when subject's always selected
v1.00a(GMT 0800 3-1-2016):
1. 1st version of this script finished
My RMVXA/RMMV/RMMZ scripts/plugins:
http://rpgmaker.net/users/DoubleX/scripts/
Reply }
#2
Updates
Added this video:

v1.00b(GMT 0800 30-1-2016):
1. Fixed missing return in targetsForOpponents and targetsForFriends
2. Fixed undefined target in targetsForReversedExcludeSelf due to typo
3. Fixed infinite loop with excludeSelf when subject's always selected
My RMVXA/RMMV/RMMZ scripts/plugins:
http://rpgmaker.net/users/DoubleX/scripts/
Reply }
#3
Updates
v1.00d(GMT 0200 6-6-2020):
1. Fixed actions having no targets not executing bug
v1.00c(GMT 0300 9-3-2020):
1. Fixed undefined subject in hasValidOriginalTargets
My RMVXA/RMMV/RMMZ scripts/plugins:
http://rpgmaker.net/users/DoubleX/scripts/
Reply }
#4
Updates
v1.00e(GMT 1100 9-9-2022):
1. Fixed infinite loop in targetsForReversedExcludeSelf due to typo
My RMVXA/RMMV/RMMZ scripts/plugins:
http://rpgmaker.net/users/DoubleX/scripts/
Reply }


Possibly Related Threads…
Thread Author Replies Views Last Post
   DoubleX RMMV Popularized ATB Compatibility DoubleX 16 23,347 12-26-2022, 06:17 AM
Last Post: DoubleX
   DoubleX RMMV Popularized ATB Clock DoubleX 2 6,503 03-25-2022, 01:04 PM
Last Post: DoubleX
   DoubleX RMMV Status Bars Compatibility DoubleX 0 1,934 02-06-2022, 07:56 AM
Last Post: DoubleX
   DoubleX RMMV Popularized ATB Bar DoubleX 3 8,599 05-19-2021, 06:10 AM
Last Post: DoubleX
   DoubleX RMMV Skill Hotkeys DoubleX 2 6,056 02-13-2021, 04:59 AM
Last Post: DoubleX
   DoubleX RMMZ Skill Item Cooldown DoubleX 4 6,181 02-07-2021, 04:11 PM
Last Post: DoubleX
   DoubleX RMMZ Skill Item Triggers DoubleX 3 5,621 12-26-2020, 04:00 PM
Last Post: DoubleX
   DoubleX RMMZ TPBS Configurations Edit DoubleX 3 5,729 12-25-2020, 12:30 PM
Last Post: DoubleX
   DoubleX RMMV Superlative ATB DoubleX 2 4,508 12-11-2020, 02:25 PM
Last Post: DoubleX
   DoubleX RMMZ Targeting AI DoubleX 3 4,738 12-02-2020, 04:22 AM
Last Post: DoubleX



Users browsing this thread: 1 Guest(s)