Как-то не очень - чревато образованием дыр, плюс, будет более ресурсоёмким.
-----
Полуркав здум форум внезапно узнал что выполнение мили зависит от "дальности зрения" монстра. Тогда возникает такой вопрос: можно ли на декоре временноизвне заблочитьпонизить обзор монстра?
Грэйт Сэнкс, получилось! ^_^
Правда небезупречно. Если НЕ монстр натыкается на щит а сам щит НА монстра, то THINGSPEC_MonsterTrigger|THINGSPEC_TriggerTargets естественно не срабатывают а оставшиеся флаги это не фиксят.
И ещё я так и не понял как активировать спешэлы через эту байду. Это что, надо прописывать экшн_спешелы в отдельном стэйте "Active:" внутри актора или как?
И чем отличаются триггер от активатора?
1. Чем регулируется длительность A_GenericFreezeDeath?
2. Если этот параметр хардкодед то каким способом можно прервать извне действие ф-ции, кроме как принудительным переводом актора в другой стэйт (боли например)?
3. Как вернуть актору оригинальную палитру (обнулить трансляцию) после прекращения действия A_GenericFreezeDeath? Т. е. я в курсе насчёт A_SetTranslation и Thing_SetTranslation, но я хз какой стринг\значения нужно вписывать для возврата каждому актору его исходных цветов.
EDIT:
Скрытый текст:
Поясняю дабы не было непоняток: ф-ция вызывается живым актором через кастомитем:
Actor Freezer : CustomInventory
{
+INVENTORY.ALWAYSPICKUP
Inventory.MaxAmount 0
States
{
Pickup:
"####" "#" 0 A_GenericFreezeDeath
Stop
}
}
Т. е. по истечении пресловутой длительности ф-ции, актор "размораживается" и действует дальше как ни в чём ни бывало. Но к сожалению исходная палитра не восстанавливается. Также актор может быть принудительно "разморожен" при переходе в пэйн.
С достаточной точностью могу только на третий пункт ответить: пишешь в TRNSLATE строку 'Normal = "0:0=0:0"' и в параметр A_SetTranslation пишешь "Normal", либо прописываешь "0:0=0:0" любым другим способом.
Первый -- никак, если ты ни в какую не хочешь использовать ZScript, так как там его код находится в открытом доступе по пути "\zscript\shared\ice.txt" (в qzdoom.pk3, v2.2pre). Через Decorate изменить невозможно, через ZScript проще всего написать свою на основе той, так как переопределить у тебя её не удастся.
В теории можно на ацс сделать имитацию, как я сделал имитацию заморозки из Duke Nukem ранее.
Морозишь актора через deactivate, меняешь ему палитру, ждёшь, убиваешь, потом обратно. Если игрок то ещё TOTALLYFROZEN добавить.
Ацс запускать из итема, который и так даётся.
Я надеюсь ацс для тебя не настолько отвратителен?)
JSO x Сэнкс за трансляцию. ^_^
И еяпп, то Граф подтверждает твои слова: у A_(Generic)FreezeDeath имеется собственный внутренний таймер с небольшой рандомизацией, который нельзя ничем контролировать извне поскольку по умолчанию оный таймер управляется только через летальную ф-цию A_FreezeDeathChunks.
Ну или таки "размораживать" актор путём его насильственного перевода в другой стэйт.
ZZYZX Ацс тоже ересь, но не столь богомерзкая по сравнению с зскриптом.
Уже делал такое на декоре, но через +FORCEPAIN +RIPPER миссиль с A_Countdown без (Де)\Активэйт.
----------
В общем вопрос был не столь в том "как сэмулировать временную заморозку" (хотя итоговая цель именно такова), а в том "как именно работает A_GenericFreezeDeath". Просто эта ф-ция выглядела столь соблазнительно своей компактностью что грех было не попробовать поэкспериментировать. )
1. Актор стреляет Рельсой в рандомную цель.
2. У него есть сиблинги (siblings, - акторы у которых один и тот же AAPTR_MASTER поинтер).
Вопрос: как прописать на декоре (можно в анон ф-циях) чтобы сиблинги игнорировали ту же цель, т. е. чтобы её видел только актор атаковавший первым? Причём убийство сиблингов (A_KillSiblings) не допустимо, они должны оставаться живы и выбирать другие "не занятые" цели.
Мы тут посовещались в дискорде немного и пришли к выводу что тебе всё же нужен зскрипт
Хотя очень примитивный способ это сделать — сделай итем какой-нибудь, и давай его цели монстра.
Когда цель меняется или монстр умирает то обязательно нужно забрать итем (иначе всё сломается и появятся цели на которые не нападает НИКТО).
После этого делаешь A_Look и если у цели есть этот итем (соответственно его кто-то затаргетил) то не нападаешь на него и переводишь своего актора обратно в Spawn, пусть дальше врагов ищет.
Но мне кажется это будет чревато прыжками из стейта в стейт (если у тебя стейт где врага ищут анимирован)
Соответственно если ты делаешь A_Look и у цели нет итема, то ты переходишь в стейт See и там эта проверка делаться не должна (иначе монстр будет мешать сам себе)
Для отслеживания смерти самого целевого монстра я думаю нужен ацс, который будет запускаться итемом и следить за здоровьем "своей" цели. Если упало до 0 — стоп скрипта и удаляем итем.
Этот же скрипт будет вешать на цель в TRACER указатель на мастера монстра, который его атакует в данный момент.
Это нужно чтобы если кого-то реснет арчвайл, его опять взяли в цель.
Кроме итема необходимо назначить мастеру TID (для примера 16000, но вообще лучше юзать UniqueTID) и при выборе цели сверять следующее:
(ацс)
script "CheckIfTargetedByCurrentGroup" (int needTid) // ACS_NamedExecuteWithResult("CheckIfTargetedByCurrentGroup", 16000)
{
SetActivator(0, AAPTR_TARGET);
SetActivator(0, AAPTR_TRACER);
if (ActivatorTID() == needTid) // моб выделен текущей группой (с текущим мастером)
SetResultValue(1);
}
Минус подхода — неоптимизировано (все монстры будут перебираться по 100500 раз, причём дум старается каждый раз выбирать ближайших, он выбирает — ты отклоняешь, и так пока не надоест).
Возможно впадание в бесконечные циклы.
Также если несколько разных групп пересекутся и выберут одну цель то будет полная жопа. Это надёжно реализуемо только для категорий в стиле "все монстры определённого класса", но не "все монстры определённого класса под определённым мастером".
Мда... я полагал что прошаренные профи сразу заподозрят о чём идёт речь. В общем сам виноват, надо было сразу вскрывать карты.
1. Всё предложенное выше прекрасно пишется без ацс и перебора тидов.
2. Но к сожалению всё это даже близко не решает проблему ибо все сиблинги это стрелкИ рельсо-лучей из бфг-шара. Т. е. поскольку у них у всех обзор в 360 градусов + находятся в одной точке, то сколько ни переводи других сиблингов в спаун (даже с затиранием таргетфилда А_КлирТаргетом или А_РеарранжПоинтерс), а они всё равно будут начинать поиск цели с ближайшей, т. е. уже занятой самым первым лучом. Соответственно все сиблинги будут дружно игнорить любые цели кроме ближайшей.
Я пробовал в спауне ставить A_LookEx(LOF_NOSOUNDCHECK,0,frandom(128,1024)) но во-первых, это по-прежнему дичайшая рулетка, а во-вторых, опять-таки потеря КПД.
На данный момент "лучший" вариант получается если "маркировать" цели флагом A_ChangeFlag("INVISIBLE",1), а того кто "наградил" цель этим "маркером" также "награждать" флагом A_ChangeFlag("SEEINVISIBLE",1). Получается что только тот луч который первым ударил цель может её же видеть, тогда как остальные лучи-сиблинги будут вынуждены начать искать новые цели среди видимых акторов. Всё было бы хорошо если бы не одно "но"... Флаг SEEINVISIBLE НЕ РАБОТАЕТ для игрока! И я хз как вообще игрок может увидеть инвиз актор.
Кароч фундаментальная трабла никуда не делась - просто запретить атаковать "занятую" цель это не проблема, проблема же в том чтобы полностью исключить оную цель из последующих проверок сиблингами на приемлемость цели.
На данный момент "лучший" вариант получается если "маркировать" цели флагом A_ChangeFlag("INVISIBLE",1), а того кто "наградил" цель этим "маркером" также "награждать" флагом A_ChangeFlag("SEEINVISIBLE",1). Получается что только тот луч который первым ударил цель может её же видеть, тогда как остальные лучи-сиблинги будут вынуждены начать искать новые цели среди видимых акторов. Всё было бы хорошо если бы не одно "но"... Флаг SEEINVISIBLE НЕ РАБОТАЕТ для игрока! И я хз как вообще игрок может увидеть инвиз актор.
Это ничем не лучше моего варианта с итемами. Два бфг шара не смогут бить мобов друг друга, и ещё надо эти самые награждения флагами возвращать как было после того как бфг пропадает.
Вообще на самом деле ты усложняешь.
Такие извращения нужны если эти акторы физически должны быть разными (например если игрок оружием выпускает стаю дронов которые бьют врага).
А для бфг шаров есть техника отработанная годами за время эмуляции дум3/дум4. Пусть шар будет одним монстром и сам бьёт всех. Конструкция следующая — A_LookEx(LOF_NOJUMP) чтобы сменить цель без прыжка стейтов, потом A_CustomRailgun, потом повторяешь. И так несколько раз в цикле по количеству лучей. Работает гораздо лучше.
А для бфг шаров есть техника отработанная годами за время эмуляции дум3/дум4. Пусть шар будет одним монстром и сам бьёт всех. Конструкция следующая — A_LookEx(LOF_NOJUMP) чтобы сменить цель без прыжка стейтов, потом A_CustomRailgun, потом повторяешь. И так несколько раз в цикле по количеству лучей. Работает гораздо лучше.
Всё так же остаётся проблема распределения "1 луч на 1 цель". Шар может выбрать одну и ту же цель повторно, и походу в этом случае без АЦС уже не обойтись. Тогда как в случае с отдельными монстро-лучами они легче привязываются к цели через флаг NOTARGETSWITCH.
Хотя можно попробовать считать ко-во монстров в радиусе и вызывать рельс-атак не более чем есть мобов вокруг... сссука, хотя это по-прежнему не лечит проблему распределения лучей.
Блин, я конечно чуял что мороки с Ку2-бфг будет много...
Добавлено спустя 10 минут 29 секунд:
Хотя наверное между A_LookEx и рельсой можно вызывать проверку нумерованных итмем-токенов у намеченной цели по принципу "этому дала, этому дала, а тому ещё не дала", но это писец какое извращение даже для меня.
Для 100% гарантии именно того что тебе нужно делается примерно так:
1) помечаешь шар тидом (любым)
2) делаешь A_RadiusGive со скриптом вызываемым из итема
3) скрипт задаёт временный тид монстру (которому упал итем), переключается на мастера (на шар) и заставляет его выстрелить рейлганом 1 раз, установив цель на монстра (через SetActorState)
И никакого зскрипта, что характерно. Огрызки подобной логики можно увидеть в коде моего монстра, который был написан задолго до зскрипта: https://www.youtube.com/watch?v=F2P-le_aSWY Но там именно что подобной, реализовывается связь бфг-шаров с мастером-арчем. Но в принципе если бы мне захотелось чтобы вся эта конструкция светилась рейлганом то это реализовалось бы добавлением пары строк в декор )
Начинай уже учиться, а не морочиться. Я на это 15 минут потратил и всё работает.
Ты бы это время мог потратить на разработку новых идей для мода, а не извращизмов на декоре.
Или раба себе найди который загорится идеей и будет за тебя всё прогать ))))) Если прям вообще никак к программированию подступиться не можешь, так хоть навыки управленца развивай, чо.
Gzdoom/zscript, можно ли нынче в нем сделать такую сложнейшую вещь как камера от третьего лица,
особенностями, которой были бы:
•свободный поворот камеры мышкой, и привязанное к такой камере управление думгаем.
•динамическое изменение прозрачности rstyle translucent- акторов, если они очень близки к камере.
•насколько это возможно незастревание в 1-side стенках
•захват монстра в цель, при этом, чтобы думгай не выпадал из объектива.
Любой из этих пунктов - титаническая работа, но я пока просто хочу понять возможно ли это на сегодняшний день.
стоит ли мне засунуть голову под кран или это выполнимо
Все 4 пункта можно.
Пожалуй с прозрачностью акторов почти самое сложное, т.к. некоторые акторы насильственно ставят себе в каждом кадре прозрачность (те которые это анимируют).
Но вот ваще самый сложный пункт это как ни странно первый. Потому что нужно правильно состыковывать направление прицела от третьего лица с выстрелом из оружия от первого (углы пересчитывать).
Так же и с последним больше проблема не в зскрипте, а в математике процесса которую нужно понимать )
Незастревание делается очень легко. Актора камеры делаешь +NOINTERACTION, а вот позицию камеры определяешь с помощью Trace (этим классом). После чего этого актора телепортируешь в то место где остановился Trace, минус пару пикселей чтобы достать его из стены. При таком подходе застревать он не будет нигде и никогда.
Шары несамостоятельны, потестировал, ни разу не видел чтобы два шара били одного моба, независимо от дистанции.
Да, есть такое я в инфо-лумпе это сразу упомянул. Я так полагаю что перед тем как "залочить" цель нужен более хитрый чек одновременно как на наличие у цели таргетлок-токена, так И на принадлежность луча к одному ААПТР_МАСТЕР. Т. е. нужна аутентификация МАСТЕРА, но я хз как это можно надекорить. (
Да это ерунда, косметика же. Твой шар по функционалу значительно лучше и каноничнее, молодца, красивый код. Я так понял там каждый моб получивший скрипт-итем говорит что он "уник" и заставляет выстрелить в него, лол. )
Т. е. нужна аутентификация МАСТЕРА, но я хз как это можно надекорить.
Вообще есть такое выражение https://zdoom.org/wiki/IsPointerEqual Но у тебя проблема в том, что ты даёшь монстру итем, и мастера можно назначить только этому итему. А добыть мастера из итема невозможно (да и итемы разные могут быть, а если дать много итемов то это будет физически один объект, только со счётчиком количества). Поэтому затея с тем чтобы что-то давать монстру изначально неполноценна (даже в зскрипте), этим должен управлять исходный актор (тот который стреляет).
Вообще есть такое выражение https://zdoom.org/wiki/IsPointerEqual Но у тебя проблема в том, что ты даёшь монстру итем, и мастера можно назначить только этому итему. А добыть мастера из итема невозможно (да и итемы разные могут быть, а если дать много итемов то это будет физически один объект, только со счётчиком количества). Поэтому затея с тем чтобы что-то давать монстру изначально неполноценна (даже в зскрипте), этим должен управлять исходный актор (тот который стреляет).
IsPointerEqual и так задействована, но к сожалению на декоре не существует явных поинтеров AAPTR_CHILDREN\SIBLINGS.
Накостылил обособление всех лучей одного шара путём объединением через A_GiveToSiblings, теперь разные шары могут стрелять в одну цель:
Но порочный круг продолжился в несколько ином ключе.
Во-первых, одна цель не всегда выбирается разными шарами даже когда ко-во потенциальных целей вокруг незначительно:
Во-вторых, в толпе шанс того что одна цель будет выбрана более чем одним шаром стремится к нулю:
Ну и наконец очень редко происходят коллизии когда шар вообще остаётся без целей:
В общем буду признателен если кто укажет где косяк, и можно ли его пофиксить или для декора это уже предел костылизма.
Новый код лучей:
Скрытый текст:
Actor Q2BFGRail
{
Radius 1
Height 1
//MaxTargetRange 2048
//FriendlySeeBlocks 20 //measured in blocks of 128 map unit per block
Species "Q2BFGAllies" //Need for safety shooting
+ISMONSTER
+FRIENDLY
+NOINTERACTION
+LOOKALLAROUND
+DONTTHRUST
States
{
Spawn:
TNT1 A 0 NoDelay A_LookEx(LOF_NOJUMP|LOF_NOSOUNDCHECK,0,frandom(512,128*random(5,10))) //Distance values defines rays distance activation
//TNT1 A 0 A_GiveToSiblings("ItIsMyRay")
TNT1 A 0 A_JumpIf(IsPointerEqual(AAPTR_MASTER,AAPTR_NULL)==1,"DeathMarked") //If BFGBall is dead
TNT1 A 0 A_JumpIf(IsPointerEqual(AAPTR_TARGET,AAPTR_NULL)==1,"DeathMarked") //If no more available targets
TNT1 A 0 A_CheckFlag("CORPSE","DeathMarked",AAPTR_TARGET) //If curent target is dead
//TNT1 A 0 A_GiveToSiblings("ItIsMyRay")
TNT1 A 0 A_JumpIf((CountInv("PersonalTargetMark",AAPTR_TARGET)==1)&&(CountInv("ItIsMyRay")==1),"DeathMarked") //Combined сheck for occupied target + проверка на принадлежность лучей к одному БФГ-шару
TNT1 A 0 A_GiveToTarget("PersonalTargetMark") //Lock target token-mark
TargetLocked:
TNT1 A 0 A_GiveToSiblings("ItIsMyRay") //Lock target token-mark2, allow to shoot from anoter BFGBall
TNT1 A 0 A_CheckFlag("CORPSE","Death",AAPTR_TARGET) //Если текущая цель труп
TNT1 A 0 A_JumpIf(IsPointerEqual(AAPTR_MASTER,AAPTR_NULL)==1,"Death") //Если BFGBall лопнул
TNT1 A 0 A_JumpIf(IsPointerEqual(AAPTR_TARGET,AAPTR_NULL)==1,"Death") //Если больше нет доступных целей
//TNT1 A 0 A_JumpIf(GetDistance(1,AAPTR_TARGET)>512,"Death") //Если дистанция до цели слишком велика; чем больше значение тем дольше и дальше держится луч
POSS A 1
{
A_Warp(AAPTR_MASTER,0,0,8,WARPF_NOCHECKPOSITION|WARPF_COPYINTERPOLATION);
A_GiveToSiblings("ItIsMyRay");
A_CustomRailgun(Random(3,8),0,None,"00 FF 00",RGF_SILENT|RGF_FULLBRIGHT|RGF_NORANDOMPUFFZ,2,0,"Q2BFGRailPuff",0,0,0,1,1.00,0.0,"Q2BFGRailRayNode",0,270,5); //5 targets allowed to pierce
}
Loop
DeathMarked: //Alt-Death state for rays without accepted target
TNT1 A 0
Stop
Death: //Death state for active rays
TNT1 A 0 A_TakeFromTarget("PersonalTargetMark") //Releases target lock
Stop
}
}
Actor ItIsMyRay : Inventory {Inventory.MaxAmount 1}
Actor PersonalTargetMark : Inventory {Inventory.MaxAmount 1}
Доброго времени суток, уважаемые Думеры.
Собственно, возник такой вопрос, который давно не даёт покоя. По части кода в Decorate.
Имею в своём распоряжении GZDoom 4.1.0.
Есть у меня три класса.
Скрытый текст:
Все они базируются на оригинальном классе Думгая - ничем, кроме mugshot и скина не отличаются. Стилистика под классику.
Есть немного модифицированный пистолет из Ванили в виде отдельного Actor.
Вопрос - можно ли к каждому отдельному классу, которые будут использовать одни и те же подбираемые оружия, привязать собственные спрайты как ниже? Конечно, отличие будет состоять исключительно в графике рук.
Скрытый текст:
Что на Discord канале ZDoom, что на QCDE (Quake Champions: Doom Edition) мне советовали создать Actor типа CustomInventory, который должен выдаваться конкретному классу "Player.StartItem<>", который и будет определять проверку спрайтов. Не помогло. В коде не силён, но ошибок мой код не вызывал.
Скрытый текст:
Благодарю за внимание.
P.S. Прошу прощения, если задал вопрос в неподходящем разделе.
Xtor мб проблема в goto в обычный селект и +1? попробуй следать goto в селектТР
или без этой +1 на конце, а то вроде декорейт странно работает на первом фрейме
Скрытый текст:
а зачем так вообще? будет фича смены класса игрока по ходу игры?