Перейти к контенту

Скриптование


Svoboда

Рекомендуемые сообщения

Kirag,

Да, всё так. Ещё раз спасибо за участие в нашей проблеме!

Но, вроде бы, такой конструкции там нет: alife():create(N).

Там конструкции строго на стори_айди - alife():story_object(N) или я чего то пропустил?

А стори_айди у нас как раз и не совпадали. Вот и спавнился "воздух".

Изменено пользователем antreg

Поделиться этим сообщением


Ссылка на сообщение

Kirag, Artos,

После "чистки" от неиспользуемых у нас условий и функций, с функцией first_run() теперь всё в норме. Сложнее оказалось с функцией check_spawn()

После того, как убрали все неиспользуемые в нашей сборке условия и прочее,

остался вот такой массив:

function check_spawn()

amk_anoms.init()

spawn_unspawned_respawners()

if (news_main) then

news_main.init()

end

if (amk_offline_alife) then

amk_offline_alife.init()

end

if (amk_corpses) then

amk_corpses.init()

end

if (amk_objects) then

amk_objects.init()

end

 

if amk.load_variable("freeplay",0)==1 then

amk.save_variable("freeplay",2)

elseif amk.load_variable("freeplay",0)==2 and (not has_alife_info("cit_fail_first_task")) then

db.actor:give_info_portion("cit_fail_first_task")

end

 

--level_changers section

local lname = level.name()

local sname = amk.load_variable("level_on_save","")

 

if (amk_offline_alife) then

amk_offline_alife.update_npc_tables()

end

if (amk_corpses) then

amk_corpses.update_all_corpses()

end

if lname ~= sname and amk_objects then

amk_objects.update()

end

 

-- Выдадим сообщения при переходе на уровень.

if news_main then

if (lname ~= sname and sname ~= "") then

if (news_main.isIsolatedLevel(lname)== true and news_main.isIsolatedLevel(sname) == false) then -- Спустились под землю.

news_main.on_disconnect()

elseif (news_main.isIsolatedLevel(lname) == false and news_main.isIsolatedLevel(sname) == true) then -- Выбрались из-под земли.

news_main.on_connect()

end

if (amk_offline_alife) then

amk_offline_alife.update_trade()

end

end

end

 

if weather_types[lname]==0 then

w=amk.load_variable("dynweather",nil) or level.get_weather()

else

w=level.get_weather()

end

if amk.load_variable("blowout",0)>0 then amk.save_variable("weather",level.get_weather()) end

level.set_weather("amk_for_blow",true)

game.start_tutorial("restore_sun")

 

if amk.load_variable("blowout",0)>0 and amk.load_variable("blowout",0)<4 then

local bt=blowout_type()

level.add_cam_effector("camera_effects\\earthquake.anm", 2002, true, "")

if bt<1 then

level.set_weather("amk_for_blow",true)

level.add_pp_effector("vibros.ppe", 2001, true)

blowout_psy_sound("start")

end

end

 

if db.actor and not has_alife_info("game_over") then

local flame = db.actor:object("wpn_flame")

if flame then

db.actor:iterate_inventory(

function(dummy,item)

if item:section()=="wpn_flame" then

alife():release(alife():object(item:id()))

end

end

,db.actor)

 

end

end

end

 

 

Комментирование оставшихся составляющих массива функции check_spawn()

для того, чтобы отловить проблемную функцию,

приводит к вылету при сэйв/лоад с логом:

! Unknown command: ZAMET:start_game_callback___called

 

FATAL ERROR

 

[error]Expression : fatal error

[error]Function : CScriptEngine::lua_error

[error]File : E:\stalker\patch_1_0004\xr_3da\xrGame\script_engine.cpp

[error]Line : 73

[error]Description : <no expression>

[error]Arguments : LUA error: d:\st\008_tt2_final\gamedata\scripts\_g.script:1245: attempt to index global 'amk' (a nil value)

 

 

Получается, что тут, как бы, вторая ступень коллбэков.

И непонятно, куда дальше "копать", откуда идёт вызов тех функций и условий,

что остались. Возможно, эта задача, что мы хотим решить, не имеет решения,

а возможно и имеет.

К сожалению, я не имею навыков в прочтении таких функций.

1) Можно ли расшифровать оставшиеся составляющие функции check_spawn()

