28

» WarCraft 3 / Предметные способности - можно ли заюзать триггерно?

А разве триггерно через ID можно?
Конечно, через id ПРИКАЗА, а не равкода способности.
28

» WarCraft 3 / Простой вопрос по ForceUIKey

local Player p
local integer i = 0
loop
    exitwhen i > 11
    set p = Player(i)
    call SetUnitOwner( gg_unit_ogru_0009, p, true )
    if GetLocalPlayer() == p then
        call SelectUnit( gg_unit_ogru_0009, true)
        call ForceUIKey("L")
        // Пиши сколько нужно SelectUnit(whichUnit, true), но не забудь прописать ClearSelection() после выбора 12 юнитов.
    endif
    // Передача юнита нейтралу будет совершена после цикла, всё равно ты его будешь давать разным игрокам.
    set i = i + 1
endloop
call ClearSelection()
call SetUnitOwner( gg_unit_ogru_0009, Player(PLAYER_NEUTRAL_AGGRESSIVE), true )
set p = null //Необязательно.
28

» WarCraft 3 / Простой вопрос по ForceUIKey

вот через ForceUIKey без локального игрока - еще могло бы
Почему? Ты же не создаёшь хендл или что-то в этом роде.
через call SelectUnitForPlayerSingle
Дело в том, что чтобы нажать L только у конкретного игрока тоже нужно условие с GetLocalPlayer(), а если использовать эту функцию, то тогда одно и тоже условие вычислится два раза. Зачем? Потому я и написал
if GetLocalPlayer() == owner then
    call ClearSelection()
    call SelectUnit(u, true)
    call ForceUIKey("L")
endif
SelectUnit() ДОБАВЛЯЕТ юнита в выделение игрока, если flag == true, потому написал ещё и ClearSelection(), что очищает выделение у игрока. Но необходимость этой функции зависит от контекста.
Raised:
Проверить обычно быстрее чем дождаться ответа.
Я так на много своих вопросов и ответил.
28

» WarCraft 3 / Простой вопрос по ForceUIKey

Если просто написать ForceUIKey(), то тогда L нажмётся у всех игроков. Смотри ForceUIKeyBJ.
Да и чтобы выделить юнита только конкретному игроку, нужно также написать перед SelectUnit() условие с GetLocalPlayer().
if GetLocalPlayer() == owner then
    call ClearSelection()
    call SelectUnit(u, true)
    call ForceUIKey("L")
endif
А десинк можно проверить с другом по сетке или через эмуляцию.
28

» WarCraft 3 / Удаление трупов

Используй хештаблицу и таймер.
globals
    constant hashtable Hash = InitHashtable()
    constant integer UNIT_INDEX_DELAYED_REMOVAL = 0
    constant real DELAYED_REMOVAL_TIME = 5. // Нужное время в секундах.
endglobals

function DelayedRemoval takes nothing returns nothing
	local timer t = GetExpiredTimer()
	local integr id = GetHandleId(t)
	call RemoveUnit(LoadUnitHandle(Hash, id, UNIT_INDEX_DELAYED_REMOVAL))
	call RemoveSavedHandle(Hash, id, UNIT_INDEX_DELAYED_REMOVAL)
	call RemoveTimer(t)
	set t = null
endfunction

function Trig_UnitDecay_Actions takes nothing returns nothing
	local timer t = CreateTimer()
	call SaveUnitHandle(Hash, GetHandleId(t), UNIT_INDEX_DELAYED_REMOVAL, GetDecayingUnit())
	call TimerStart(t, DELAYED_REMOVAL_TIME, false, function DelayedRemoval)
	// Время можно менять в зависимости от типа юнита и прочего, оно не обязательно должно быть константой.
	set t = null
endfunction

function InitTrig_UnitDecay takes nothing returns nothing
    set gg_trg_UnitDecay = CreateTrigger()
    call TriggerRegisterAnyUnitEventBJ( gg_trg_UnitDecay, EVENT_PLAYER_UNIT_DECAY )
    call TriggerAddAction(gg_trg_UnitDecay, function Trig_UnitDecay_Actions)
endfunction
Если надо на гуи, могу сделать.
28

» WarCraft 3 / Какой путь для иконки?

DISBTNGem.blp, станет затемнённой для всех иконок имени xxx\BTNGem.blp, где бы они не лежали?
Именно, сам так делаю. Прочитал про этот трюк в какой-то статье на сайте. Приставка BTN необязательна, так как на тип иконки указывает её путь.
28

» WarCraft 3 / Какой путь для иконки?

Можно сделать импорт всего 2 раза.
Active\BTNGem.blp - активная иконка.
Inactive\BTNGem.blp - активная иконка для выключенного предмета, переименована из DISBTNGem.blp
ReplaceableTextures\CommandButtonsDisabled\DISBTNGem.blp - неактивная иконка.
Я думал сначала, что для выключенной иконки будет своя неактивная.
28

» WarCraft 3 / Функция Atan2

