Mr.Mine: Automation Guide V0.4

Updated guide for simple automation in Mr. Mine, heavily inspired by others work but fixes most of the problems introduces with the recent updates.

 

Intro

I in no way take credit for most of the work, just fixing what was broken.

Make sure you back up your files before making any changes so that you can always revert back to the original in need, or comment the old code with “//” or “/* */”.

Files are located in your steam game folder. Probably in “C:\Program Files (x86)\Steam\steamapps\common\MrMine“.

Resources

Automatically sell resources when full

Auto Sell
File to modify: resources/app/Shared/mineralmanagement.js
Function to modify: getUsedMineralCapacity()

Replace:

function getUsedMineralCapacity()
{
    capacity = cachedCountsTowardsCapacityAndValue.reduce((sum, resource) => sum + resource.numOwned, 0)

    if(!isSimulating)
    {
        if(mutecapacity == 0 && isCapacityFull())
        {
            capacityFullAudio.play();
        }
    }
}

With:

function getUsedMineralCapacity()
{
    capacity = cachedCountsTowardsCapacityAndValue.reduce((sum, resource) => sum + resource.numOwned, 0)

    if(!isSimulating)
    {
        if(mutecapacity == 0 && isCapacityFull())
        {
            capacityFullAudio.play();
        }
        if(mutecapacity == 1 && isCapacityFull())
        {
            sellAllMinerals(0);
        }
    }
}
TLDR: Add an “if” statement that checks if resources are full and alarms is set to off, then sells everything.

Combat
Battle automation

Auto Attack
File to modify: resources/app/popups/BattleWindow.js
Function to modify: render()

Replace:

this.context.fillStyle = "#dddddd";
this.context.globalAlpha = 0.8;
this.context.fillRect(weaponChargeX, weaponChargeY, (weaponChargeWidth * pcentAtk), this.boundingBox.height * .05);
this.context.globalAlpha = 1;

With:

this.context.fillStyle = "#dddddd";
this.context.globalAlpha = 0.8;
this.context.fillRect(weaponChargeX, weaponChargeY, (weaponChargeWidth * pcentAtk), this.boundingBox.height * .05);
this.context.globalAlpha = 1;
atk(bi);

TLDR: Add a line “atk(bi);” to automate attack with each weapon when ready.

Auto start fight
File to modify: resources/app/Shared/battle.js
Function to modify:spawnBattleOnFloor()

Replace:

function spawnBattleOnFloor(spawnY, spawnX)
{
    if(battleWaiting.length == 0 && depth > 303)
    {
        if(!isDepthWithoutWorkers(spawnY))
        {
            newNews(_("Miner #{0} is being attacked at Depth {1}km!", spawnX, spawnY), true);
            var somePrand = battleSpawnRoller.rand(0, 100);
            var whichFromTable = 0;
            if(somePrand < 5)
            {
                whichFromTable = 2;
            }
            else if(somePrand < 25)
            {
                whichFromTable = 1;
            }
            var spawnMonDetails = monstersOnLevels[Math.floor((spawnY - 300) / 10)][whichFromTable];
            battleWaiting = [spawnX, spawnY, spawnMonDetails[0], spawnMonDetails[1]];
        }
    }
}

With:

function spawnBattleOnFloor(spawnY, spawnX)
{
    if(battleWaiting.length == 0 && depth > 303)
    {
        if(!isDepthWithoutWorkers(spawnY))
        {
            newNews(_("Miner #{0} is being attacked at Depth {1}km!", spawnX, spawnY), true);
            var somePrand = battleSpawnRoller.rand(0, 100);
            var whichFromTable = 0;
            if(somePrand < 5)
            {
                whichFromTable = 2;
            }
            else if(somePrand < 25)
            {
                whichFromTable = 1;
            }
            var spawnMonDetails = monstersOnLevels[Math.floor((spawnY - 300) / 10)][whichFromTable];
            battleWaiting = [spawnX, spawnY, spawnMonDetails[0], spawnMonDetails[1]];
            onWorkerClicked((battleWaiting[1] + 5 - currentlyViewedDepth), battleWaiting[0]);
        }
    }
}
TLDR: Simulates clicking on the attacked worker by adding the line “onWorkerClicked((battleWaiting[1] + 5 – currentlyViewedDepth), battleWaiting[0]);

Chest automation

Chest collection automation

Auto open new chest
File to modify: resources/app/Shared/src/chest/ChestService.js
Function to modify: spawnChest()

Replace:

spawnChest(spawnDepth, source = Chest.natural, type = ChestType.basic, miner = -1)
    {
        var isCollectable = (source == Chest.natural || source == Chest.superminer) && !this.isChestCollectorFull();
        var collectionRoll = (chestSpawnRoller.rand(1, 100) <= this.getStoredChestsChance());
        let chanceOfCollision = (this.chests.length + 1) / (depth / 10); //this is here to simulate how chest spawns acted in the old system.
        var canSpawnInWorld = source != Chest.natural || !chestSpawnRoller.boolean(chanceOfCollision);

        
        console.log("spawnChest - "+canSpawnInWorld+" - "+chanceOfCollision+" - "+collectionRoll);

        if(isCollectable && collectionRoll)
        {
            this.storeChest(type);
            return true;
        }
        else if(canSpawnInWorld)
        {
            //check if miner already has a chest or is an invalid index
            if(miner < 0 || this.getChest(spawnDepth, miner) || miner > workersHiredAtDepth(spawnDepth))
            {
                var availableMiners = this.getAvailableMiners(spawnDepth);
                var minerIndex = rand(0, availableMiners.length - 1);
                miner = availableMiners[minerIndex];
            }
            var newChest = source.new(source, spawnDepth, miner, type);
            this.chests.push(newChest);
            return newChest;
        }

        return false;
    }

With:

spawnChest(spawnDepth, source = Chest.natural, type = ChestType.basic, miner = -1)
    {
        var isCollectable = (source == Chest.natural || source == Chest.superminer) && !this.isChestCollectorFull();
        var collectionRoll = (chestSpawnRoller.rand(1, 100) <= this.getStoredChestsChance());
        let chanceOfCollision = (this.chests.length + 1) / (depth / 10); //this is here to simulate how chest spawns acted in the old system.
        var canSpawnInWorld = source != Chest.natural || !chestSpawnRoller.boolean(chanceOfCollision);

        console.log("spawnChest - "+canSpawnInWorld+" - "+chanceOfCollision+" - "+collectionRoll);

        if(isCollectable && collectionRoll)
        {
            this.storeChest(type);
            return true;
        }
        else if(canSpawnInWorld)
        {
            //check if miner already has a chest or is an invalid index
            if(miner < 0 || this.getChest(spawnDepth, miner) || miner > workersHiredAtDepth(spawnDepth))
            {
                var availableMiners = this.getAvailableMiners(spawnDepth);
                var minerIndex = rand(0, availableMiners.length - 1);
                miner = availableMiners[minerIndex];
            }
            var newChest = source.new(source, spawnDepth, miner, type);
            this.chests.push(newChest);
            this.presentChest(spawnDepth);
            return newChest;
        }
        return false;
    }

TLDR: Add a line “this.presentChest(spawnDepth);;” to automatically click a new chest.

Auto collect chest reward
File to modify: resources/app/Shared/src/chest/ChestService.js
Function to modify: presentChest()

Replace:

presentChest(spawnDepth, workerNum = -1)
    {
        let chest = this.getChest(spawnDepth, workerNum);
        if(typeof chest == "undefined" && metalDetectorStructure.level >= 5)
        {
            chest = this.getChestsAtDepth(spawnDepth)[0];
        }

        if(!isSimulating && !keysPressed["Shift"] && chestService.chestPopupEnabled)
        {
            openUiWithoutClosing(ChestWindow, null, chest);
        }
        else
        {
            this.giveChestReward(chest);
            newNews(_("You got {0} from a Chest!", chestService.getChestRewardText()), true);
        }

        trackEvent_FoundChest(chest.type)
    }

With:

presentChest(spawnDepth, workerNum = -1)
    {
        let chest = this.getChest(spawnDepth, workerNum);
        if(typeof chest == "undefined" && metalDetectorStructure.level >= 5)
        {
            chest = this.getChestsAtDepth(spawnDepth)[0];
        }

        if(keysPressed["Shift"])
        {
            openUiWithoutClosing(ChestWindow, null, chest);
        }
        else
        {
            this.giveChestReward(chest);
            newNews(_("You got {0} from a Chest!", chestService.getChestRewardText()), true);
        }

        trackEvent_FoundChest(chest.type)
    }
TLDR: Modify the condition ” if(keysPressed[“Shift”])” so that it will always give the reward automatically unless you hold the “SHIFT” key. This fixes the treasures chests that will collect infinitely if you click on them, using the “SHIFT” key allows you to open the popup normally (cave, scientists, monsters…).


Thanks to Myst03 for his excellent guide, all credits belong to his effort. if this guide helps you, please support and rate it via Steam Community. enjoy the game.

Related Posts:

Leave a Comment