для дальнейшей работы по отлову проблемного в нашем случае места?

И второй вопрос: комментирование коллбэка на всю функцию check_spawn()

целиком, в файле бинд_сталкер.скрипт к каким последствиям приведёт в дальнейшем?

Чего мы лишаемся в этом случае?

 

Изменено пользователем antreg

Поделиться этим сообщением


Ссылка на сообщение

_Призрак_,

Если ты внимательно прочитал сообщения выше, то там написано, что данный вылет с таким логом происходит после комментирования одной из функций. И ключевой, в логе вылета, является строка: start_game_callback___called, указывающая на то, что мы искусственно создали условие для вылета, закомментировав одну из функций массива, нарушив стартовый вызов (колбэк), т.е. специально создали ошибку. В этом и есть вопрос, как теперь расшифровать те функции и условия, которые невозможно закомментировать для отлова проблемы.

 

Поделиться этим сообщением


Ссылка на сообщение

KD87,

Конечно, но вопрос то совсем в другом был. То, что я искусственно создал такой вылет - это и так понятно.

Комментирование функции с вызовом через колбэк конечно вызовет синтаксическую ошибку.

Вопрос то совсем не в этом. Это только последствия последовательных действий поиска проблемы, с целью найти причину, мешающую нам адаптировать то, что задумано. Поиск проблемы адаптации пока зашёл в тупик, так как пропала возможность путём "тыка" (комментирования) найти некорректный контент, мешающий адаптации. Если кто-то может реально помочь, прошу поучаствовать в решении. Только прошу, вникните вначале в суть вопроса.

Поделиться этим сообщением


Ссылка на сообщение

-=Krovosos=-,

[smart_terrains]

none = true

 

[logic]

active = camper@my_npc

combat_ignore = combat_ignore

on_hit = hit

 

[camper@my_npc]

path_walk = my_npc_walk

path_look = my_npc_look

meet = meet@my_npc

danger = danger_condition@my_npc

combat_ignore_cond = always

 

[danger_condition@my_npc]

ignore_distance = 0

ignore_distance_corpse = 0

 

[meet@my_npc]

use = true

use_wpn = false

meet_talk_enabled = true

 

[hit]

on_info = %=actor_enemy%

 

 

Поделиться этим сообщением


Ссылка на сообщение

Добрый день!

Необходимо сделать логику НПС-врага так, чтобы он реагировал на всех своих врагов, согласно заданным параметрам в файле game_relations.ltx, но до определённого момента не трогал бы актёра, оставаясь для него врагом, но тем не менее игнорировал бы его как врага.

Есть, конечно, вариант в логике вписать условие игнорирования:

combat_ignore_cond = always

, но это заставляет НПС игнорировать всё и вся.

Пробовал так:

combat_ignore_cond = {=fighting_actor}

и так:

combat_ignore_cond = {=actor_enemy}

- результата нет.

Нужно что-то типа того, как идёт игнорирование другого НПС по его стори_айди:

combat_ignore_cond = {=check_fighting(9608)}

, где 9608 стори_айди какого-нибудь НПС, но только применительно к актёру.

Так тоже не получилось:

combat_ignore_cond = {=check_fighting(actor)}

Есть ещё какие варианты? ТЧ 1.0004 + АМК

 

Пользуйтесь пожалуйста тегами. ColR_iT

Изменено пользователем ColR_iT

Поделиться этим сообщением


Ссылка на сообщение

Добрый день!

Помогите найти пути лечения такого вылета:

! Unknown command: ZAMET:weather_update___day___[5]

! Unknown command: ZAMET:***______sar_monolith_general___--___State:___0___--___Total___population:___11/11___--___Non___exclusive___population:___0/0

! Unknown command: ZAMET:***______sar_monolith_sklad___--___State:___0___--___Total___population:___5/5___--___Non___exclusive___population:___0/0

! Unknown command: ZAMET:*SND*___play___SND___to___[state]___for___[bar_bar_lisiy]

! Unknown command: ZAMET:ERROR:___Watchdog___100.Reason___cn___on_news___offline_alife___exit

 

FATAL ERROR

 

[error]Expression : fatal error

[error]Function : CScriptEngine::lua_error

[error]File : E:\stalker\patch_1_0004\xr_3da\xrGame\script_engine.cpp

[error]Line : 73

[error]Description : <no expression>