Пушистый:
Возвращает угол в радианах. Пример использования: angle = Atan2(y2-y1,x2-x1) (вернет угол из точки 1 в точку 2 в радианах).
Я так понимаю угол между отрезком AB и осью OX?
То есть Atan просто возвращает угол из значения его тангенса, а Atan2 возвращает угол между отрезком (0, 0) - (x, y) и осью Ox?
28

» WarCraft 3 / Какой путь для иконки?

Ты импортируй DISBTNGem.blp два раза, но с разными именами. Одна будет ReplaceableTextures\CommandButtonsDisabled\DISBTNGem.blp, а другая BTNGemDisabled.blp. Тогда неактивная для BTNGemDisabled.blp будет ReplaceableTextures\CommandButtonsDisabled\DISBTNGemDisabled.blp.
28

» WarCraft 3 / Ещё немного интересных фишек

DracoL1ch:
По поводу Barrage.
Damage Per Target - 0.00
Maximum Number of Targets - 0
Maximum Total Damage - X.00
Будет вылетать X дополнительных снарядов. Если X = 0, то тогда будет вылетать столько дополнительных снарядов, сколько есть допустимых целей помимо основной цели.
Написал в тот документ.
Naadir, добавь в свою статью равкоды, не у всех ру версия редактора.
28

» WarCraft 3 / Операции сравнения

Clamp:
Статью уже кидали, ответа на вопрос там нет.
Давно видел эту статейку на HIVE, думал, что её уже давно кинут сюда)
Там и есть ответы на интересующие меня вопросы.
Вот тут ещё об этом.
28

» WarCraft 3 / Можно ли локально отдать приказ юниту?

Что значит локально? Только у конкретных игроков имеется в виду?
Могу дать JNPG с плагином эмуляции игры по сети, можно там проверить.
28

» WarCraft 3 / Операции сравнения

UrsaBoss, спасибо за статью, а вот что я выяснил своими тестами:
  1. R2SW(r, 0, -1) возвращает столько знаков после запятой, сколько есть (до 6).
  2. R2I(9.999999) = 9, если бы округлялось после 4-х знаков, то ответ был бы 10.
  3. R2I(9.9999999) и далее выдаёт 10.
  4. R2I(9.9999998) = 9.
Судя по статье, real == float, у которого всего 7.22 десятичных разряда, то есть округление происходит не всегда после 4-го знака за запятой.
28

» WarCraft 3 / Операции сравнения

Любое число с плавающей запятой (в jass) у которого больше 4 знаков после запятой - округляется до 4 знаков
Откуда такая информация? Просто Тест 2 говорит об обратном: в случае сложения и умножения вышла точность в 6 цифр после запятой. Также константы bj_PI и bj_E имеют 5 знаков после запятой.
Мне и 4-х цифр после запятой хватит, да и вопрос не в этом, но источник информации хочется узнать.
28

» WarCraft 3 / Операции сравнения

Ребята, а вы читали вопрос, смотрели функции? Потому что ваши ответы никак не отвечают на вопросы.
UrsaBoss, ты написал такую же функцию, что и у меня в вопросе (только разделил => на > и ==). Причём тут 9.9999/2?
К примеру: 9.9999 станет 10.000, или 1.0001 станет 1.000
Это не так, я только что тестировал, в JASS действительные числа часто точны до 6-го знака после запятой, точно до 4-го. R2SW адекватно работает при precision < 7, при бОльших значениях часто выдаёт бред.
Я повторю вопросы ещё раз:
  1. Почему когда я использую >= получаю верный ответ, а когда ==, то неверный, хотя => сильнее ==? R2I(9.9999) = 9, это я проверял, тогда 9.9999 - 9.0 == 1 выдаёт правду, но 9.9999 - 9.0 >= 1 выдаёт ложь. Как так?
  2. Какие операции сравнения (==, !=, >, <, >=, <=) лучше для действительных чисел в JASS (слышал и убедился сам, что сравнение через == плохо)?
Я знаю про стандарт IEEE754 и про неточность арифметических действий с float, меня интересует лишь сравнение этих чисел конкретно в JASS.
Тесты, что я проводил:
Test 1
function R2Idown takes real r returns integer
    local integer i = R2I(r)
    if r - I2R(i) >= 1. then
        return i + 1
    endif
    return i
endfunction

function R2Iup takes real r returns integer
    local integer i = R2I(r)
    if r > I2R(i) then
        return i + 1
    endif
    return i
endfunction

...
    set r = 9. // от 9. до 9.9999999999
    set r2i = R2I(r)
    set r2idown = R2Idown(r) // "исправленная" R2I()
    set r2iup = R2Iup(r)
    call DebugMsg("Real: x") // вместо x значение r, записанное вручную.
    call DebugMsg("R2S: " + R2S(r))
    call DebugMsg("R2SW-1: " + R2SW(r, 0, -1))
    call DebugMsg("R2SW0: " + R2SW(r, 0, 0))
    call DebugMsg("R2SW6: " + R2SW(r, 0, 6))
    call DebugMsg("R2SW7: " + R2SW(r, 0, 7))
    call DebugMsg("R2SW8: " + R2SW(r, 0, 8))
    call DebugMsg("R2SW9: " + R2SW(r, 0, 9))
    call DebugMsg("R2I: " + I2S(r2i))
    call DebugMsg("R2Idown: " + I2S(r2idown))
    call DebugMsg("R2Iup: " + I2S(r2iup) + "\n")
