您需要先安装一个扩展,例如 篡改猴、Greasemonkey 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 暴力猴,之后才能安装此脚本。
您需要先安装一个扩展,例如 篡改猴 或 Userscripts ,之后才能安装此脚本。
您需要先安装一款用户脚本管理器扩展,例如 Tampermonkey,才能安装此脚本。
您需要先安装用户脚本管理器扩展后才能安装此脚本。
Скрины с функционалом ниже. 1.) Показывает урон всех стеков одной стороны по одному выбранному стеку второй стороны. 2.) Если навести курсор на 1 существо, нажать 'e' (русская 'у'), сделать то же самое со вторым, то в чате появится урон первого по второму. Доп. выборы и настройка скорости анимации в настройках боя.
当前为
- // ==UserScript==
- // @name battle_damage_tooltip
- // @namespace http://tampermonkey.net/
- // @version 2.4
- // @description Скрины с функционалом ниже. 1.) Показывает урон всех стеков одной стороны по одному выбранному стеку второй стороны. 2.) Если навести курсор на 1 существо, нажать 'e' (русская 'у'), сделать то же самое со вторым, то в чате появится урон первого по второму. Доп. выборы и настройка скорости анимации в настройках боя.
- // @author Something begins
- // @license None
- // @match https://www.heroeswm.ru/war*
- // @match https://my.lordswm.com/war*
- // @match https://www.lordswm.com/war*
- // @icon data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw==
- // @grant GM_setValue
- // @grant GM_getValue
- // @grant unsafeWindow
- // ==/UserScript==
- // Активация горячих кнопок на Alt, поменять можно в переменной triggerKey
- // Выбор биндов горячих кнопок, редактировать можно снизу, спец символы копировать из списка keyboardKeycodes на 23 строке
- // посмотреть урон
- const seeDamage = "E";
- // посмотреть рельсу
- const seeMagShot = "U"
- // кнопка, зажав которую, становятся активны кнопки ниже
- const triggerKey = "alt";
- // автобой
- const autoBattle = "A";
- // вкл/выкл кастом скорость боя
- const toggleSpeed = "S";
- // авто расстановка
- const autoPlacement = "R";
- // кнопка назад
- const backToGame = "Z";
- // начать бой
- const startBattle = "B";
- const keyboardKeycodes = {
- "backspace": 8,
- "tab": 9,
- "enter": 13,
- "shift": 16,
- "ctrl": 17,
- "alt": 18,
- "pause": 19,
- "capslock": 20,
- "escape": 27,
- "space": 32,
- "pageup": 33,
- "pagedown": 34,
- "end": 35,
- "home": 36,
- "leftarrow": 37,
- "uparrow": 38,
- "rightarrow": 39,
- "downarrow": 40,
- "insert": 45,
- "delete": 46,
- "0": 48,
- "1": 49,
- "2": 50,
- "3": 51,
- "4": 52,
- "5": 53,
- "6": 54,
- "7": 55,
- "8": 56,
- "9": 57,
- "a": 65,
- "b": 66,
- "c": 67,
- "d": 68,
- "e": 69,
- "f": 70,
- "g": 71,
- "h": 72,
- "i": 73,
- "j": 74,
- "k": 75,
- "l": 76,
- "m": 77,
- "n": 78,
- "o": 79,
- "p": 80,
- "q": 81,
- "r": 82,
- "s": 83,
- "t": 84,
- "u": 85,
- "v": 86,
- "w": 87,
- "x": 88,
- "y": 89,
- "z": 90,
- "leftwindowkey": 91,
- "rightwindowkey": 92,
- "selectkey": 93,
- "numpad0": 96,
- "numpad1": 97,
- "numpad2": 98,
- "numpad3": 99,
- "numpad4": 100,
- "numpad5": 101,
- "numpad6": 102,
- "numpad7": 103,
- "numpad8": 104,
- "numpad9": 105,
- "multiply": 106,
- "add": 107,
- "subtract": 109,
- "decimalpoint": 110,
- "divide": 111,
- "f1": 112,
- "f2": 113,
- "f3": 114,
- "f4": 115,
- "f5": 116,
- "f6": 117,
- "f7": 118,
- "f8": 119,
- "f9": 120,
- "f10": 121,
- "f11": 122,
- "f12": 123,
- "numlock": 144,
- "scrolllock": 145,
- "semicolon": 186,
- "equal": 187,
- "comma": 188,
- "dash": 189,
- "period": 190,
- "forwardslash": 191,
- "graveaccent": 192,
- "openbracket": 219,
- "backslash": 220,
- "closebracket": 221,
- "singlequote": 222
- };
- const pressedKeys = new Set();
- function handleKeyDown(event) {
- pressedKeys.add(event.keyCode);
- }
- function handleKeyUp(event) {
- pressedKeys.delete(event.keyCode);
- }
- document.addEventListener("keydown", handleKeyDown);
- document.addEventListener("keyup", handleKeyUp);
- // Странные способы в некоторых местах обусловлены конфликтом со скриптом battleHelper от omne
- let outer_chat = document.getElementById("chat_format");
- let atLaunch = true;
- const physCalcColor = "#141736";
- const magCalcColor = "#150f1c";
- const calcHellFireColor = "rgba(255,0,0,0.1)";
- outer_chat.insertAdjacentHTML("beforeend", `
- <div id="cre_distance_div" style="display: none"></div>
- <div id="individual_calc"></div>
- <div id="mag_calc"></div>
- <div id="dmg_list_container"></div>
- <button id="dmg_list_refresh" style="background-color: #3d3d29; color: white; padding: 5px 10px; border: none; border-radius: 4px; font-size: 10px; cursor: pointer">Открыть</button>
- <select style="display : none; background-color: #333; color: white; margin: 10px" id="choose_cre"></select>
- <button id="change_side" style="background-color: #6b6b47; color: white; padding: 5px 10px; border: none; border-radius: 4px; font-size: 10px; cursor: pointer; display: none">Сменить сторону</button>
- <button id="collapse" style="background-color: #000000; color: white; padding: 5px 10px; border: none; border-radius: 4px; font-size: 10px; cursor: pointer; display: none; margin:10px">Свернуть</button> `)
- let last_individual_calc = {}
- let isOpen = false
- let ini_weight = 10;
- let chosen = { side: 1, creature: "Высшие вампиры", afterSideSwitchCre: { "-1": "", "1": "" } }
- let chat = document.getElementById("chat_inside");
- let select = document.getElementById("choose_cre")
- let refresh_button = document.getElementById("dmg_list_refresh")
- let side_button = document.getElementById("change_side")
- let collapse_button = document.getElementById("collapse")
- let individual_calc = document.querySelector("#individual_calc")
- let cre_distance_div = document.querySelector("#cre_distance_div")
- const settings_panel = document.querySelector("#webgl_settings_whole")
- let dmg_list_container = document.querySelector("#dmg_list_container")
- cre_distance_div.innerHTML = `<span>Выбранное расстояние: ${GM_getValue('cre_distance')}</span><br>`;
- // ========= utils ============
- function get_GM_value_if_exists(GM_key, default_value) {
- const GM_value = GM_getValue(GM_key)
- return GM_value != undefined ? GM_value : default_value;
- }
- function triggerMouseUpEvent(element) {
- let clickEvent = document.createEvent('MouseEvents');
- clickEvent.initEvent("mouseup", true, true);
- element.dispatchEvent(clickEvent);
- }
- function getCurrentBattleSpeed() {
- for (let i = 1; i <= 3; i++) {
- let div = document.querySelector(`#speed${i}_button`)
- if (div.style.display === 'none') continue
- if (i === 1) return 2
- else if (i === 3) return 1
- else return 4
- }
- }
- function setBattleSpeed(value) {
- if (value === 0) return value
- else if (value < 1) {
- unsafeWindow.timer_interval = Math.abs(value) * 20;
- return value
- }
- unsafeWindow.animspeed_def = unsafeWindow.animspeed = value
- unsafeWindow.animspeed_init = unsafeWindow.animspeed > 4 ? 0.5 : 2;
- unsafeWindow.timer_interval = Math.abs(value - 20);
- !unsafeWindow.timer_interval && unsafeWindow.timer_interval++;
- return value
- }
- function countOccurrences(arr, element) {
- return arr.reduce((acc, curr) => (curr === element ? acc + 1 : acc), 0);
- }
- // инфа о гейтах на карте
- function initGates() {
- const match = document.body.innerHTML.match(/umka\|(.+?)\|/);
- if (!match) return;
- const umka = match[1];
- const factions = [];
- for (let i = 1; i < umka.length; i += 14) {
- factions.push(umka[i]);
- }
- const demonsNo = countOccurrences(factions, "7");
- if (demonsNo < 1) return;
- document.head.insertAdjacentHTML("beforeEnd", `
- <style>
- #floatingBox {
- position: absolute;
- background-color: rgba(255, 255, 255, 0.5);
- color: white;
- padding: 10px;
- border-radius: 8px;
- pointer-events: none;
- white-space: nowrap;
- display: none;
- }
- .line {
- font-family: Arial, sans-serif;
- font-size: 16px;
- margin: 5px 0;
- }
- </style>
- `);
- document.body.insertAdjacentHTML("beforeEnd", `
- <div id="floatingBox">
- <div class="line" id = "gate_name">Гейт [#] </div>
- ${demonsNo > 1 ? '<div class="line" id = "gate_owner"> Владелец</div>' : ''}
- </div>
- `);
- const floatingBox = document.getElementById('floatingBox');
- document.addEventListener("mousemove", event => {
- const [gate_x, gate_y] = [xr_last, yr_last]
- if (gate_x > defxn || gate_y > defyn || gate_x < 0 || gate_y < 0) {
- floatingBox.style.display = "none";
- return;
- }
- let foundGate = false;
- let curGate;
- for (const cre of Object.values(stage.pole.obj)) {
- if (cre.nownumber !== -1) continue;
- if (cre.x !== gate_x || cre.y !== gate_y) continue;
- foundGate = true;
- curGate = cre;
- break;
- }
- if (!foundGate) {
- floatingBox.style.display = "none";
- return;
- };
- floatingBox.style.display = "block";
- const mouseX = event.pageX;
- const mouseY = event.pageY;
- floatingBox.style.left = mouseX + 10 + 'px';
- floatingBox.style.top = mouseY + 10 + 'px';
- document.querySelector("#gate_name").innerHTML = `${curGate.nametxt} [${curGate.maxnumber}]`;
- document.querySelector("#floatingBox").style.color = curGate.get_color();
- if (demonsNo < 2) return;
- const owner = stage.pole.obj[heroes[curGate.owner]]
- document.querySelector("#gate_owner").innerHTML = `${owner.nametxt} [${owner.maxhealth}]`
- })
- }
- function calcKilled(dmg, defender) {
- let killed;
- if (dmg % defender.maxhealth > defender.nowhealth) killed = Math.floor(dmg / defender.maxhealth) + 1
- else killed = Math.floor(dmg / defender.maxhealth);
- return killed
- }
- function calcHellFireHTML(attacker, defender, cre_collection, physDamage) {
- if (!isperk(attacker.obj_index, 7) || attacker.hero === 1) {
- return "";
- }
- const dmg = calcHellFire(attacker, defender, cre_collection);
- const minDamage = dmg + physDamage.min;
- const maxDamage = dmg + physDamage.max;
- const minKilled = calcKilled(minDamage, defender);
- const maxKilled = calcKilled(dmg + physDamage.max, defender);
- return `<p id="${0}" style=" background-color: ${calcHellFireColor}">
- <span style="color:white; font-size: 90%">Адское пламя: </span> <span style = "color:red">${dmg}</span> <span style = "font-size: 80%">урона</span><br>
- <b style="color:#ffffff; font-size: 120%; text-decoration: underline;">${minKilled}-${maxKilled}</b> существ <span style="color:#ffffff">(${minDamage}-${maxDamage})
- </p><br>`;
- }
- function calcStormHTML(attacker, defender) {
- let koef;
- //console.log(attacker);
- if (attacker.stormstrike) koef = 0.5;
- else if (attacker.flamestrike) koef = 1.2;
- else return "";
- let xr = defender.x;
- let yr = defender.y;
- let i = attacker.obj_index;
- let dmgMap;
- Totalmagicdamage = 0;
- Totalmagickills = 0;
- var ok = false;
- var xx = 0,
- yy = 0,
- xp = 0,
- yp = 0;
- mul = 1;
- var len = stage.pole.obj_array.length;
- for (var k1 = 0; k1 < len; k1++) {
- var j = stage.pole.obj_array[k1];
- stage.pole.obj[j]['attacked'] = 1;
- stage.pole.obj[j]['attacked2'] = 1;
- }
- var herd = 0;
- var hera = 0;
- for (var k1 = 0; k1 < len; k1++) {
- k = stage.pole.obj_array[k1];
- if ((stage.pole.obj[k].hero) && (stage.pole.obj[k].owner == stage.pole.obj[mapobj[xr + yr * defxn]].owner)) herd = k;
- if ((stage.pole.obj[k].hero) && (stage.pole.obj[k].owner == stage.pole.obj[i].owner)) hera = k;
- }
- let b = 0;
- if ((magic[hera]) && (magic[hera]['mle'])) {
- b = magic[hera]['mle']['effect'];
- magic[hera]['mle']['effect'] = 0;
- }
- if (magic[herd]) {
- let rangedDef;
- if (magic[herd]['msk']) rangedDef = magic[herd]['msk']['effect'];
- else rangedDef = 0;
- if (magic[herd]['mld']) {
- let b = magic[herd]['mld']['effect'];
- magic[herd]['mld']['effect'] = rangedDef;
- dmgMap = get_dmg_info(attacker.obj_index, defender.obj_index, koef);
- magic[herd]['mld']['effect'] = b;
- } else {
- magic[herd]['mld'] = [];
- magic[herd]['mld']['effect'] = rangedDef;
- dmgMap = get_dmg_info(attacker.obj_index, defender.obj_index, koef);
- delete magic[herd]['mld'];
- }
- } else {
- dmgMap = get_dmg_info(attacker.obj_index, defender.obj_index, koef);
- }
- if (b != 0) {
- magic[hera]['mle']['effect'] = b;
- }
- console.log(dmgMap);
- return `<p id="${0}" style=" background-color: ${calcHellFireColor}">
- <span style="color:white; font-size: 90%">Урон абилкой: </span><br>
- <b style="color:#ffffff; font-size: 120%; text-decoration: underline;">${dmgMap.min_killed}-${dmgMap.max_killed}</b> существ <span style="color:#ffffff">(${dmgMap.min}-${dmgMap.max})
- </p><br>`;
- }
- function calcMagicHTML(attacker, defender, cre_collection, dmg, inList = false) {
- if (!mag_damage_on) return "";
- let calcHTML = "";
- const disclaimerHTML = `<span class="tooltip"> !!! <span class="tooltiptext" style = "width:3000%; transform: translateX(-30%);"> (в КБО) это заклинание показывает <br> неправильный урон </span>
- </span>`;
- const incorrectSpellIDs = ["circle_of_winter", "swarm", "stormcaller"];
- // если темная сила, то дописать урон с усилком
- const isPowered = attacker.hero && unsafeWindow.isperk(attacker.obj_index, 6) ? true : false;
- for (let spellID of Object.keys(damageSpells)) {
- let additionalInfoHTML = "";
- if (attacker[spellID]) {
- if (spellID === "calllightning") spellID = "lighting";
- const dmg = unsafeWindow.stage.pole.calcmagic_script(attacker.x, attacker.y, defender.x, defender.y, spellID);
- if (spellID === "meteor") {
- let meteorText = "Целей:<br>";
- for (let i = 1; i <= 4; i++) {
- let dmg2 = Math.floor(dmg * Math.pow(0.85, i));
- let killed2 = calcKilled(dmg2, defender);
- const poweredDamage = Math.round(dmg2 * 1.5);
- const poweredKilled = calcKilled(poweredDamage, defender);
- const poweredDamageText = isPowered ? `<span style = "font-style:italic; font-size:80%"><br>\t[1.5x] ${poweredKilled} существ (${poweredDamage})<br></span>` : "";
- meteorText += `[${i+1}]: ${killed2} существ (${dmg2}) ${poweredDamageText}<br>`;
- }
- additionalInfoHTML = `<span class="tooltip"> +++ <span class="tooltiptext" style = "width:1000%; transform: ${isPowered? "translateY(30%);" : "translateX(-60%);"}">${meteorText}</span>
- </span>`;
- }
- if (spellID === "chainlighting") {
- let chainText = "Цель №<br>";
- const penaltyArr = Array(0.5, 0.25, 0.125);
- for (let i = 0; i < 3; i++) {
- let dmg2 = unsafeWindow.stage.pole.calcmagic_script(attacker.x, attacker.y, defender.x, defender.y, spellID, penaltyArr[i]);
- let killed2 = calcKilled(dmg2, defender);
- const poweredDamage = Math.round(dmg2 * 1.5);
- const poweredKilled = calcKilled(poweredDamage, defender);
- const poweredDamageText = isPowered ? `<span style = "font-style:italic; font-size:80%"><br>\t[1.5x] ${poweredKilled} существ (${poweredDamage})<br></span>` : "";
- chainText += `${i+2} : ${killed2} существ (${dmg2}) ${poweredDamageText}<br>`;
- }
- additionalInfoHTML = `<span class="tooltip"> +++ <span class="tooltiptext" style = "width:1000%; transform: ${isPowered? "translateY(30%);" : "translateX(-60%);"};">${chainText}</span>
- </span>`;
- }
- if (spellID === "poison") {
- additionalInfoHTML = `<span class="tooltip"> !!! <span class="tooltiptext" style = "width:1000%; transform: ${isPowered? "translateY(30%);" : "translateX(-60%);"};">Погрешность +-10%</span>
- </span>`;
- }
- let killed = calcKilled(dmg, defender);
- const poweredDamage = Math.round(dmg * 1.5);
- const poweredKilled = calcKilled(poweredDamage, defender);
- const poweredDamageText = isPowered ? `<span style = "font-style:italic; font-size:80%"><br>\t[1.5x] ${poweredKilled} существ (${poweredDamage})<br></span>` : "";
- // calcHTML+= `${damageSpells[spellID]} ---> ${dmg} \t (${killed} существ)`;
- calcHTML += `<p id="${0}" style=" background-color: ${magCalcColor}">
- <span style="color:white; font-size: 90%">${damageSpells[spellID]}: </span><br>
- <b style="color:#ffffff; font-size: 120%; text-decoration: underline;">${killed}</b> существ <span style="color:#ffffff">(${dmg}) ${poweredDamageText}</span> ${incorrectSpellIDs.includes(spellID) ? disclaimerHTML : additionalInfoHTML}
- </p>`;
- }
- }
- calcHTML += "<br>";
- return calcHTML;
- }
- function calcPhysHTML(attacker, defender, dmg, distance_str) {
- return ` <div id="individual_cre_heading" style="display:inline; background-color: ${physCalcColor}">
- ${distance_str}
- <span>Урон <br>
- </span>
- <span>
- <b>${attacker.nametxt}</b> ${attacker.hero === 1 ? "" : ("[" + attacker.nownumber + "]")} по <b>${defender.nametxt}</b> [${defender.nownumber}]: <br>
- <br>
- </span>
- </div>
- <p id="${0}" style=" background-color: ${physCalcColor}">
- <span style=color:#bfbfbf"></span>
- <b style="color:#ffffff; font-size: 120%; text-decoration: underline;">${dmg.min_killed}-${dmg.max_killed}</b> существ (<span style="color:#ffffff">${dmg.min}-${dmg.max}</span>)
- </p>
- <br>`;
- }
- function individual_calc_innerHTML(atk_obj_index, def_obj_index) {
- if (atk_obj_index === undefined || def_obj_index === undefined) return "";
- let cre_collection = unsafeWindow.stage.pole.obj;
- let attacker = cre_collection[atk_obj_index];
- let defender = cre_collection[def_obj_index];
- let dmg = get_dmg_info(atk_obj_index, def_obj_index);
- let distance_str = dmg.distance === "" ? "" : `<p> Прыжок на <u>${dmg.distance}</u> клеток </p>`;
- last_individual_calc.atk_obj_index = atk_obj_index;
- last_individual_calc.def_obj_index = def_obj_index;
- let calcHTML = calcPhysHTML(attacker, defender, dmg, distance_str) + calcHellFireHTML(attacker, defender, cre_collection, dmg) + calcStormHTML(attacker, defender) + (lastturn > 0 ? calcMagicHTML(attacker, defender, cre_collection, dmg) : "");
- return calcHTML;
- }
- function paint_coords(x, y, color, timeout = 2077) {
- let tile = shado[x + y * defxn]
- if (tile == undefined) return
- tile.fill(color)
- set_visible(tile, 1)
- setTimeout(() => {
- tile.fill(null)
- set_visible(tile, 0)
- }, timeout)
- }
- // const observer = new MutationObserver((mutationsList, observer) => {
- // for (const mutation of mutationsList) {
- // if (mutation.type !== 'childList') return
- // for (const addedNode of mutation.addedNodes) {
- // if (!(addedNode.classList && addedNode.classList.contains('cont') || ["B", "BR"].includes(addedNode.tagName))) continue
- // wrap_battlehelper();
- // battlehelper_div.style.display = battleHelper_on ? "inline" : "none";
- // }
- // }
- // });
- function GM_toggle_boolean(GM_key, boolean) {
- boolean = !boolean
- GM_setValue(GM_key, boolean);
- return boolean
- }
- function set_Display(element_arr, displayProperty) {
- element_arr.forEach(element => {
- if (element == null) return
- element.style.display = displayProperty
- })
- }
- function readjust_elements() {
- chat = document.getElementById("chat_inside");
- select = document.getElementById("choose_cre")
- refresh_button = document.getElementById("dmg_list_refresh")
- side_button = document.getElementById("change_side")
- collapse_button = document.getElementById("collapse")
- dmg_list_container = document.querySelector("#dmg_list_container")
- individual_calc = document.querySelector("#individual_calc")
- cre_distance_div = document.querySelector("#cre_distance_div")
- }
- // -----------------------------------
- // ========= Настройки ============
- let cre_distance = get_GM_value_if_exists('cre_distance', "")
- let cre_distance_on = get_GM_value_if_exists('cre_distance_on', false)
- let coeff_on = get_GM_value_if_exists('coeff_on', false)
- let animation_speed_on = get_GM_value_if_exists("animation_speed_on", false);
- let mag_damage_on = get_GM_value_if_exists("mag_damage_on", true);
- const new_settings = `
- <style>
- .tooltip {
- position: relative;
- display: inline-block;
- text-size: 150%;
- color: brown;
- text-decoration: underline;
- }
- .tooltip .tooltiptext {
- visibility: hidden;
- position: absolute;
- bottom: 100%;
- left: 50%;
- padding: 5px;
- background-color: #555;
- color: #fff;
- border-radius: 6px;
- word-wrap: break-word;
- }
- .tooltip:hover .tooltiptext {
- visibility: visible;
- }
- </style>
- <div class="info_row">
- <label class="checkbox_container">коэф. урона <span class="tooltip">? <span class="tooltiptext" style = "width: 5000%; transform: translateX(-30%);">отношение урон/хп (т.е. у кого больше всех коэф., с того выгоднее начинать. <br>Работает в списке уронов если нажать на "Открыть" в чате)</span>
- </span>
- <input type="checkbox" checked="true" id="coeff_on">
- <span class="checkbox_checkmark"></span>
- </label>
- </div>
- <div class="info_row">
- <label class="checkbox_container">Расстояние между стеками <span class="tooltip">? <span class="tooltiptext transform: translateX(-30%);" style = "width: 5000%;">Расстояние между атакующим и защищающимся стеками. Выбирать расстояние стрелочками в текстовом поле снизу. <br>
- Влияет на статус урона стрелка (ближний/дальний урон, кривая/прямая стрела),
- разбег и прочие абилки, зависящие от расстояния. <br> Если выставить "Расстояние: 1", то стрелок будет считаться заблокированным.
- Если выставить расстояние больше 1,
- то стрелок будет считаться не заблокированным (даже если рядом с ним вражеское существо). </span>
- </span>
- <input type="checkbox" checked="true" id="cre_distance_on">
- <span class="checkbox_checkmark"></span>
- </label>
- <input type="number" style="width: 4%; margin: 2px 2px 2px 80px" id="cre_distance" onkeydown="return false;" value=${cre_distance}>
- </div>
- <div class="info_row">
- <label class="checkbox_container">Скорость анимации <span class="tooltip">? <span class="tooltiptext" style = "width: 5000%; transform: translateX(-30%);"> Скорость боевых анимаций. <br> Выбирать расстояние стрелочками в текстовом поле снизу или если зажать кнопку Alt и нажимать на стрелки клавиатуры.<br> Включить/выключить анимацию [Alt + P (русская З)].<br> Анимацию можно как ускорить, так и замедлить.<br>Верхний потолок у скорости 20, нижнего нету.<br> Негативный показатель означает скорость ниже возможной гвдшной. </span>
- </span>
- <input type="checkbox" checked="true" id="animation_speed_on">
- <span class="checkbox_checkmark"></span>
- </label>
- <input type="number" style="width: 5%; margin: 2px 2px 2px 80px" id="anim_speed" onkeydown="return false;" >
- </div>
- <div class="info_row">
- <label class="checkbox_container">Расчет маг. урона <span class="tooltip"> * <span class="tooltiptext" style = "width: 5000%; transform: translateX(-30%);"> Расчет магического урона не работает во время расстановки
- </span></span>
- <input type="checkbox" checked="true" id="mag_damage_on">
- <span class="checkbox_checkmark"></span>
- </label>
- </div>
- `
- settings_panel.insertAdjacentHTML("beforeend", new_settings)
- let settings_interval = setInterval(() => {
- if (Object.keys(unsafeWindow.stage.pole.obj).length !== 0) {
- initMagicCalc();
- document.querySelector("#mag_damage_on").checked = mag_damage_on;
- document.querySelector("#coeff_on").checked = coeff_on
- document.querySelector("#cre_distance_on").checked = cre_distance_on
- document.querySelector("#animation_speed_on").checked = animation_speed_on
- let spd = get_GM_value_if_exists("anim_speed", getCurrentBattleSpeed())
- document.querySelector("#anim_speed").value = spd
- if (GM_getValue("animation_speed_on")) setBattleSpeed(spd);
- // без таймаута гвд крашится :\
- //if (btype === 66) setTimeout(make_ins_but, 1000);
- // убрал, чет лагает с этим
- if (location.href.includes("<")) {
- const test = document.querySelector("#pause_button");
- if (test.style.display === "none") {
- show_button("pause_button");
- pause_button_onRelease()
- }
- }
- clearInterval(settings_interval)
- }
- }, 300)
- const distance_counter = document.getElementById("cre_distance");
- const anim_speed_counter = document.querySelector("#anim_speed")
- // ========= Event Listeners ============
- document.body.addEventListener('input', function(event) {
- switch (event.target.id) {
- case "cre_distance":
- if (distance_counter.value < 1) {
- distance_counter.value = 1
- return
- }
- if (!cre_distance_on) return
- GM_setValue('cre_distance', distance_counter.value)
- if (isOpen) refresh()
- individual_calc.innerHTML = individual_calc_innerHTML(last_individual_calc.atk_obj_index, last_individual_calc.def_obj_index)
- cre_distance_div.innerHTML = `<span>Выбранное расстояние: ${GM_getValue('cre_distance')}</span><br>`
- break;
- case "anim_speed":
- if (anim_speed_counter.value > 20) {
- anim_speed_counter.value = 20
- return
- }
- GM_setValue('anim_speed', anim_speed_counter.value)
- if (!animation_speed_on) return
- setBattleSpeed(anim_speed_counter.value)
- break;
- }
- });
- const anim_speed_input = document.querySelector('#anim_speed')
- document.addEventListener('keydown', event => {
- if ((document.querySelector("#chattext") === document.activeElement) || (document.querySelector("#chattext_classic") === document.activeElement)) return;
- const keyCode = parseInt(event.keyCode);
- //console.log(keyboardKeycodes[triggerKey.toLowerCase()].toString(), pressedKeys);
- if (!pressedKeys.has(keyboardKeycodes[triggerKey.toLowerCase()]) || !Object.values(keyboardKeycodes).includes(keyCode)) return;
- //console.log(keyCode, keyboardKeycodes[backToGame.toLocaleLowerCase()], keyboardKeycodes[backToGame.toLocaleLowerCase()] === keyCode);
- if (keyCode === keyboardKeycodes[toggleSpeed.toLowerCase()]) {
- animation_speed_on = GM_toggle_boolean("animation_speed_on", GM_getValue("animation_speed_on"))
- document.querySelector("#animation_speed_on").checked = animation_speed_on
- if (animation_speed_on) {
- GM_setValue('anim_speed', anim_speed_counter.value)
- setBattleSpeed(anim_speed_counter.value);
- } else {
- setBattleSpeed(getCurrentBattleSpeed());
- }
- }
- if (event.key === 'ArrowUp' || event.key === 'ArrowDown') {
- event.preventDefault();
- const increment = event.key === 'ArrowUp' ? 1 : -1;
- anim_speed_input.value = parseInt(anim_speed_input.value) + increment;
- anim_speed_input.dispatchEvent(new Event('input', { bubbles: true }));
- }
- if (keyCode === keyboardKeycodes[autoBattle.toLowerCase()]) {
- fastbut_onRelease2();
- }
- if (keyCode === keyboardKeycodes[autoPlacement.toLowerCase()]) {
- make_ins_but();
- }
- if (keyCode === keyboardKeycodes[startBattle.toLowerCase()]) {
- document.querySelector("#confirm_ins_img") && triggerMouseUpEvent(document.querySelector("#confirm_ins_img"));
- }
- if (keyCode === keyboardKeycodes[backToGame.toLowerCase()]) {
- // document.querySelector("#back_to_game > img") && document.querySelector("#back_to_game > img").click();
- if (history.length > 1) {
- back_to_game_button_onRelease();
- } else {
- back_to_home_button_onRelease();
- }
- }
- });
- document.body.addEventListener('change', function(event) {
- switch (event.target.id) {
- case "mag_damage_on":
- mag_damage_on = GM_toggle_boolean("mag_damage_on", mag_damage_on);
- if (isOpen) refresh();
- individual_calc.innerHTML = individual_calc_innerHTML(last_individual_calc.atk_obj_index, last_individual_calc.def_obj_index)
- break;
- case "coeff_on":
- coeff_on = GM_toggle_boolean("coeff_on", coeff_on);
- if (isOpen) refresh();
- break;
- case "choose_cre":
- chosen.creature = select.value
- refresh()
- break;
- case "cre_distance_on":
- cre_distance_on = GM_toggle_boolean("cre_distance_on", cre_distance_on)
- cre_distance_on ? GM_setValue('cre_distance', distance_counter.value) : GM_setValue('cre_distance', "")
- if (cre_distance_on) {
- cre_distance_div.innerHTML = `<span>Выбранное расстояние: ${GM_getValue('cre_distance')}</span><br>`
- cre_distance_div.style.display = "inline"
- if (isOpen) refresh()
- individual_calc.innerHTML = individual_calc_innerHTML(last_individual_calc.atk_obj_index, last_individual_calc.def_obj_index)
- } else {
- cre_distance_div.innerHTML = ""
- }
- if (isOpen) refresh()
- individual_calc.innerHTML = individual_calc_innerHTML(last_individual_calc.atk_obj_index, last_individual_calc.def_obj_index)
- break;
- case "animation_speed_on":
- animation_speed_on = GM_toggle_boolean("animation_speed_on", GM_getValue("animation_speed_on"))
- if (animation_speed_on) {
- GM_setValue('anim_speed', anim_speed_counter.value)
- setBattleSpeed(anim_speed_counter.value);
- } else {
- setBattleSpeed(getCurrentBattleSpeed());
- }
- break;
- }
- });
- document.body.addEventListener('click', function(event) {
- if (event.target.parentElement && /speed(.)_button/.test(event.target.parentElement.id)) {
- setBattleSpeed(getCurrentBattleSpeed());
- document.querySelector("#animation_speed_on").checked = false
- GM_setValue('animation_speed_on', false)
- }
- switch (event.target.id) {
- case "dmg_list_refresh":
- readjust_elements()
- refresh()
- break
- case "change_side":
- chosen.afterSideSwitchCre[chosen.side] = chosen.creature
- chosen.side = -chosen.side
- chosen.creature = chosen.afterSideSwitchCre[chosen.side]
- refresh()
- break
- case "collapse":
- readjust_elements()
- isOpen = false
- refresh_button.innerHTML = "Открыть";
- set_Display([select, side_button, collapse_button, document.querySelector("#chosen_cre_heading"), dmg_list_container, individual_calc, cre_distance_div], "none")
- break
- // case "confirm_ins_img":
- // observer.observe(outer_chat, { childList: true });
- // setTimeout(function() {
- // observer.disconnect();
- // }, 190000);
- // break;
- }
- });
- function paint_two_coords() {
- }
- let calc_x, calc_y, magshot_x, magshot_y;
- function manageDamageCalc() {
- // если бой не начался, популизирует mapobj
- if (lastturn < 0) {
- for (const cre of Object.values(stage.pole.obj)) {
- unsafeWindow.mapobj[cre.x + cre.y * defxn] = cre.obj_index;
- }
- }
- let cre_collection = unsafeWindow.stage.pole.obj
- if (mapobj[xr_last + yr_last * defxn] === undefined || cre_collection[mapobj[xr_last + yr_last * defxn]].rock === 1) {
- paint_coords(xr_last, yr_last, "#cccccc")
- return
- }
- if (calc_x === undefined) {
- [calc_x, calc_y] = [xr_last, yr_last];
- paint_coords(xr_last, yr_last, "#800000");
- let attacker = cre_collection[mapobj[calc_x + calc_y * defxn]]
- if (attacker.hero === 1) {
- readjust_elements();
- individual_calc.innerHTML = ` <div id="individual_cre_heading" style="display:inline; background-color: ${physCalcColor}">
- <span>Урон <br>
- </span>
- <b>${attacker.nametxt}</b> по
- <br>
- </div>
- `;
- }
- } else {
- readjust_elements();
- let atk_obj_index = unsafeWindow.mapobj[calc_x + calc_y * defxn]
- let def_obj_index = unsafeWindow.mapobj[xr_last + yr_last * defxn]
- set_Display([individual_calc, collapse_button], "inline")
- if (cre_distance_on) {
- cre_distance_div.style.display = "inline";
- cre_distance_div.innerHTML = `<span>Выбранное расстояние: ${GM_getValue('cre_distance')}</span><br>`
- }
- individual_calc.innerHTML = individual_calc_innerHTML(atk_obj_index, def_obj_index);
- calc_x = calc_y = undefined
- paint_coords(xr_last, yr_last, "blue")
- }
- }
- let mobileSetting;
- // если есть настройка подтверждения хода = моб. версия, + поддержка моб версии
- const loadedInterval = setInterval(() => {
- mobileSetting = document.querySelector("#submit_hod_settings_whole");
- if (!mobileSetting) return;
- clearInterval(loadedInterval);
- if (android || iOS) {
- const helpButtonHTML = `<div id="help_buttonScript" class="toolbars_mobile_img"><span style = "color:white;">урон</span><img id = "help_imgScript" src="https://dcdn.heroeswm.ru/i/combat/btn_help.png?v=6" style="opacity:0.5"><br></div>`
- document.querySelector("#left_button").insertAdjacentHTML("beforeEnd", helpButtonHTML);
- const helpButton = document.querySelector("#help_buttonScript");
- helpButton.addEventListener("touchend", event => {
- calc_x = calc_y = undefined;
- const firstTime = localStorage.getItem("battle_damage_tooltip_mobile_first_time");
- if (!firstTime) {
- localStorage.setItem("battle_damage_tooltip_mobile_first_time", 1);
- alert("Кнопка с вопросительным знаком -- активация просмотра урона в скрипте battle_damage_tooltip. Чтобы посмотреть урон, нужно, чтобы эта кнопка была активной. Тап на атакующее существо (клетка с существом помечается красным цветом), затем тап на атакуемое существо (клетка синим цветом). Урон будет в боевом чате");
- }
- const img = helpButton.querySelector("img");
- img.style.opacity = img.style.opacity === "0.5" ? "1" : "0.5";
- helpButton.classList.toggle("active");
- })
- document.addEventListener("touchend", event => {
- info_btn_cnt = 0;
- if (!helpButton.classList.contains("active") || event.target.id === "help_imgScript") return;
- manageDamageCalc();
- })
- }
- }, 100);
- // Урон одного стека по другому по выбору нажатием кнопки E
- window.addEventListener("keyup", event => {
- const keyCode = parseInt(event.keyCode);
- /* // Должно быть открытие настроек на Esc, но чтоб не мешало в бою надо устранять ситуацию когда открыта инфа о существе и на esc она закрывается
- if (event.key === 'Escape'){
- for (const panel of document.querySelectorAll(".window_relative")){
- if (panel.style.display !== "none" && panel.id !== "win_Settings") {console.log("smth opened already"); return}
- }
- document.querySelector("#win_Settings").style.display = document.querySelector("#win_Settings").style.display ? '' : 'none';
- } */
- if ((document.querySelector("#chattext") === document.activeElement) || (document.querySelector("#chattext_classic") === document.activeElement)) return;
- if (keyCode === keyboardKeycodes[seeDamage.toLowerCase()]) manageDamageCalc();
- if (keyCode === keyboardKeycodes[seeMagShot.toLowerCase()]) {
- //if (["N", "n", "т", "Т"].includes(event.key)) {
- if (!magshot_x) {
- [magshot_x, magshot_y] = [xr_last, yr_last]
- paint_coords(xr_last, yr_last, "#FC7052", 4000)
- } else {
- paint_coords(xr_last, yr_last, "#7A71FE", 4000)
- magshot(magshot_x, magshot_y, xr_last, yr_last)
- magshot_x = magshot_y = null
- }
- }
- });
- // -----------------------------------
- // ========= battleHelper ============
- // function wrap_battlehelper() {
- // for (const child of battlehelper_div.children) {
- // if (child.className === "cont") return
- // }
- // readjust_elements();
- // let el_transfer = [];
- // [...outer_chat.children].forEach(child => {
- // if (["B", "BR"].includes(child.tagName) || child.className == "cont") {
- // el_transfer.push(child)
- // }
- // });
- // for (const el of el_transfer) battlehelper_div.appendChild(el);
- // const first_icons = battlehelper_div.querySelectorAll('br + div.cont');
- // let teams_text = [...outer_chat.childNodes].filter(node => (node.nodeType === node.TEXT_NODE && /Команда №(\d)/.test(node.textContent.trim())));
- // let i = 0
- // for (const img_div of first_icons) {
- // img_div.previousSibling.insertAdjacentHTML('beforebegin', teams_text[i].textContent);
- // i++;
- // }
- // for (const el of teams_text) el.remove()
- // let title_arr = [...battlehelper_div.children].filter(child => child.textContent === "Стартовый бонус АТБ")
- // if (battlehelper_div.children.length === 2 && title_arr.length === 1) {
- // battlehelper_div.innerHTML = " "
- // }
- // }
- // observer.observe(outer_chat, { childList: true });
- // setTimeout(function() {
- // observer.disconnect();
- // }, 30000);
- // -----------------------------------
- // ========= маг. урон ============
- const damageSpells = {
- "meteor": "Метеоритный дождь",
- "lighting": "Молния",
- "implosion": "Взрыв",
- "fireball": "Огненный шар",
- "chainlighting": "Цепная молния",
- "firewall": "Огненная стена",
- "magicarrow": "Магическая стрела",
- "stonespikes": "Каменные шипы",
- "magicfist": "Магический кулак",
- "icebolt": "Ледяная глыба",
- "circle_of_winter": "Кольцо холода",
- "swarm": "Осиный рой",
- "angerofhorde": "Ярость орды",
- "poison": "Разложение",
- "stormcaller": "Зов бури",
- "calllightning": "Зов молний",
- "firearrow": "Огненная стрела",
- "divinev": "Божественная месть"
- }
- function calcFactionModifier(attacker, defender) {
- let modifier, k;
- if ((umelka[attacker['owner']][0] > 0) && (umelka[defender['owner']][0] > 0)) {
- k = umelka[attacker['owner']][0];
- if ((k > 0) && (k < 11)) {
- let j = umelka[defender['owner']][k];
- modifier = 1 - j * 0.03;
- };
- };
- return modifier;
- }
- function calcHellFire(attacker, defender, cre_collection) {
- const factionModifier = calcFactionModifier(attacker, defender);
- const spellPower = cre_collection[heroes[attacker.owner]].maxnumber;
- const perkModifier = isperk(attacker.obj_index, 104) ? 1.5 : 1;
- // console.log("round: ", Math.round((7 * spellPower + 7) * perkModifier) * factionModifier);
- const res = Math.floor(Math.round((7 * spellPower + 7) * perkModifier) * factionModifier);
- // console.log("floor: ", Math.floor((7 * spellPower + 7) * perkModifier) * factionModifier);
- // return Math.round((7 * spellPower + 7) * perkModifier * factionModifier);
- return res;
- }
- // добавление spellname_magiceff для объекта для дальнийших расчетов
- function initEff(s, activeobj_S) { // s = spell name
- if (stage[war_scr].obj[activeobj_S][s + 'effmain'] > 0) {
- let eff;
- if (stage[war_scr].obj[activeobj_S].hero) {
- var s1 = 0;
- if ((isperk(activeobj_S, 93)) && ((s == 'magicfist') || (s == 'raisedead'))) { s1 = 4; };
- if ((isperk(activeobj_S, 78)) && ((s == 'poison') || (s == 'mpoison'))) { s1 += 5; };
- if ((isperk(activeobj_S, 89)) && ((s == 'poison') || (s == 'mpoison'))) { s1 += 3; };
- eff = (stage[war_scr].obj[activeobj_S][s + 'effmain'] + stage[war_scr].obj[activeobj_S][s + 'effmult'] * (stage[war_scr].getspellpower(activeobj_S, s) + s1));
- if (stage[war_scr].obj[activeobj_S][s + 'effmult'] == 1.5) { eff = Math.round(eff); };
- var teff = eff;
- } else {
- eff = Math.round(stage[war_scr].obj[activeobj_S][s + 'effmain'] + stage[war_scr].obj[activeobj_S][s + 'effmult'] * Math.pow(stage[war_scr].obj[activeobj_S]['nownumber'], 0.7));
- if (s == 'blind') {
- eff = Math.round(stage[war_scr].obj[activeobj_S][s + 'effmain'] + stage[war_scr].obj[activeobj_S][s + 'effmult'] * stage[war_scr].obj[activeobj_S]['nownumber']);
- };
- var teff = eff;
- }
- stage[war_scr].obj[activeobj_S][s + '_magiceff'] = eff;
- }
- }
- function initMagicCalc() {
- // родной calcmagic с удалением кодом массовых заклов и др. побочных эффектов наведения курсора с активным заклом
- unsafeWindow.stage.pole.calcmagic_script = function calcmagic(atk_x, atk_y, xr, yr, magicuse, penalty = 1) {
- console.log(magicuse);
- let i = mapobj[atk_x + defxn * atk_y];
- const activeobj_S = i;
- initEff(magicuse, i);
- unsafeWindow.Totalmagicdamage = 0;
- unsafeWindow.Totalmagickills = 0;
- var ok = false;
- unsafeWindow.mul = 1;
- var len = unsafeWindow.stage.pole.obj_array.length;
- for (var k1 = 0; k1 < len; k1++) {
- var j = unsafeWindow.stage.pole.obj_array[k1];
- unsafeWindow.stage.pole.obj[j]['attacked'] = 1;
- unsafeWindow.stage.pole.obj[j]['attacked2'] = 1;
- };
- if ((magicuse == 'magicfist') || (magicuse == 'angerofhorde')) {
- var eff = unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'];
- if ((magicuse == 'magicfist') && (unsafeWindow.stage.pole.obj[mapobj[xr + yr * defxn]]['organicarmor'])) eff = Math.round(eff * 0.2);
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], eff, 'neutral', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'swarm') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'], 'other', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse === "divinev") {
- var separhsum = (stage.pole.obj[mapobj[xr + yr * defxn]].separhsum ? 1 : 0);
- var eff = (stage.pole.obj[i]['divineveffmain'] + Math.round(stage.pole.obj[i]['divineveffmult'] * Math.pow(stage.pole.obj[i]['nownumber'], 0.7))) * Math.sqrt(separhsum);
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], eff, 'other', 'divinev', 0, 0, 0);
- ok = true;
- }
- if ((magicuse == 'magicarrow') || (magicuse == 'lighting')) {
- if (unsafeWindow.stage.pole.obj[activeobj_S]['calllightning']) {
- unsafeWindow.stage.pole.obj[activeobj_S]['lighting_magiceff'] = 50 * unsafeWindow.stage.pole.obj[activeobj_S]['nownumber'];
- };
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'air', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'firearrow') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'fire', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'icebolt') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'cold', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'implosion') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'poison') {
- unsafeWindow.stage.pole.calcpoison(i, mapobj[xr + yr * defxn], unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff']);
- ok = true;
- };
- if (magicuse == 'meteor') {
- var eff = unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'];
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(eff * mul), 'earth', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'chainlighting') {
- var eff = unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'];
- if (unsafeWindow.stage.pole.obj[activeobj_S]['spmult'] > 1) {
- eff = Math.round(unsafeWindow.stage.pole.obj[activeobj_S]['spmult'] * (unsafeWindow.stage.pole.obj[activeobj_S]['chainlightingeffmain'] + unsafeWindow.stage.pole.obj[activeobj_S]['chainlightingeffmult'] * Math.pow(unsafeWindow.stage.pole.obj[activeobj_S]['nownumber'], 0.7)));
- }
- if (penalty === 1) {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(eff * mul), 'air', 'lighting', 0, 0, 0);
- } else {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.floor(Math.round(eff * mul) * penalty), 'air', 'lighting', 0, 0, 0);
- }
- ok = true;
- };
- if (magicuse == 'fireball') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'fire', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'stormcaller') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S].nownumber * 10), 'air', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'firewall') {
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'], 'fire', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'circle_of_winter') {
- console.log("mul", mul);
- console.log("eff", unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff']);
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'water', magicuse, 0, 0, 0);
- ok = true;
- };
- if (magicuse == 'stonespikes') {
- // unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn + 1], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- // unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn - 1], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- // unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + (yr + 1) * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- // unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + (yr - 1) * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- unsafeWindow.stage.pole.attackmagic(i, mapobj[xr + yr * defxn], Math.round(unsafeWindow.stage.pole.obj[activeobj_S][magicuse + '_magiceff'] * mul), 'earth', magicuse, 0, 0, 0);
- ok = true;
- };
- // if ((ok) && (magicuse != '') && ((magicuse == 'circle_of_winter') || (magicuse == 'icebolt')) && (((unsafeWindow.stage.pole.obj[activeobj_S]['hero']) && (isperk(activeobj_S, 99))) || (unsafeWindow.stage.pole.obj[activeobj_S]['master_of_ice']))) {
- // unsafeWindow.stage.pole.showatb();
- // };
- // if ((ok) && (magicuse != '') && (unsafeWindow.stage.pole.obj[activeobj_S][magicuse + 'elem'] == 'air') && (((unsafeWindow.stage.pole.obj[activeobj_S]['hero']) && (isperk(activeobj_S, 100))) || (unsafeWindow.stage.pole.obj[activeobj_S]['master_of_storms']))) {
- // unsafeWindow.stage.pole.showatb();
- // };
- return Totalmagicdamage;
- };
- // копипаст с удаленем запрета на показ урона по своим стекам
- stage.pole.attackmagic = function attackmagic(attacker, defender, eff, element, iname, noexp, nodamage, nomult) {
- if (defender == 1000) return 0;
- if ((defender <= 0) || (defender == undefined) || (!this.obj[defender])) return 0;
- // if (this.obj[attacker].getside()==this.obj[defender]['side']) return 0;
- if ((this.obj[defender]['rock']) || (this.obj[defender]['hero'])) return 0;
- if (!nomult) nomult = 0;
- if (this.obj[defender]['y'] < 0) return 0;
- if (this.obj[defender]['attacked'] != 1) return 0;
- if ((magic[attacker]['apc']) && (magic[attacker]['apc']['effect'] > 0)) {
- eff *= magic[attacker]['apc']['effect'] / 100;
- };
- if (this.obj[defender]['building']) {
- eff *= 0.05;
- };
- if ((magic[defender]['enc']) && (magic[defender]['enc']['effect'] == 1)) {
- eff *= 0.5;
- };
- if (this.obj[attacker]['forbiddenspell']) {
- eff *= this.check_forbiddenspell(attacker);
- }
- this.obj[defender]['attacked'] = 0;
- if ((this.obj[defender]['owner'] == 2) && ((is_naim_guild(btype)) || ((btype != 13) && (plid2 == -2))) && (this.obj[attacker]['hero'])) {
- eff *= checkmage(this.obj[attacker]['owner'], iname);
- };
- if ((btype == 108) && (checkwall2(this.obj[attacker]['x'], this.obj[attacker]['y'], this.obj[defender]['x'], this.obj[defender]['y'], attacker))) eff *= 0.5;
- if ((btype == 118) && (checkwall2(this.obj[attacker]['x'], this.obj[attacker]['y'], this.obj[defender]['x'], this.obj[defender]['y'], attacker))) eff *= 0.5;
- var hera = 0;
- var herd = 0;
- var len = this.obj_array.length;
- for (var k1 = 0; k1 < len; k1++) {
- var k = this.obj_array[k1];
- if ((this.obj[k].hero) && (this.obj[k].owner == this.obj[attacker].owner)) hera = k;
- if ((this.obj[k].hero) && (this.obj[k].owner == this.obj[defender].owner)) herd = k;
- };
- if ((hera > 0) && (magic[hera]['bna'])) {
- eff = eff * (1 + magic[hera]['bna']['effect'] / 100);
- };
- if ((!this.obj[attacker]['hero']) && (isperk(attacker, _PERK_BLESS))) {
- eff *= 1.04;
- };
- if ((herd > 0) && (magic[herd]['bnd'])) {
- eff = eff / (1 + magic[herd]['bnd']['effect'] / 100);
- };
- if ((herd > 0) && (magic[herd]['fld'])) {
- eff = eff * (1 - magic[herd]['fld']['effect'] / 100);
- };
- if ((herd > 0) && (magic[herd]['rcd']) && (monster_race[this.obj[attacker]['id']] == magic[herd]['rcd']['effect'])) {
- eff = eff * 0.93;
- };
- if ((!this.obj[attacker]['hero']) && (magic[attacker]['zat']) && ((magic[attacker]['zat']['effect'] == 1) || (magic[attacker]['zat']['effect'] == 2))) {
- eff *= 1.15;
- };
- if ((magic[defender]['sum']) && (isperk(attacker, _PERK_EXORCISM)) && (nomult == 0)) {
- eff *= 2;
- };
- //eff1=24 eff2=24 eff3=31.056 eff4=27.28 imm=70.6 imm2=83.0068 eff5=22.64425504
- eff = this.calceffmagic(attacker, defender, eff, element);
- ignor = 0;
- if ((magic[defender]['mmn']) && (element != 'neutral')) {
- eff *= 1 + magic[defender]['mmn']['effect'] / 100;
- }
- if ((hera > 0) && (this.obj[hera]['hero'])) {
- h = hera;
- if (nomult == 0) {
- if ((magic[h]['_en']) && (element == 'neutral')) {
- eff *= 1 + magic[h]['_en']['effect'] / 100;
- };
- if ((magic[h]['_ea']) && (element == 'air')) {
- eff *= 1 + magic[h]['_ea']['effect'] / 100;
- };
- if ((magic[h]['_ew']) && (element == 'cold')) {
- eff *= 1 + magic[h]['_ew']['effect'] / 100;
- };
- if ((magic[h]['_ef']) && (element == 'fire')) {
- eff *= 1 + magic[h]['_ef']['effect'] / 100;
- };
- if ((magic[h]['_ee']) && (element == 'earth')) {
- eff *= 1 + magic[h]['_ee']['effect'] / 100;
- };
- };
- if ((magic[h]['_Ia']) && ((element == 'air') || (iname == 'lighting'))) {
- ignor = magic[h]['_Ia']['effect'] / 100;
- };
- if ((magic[h]['_Iw']) && (element == 'cold')) {
- ignor = magic[h]['_Iw']['effect'] / 100;
- };
- if ((magic[h]['_If']) && (element == 'fire')) {
- ignor = magic[h]['_If']['effect'] / 100;
- };
- if ((magic[h]['_Ie']) && (element == 'earth')) {
- ignor = magic[h]['_Ie']['effect'] / 100;
- };
- };
- magicdamage = Math.round(eff);
- if ((umelka[this.obj[attacker]['owner']][0] > 0) && (umelka[this.obj[defender]['owner']][0] > 0)) {
- var k = umelka[this.obj[attacker]['owner']][0];
- if ((k > 0) && (k < 11)) {
- j = umelka[this.obj[defender]['owner']][k];
- magicdamage = magicdamage * (100 - j * 3) / 100;
- };
- };
- immune = this.getattackimmune(attacker, defender, element, iname, 1);
- if (hera > 0) {
- h = hera;
- if ((magic[h]['nut']) && (plid2 == -2)) {
- magicdamage = magicdamage * (100 + magic[h]['nut']['effect']) / 100;
- };
- if ((magic[h]['imd'])) {
- ignor = 1 - (1 - ignor) * (1 - magic[h]['imd']['effect'] / 100);
- };
- if ((this.obj[defender]['mechanical']) && (magic[hera]['MEC']) && (element == 'neutral')) {
- magicdamage *= 1 + magic[hera]['MEC']['effect'] / 100;
- };
- };
- if (isperk(defender, _PERK_BONEWARD)) {
- immune *= 0.8;
- };
- immune2 = 0;
- if (element != 'neutral') {
- var xx = 0,
- yy = 0,
- xx1 = 0,
- yy1 = 0;
- var bigx = this.obj[defender]['big'];
- var bigy = this.obj[defender]['big'];
- if (this.obj[defender]['bigx']) bigx = 1;
- if (this.obj[defender]['bigy']) bigy = 1;
- for (xx = -1; xx <= 1 + bigx; xx++) {
- for (yy = -1; yy <= 1 + bigy; yy++) {
- xx1 = this.obj[defender]['x'] + xx;
- yy1 = this.obj[defender]['y'] + yy;
- if ((mapobj[xx1 + yy1 * defxn] > 0) && (!this.obj[defender]['magnetism']) && (this.obj[mapobj[xx1 + yy1 * defxn]]['side'] == this.obj[defender]['side']) && (this.obj[mapobj[xx1 + yy1 * defxn]]['magnetism'])) {
- if (immune2 < this.obj[mapobj[xx1 + yy1 * defxn]]['nownumber']) {
- immune2 = this.obj[mapobj[xx1 + yy1 * defxn]]['nownumber'];
- var mg = mapobj[xx1 + yy1 * defxn];
- };
- break;
- };
- };
- };
- immune2 = Math.min(100, immune2);
- if ((this.obj[defender]['enchantedarmor']) && (this.obj[defender]['nownumber'] > 0) && (this.obj[attacker]['side'] == this.obj[defender]['side'])) { immune2 = 100; var mg = defender; };
- };
- if (this.obj[defender]['organicarmor']) ignor = 0;
- immune1 = (100 - (100 - immune) * (1 - ignor));
- dambefore = Math.round(magicdamage * immune1 / 100);
- immune *= 1 - immune2 / 100;
- immune = (100 - (100 - immune) * (1 - ignor));
- magicdamage = Math.round(magicdamage * immune / 100);
- if (magic[defender]['rag']) {
- magicdamage = this.ragedamage(defender, magicdamage);
- };
- Totalmagicdamage += magicdamage;
- var totalh = (this.obj[defender]['nownumber'] - 1) * this.obj[defender]['maxhealth'] + this.obj[defender]['nowhealth'];
- var kills = Math.floor(Math.min(magicdamage, totalh) / this.obj[defender]['maxhealth']);
- var nowhealth = this.obj[defender]['nowhealth'] - (Math.min(magicdamage, totalh) - kills * this.obj[defender]['maxhealth']);
- if (nowhealth <= 0) kills++;
- Totalmagickills += kills;
- if ((magicuse != '') && (defender > 0) && (this.obj[attacker][magicuse + 'elem'] == 'air') && (((this.obj[attacker]['hero']) && (isperk(attacker, 100 /*_PERK_MASTER_OF_STORMS*/ ))) || (this.obj[activeobj]['master_of_storms']))) {
- var a = 0.3;
- if (this.obj[activeobj]['master_of_storms']) a = this.obj[activeobj]['master_of_storms'] / 100;
- init = Math.floor((100 - this.obj[defender]['nowinit'] + this.obj[attacker]['nowinit']) * a);
- this.obj[defender]['reset_init'] = init;
- };
- if ((magicuse != '') && ((magicuse == 'circle_of_winter') || (magicuse == 'icebolt')) && (((this.obj[activeobj]['hero']) && (isperk(activeobj, 99 /*_PERK_MASTER_OF_ICE*/ ))) || (this.obj[activeobj]['master_of_ice']))) {
- var a = 30;
- if (this.obj[activeobj]['master_of_ice']) a = this.obj[activeobj]['master_of_ice'];
- setn_temp_magic(defender, 'cld', a);
- };
- }
- stage.pole.calcpoison = function calcpoison(i, j, eff) {
- var defender = j;
- var attacker = i;
- function experimental() {
- if ((magic[attacker]['apc']) && (magic[attacker]['apc']['effect'] > 0)) {
- eff *= magic[attacker]['apc']['effect'] / 100;
- };
- if (stage.pole.obj[attacker]['forbiddenspell']) {
- eff *= stage.pole.check_forbiddenspell(attacker);
- }
- if ((!stage.pole.obj[attacker]['hero']) && (isperk(attacker, _PERK_BLESS))) {
- eff *= 1.04;
- };
- if ((herd > 0) && (magic[herd]['fld'])) {
- eff = eff * (1 - magic[herd]['fld']['effect'] / 100);
- };
- if ((herd > 0) && (magic[herd]['rcd']) && (monster_race[stage.pole.obj[attacker]['id']] == magic[herd]['rcd']['effect'])) {
- eff = eff * 0.93;
- };
- if ((!stage.pole.obj[attacker]['hero']) && (magic[attacker]['zat']) && ((magic[attacker]['zat']['effect'] == 1) || (magic[attacker]['zat']['effect'] == 2))) {
- eff *= 1.15;
- };
- if ((magic[defender]['sum']) && (isperk(attacker, _PERK_EXORCISM)) && (nomult == 0)) {
- eff *= 2;
- };
- if ((hera > 0) && (stage.pole.obj[hera]['hero'])) {
- h = hera;
- if (nomult == 0) {
- if ((magic[h]['_ee'])) {
- eff *= 1 + magic[h]['_ee']['effect'] / 100;
- };
- };
- if ((magic[h]['_Ie'])) {
- ignor = magic[h]['_Ie']['effect'] / 100;
- };
- };
- }
- //experimental();
- if ((defender <= 0) || (defender == undefined)) return 0;
- // if (stage.pole.obj[attacker].getside() == stage.pole.obj[defender]['side']) return 0;
- if ((stage.pole.obj[defender]['rock']) || (stage.pole.obj[defender]['hero'])) return 0;
- if (stage.pole.obj[defender]['y'] < 0) return 0;
- if (stage.pole.obj[defender]['attacked'] != 1) return 0;
- stage.pole.obj[defender]['attacked'] = 0;
- var hera = 0;
- var herd = 0;
- var attacker = i;
- var len = stage.pole.obj_array.length;
- for (var k1 = 0; k1 < len; k1++) {
- var k = stage.pole.obj_array[k1];
- if ((stage.pole.obj[k].hero) && (stage.pole.obj[k].owner == stage.pole.obj[attacker].owner)) hera = k;
- if ((stage.pole.obj[k].hero) && (stage.pole.obj[k].owner == stage.pole.obj[defender].owner)) herd = k;
- };
- if (stage.pole.obj[j]['absolutepurity']) eff = 0;
- if (stage.pole.obj[j]['building']) eff *= 0.05;
- if (hera > 0) {
- h = hera;
- if (magic[h]['_ee']) {
- eff *= 1 + magic[h]['_ee']['effect'] / 100;
- };
- eff = Math.round(eff);
- if ((hera > 0) && (magic[hera]['bna'])) {
- eff = Math.round(eff * (1 + magic[hera]['bna']['effect'] / 100));
- };
- if ((herd > 0) && (magic[herd]['bnd'])) {
- eff = Math.round(eff / (1 + tmagic[herd]['bnd']['effect'] / 100));
- };
- if (stage.pole.obj[j]['vulnerabletoshadowmagic']) eff *= 1.25;
- };
- eff = Math.round(eff);
- var magicdamage = eff;
- if ((umelka[stage.pole.obj[attacker]['owner']][0] > 0) && (umelka[stage.pole.obj[defender]['owner']][0] > 0)) {
- var k = umelka[stage.pole.obj[attacker]['owner']][0];
- if ((k > 0) && (k < 11)) {
- j = umelka[stage.pole.obj[defender]['owner']][k];
- magicdamage = magicdamage * (100 - j * 3) / 100;
- };
- };
- magicdamage = Math.round(magicdamage);
- Totalmagicdamage += magicdamage;
- Totalmagicdamage = Math.round(Totalmagicdamage / 1.1);
- var totalh = (stage.pole.obj[defender]['nownumber'] - 1) * stage.pole.obj[defender]['maxhealth'] + stage.pole.obj[defender]['nowhealth'];
- var kills = Math.floor(Math.min(magicdamage, totalh) / stage.pole.obj[defender]['maxhealth']);
- var nowhealth = stage.pole.obj[defender]['nowhealth'] - (Math.min(magicdamage, totalh) - kills * stage.pole.obj[defender]['maxhealth']);
- if (nowhealth <= 0) kills++;
- Totalmagickills += kills;
- };
- unsafeWindow.check_keys = function check_keys(key) {
- if (key == 27) {
- if ((buttons_visible['magicbook_button_close']) || (buttons_visible['magicbook_button_close2']))
- hide_magic_book();
- if (buttons_visible['rune_off_button'])
- rune_button_off_onRelease();
- if (buttons_visible['info_off'])
- info_off_onRelease();
- if ((buttons_visible['oneskill_button_close']) || (buttons_visible['oneskill_button_close2'])) {
- stage[war_scr].oneskillbutton_onRelease();
- };
- hide_button('win_InfoCreature');
- hide_button('win_InfoHero');
- hide_button('win_InfoHero2');
- hide_button('win_InfoCreatureEffect');
- };
- if (chatfocus) {
- if (key == 13) {
- btn_SendChatMessage_release();
- };
- return 0;
- }
- if ((key == 68) && ((buttons_visible['defend_button']) || (buttons_visible['defend_button2'])))
- defend_button_release();
- if (key == 32) {
- if (buttons_visible['pause_button']) {
- pause_button_onRelease();
- } else if (buttons_visible['play_button']) {
- play_button_onRelease();
- };
- };
- if ((key == 87) && ((buttons_visible['wait_button']) || (buttons_visible['wait_button2'])))
- wait_button_release();
- if (key == 67) {
- if ((buttons_visible['magicbook_button']) || (buttons_visible['magicbook_button2']))
- magicbook_button_release();
- else if ((buttons_visible['magicbook_button_close']) || (buttons_visible['magicbook_button_close2']))
- hide_magic_book();
- if ((buttons_visible['oneskill_button']) || (buttons_visible['oneskill_button2']) || (buttons_visible['oneskill_button_close']) || (buttons_visible['oneskill_button_close2'])) {
- stage[war_scr].oneskillbutton_onRelease();
- };
- };
- }
- defend_button_release = function defend_button_release() {
- console.log("altered defend funtcion")
- if ((is_visible_element('magic_book')) || (buttons_visible['scroll_runes'])) {
- return 0;
- }
- if ((someactive) || (!inserted)) {
- return 0;
- }
- if (Object.values(heroes).includes(activeobj)) {
- alert("Скрипт battle_damage_tooltip заблокировал оборону во время хода героя! Клик по кнопке свободен.")
- return 0;
- }
- if ((loader.loading) || (activeobj == 0)) {
- return 0;
- }
- if ((info_button) && (android)) {
- return 0;
- };
- loader.loading = true;
- pl_id = player;
- if (player2 > 0)
- pl_id = player2;
- loadmy('battle.php?warid=' + warid + '&move=1&defend=1&pl_id=' + pl_id + '&my_monster=' + activeobj + '&x=' + stage[war_scr].obj[activeobj].x + '&y=' + stage[war_scr].obj[activeobj].y + '&lastturn=' + lastturn + '&lastmess=' + lastmess + '&lastmess2=' + lastmess2 + '&rand=' + mathrandom());
- }
- }
- // -----------------------------------
- // Функция рельсы гвд с поправкой на выбор клеток юзером
- function magshot(x1, y1, xr, yr) {
- var x2 = xr;
- var y2 = yr;
- var dx = Math.abs(x1 - x2);
- var dy = Math.abs(y1 - y2);
- var skip = false;
- if (x1 < x2) {
- var xp = 1;
- } else {
- var xp = -1;
- };
- if (y1 < y2) {
- var yp = 1;
- } else {
- var yp = -1;
- };
- if (dx > dy) {
- if (x1 > x2) {
- var x = -5;
- } else {
- var x = defxn + 3 - 1;
- };
- var y = (y2 - y1) / (x2 - x1) * (x - x1) + y1;
- } else {
- if (y1 > y2) {
- var y = -5;
- } else {
- var y = defyn + 5 + 1;
- };
- var x = (x2 - x1) / (y2 - y1) * (y - y1) + x1;
- };
- x = x1;
- y = y1;
- while ((x > 0) && (y > 0) && (x <= defxn - 2) && (y <= defyn)) {
- if (dx > dy) {
- x += xp;
- y = (y2 - y1) / (x2 - x1) * (x - x1) + y1;
- } else {
- y += yp;
- x = (x2 - x1) / (y2 - y1) * (y - y1) + x1;
- };
- let shot_coords = []
- if ((Math.round(x) > 0) && (Math.round(y) > 0) && (Math.round(x) <= defxn - 2) && (Math.round(y) <= defyn)) {
- if (shado[Math.round(x) + Math.round(y) * defxn]) {
- set_visible(shado[Math.round(x) + Math.round(y) * defxn], 1);
- shot_coords.push({ x: Math.round(x), y: Math.round(y) })
- }
- };
- setTimeout(() => {
- for (const coord of shot_coords) {
- set_visible(shado[coord.x + coord.y * defxn], 0);
- }
- }, 4000)
- };
- };
- // Родная функция гвд с поправками на переменную l и модификаторами magic[]
- function attackmonster(attacker, ax, ay, x, y, defender, cre_distance, shootok, koef, inuse) {
- let cre_collection = unsafeWindow.stage.pole.obj
- var mainattack = 1;
- var ax1 = ax;
- var ay1 = ay;
- if (defender == 1000) return 0;
- if (defender <= 0) return 0;
- if (!cre_collection[defender]) return 0;
- if (cre_collection[defender]['hero']) return 0;
- if (cre_collection[defender]['rock']) return 0;
- if (koef == undefined) koef = 1;
- if (inuse == undefined) inuse = '';
- var len = unsafeWindow.wmap2[y * defxn + x];
- if ((cre_collection[attacker].x == x) && (cre_collection[attacker].y == y)) len = spd;
- shootok = 1;
- function getAdjacentAndDiagonalCoords(x, y) {
- const adjacentAndDiagonalCoords = [];
- adjacentAndDiagonalCoords.push([x + 1, y]);
- adjacentAndDiagonalCoords.push([x - 1, y]);
- adjacentAndDiagonalCoords.push([x, y + 1]);
- adjacentAndDiagonalCoords.push([x, y - 1]);
- adjacentAndDiagonalCoords.push([x + 1, y + 1]);
- adjacentAndDiagonalCoords.push([x - 1, y + 1]);
- adjacentAndDiagonalCoords.push([x + 1, y - 1]);
- adjacentAndDiagonalCoords.push([x - 1, y - 1]);
- return adjacentAndDiagonalCoords;
- }
- if (cre_collection[attacker].shots === 0) {
- shootok = 0
- } else {
- let attacker_adjacent_coords = getAdjacentAndDiagonalCoords(stage.pole.obj[attacker].x, stage.pole.obj[attacker].y)
- let enemies_list = Object.values(stage.pole.obj).filter(creature => creature.side != stage.pole.obj[attacker].side)
- enemies_list.forEach(enemy => {
- attacker_adjacent_coords.forEach(coord => {
- if (coord[0] == enemy.x && coord[1] == enemy.y && ![0, -1].includes(enemy.nownumber)) shootok = 0
- })
- })
- }
- if (cre_collection[attacker]['big']) {
- if (ax > x) {
- x++;
- };
- if (ay > y) {
- y++;
- };
- };
- if (cre_collection[attacker]['bigx']) {
- if (ax > x) {
- x++;
- };
- };
- if (cre_collection[attacker]['bigy']) {
- if (ay > y) {
- y++;
- };
- };
- var spd = Math.max(0, Math.round((cre_collection[attacker].speed + cre_collection[attacker]['ragespeed'] + cre_collection[attacker]['speedaddon']) * cre_collection[attacker].speedmodifier));
- if (unsafeWindow.magic[attacker]['ent']) {
- spd = 0;
- };
- var movelen = spd - len;
- unsafeWindow.attacker_c = attacker;
- unsafeWindow.ax_c = ax;
- unsafeWindow.ay_c = ay;
- unsafeWindow.x_c = x;
- unsafeWindow.y_c = y;
- unsafeWindow.defender_c = defender;
- unsafeWindow.shootok_c = shootok;
- if ((x == 0) && (y == 0)) {
- x = cre_collection[attacker]['x'];
- y = cre_collection[attacker]['y'];
- };
- if ((defender > 0) && (cre_collection[defender]['big'])) {
- if ((x - ax > 1) && (ax < x) && (defender == mapobj[ay * defxn + ax + 1])) {
- ax++;
- };
- if ((y - ay > 1) && (ay < y) && (defender == mapobj[(ay + 1) * defxn + ax])) {
- ay++;
- };
- if ((ax - x > 1) && (ax > x) && (defender == mapobj[ay * defxn + ax - 1])) {
- ax--;
- };
- if ((ay - y > 1) && (ay > y) && (defender == mapobj[(ay - 1) * defxn + ax])) {
- ay--;
- };
- };
- if ((defender > 0) && (cre_collection[defender]['bigx'])) {
- if ((x - ax > 1) && (ax < x) && (defender == mapobj[ay * defxn + ax + 1])) {
- ax++;
- };
- if ((ax - x > 1) && (ax > x) && (defender == mapobj[ay * defxn + ax - 1])) {
- ax--;
- };
- };
- if ((defender > 0) && (cre_collection[defender]['bigy'])) {
- if ((y - ay > 1) && (ay < y) && (defender == mapobj[(ay + 1) * defxn + ax])) {
- ay++;
- };
- if ((ay - y > 1) && (ay > y) && (defender == mapobj[(ay - 1) * defxn + ax])) {
- ay--;
- };
- };
- let dx = x - ax;
- let dy = y - ay;
- l = dx * dx + dy * dy;
- if (movelen == undefined) movelen = 0;
- if (cre_distance !== "") {
- movelen = cre_distance
- l = Math.round(cre_distance * cre_distance)
- if (l > 2) shootok = 1
- else shootok = 0
- if (cre_collection[attacker].shots === 0) shootok = 0
- }
- unsafeWindow.PhysicalModifiers = 1;
- unsafeWindow.PhysicalModifiers *= koef;
- if (cre_collection[attacker]['shadowattack']) l = 0;
- var hera = 0;
- var herd = 0;
- len = unsafeWindow.stage.pole.obj_array.length;
- for (var k1 = 0; k1 < len; k1++) {
- unsafeWindow.k = unsafeWindow.stage.pole.obj_array[k1];
- if ((cre_collection[k].hero) && (cre_collection[k].owner == cre_collection[attacker].owner)) hera = unsafeWindow.k;
- if ((cre_collection[k].hero) && (cre_collection[k].owner == cre_collection[defender].owner)) herd = unsafeWindow.k;
- };
- if ((cre_collection[defender]['pirate']) && ((unsafeWindow.magic[defender]['sea']) || (unsafeWindow.gtype == 125) || (unsafeWindow.gtype == 126) || (unsafeWindow.gtype == 133))) {
- unsafeWindow.PhysicalModifiers *= 0.85;
- };
- if (cre_collection[defender]['deadflesh']) {
- unsafeWindow.PhysicalModifiers *= 0.8;
- };
- if (cre_collection[defender]['immaterial']) {
- unsafeWindow.PhysicalModifiers *= 0.65;
- };
- if ((cre_collection[attacker]['oppressionofweak']) && (cre_collection[defender]['level'] == 1)) {
- unsafeWindow.PhysicalModifiers *= 1.5;
- };
- if ((cre_collection[attacker]['fearofstrong']) && (cre_collection[defender]['level'] == 7)) {
- unsafeWindow.PhysicalModifiers *= 0.5;
- };
- if ((hera > 0) && (unsafeWindow.magic[hera]['bna'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 + unsafeWindow.magic[hera]['bna']['effect'] / 100);
- if ((cre_collection[defender]['mechanical']) && (unsafeWindow.magic[hera]['MEC'])) {
- unsafeWindow.PhysicalModifiers *= 1 + unsafeWindow.magic[hera]['MEC']['effect'] / 100;
- };
- if ((cre_collection[attacker]['mechanical']) && (unsafeWindow.magic[hera]['mch'])) {
- unsafeWindow.PhysicalModifiers *= 1 + unsafeWindow.magic[hera]['mch']['effect'] / 100;
- };
- };
- if ((cre_collection[defender]['building']) && (!cre_collection[attacker]['siegewalls'])) {
- unsafeWindow.PhysicalModifiers *= 0.05;
- };
- if ((defender > 0) && (cre_collection[attacker]['cruelty']) && ((cre_collection[defender]['nowhealth'] < cre_collection[defender]['maxhealth']) || (cre_collection[defender]['nownumber'] < cre_collection[defender]['maxnumber']))) {
- unsafeWindow.PhysicalModifiers *= 1.15;
- };
- if ((defender > 0) && (cre_collection[attacker]['morecruelty']) && ((cre_collection[defender]['nowhealth'] < cre_collection[defender]['maxhealth']) || (cre_collection[defender]['nownumber'] < cre_collection[defender]['maxnumber']))) {
- unsafeWindow.PhysicalModifiers *= 1.3;
- };
- if ((cre_collection[attacker]['giantkiller']) && (cre_collection[defender]['big'])) unsafeWindow.PhysicalModifiers *= 2;
- if ((cre_collection[attacker]['pygmykiller']) && (!cre_collection[defender]['big'])) unsafeWindow.PhysicalModifiers *= 1.33;
- if (cre_collection[attacker]['stormstrike']) unsafeWindow.PhysicalModifiers *= 2;
- if ((cre_collection[attacker]['undeadkiller']) && (cre_collection[defender]['undead'])) unsafeWindow.PhysicalModifiers *= 1.5;
- if ((cre_collection[attacker]['pirate']) && (unsafeWindow.magic[defender]['blb'])) unsafeWindow.PhysicalModifiers *= 1.5;
- if ((!cre_collection[attacker]['hero']) && (unsafeWindow.magic[attacker]['zat'])) {
- unsafeWindow.PhysicalModifiers *= 1.15;
- };
- if ((herd > 0) && (unsafeWindow.magic[herd]['bnd'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers / (1 + unsafeWindow.magic[herd]['bnd']['effect'] / 100);
- };
- if ((herd > 0) && (unsafeWindow.magic[herd]['fld'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 - unsafeWindow.magic[herd]['fld']['effect'] / 100);
- };
- if ((herd > 0) && (unsafeWindow.magic[herd]['rcd']) && (monster_race[cre_collection[attacker]['id']] == unsafeWindow.magic[herd]['rcd']['effect'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.93;
- };
- if (unsafeWindow.magic[attacker]['prp']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 + unsafeWindow.magic[attacker]['prp']['effect'] / 100);
- };
- if (unsafeWindow.magic[defender]['sta']) {
- unsafeWindow.PhysicalModifiers *= 0.5;
- };
- if ((unsafeWindow.magic[attacker]['chd']) && (cre_collection[unsafeWindow.magic[attacker]['chd']['effect']]['nownumber'] > 0) && (unsafeWindow.magic[attacker]['chd']['effect'] != defender)) {
- unsafeWindow.PhysicalModifiers *= 0.55;
- };
- unsafeWindow.PhysicalModifiers *= unsafeWindow.stage.pole.checkmembrane(defender);
- if (!cre_collection[attacker]['hero']) {
- if ((l <= 2 || shootok === 0) && (cre_collection[attacker]['shooter']) && (!cre_collection[attacker]['nopenalty']) && (!cre_collection[attacker]['warmachine'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.5;
- };
- if ((l > 2) && (cre_collection[attacker]['rangepenalty'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.5;
- };
- unsafeWindow.rangemod = 1;
- if (l > 2 && (shootok !== 0 || cre_collection[attacker].shots !== 0) && (cre_collection[attacker]['shooter']) && (((cre_collection[attacker]['range'] < Math.sqrt(l)) && (!cre_collection[attacker].shadowattack)) || ((iswalls) && (!cre_collection[attacker]['hero']) && (unsafeWindow.checkwall(x, y, ax, ay))))) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.5;
- unsafeWindow.rangemod = 0.5;
- };
- if (l > 2 && (shootok !== 0 || cre_collection[attacker].shots !== 0) && (cre_collection[attacker]['shooter']) && (iswalls2) && (!cre_collection[attacker]['hero']) && (((!cre_collection[attacker].siegewalls) || (btype == 118)) || (!cre_collection[defender].stone)) && (unsafeWindow.checkwall2(x, y, ax, ay, attacker))) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.5;
- unsafeWindow.rangemod *= 0.5;
- };
- };
- var _PERK_ARCHERY = 11;
- var _PERK_EVASION = 22;
- if ((defender > 0) && ((((cre_collection[attacker].shooter && shootok == 0) || (cre_collection[attacker].shooter != 1) || cre_collection[attacker].shots == 0) && (!cre_collection[attacker]['ballista']) && (inuse != 'ssh') && (inuse != 'mga') && (inuse != 'dcd') && (inuse != 'chs') && (!cre_collection[attacker]['hero'])) || (inuse == 'brs') || (inuse == 'cpt'))) {
- if (cre_collection[defender]['dodge'])
- unsafeWindow.PhysicalModifiers *= 0.5;
- if (cre_collection[defender]['brittle'])
- unsafeWindow.PhysicalModifiers *= 1.25;
- };
- if ((shootok === 1) && (!cre_collection[attacker]['hero']) && (cre_collection[attacker]['shooter'])) {
- if (unsafeWindow.isperk(attacker, _PERK_ARCHERY)) unsafeWindow.PhysicalModifiers *= 1.2;
- if (unsafeWindow.isperk(defender, _PERK_EVASION)) unsafeWindow.PhysicalModifiers *= 0.8;
- if ((!cre_collection[defender]['lshield']) && (unsafeWindow.stage.pole.shieldother(defender))) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.75;
- };
- if ((cre_collection[defender]['lshield']) || (cre_collection[defender]['hollowbones'])) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.5;
- };
- if (cre_collection[defender]['diamondarmor']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.1;
- };
- if (cre_collection[defender]['shielded']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 0.75;
- };
- if (cre_collection[defender]['unprotectedtarget']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * 1.25;
- };
- if (unsafeWindow.magic[defender]['dfm']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 - unsafeWindow.magic[defender]['dfm']['effect'] / 100);
- };
- if (unsafeWindow.magic[attacker]['cnf']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 - unsafeWindow.magic[attacker]['cnf']['effect'] / 100);
- };
- if (hera > 0) {
- if (unsafeWindow.magic[hera]['sat']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 + unsafeWindow.magic[hera]['sat']['effect']) / 100;
- };
- };
- };
- if ((!cre_collection[attacker]['hero']) && (unsafeWindow.isperk(attacker, _PERK_BLESS))) {
- unsafeWindow.PhysicalModifiers *= 1.04;
- };
- let o = cre_collection[attacker]['owner'];
- if (unsafeWindow.magic[defender]['mf' + o]) {
- unsafeWindow.PhysicalModifiers *= 1 + unsafeWindow.magic[defender]['mf' + o]['effect'] / 100;
- };
- if ((!cre_collection[attacker]['hero']) && (unsafeWindow.isperk(attacker, _PERK_FERVOR))) {
- unsafeWindow.PhysicalModifiers *= 1.03;
- };
- if (hera > 0) {
- var h = hera;
- if ((unsafeWindow.magic[h]['nut']) && ((plid2 == -2) || (ohotnik_set_neutral()))) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 + unsafeWindow.magic[h]['nut']['effect']) / 100;
- };
- if ((unsafeWindow.magic[h]['mle']) && ((cre_collection[attacker].shooter && shootok == 0) || (cre_collection[attacker].shooter != 1) || cre_collection[attacker].shots == 0)) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 + unsafeWindow.magic[h]['mle']['effect']) / 100;
- };
- if (unsafeWindow.magic[attacker]['fbd']) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 + Math.floor(unsafeWindow.magic[attacker]['fbd']['effect'] / 10)) / 100;
- };
- };
- let leap_atk_bonus, leap_distance = 0;
- if (cre_collection[attacker].leap && l >= 4) {
- leap_distance = cre_distance ? cre_distance : Math.min((movelen - 1) * 2, Math.round(Math.sqrt(l)));
- leap_atk_bonus = cre_collection[attacker].attack * (1 + leap_distance * 0.1) - cre_collection[attacker].attack
- cre_collection[attacker]['attackaddon'] += leap_atk_bonus
- }
- unsafeWindow.monatt = cre_collection[attacker]['attack'] + cre_collection[attacker]['attackaddon'] + cre_collection[attacker]['rageattack'];
- if ((defender > 0) && (cre_collection[attacker]['giantslayer']) && (cre_collection[defender]['big'])) unsafeWindow.monatt += 4;
- if ((!cre_collection[attacker]['undead']) && (!cre_collection[attacker]['hero']) && (!cre_collection[attacker]['perseverance'])) {
- unsafeWindow.frig2 = false;
- unsafeWindow.i = attacker;
- var bigx = cre_collection[i]['big'];
- var bigy = cre_collection[i]['big'];
- if (cre_collection[i]['bigx']) bigx = 1;
- if (cre_collection[i]['bigy']) bigy = 1;
- unsafeWindow.xd = cre_collection[i]['x'];
- unsafeWindow.yd = cre_collection[i]['y'];
- for (var xz = unsafeWindow.xd - 1; xz <= unsafeWindow.xd + 1 + bigx; xz++) {
- for (var yz = unsafeWindow.yd - 1; yz <= unsafeWindow.yd + 1 + bigy; yz++) {
- if ((!unsafeWindow.frig2) && (mapobj[yz * defxn + xz] > 0) && (cre_collection[mapobj[yz * defxn + xz]]['side'] != cre_collection[i]['side']) && (cre_collection[mapobj[yz * defxn + xz]]['festeringaura']) && (cre_collection[mapobj[yz * defxn + xz]]['nownumber'] > 0)) {
- unsafeWindow.monatt -= 4;
- unsafeWindow.frig2 = true;
- };
- };
- };
- };
- if ((unsafeWindow.magic[attacker]['bsr']) || (unsafeWindow.magic[attacker]['rof'])) {
- unsafeWindow.monatt += Math.floor((cre_collection[attacker]['defence'] + cre_collection[attacker]['defenceaddon'] + cre_collection[attacker]['ragedefence']) * cre_collection[attacker]['defencemodifier']);
- };
- if (herd > 0) {
- h = herd;
- console.log("ass", unsafeWindow.magic[h]['mld']);
- if ((unsafeWindow.magic[h]['mld']) && ((cre_collection[attacker].shooter && shootok == 0) || (cre_collection[attacker].shooter != 1) || cre_collection[attacker].shots == 0)) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 - unsafeWindow.magic[h]['mld']['effect']) / 100;
- };
- if ((unsafeWindow.magic[h]['_ia']) && (!cre_collection[attacker]['perseverance'])) {
- unsafeWindow.monatt *= (1 - unsafeWindow.magic[h]['_ia']['effect'] / 100);
- };
- if ((!cre_collection[attacker]['hero']) && (cre_collection[attacker].shooter) && (cre_collection[attacker].shots != 0) && (unsafeWindow.magic[h]['msk']) && shootok == 1) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (100 - unsafeWindow.magic[h]['msk']['effect']) / 100;
- };
- };
- unsafeWindow.defadd = 0;
- if (cre_collection[defender]['agility']) {
- if (!unsafeWindow.magic[defender]['agl']) unsafeWindow.defadd = cre_collection[defender]['speed'] * 2;
- };
- if ((cre_collection[defender]['spirit']) && (!unsafeWindow.magic[defender]['spi'])) {
- unsafeWindow.PhysicalModifiers *= 0.5;
- };
- if ((cre_collection[attacker]['rageagainsttheliving']) && (cre_collection[defender]['alive'])) {
- unsafeWindow.PhysicalModifiers *= 1.3;
- };
- if ((cre_collection[defender]['defensivestance']) && (!unsafeWindow.magic[defender]['mvd'])) {
- unsafeWindow.defadd += 5;
- };
- if ((!cre_collection[defender]['undead']) && (!cre_collection[defender]['armoured']) && (!cre_collection[defender]['organicarmor'])) {
- unsafeWindow.frig2 = false;
- unsafeWindow.i = defender;
- bigx = cre_collection[i]['big'];
- bigy = cre_collection[i]['big'];
- if (cre_collection[i]['bigx']) bigx = 1;
- if (cre_collection[i]['bigy']) bigy = 1;
- unsafeWindow.xd = cre_collection[i]['x'];
- unsafeWindow.yd = cre_collection[i]['y'];
- for (let xz = unsafeWindow.xd - 1; xz <= unsafeWindow.xd + 1 + bigx; xz++) {
- for (let yz = unsafeWindow.yd - 1; yz <= unsafeWindow.yd + 1 + bigy; yz++) {
- if ((!unsafeWindow.frig2) && (mapobj[yz * defxn + xz] > 0) && (cre_collection[mapobj[yz * defxn + xz]]['side'] != cre_collection[i]['side']) && (cre_collection[mapobj[yz * defxn + xz]]['festeringaura']) && (cre_collection[mapobj[yz * defxn + xz]]['nownumber'] > 0)) {
- unsafeWindow.defadd -= 4;
- unsafeWindow.frig2 = true;
- };
- };
- };
- };
- if ((attacker > 0) && (cre_collection[defender]['giantslayer']) && (cre_collection[attacker]['big'])) unsafeWindow.defadd += 4;
- unsafeWindow.mondef = Math.round((cre_collection[defender]['defence'] + cre_collection[defender]['defenceaddon'] + unsafeWindow.defadd + cre_collection[defender]['ragedefence']) * cre_collection[defender]['defencemodifier']);
- if (unsafeWindow.magic[defender]['bsr']) {
- unsafeWindow.mondef = 0;
- };
- if ((cre_collection[attacker]['preciseshot']) && (l > 2) && (l <= 9) && (unsafeWindow.rangemod >= 1)) {
- unsafeWindow.mondef = 0;
- };
- if ((cre_collection[attacker]['ignoredefence'])) {
- unsafeWindow.mondef *= (1 - cre_collection[attacker]['ignoredefence'] / 100);
- };
- if (cre_collection[attacker]['crushingleadership']) {
- var morale_delta = unsafeWindow.stage.pole.getmorale(attacker) - unsafeWindow.stage.pole.getmorale(defender);
- if (morale_delta > 0) {
- unsafeWindow.mondef *= Math.max(0, 1 - morale_delta / 10);
- };
- };
- if (cre_collection[attacker]['sacredweapon']) {
- var dark_count = get_dark_count(defender);
- if (dark_count > 0) {
- unsafeWindow.mondef *= Math.max(0, 1 - 0.15 * dark_count);
- };
- };
- if (unsafeWindow.isperk(attacker, _PERK_PIERCING_LUCK)) {
- unsafeWindow.mondef *= 1 - Math.max(0, 0.025 * (cre_collection[attacker]['luck'] + cre_collection[attacker]['luckaddon']));
- };
- if ((cre_collection[defender]['ignoreattack'])) {
- unsafeWindow.monatt *= (1 - cre_collection[defender]['ignoreattack'] / 100);
- };
- if ((cre_collection[attacker]['ridercharge']) && (movelen > 0)) {
- unsafeWindow.mondef = unsafeWindow.mondef * (5 - movelen) / 5;
- };
- if ((cre_collection[attacker]['forcearrow']) && (!cre_collection[defender]['armoured']) && (!cre_collection[defender]['organicarmor']) && (l > 2)) {
- unsafeWindow.mondef *= 0.8;
- };
- if ((cre_collection[attacker]['armorpiercing']) && (!cre_collection[defender]['armoured']) && (!cre_collection[defender]['organicarmor']) && (l > 2)) {
- unsafeWindow.mondef *= 0.5;
- };
- if (cre_collection[defender]['shroudofdarkness']) {
- unsafeWindow.PhysicalModifiers *= Math.max(0, 1 - 0.15 * get_dark_count(defender));
- };
- if (cre_collection[attacker]['tasteofdarkness']) {
- unsafeWindow.PhysicalModifiers *= 1 + get_dark_count(defender) * 0.12;
- };
- if ((cre_collection[attacker]['jousting']) && (movelen > 0)) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 + 0.05 * movelen);
- };
- if (((cre_collection[attacker]['blindingcharge']) || (cre_collection[attacker]['charge'])) && (movelen > 0)) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * (1 + 0.1 * movelen);
- };
- if ((cre_collection[defender]['shieldwall']) && (movelen > 0)) {
- unsafeWindow.PhysicalModifiers = unsafeWindow.PhysicalModifiers * Math.max(0.1, 1 - 0.1 * movelen);
- };
- if ((unsafeWindow.magic[defender]['enc']) && (unsafeWindow.magic[defender]['enc']['effect'] == 1)) {
- unsafeWindow.PhysicalModifiers *= 0.5;
- };
- if ((cre_collection[attacker]['safeposition']) && (movelen == 0)) {
- unsafeWindow.PhysicalModifiers *= 1.5;
- };
- if ((cre_collection[attacker]['agilesteed']) && (movelen > 0)) {
- unsafeWindow.PhysicalModifiers *= 1 - 0.05 * movelen;
- };
- if (unsafeWindow.mondef < 0) {
- unsafeWindow.mondef = 0;
- };
- unsafeWindow.air = 0;
- unsafeWindow.fire = 0;
- unsafeWindow.water = 0;
- unsafeWindow.earth = 0;
- if ((hera > 0) && (!cre_collection[attacker]['taran'])) {
- h = hera;
- if (unsafeWindow.magic[h]['_id']) {
- unsafeWindow.mondef *= (1 - unsafeWindow.magic[h]['_id']['effect'] / 100);
- };
- if (unsafeWindow.magic[h]['_aa']) {
- unsafeWindow.air = unsafeWindow.magic[h]['_aa']['effect'] / 100;
- };
- if (unsafeWindow.magic[h]['_af']) {
- unsafeWindow.fire = unsafeWindow.magic[h]['_af']['effect'] / 100;
- };
- if (unsafeWindow.magic[h]['_aw']) {
- unsafeWindow.water = unsafeWindow.magic[h]['_aw']['effect'] / 100;
- };
- if (unsafeWindow.magic[h]['_ae']) {
- unsafeWindow.earth = unsafeWindow.magic[h]['_ae']['effect'] / 100;
- };
- };
- if ((cre_collection[defender]['armoured']) || (cre_collection[defender]['organicarmor'])) {
- unsafeWindow.mondef = Math.round((cre_collection[defender]['defence'] + cre_collection[defender]['defenceaddon'] + cre_collection[defender]['ragedefence']) * cre_collection[defender]['defencemodifier']);
- };
- if (unsafeWindow.monatt < 0) {
- unsafeWindow.monatt = 0;
- };
- if (unsafeWindow.monatt > unsafeWindow.mondef) {
- unsafeWindow.AttackDefenseModifier = 1 + (unsafeWindow.monatt - unsafeWindow.mondef) * 0.05;
- } else {
- unsafeWindow.AttackDefenseModifier = 1 / (1 + (unsafeWindow.mondef - unsafeWindow.monatt) * 0.05);
- };
- if (cre_collection[attacker]['hero']) {
- unsafeWindow.AttackDefenseModifier = 1;
- };
- var _PERK_ATTACK1 = 8;
- var _PERK_ATTACK2 = 9;
- var _PERK_ATTACK3 = 10;
- var _PERK_DEFENSE1 = 19;
- var _PERK_DEFENSE2 = 20;
- var _PERK_DEFENSE3 = 21;
- if ((!cre_collection[attacker]['hero']) && ((cre_collection[attacker].shooter && shootok == 0) || (cre_collection[attacker].shooter != 1))) {
- if (unsafeWindow.isperk(attacker, _PERK_ATTACK3)) {
- unsafeWindow.PhysicalModifiers *= 1.3;
- } else {
- if (unsafeWindow.isperk(attacker, _PERK_ATTACK2)) {
- unsafeWindow.PhysicalModifiers *= 1.2;
- } else
- if (unsafeWindow.isperk(attacker, _PERK_ATTACK1)) unsafeWindow.PhysicalModifiers *= 1.1;
- };
- if (unsafeWindow.isperk(defender, _PERK_DEFENSE3)) {
- unsafeWindow.PhysicalModifiers *= 0.7;
- } else {
- if (unsafeWindow.isperk(defender, _PERK_DEFENSE2)) {
- unsafeWindow.PhysicalModifiers *= 0.8;
- } else {
- if (unsafeWindow.isperk(defender, _PERK_DEFENSE1)) unsafeWindow.PhysicalModifiers *= 0.9;
- };
- };
- };
- if ((cre_collection[attacker]['siegewalls']) && (cre_collection[defender]['stone'])) {
- unsafeWindow.PhysicalModifiers *= 10;
- };
- var _PERK_COLD_STEEL = 14;
- var _PERK_FIERY_WRATH = 101;
- var _PERK_HELLFIRE_AURA = 123;
- var _PERK_RETRIBUTION = 16;
- if (unsafeWindow.isperk(attacker, _PERK_COLD_STEEL)) unsafeWindow.water = 1 - (1 - unsafeWindow.water) * (0.9);
- if (unsafeWindow.isperk(attacker, _PERK_FIERY_WRATH)) unsafeWindow.fire = 1 - (1 - unsafeWindow.fire) * (0.85);
- if (unsafeWindow.isperk(attacker, _PERK_HELLFIRE_AURA)) unsafeWindow.fire = 1 - (1 - unsafeWindow.fire) * (0.95);
- if (unsafeWindow.magic[attacker]['cre']) {
- unsafeWindow.air = 1 - (1 - unsafeWindow.air) * (1 - unsafeWindow.magic[attacker]['cre']['effect'] / 100);
- };
- if (unsafeWindow.isperk(attacker, _PERK_RETRIBUTION)) unsafeWindow.PhysicalModifiers *= (1 + Math.min(Math.max(unsafeWindow.stage.pole.getmorale(attacker, x, y), 0), 5) / 20);
- if ((cre_collection[attacker]['viciousstrike']) && (Math.max(0, Math.round((cre_collection[defender]['speed'] + cre_collection[defender]['ragespeed'] + cre_collection[defender]['speedaddon']) * cre_collection[defender]['speedmodifier'])) == 0)) unsafeWindow.PhysicalModifiers *= 1.5;
- unsafeWindow.PhysicalModifiers *= unsafeWindow.stage.pole.magicmod(attacker, defender, unsafeWindow.fire, unsafeWindow.air, unsafeWindow.water, unsafeWindow.earth, 0.1);
- if ((cre_collection[attacker]['bloodfrenzy']) && (unsafeWindow.magic[defender]['fd1'])) {
- unsafeWindow.PhysicalModifiers *= 1.3;
- };
- unsafeWindow.UmelkaModifiers = 1;
- if ((umelka[cre_collection[attacker]['owner']][0] > 0) && (umelka[cre_collection[defender]['owner']][0] > 0)) {
- unsafeWindow.k = umelka[cre_collection[attacker]['owner']][0];
- if ((unsafeWindow.k > 0) && (unsafeWindow.k < 11)) {
- let j = umelka[cre_collection[defender]['owner']][k];
- unsafeWindow.UmelkaModifiers = 1 - j * 0.03;
- };
- };
- unsafeWindow.NumCreatures = cre_collection[attacker]['nownumber'];
- let tsc = 0;
- bigx = cre_collection[defender]['big'];
- bigy = cre_collection[defender]['big'];
- if (cre_collection[defender]['bigx']) bigx = 1;
- if (cre_collection[defender]['bigy']) bigy = 1;
- for (var xs = cre_collection[defender]['x'] - 1; xs <= cre_collection[defender]['x'] + 1 + bigx; xs++) {
- for (var ys = cre_collection[defender]['y'] - 1; ys <= cre_collection[defender]['y'] + 1 + bigy; ys++) {
- if ((mapobj[xs + ys * defxn] > 0) && (mapobj[xs + ys * defxn] != defender) && (cre_collection[mapobj[xs + ys * defxn]]['shieldguard']) && (cre_collection[defender]['side'] == cre_collection[mapobj[xs + ys * defxn]]['side'])) {
- tsc++;
- };
- };
- };
- unsafeWindow.PhysicalModifiers /= (tsc + 1);
- var minmag = 0;
- var maxmag = 0;
- if ((inuse == 'lep') && (cre_collection[attacker]['crashingleap'])) {
- unsafeWindow.Totalmagicdamage = 0;
- cre_collection[defender]['attacked'] = 1;
- unsafeWindow.stage.pole.attackmagic(attacker, defender, cre_collection[attacker]['nownumber'] * 4, 'cold', '', 0, 0, 0);
- minmag = unsafeWindow.Totalmagicdamage;
- unsafeWindow.Totalmagicdamage = 0;
- cre_collection[defender]['attacked'] = 1;
- unsafeWindow.stage.pole.attackmagic(attacker, defender, cre_collection[attacker]['nownumber'] * 6, 'cold', '', 0, 0, 0);
- maxmag = unsafeWindow.Totalmagicdamage;
- };
- unsafeWindow.mindam = cre_collection[attacker]['mindam'] + cre_collection[attacker]['damageaddon'] + (cre_collection[attacker]['maxdam'] - cre_collection[attacker]['mindam']) * (cre_collection[attacker]['mindamaddon']) + cre_collection[attacker]['ragedamage'];
- unsafeWindow.maxdam = cre_collection[attacker]['maxdam'] + cre_collection[attacker]['damageaddon'] - (cre_collection[attacker]['maxdam'] - cre_collection[attacker]['mindam']) * (cre_collection[attacker]['maxdamaddon']) + cre_collection[attacker]['ragedamage'];
- h = hera;
- if ((h > 0) && (unsafeWindow.magic[h]) && (unsafeWindow.magic[h]['BLS']) && (unsafeWindow.magic[h]['BLS']['effect'] > 0)) unsafeWindow.mindam = unsafeWindow.maxdam;
- if ((h > 0) && (unsafeWindow.magic[h]) && (unsafeWindow.magic[h]['CRS']) && (unsafeWindow.magic[h]['CRS']['effect'] > 0)) unsafeWindow.maxdam = unsafeWindow.mindam;
- if ((cre_collection[attacker]['taran']) && (cre_collection[defender]['stone'])) {
- h = hera;
- unsafeWindow.mindam = Math.floor(Math.pow(cre_collection[h]['maxhealth'], 0.5) * 200 * cre_collection[attacker]['mindam']);
- unsafeWindow.maxdam = Math.floor(Math.pow(cre_collection[h]['maxhealth'], 0.5) * 400 * cre_collection[attacker]['maxdam']);
- };
- if (cre_collection[attacker]['accuracy']) unsafeWindow.mindam = unsafeWindow.maxdam;
- unsafeWindow.BaseDamage = unsafeWindow.mindam;
- unsafeWindow.PhysicalDamage = unsafeWindow.NumCreatures * unsafeWindow.BaseDamage * unsafeWindow.AttackDefenseModifier * unsafeWindow.PhysicalModifiers * unsafeWindow.UmelkaModifiers + minmag;
- unsafeWindow.PhysicalDamage2 = unsafeWindow.NumCreatures * unsafeWindow.maxdam * unsafeWindow.AttackDefenseModifier * unsafeWindow.PhysicalModifiers * unsafeWindow.UmelkaModifiers + maxmag;
- if ((cre_collection[attacker]['deathstrike']) && (cre_collection[defender]['maxhealth'] < 400) && (!cre_collection[defender]['stone'])) {
- if ((cre_collection[defender]['nownumber'] - 1) * cre_collection[defender]['maxhealth'] + cre_collection[defender]['nowhealth'] > unsafeWindow.PhysicalDamage) {
- unsafeWindow.PhysicalDamage += cre_collection[defender]['maxhealth'] - unsafeWindow.PhysicalDamage % cre_collection[defender]['maxhealth'];
- };
- if ((cre_collection[defender]['nownumber'] - 1) * cre_collection[defender]['maxhealth'] + cre_collection[defender]['nowhealth'] > unsafeWindow.PhysicalDamage2) {
- unsafeWindow.PhysicalDamage2 += cre_collection[defender]['maxhealth'] - unsafeWindow.PhysicalDamage2 % cre_collection[defender]['maxhealth'];
- };
- };
- if (cre_collection[attacker]['bladeofslaughter']) {
- unsafeWindow.PhysicalDamage += Math.min(500, cre_collection[defender]['nownumber'] * 2);
- unsafeWindow.PhysicalDamage2 += Math.min(500, cre_collection[defender]['nownumber'] * 2);
- };
- if (unsafeWindow.magic[attacker]['brk']) {
- unsafeWindow.PhysicalDamage *= (1 + unsafeWindow.magic[attacker]['brk']['effect'] * 0.03);
- unsafeWindow.PhysicalDamage2 *= (1 + unsafeWindow.magic[attacker]['brk']['effect'] * 0.03);
- };
- if (unsafeWindow.PhysicalDamage < 1) {
- unsafeWindow.PhysicalDamage = 1;
- };
- if (unsafeWindow.PhysicalDamage2 < 1) {
- unsafeWindow.PhysicalDamage2 = 1;
- };
- if ((cre_collection[attacker]['magicattack']) && (unsafeWindow.l > 2) && (unsafeWindow.stage.pole.issomething(defender, 'dampenmagic'))) unsafeWindow.PhysicalDamage = 0;
- if (unsafeWindow.magic[defender]['rag']) {
- unsafeWindow.PhysicalDamage = unsafeWindow.stage.pole.ragedamage(defender, unsafeWindow.PhysicalDamage);
- unsafeWindow.PhysicalDamage2 = unsafeWindow.stage.pole.ragedamage(defender, unsafeWindow.PhysicalDamage2);
- };
- if ((cre_collection[attacker]['vorpalsword']) && (cre_collection[defender]['maxhealth'] < 400) && (!cre_collection[defender]['stone'])) {
- unsafeWindow.PhysicalDamage += cre_collection[defender]['maxhealth'];
- unsafeWindow.PhysicalDamage2 += cre_collection[defender]['maxhealth'];
- };
- unsafeWindow.PhysicalDamage = Math.round(unsafeWindow.PhysicalDamage);
- unsafeWindow.PhysicalDamage2 = Math.round(unsafeWindow.PhysicalDamage2);
- if (cre_collection[defender]['pleasureinpain']) {
- unsafeWindow.PhysicalDamage = Math.round(unsafeWindow.PhysicalDamage * 0.9);
- unsafeWindow.PhysicalDamage2 = Math.round(unsafeWindow.PhysicalDamage2 * 0.9);
- };
- if (cre_collection[defender]['raptureinagony']) {
- unsafeWindow.PhysicalDamage = Math.round(unsafeWindow.PhysicalDamage * 0.8);
- unsafeWindow.PhysicalDamage2 = Math.round(unsafeWindow.PhysicalDamage2 * 0.8);
- };
- var totalh = (cre_collection[defender]['nownumber'] - 1) * cre_collection[defender]['maxhealth'] + cre_collection[defender]['nowhealth'];
- unsafeWindow.Uronkills = Math.floor(Math.min(unsafeWindow.PhysicalDamage, totalh) / cre_collection[defender]['maxhealth']);
- unsafeWindow.Uronkills2 = Math.floor(Math.min(unsafeWindow.PhysicalDamage2, totalh) / cre_collection[defender]['maxhealth']);
- var nowhealth = cre_collection[defender]['nowhealth'] - (Math.min(unsafeWindow.PhysicalDamage, totalh) - unsafeWindow.Uronkills * cre_collection[defender]['maxhealth']);
- var nowhealth2 = cre_collection[defender]['nowhealth'] - (Math.min(unsafeWindow.PhysicalDamage2, totalh) - unsafeWindow.Uronkills2 * cre_collection[defender]['maxhealth']);
- if (nowhealth <= 0) unsafeWindow.Uronkills++;
- if (nowhealth2 <= 0) unsafeWindow.Uronkills2++;
- unsafeWindow.tUronkills += unsafeWindow.Uronkills;
- unsafeWindow.tUronkills2 += unsafeWindow.Uronkills2;
- unsafeWindow.tPhysicalDamage += unsafeWindow.PhysicalDamage;
- unsafeWindow.tPhysicalDamage2 += unsafeWindow.PhysicalDamage2;
- if (![0, 1].includes(leap_distance)) cre_collection[attacker].attackaddon -= leap_atk_bonus;
- let leap_display_distance = ""
- if (leap_atk_bonus) leap_display_distance = cre_distance ? "" : leap_distance;
- return { distance: leap_display_distance, leap_atk_bonus: leap_atk_bonus }
- }
- function get_dmg_info(attacker_obj_index, defender_obj_index, koef = 1) {
- let cre_collection = unsafeWindow.stage.pole.obj
- let attacker = cre_collection[attacker_obj_index]
- let defender = cre_collection[defender_obj_index]
- let dmg_dict = attackmonster(attacker_obj_index, attacker.x, attacker.y, defender.x, defender.y, defender_obj_index, GM_getValue("cre_distance"), 1, koef);
- let min_damage = unsafeWindow.PhysicalDamage
- let max_damage = unsafeWindow.PhysicalDamage2
- let min_killed, max_killed;
- if (min_damage % defender.maxhealth >= defender.nowhealth) min_killed = Math.floor(min_damage / defender.maxhealth) + 1
- else min_killed = Math.floor(min_damage / defender.maxhealth)
- if (max_damage % defender.maxhealth >= defender.nowhealth) max_killed = Math.floor(max_damage / defender.maxhealth) + 1
- else max_killed = Math.floor(max_damage / defender.maxhealth)
- return { min: min_damage, max: max_damage, min_killed: min_killed, max_killed: max_killed, distance: dmg_dict.distance }
- }
- let defender_obj_id = 0
- let selected_id = 0
- function refresh() {
- isOpen = true
- let cre_collection = unsafeWindow.stage.pole.obj;
- if (cre_distance_on) {
- cre_distance_div.style.display = "inline";
- cre_distance_div.innerHTML = `<span>Выбранное расстояние: ${GM_getValue('cre_distance')}</span><br>`
- }
- set_Display([select, side_button, collapse_button, document.querySelector("#chosen_cre_heading"), dmg_list_container, individual_calc], "inline")
- refresh_button.innerHTML = "Обновить"
- let cre_list = Object.values(cre_collection);
- cre_list.sort(function(a, b) {
- return a.obj_index - b.obj_index;
- });
- dmg_list_container.innerHTML = "";
- [...select.children].forEach(child => child.remove())
- let found_defender = false
- cre_list.forEach(defender => {
- if (defender.nownumber > 0 && defender.nametxt != "" && defender.side == chosen.side && defender.hero === undefined) {
- let option_id = `cre_no${cre_list.indexOf(defender)}`;
- select.insertAdjacentHTML("beforeend", `<option id = "${option_id}" value = "${defender.obj_index}">${defender.nametxt} [${defender.nownumber}] </option>`)
- if (!found_defender) {
- if (`${defender.obj_index}` == chosen.creature) found_defender = true
- defender_obj_id = defender.obj_index
- selected_id = [...select.children].indexOf(select.lastChild)
- }
- }
- });
- dmg_list_container.insertAdjacentHTML("beforeend", `<div id = "chosen_cre_heading" style="display:inline; background-color: ${physCalcColor}">
- <span>Урон по </span><span style="color:#ffffff; font-size: 110%; font-weight: bold;">${cre_collection[defender_obj_id].nametxt} [${cre_collection[defender_obj_id].nownumber}] :</span>
- </div>`)
- cre_list.forEach(attacker => {
- if (attacker.side == -chosen.side && attacker.nownumber > 0 && attacker.nametxt != "") {
- let dmg = get_dmg_info(attacker.obj_index, defender_obj_id)
- let practical_overall_hp;
- if (cre_collection[defender_obj_id].attack > attacker.defence) {
- practical_overall_hp = attacker.maxhealth * attacker.nownumber / (1 + 0.05 * Math.abs(cre_collection[defender_obj_id].attack - attacker.defence))
- } else {
- practical_overall_hp = attacker.maxhealth * attacker.nownumber * (1 + 0.05 * Math.abs(cre_collection[defender_obj_id].attack - attacker.defence))
- }
- let row_id = `row_no${cre_list.indexOf(attacker)}`
- let koef_string = `(коэф. урона <b>${( ((dmg.max + dmg.min) / 2) / practical_overall_hp ).toFixed(2)}</b>)`;
- dmg_list_container.insertAdjacentHTML("beforeend", `<p id = "${row_id}"><span style = "text-decoration: underline;color:#bfbfbf" >${attacker.nametxt}</span> [${attacker.nownumber}] --> <b style = "color:#bfbfbf">${dmg.min_killed}-${dmg.max_killed}</b> существ (${dmg.min}-${dmg.max}) ${(attacker.hero == undefined&&coeff_on) ? koef_string : ""} </p>`);
- dmg_list_container.insertAdjacentHTML("beforeend", calcHellFireHTML(attacker, cre_collection[defender_obj_id], cre_collection, dmg));
- dmg_list_container.insertAdjacentHTML("beforeend", calcStormHTML(attacker, cre_collection[defender_obj_id]));
- mag_damage_on && lastturn > 0 && dmg_list_container.insertAdjacentHTML("beforeend", calcMagicHTML(attacker, cre_collection[defender_obj_id], cre_collection, dmg));
- }
- })
- select.options.item(selected_id).selected = true
- }
- initGates();