[error]Arguments : LUA error: ...files (x86)\s.t.a.l.k.e.r\gamedata\scripts\_g.script:20: bad argument #2 to 'format' (string expected, got no value)

 

 

ТЧ + АМК. Добавлены локации новые, убраны некоторые старые (Кордон, Свалка, Агропром, ТД и радар)

Вылет (или завис, то так, то так) возникает рандомно. Находишься на локации какое-то время и может случиться такой вылет. От локации не зависит - на любой такое происходит.

Про Ватчдоги читал на форумах много всего, но в данном случае не понятно где искать.

Основываясь на логе, error содержит строку: cn on_news offline_alife exit

Эта строка присутствует в файле: news_main.script

    local gtime = game_minutes()
    
    if (gtime - timer_alife_showed > timer_alife_freq) then
        amk.oau_reason="cn on_news offline_alife start"
        amk_offline_alife.offline_alife()
        amk.oau_reason="[b]cn on_news offline_alife exit[/b]"
        timer_alife_showed = game_minutes()
    end

 

Это конструкция из большой функции on_news()

Вот она целиком:

function on_news()
    local avail = {}
    if news_stack then 
        amk.oau_reason="cn on_news first pass"
        for k,v in pairs(news_stack) do
            if v.activated == nil then
                if (v.lifetime > game_minutes()) then
                    if (v.timeout < game_minutes()) then -- Новость актуальна.
                        --table.insert(avail, k)
                    else
                        mylog("Not ready yet - ".. v.from) -- Еще не время.
                    end
                else -- Новость устарела.
                        mylog("Too old - "..v.from..": "..v.text)
                    table.remove(news_stack, k)
                end
            else -- Новость уже была.
                table.remove(news_stack, k)
            end
        end
        amk.oau_reason="cn on_news sort"
        -- Отсортируем.
        table.sort(news_stack, news_sort)
        --amk.dump_table(news_stack)
        amk.oau_reason="cn on_news second pass"
        for k,v in pairs(news_stack) do
            if v.activated == nil then
                if (v.lifetime > game_minutes()) then
                    if (v.timeout < game_minutes()) then -- Новость актуальна.
                        table.insert(avail, k)
                    else
                            mylog("Not ready yet - ".. v.from..": "..v.text) -- Еще не время.
                    end
                else -- Новость устарела.
                        mylog("Too old - "..v.from..": "..v.text)
                    table.remove(news_stack, k)
                end
            else -- Новость уже была.
                table.remove(news_stack, k)
            end
        end
    end
    
    if avail and table.getn(avail) > 0 then
        amk.oau_reason="cn on_news get available"
        --local t = avail[math.random(table.getn(avail))]
        local t = avail[1]
        local z = news_stack[t]
        if (z) then
            local bAlive = false
            local m_author_id = tonumber(z.author_id)
            if (m_author_id ~= nil) then
                amk.oau_reason="cn on_news check author"
                bAlive = false
                local obj = alife():object(m_author_id)
                amk.oau_reason="cn on_news check author obj"
                if (obj) then
                    amk.oau_reason="cn on_news author obj exists"
                    if (IsStalker(obj)) then
                        amk.oau_reason="cn on_news author obj is NPC"
                        if IsNpcStalker(obj) then
                            amk.oau_reason="cn on_news check author alive"
                    if (obj.alive and obj:alive()==true and obj.health and obj:health() > 0) then
                        if (_debug == true) then amk.add_spot_on_map(obj.id, "red_location", z.from..": "..z.text) end
                                amk.oau_reason="cn on_news author is alive"
                        bAlive = true
                    end
                end
                    end
                end
            else
                bAlive = true
            end
            if (bAlive == true) then
                amk.oau_reason="cn on_news show_news"
                --show_news(z.from, z.text, z.timeout, z.showtime, z.section)
                show_news(z.text, z.from, 0, z.showtime, z.section)
                amk.oau_reason="cn on_news set activated"
                z.activated = game_minutes()
            else
                amk.oau_reason="cn on_news show_news alive is false"
            end
        end
    else