// по результату этого теста я не нашёл разницы между R2I() и своей R2Idown(), только нашёл ошибку при использовании == в R2Idown. При каких значениях будет разница между R2I() и своей R2Idown()?
Test 2
function R2SX takes real r returns string
    return R2SW(r, 0, -1)
endfunction

...
    local integer a = 0
    local real r1 = 1.
    local real r2 = 1.
    local real r3 = 1.
    local real r4 = 1.
    local real r5 = 1.
    local real r6 = 1.
    loop
        set r1 = r1 * 1.075
        set r2 = r2 + r2 * .075
        set r3 = 1.075 * r3
        set r4 = r4 * 0.075 + r4
        set r5 = 0.075 * r5 + r5
        set r6 = r6 + 0.075 * r6
        set a = a + 1
        exitwhen a == 10
    endloop
    call DebugMsg("1: " + R2SX(r1)) // 2.061029
    call DebugMsg("2: " + R2SX(r2)) // 2.061031
    call DebugMsg("3: " + R2SX(r3)) // 2.061029
    call DebugMsg("4: " + R2SX(r4)) // 2.061031
    call DebugMsg("5: " + R2SX(r5)) // 2.061031
    call DebugMsg("6: " + R2SX(r6)) // 2.061031
28

» WarCraft 3 / Функции

TriggerEvaluate() выполняет условия триггера, возвращает логическую, наследует вызывающий поток. Используется в структурах.
28

» WarCraft 3 / Древа

Уберите тип Ancient (Древо) из классификаций юнита.
Я делал тд, где можно перемещать башни (тд так себе, очень изи). У башен способности на основе канала, а для перемещения я использовал как раз способность Root. У меня ничего не пропадало. Думаю, дело в классификации юнита, так как у моих башен из классификаций была только механическая.

Стоп, я вспомнил.
Да, все способности пропадают после Uproot. Очередная хардкорная абилка.
28

» WarCraft 3 / Древа

Можно подробнее расписать проблему? Я ничего не понял, у меня с этой способностью всё работает.
28

» WarCraft 3 / Может кто скинуть установщик JNGP R1.2?

Я скачал себе R4, всё работало хорошо, кроме pjass.exe, его заменил, и всё работает как положено (с выключенным cJassом).
Зависать может из-за Adicа. Убери галки cJass -> AdicOptimizer и cJass -> AdicParser, зависания должны уйти.
Судя по изменениям, R1.3 лучше R1.2, кину его.
Если нужно:
последний pjass.exe;
последний TESH.
Загруженные файлы
28

» WarCraft 3 / Не могу найти подходящую ауру

pro100master дело говорит, у зданий поле "Статус" отключено по умолчанию в константах, потому значок баффа не отображается.
28

» WarCraft 3 / Исследование и пасивка

А у юнита, у которого пассивка, в поле "Характеристики - Улучшения" прописано ваше улучшение? Без этого ничего улучшаться не будет.
28

» WarCraft 3 / Проблемы с новым JNGP

В последней сборке JNPG:R pjass.exe очень странный, сам добавляет Condition() там, где их нет и пр.
Это легко исправить, скачай последний pjass.exe и замени оригинальный файл в папке jasshelper, которая в папке JNPG.
Есть ещё сборка R3 у меня, а также оригинальные JNPG, могу кинуть.
28

» WarCraft 3 / Можно ли прикрепить эффект молнии к юниту?

Msey:
А если цвет молнии нужно поменять?
Делаешь несколько спелов на основе Finger Of Death с разными эффектами молний. Нужен другой эффект - удаляешь старый спел, даёшь новый и снова каст.
Если же вопрос про
native SetLightningColor takes lightning whichBolt, real r, real g, real b, real a returns boolean
В случае с даммиком никак, я думаю. :(
Можно ещё вот как. Создать БД для всех юнитов на карте, где будут записаны их Projectile Impact - Z и Projectile Launch - Z, а сами молнии делать триггерно. Тогда ничего провисать не должно, если использовать следующие формулы координат для кастера - цель:
local real x1 = GetUnitX(caster)
local real y1 = GetUnitY(caster)
local location p1 = GetUnitLoc(caster)
local real z1 = GetLocationZ(p1) + GetUnitFlyHeight(caster) + Projectile.getUnitLaunchZ(caster)
local real x2 = GetUnitX(target)
local real y2 = GetUnitY(target)
local location p2 = GetUnitLoc(target)
local real z2 = GetLocationZ(p2) + GetUnitFlyHeight(target) + Projectile.getUnitImpactZ(target)
// Projectile.getUnitImpactZ и Projectile.getUnitLaunchZ - функции написанной заранее БД.
//
// В это случае нужно вызывать RemoveLocation?
Для простого связывания юнитов (где нет кастера и цели) меняешь Projectile.getUnitLaunchZ(caster) на Projectile.getUnitImpactZ(caster).