--        mylog("on_news [5] - no news ")
    end    

    amk.oau_reason="cn on_news continue"

    if (timer_next_blow == 0) then
        local name, delay
        for a=1,100,1 do
        local tmp = amk.load_variable("gt"..a,nil)
            if tmp ~= nil then
                name     = amk.load_variable("gt"..a, nil)        
                delay     = amk.load_variable("gd"..a, nil)
                if (name and delay and name == "blow_shift") then
                    timer_next_blow = delay
                    --next_blow(delay)
                end
            end
        end    
    end

    local gtime = game_minutes()
    
    if (gtime - timer_alife_showed > timer_alife_freq) then
        amk.oau_reason="cn on_news offline_alife start"
        amk_offline_alife.offline_alife()
        amk.oau_reason="cn on_news offline_alife exit"
        timer_alife_showed = game_minutes()
    end
    if (gtime - timer_blow_showed > timer_blow_freq) then
        do_blow_news()
    end
    if (gtime - timer_eternal_stalker > timer_eternal_stalker_freq) then
        do_eternal_stalker()    
    end
    --[[ if (gtime - timer_random_spawn > timer_random_spawn_freq) then
        do_seen()
    end ]]
    if (gtime - timer_def_spawn > timer_def_spawn_freq) then
        do_seen_monster()    
    end    
    if (gtime - timer_daytime_showed > timer_daytime_freq) then
        on_daytime()
    end
end

 

Видимо, что-то не нравится связанное с сообщением о предстоящем выбросе.

Возможно, кто-то сможет помочь в этом вопросе.

Также присутствует в этой конструкции ссылка на функцию: offline_alife() из файла: amk_offline_alife.script

Фот эта функция:


--генерируем оффлайн события

function offline_alife()

 

local lname = maps[math.random(table.getn(maps))]

-- update_tables(lname)

-- amk.mylog("Offline_alife - "..lname)

local st = 0

amk.oau_reason="cn offline_alife chp1"

if off_npcs[lname] then st = table.getn(off_npcs[lname].stalkers) end

if st>0 then

amk.oau_reason="cn offline_alife chp2"

for search = 1,search_intensivity do

amk.oau_reason="cn offline_alife chp3"

local rnd = math.random(st)

amk.oau_reason="cn offline_alife chp4"

if off_npcs[lname].stalkers[rnd] then

amk.oau_reason="cn offline_alife chp5"

local victim = alife():object(off_npcs[lname].stalkers[rnd].id)

amk.oau_reason="cn offline_alife chp6"

if victim and not victim.online and victim.health and victim.can_switch_online and victim:health()>0 and victim:can_switch_online() and victim:name() == off_npcs[lname].stalkers[rnd].name then

amk.oau_reason="cn offline_alife chp7 "..tostring(victim and victim:name())

local vdata = collect_info(victim,lname)

amk.oau_reason="cn offline_alife chp8 "..tostring(victim and victim:name())

if table.getn(vdata.enemies)>0 then

--есть вражина - воюем нах!

amk.oau_reason="cn offline_alife chp9 "..tostring(victim and victim:name())

on_enemies_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.monsters)>0 then

--есть монстрятина - видели, слышали, убили, сдохли...

amk.oau_reason="cn offline_alife chp10 "..tostring(victim and victim:name())

on_monsters_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.corpses.stalkers)>0 then

--есть труп сталкера

amk.oau_reason="cn offline_alife chp11 "..tostring(victim and victim:name())

on_npc_corpses_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.corpses.monsters)>0 then

--есть труп монстра

amk.oau_reason="cn offline_alife chp12 "..tostring(victim and victim:name())

on_monster_corpses_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.weapons.seen)>0 then

--есть бесхозное оружие

amk.oau_reason="cn offline_alife chp13 "..tostring(victim and victim:name())

on_weapons_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.artefacts)>0 then

--есть арты

amk.oau_reason="cn offline_alife chp14 "..tostring(victim and victim:name())

on_artifacts_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif table.getn(vdata.inv_boxes)>0 then

--есть контейнеры. Надо обыскать.

amk.oau_reason="cn offline_alife chp18 "..tostring(victim and victim:name())

on_inv_boxes_found(victim, vdata)

break --прерываем цикл - событие отработано

elseif items[victim.id] and table.getn(items[victim.id]) > 0 then

--попробуем продать всякого

amk.oau_reason="cn offline_alife chp15 "..tostring(victim and victim:name())

-- amk.mylog("Offline: lets trade")

amk.oau_reason="cn offline_alife chp17 "..tostring(victim and victim:name())

process_trade(victim)

-- amk.mylog("Offline: trade done")

break

else

--amk.mylog("__")

end

end

end

end

end

amk.oau_reason="cn offline_alife end"

end[code]

 

 

Заключайте коды в тэги [cоde], дабы не 'убивать' отступы и не коверкать некоторые сочетания символов.

--/ Artos

Изменено пользователем Artos

Поделиться этим сообщением


Ссылка на сообщение

Добрый день!

Подскажите, пожалуйста,

есть такие простые функции для спавна и удаления предметов (объектов) из инвентаря актёра

:

--Универсальная рабочая функция удаления предмета из инвентаря
function delete_object(section,obj)
       if obj== nil then obj = db.actor end
        local item= obj:object(section)
        if item then 
        local seobj = alife():obect(item:id())
        if seobj then 
        alife():release(seobj)
        end
    end
end

--Сама функция удаления конкретного предмета
function delete_fotik()
this.delete_object("wpn_foto")
end

--Функция спавна предмета в инвентарь
function spawn_fotik()
local obj=alife():create("wpn_foto", db.actor:position(), db.actor:level_vertex_id(), db.actor:game_vertex_id(), db.actor:id())
end

 

Функции прекрасно работают с любым итемом или оружием, но как только пытаемся проделать теже манипуляции с device_torch, то сразу вылет с аргументом на неправильное задание объекта в функции. Видимо device_torch не является обычным объектом для инвентаря. Есть какое-то решение по данному вопросу?

Изменено пользователем Artos

Поделиться этим сообщением


Ссылка на сообщение

antreg, я не думаю, что ваш вопрос уместен в этой теме. Поискав нужное вам в файлах игры, найдя рестриктор, после которого активируется сцена, я наткнулся на следующий файл логики: config/scripts/agr/agr_knockdown.ltx

Вопрос более чем уместен в этой теме.

Алгоритмы из agr_knockdown.ltx не являются решением вышеописанной задачи.

Задача совсем другая.

 

Более чем НЕ уместен!

К скриптам не относится не коим образом.

Либо меняй постановку задачи либо пиши в "ковырялку", хотя абсолютно не за чем - решается с помощью кат сцены.

ColR_iT

Изменено пользователем ColR_iT

Поделиться этим сообщением


Ссылка на сообщение

Добрый день.
Вопрос по скриптовому файлу АМК: amk_anoms.script

А именно по таблице: level_anoms
Может кто-то разъяснить,
за что отвечает третий цифровой параметр в строках типа:
l11_pripyat = {100,150,900,{mincer=15 ,mosquito_bald=17 ,witches_galantine=17 ,buzz=17 ,zharka_static=17 ,gravi_zone=17}},
(в данном примере - это 900).

Поделиться этим сообщением


Ссылка на сообщение

Добрый день.
Подскажите, если знаете, STALKER ТЧ, Windows 10,

валидность координат при снятии всегда false, даже в тех местах, где реально точно есть AI.

На координатах, по факту, всё работает, но при снятии выдаётся невалидность. В чём может быть причина?
Функция снятия давно известная и работающая прекрасно на семёрке и хр:
function main_menu:LevelVertexId()
    local hud = get_hud()
 local cs = hud:GetCustomStatic("cs_debug" )
 if cs == nil then
  hud:AddCustomStatic("cs_debug", true)
  cs = hud:GetCustomStatic("cs_debug" )
 end
 local lvid, gvid = db.actor:level_vertex_id(), db.actor:game_vertex_id()
 local pos, dir = db.actor: position(), db.actor:direction()
 local pos2 = level.vertex_position(lvid)
 local valid = pos2:distance_to(pos) <= 0.7
 local msg = string.format("lvid: %d\\n", lvid) ..
    string.format("gvid: %d\\n", gvid) ..
    string.format("pos: %f,%f,%f\\n", pos.x, pos.y, pos.z) ..
    string.format("dir: %f,%f,%f\\n", dir.x, dir.y, dir.z) ..
    string.format("valid: %s", tostring(valid))
 if cs ~= nil then
  cs:wnd():SetText(msg)
 end
end

Поделиться этим сообщением


Ссылка на сообщение
  • Недавно просматривали   0 пользователей

    • Ни один зарегистрированный пользователь не просматривает эту страницу.
×
×
  • Создать...