Overf1rst 1 535 Опубликовано 1 июля, 2020 Тема посвящена моддингу на платформе Зов Припяти. Правила темы: Здесь задают вопросы и получают на них ответы. Прежде чем задать вопрос, воспользуйтесь поиском, ответ на него, вероятно, уже есть. Если у вас произошёл вылет, проверьте лог и поищите информацию об ошибке в справочнике. Также будет полезно посмотреть справочник ошибок. Если у Вас вылетает какой-то мод, то следует написать в тему этого мода. Грамотно оформляйте свой пост, чётко доносите суть своего вопроса (ответа). Благодарность выражаем в личке или же ставим реакцию. Посты с благодарностями в теме будут удаляться. 19 10 1 1 2 6 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
FacingSlave 121 Опубликовано 9 июня а ты как в кастом дату написал рестриктора? Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
RomaL23 4 Опубликовано 9 июня FacingSlave [logic] cfg = scripts\dead_city\restrictor\dead_city_start_space_restrictor_logic.ltx Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
denis2000 1 069 Опубликовано 9 июня (изменено) DEL Изменено 9 июня пользователем denis2000 Путь во мгле. Связь времен."Он ловко выхватил из-под себя табуретку и очень метко и сильно бросил ее в докладчика..." (Чугунный всадник) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
RomaL23 4 Опубликовано 9 июня P.S. решил тем что перебросил файл с логикой в другую папку 1 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Бессмертный 2 Опубликовано 9 июня (изменено) Решил "воссоздать" в механику рассказа НПС у костра историй и легенд голосом Профа, с последующей выдачей окружающими НПС реакций типа "ого!". В скриптах я полный ноль, поэтому решил просто копировать готовое. За пример брал секцию "story" и "test_story" в конфигах и скриптах. Таким образом, в папке configs\misc в файле sound_stories.ltx были проведены следующие манипуляции: Спойлер [test_story] ;номер, звук, пауза(сек) 0 = teller, intro_joke, 1 1 = teller, joke, 0.1 2 = reaction_all, reac_laugh, 0.2 3 = reaction, reac_joke, 0 [test_legend] -- моя секция для легенд/история ;номер, звук, пауза(сек) 0 = teller, legend, 0.1 1 = reaction, reac_legend, 0 В файле script_sound_music_and_stories.ltx были прописаны следующие секции: Спойлер legend reac_legend [legend] type = npc avail_communities = stalker npc_prefix = true path = talk\stories\legend002_part_ shuffle = rnd idle = 0,0 group_snd = true [reac_legend] type = npc avail_communities = stalker npc_prefix = true path = reactions\story\cool_info_ shuffle = rnd idle = 0,0 Далее идут скрипты. Там в файле xr_kamp я просто дублировал все значения и строки, связанные с секцией story. Прикладываю измененные фрагменты кода. Спойлер local avail_state = { idle = {directed = standard_states}, pre_harmonica = {directed = {"wait_harmonica"}, undirected = standard_states}, harmonica = {directed = {"play_harmonica"}, undirected = standard_states}, post_harmonica = {directed = {"wait_harmonica"}, undirected = standard_states}, pre_guitar = {directed = {"wait_guitar"}, undirected = standard_states}, guitar = {directed = {"play_guitar"}, undirected = standard_states}, post_guitar = {directed = {"wait_guitar"}, undirected = standard_states}, story = {directed = {"declarate"}, undirected = standard_states}, legend = {directed = {"declarate"}, undirected = standard_states}, } local avail_sound = { idle = {directed = "idle"}, pre_harmonica = {directed = "pre_harmonica", undirected = ""}, harmonica = {directed = "", undirected = ""}, post_harmonica = {directed = "", undirected = "reac_harmonica"}, pre_guitar = {directed = "pre_guitar", undirected = ""}, guitar = {directed = "", undirected = ""}, post_guitar = {directed = "", undirected = "reac_guitar"}, story = {directed = "", undirected = ""}, legend = {directed = "", undirected = ""}, } local timeout = { idle = {min = 30000}, pre_harmonica = {min = 3000}, harmonica = {min = 5000, soundstart = true}, post_harmonica = {min = 3000}, pre_guitar = {min = 3000}, guitar = {min = 5000, soundstart = true}, post_guitar = {min = 3000}, story = {min = 1000, soundstart = true}, legend = {min = 1000, soundstart = true}, } local target_states = { idle = {idle = 0, pre_harmonica = 25, pre_guitar = 25, story = 50, legend = 50}, pre_harmonica = {harmonica = 100}, harmonica = {post_harmonica = 100}, post_harmonica = {idle = 70, harmonica = 30}, pre_guitar = {guitar = 100}, guitar = {post_guitar = 100}, post_guitar = {idle = 70, guitar = 30}, story = {idle = 100}, legend = {idle = 100}, } ----- local p = math.random(0, max_rnd) for state_name, prob in pairs (avail_states) do p = p - prob if p <= 0 then if state_name == "idle" then self.director = nil if self.kamp_state ~= "idle" then camp_npc.begin = nil end elseif state_name == "story" then self.sound_manager:set_story("test_story") self.director = npc_id else camp_npc.begin = nil if timeout[state_name].soundstart then camp_npc.need_sound_begin = true end self.director = npc_id end self.kamp_state = state_name self.begin = time_global() for _, npc_data in pairs (self.npc) do npc_data.is_new = true end return end end ------ local p = math.random(0, max_rnd) for state_name, prob in pairs (avail_states) do p = p - prob if p <= 0 then if state_name == "idle" then self.director = nil if self.kamp_state ~= "idle" then camp_npc.begin = nil end elseif state_name == "legend" then self.sound_manager:set_legend("test_legend") self.director = npc_id else camp_npc.begin = nil if timeout[state_name].soundstart then camp_npc.need_sound_begin = true end self.director = npc_id end self.kamp_state = state_name self.begin = time_global() for _, npc_data in pairs (self.npc) do npc_data.is_new = true end return end end end ----- if self.kamp_state == "story" then sound = "" else sound = avail_sound[self.kamp_state][is_director and "directed" or "undirected"] end if self.kamp_state == "legend" then sound = "" else sound = avail_sound[self.kamp_state][is_director and "directed" or "undirected"] end return state, sound end ------ if trance_state == nil then self.npc[npc_id] = { position_idx = nil, trance_state = nil, is_new = false, need_sound_begin = false, states = {declarate = true, sit = true, sit_ass = true, sit_knee = true}, kamp_states = {idle = true, story = true, legend = true}, } else self.npc[npc_id] = { position_idx = nil, trance_state = trance_state, is_new = false, need_sound_begin = false, states = {declarate = true, trans = true}, kamp_states = {idle = true, story = true, legend = true}, } end И, наконец, в скрипте sound_manager добавил функции set_legend и CLegend по аналогии с set_story и CStory Спойлер -' Установить какую историю менеджер должен отыграть function sound_manager:set_story(story_id) self.story = CStory(story_id) --printf("Set story sm [%s] = [%s]", self.id, story_id) end --' Установить какую легенду менеджер должен отыграть function sound_manager:set_legend(legend_id) self.story = CLegend(legend_id) --printf("Set story sm [%s] = [%s]", self.id, legend_id) end ----- --' Класс "история". Содержит дерево фраз. У каждой фразы указано должен ли ее говорить рассказчик или слушатели. class "CStory" function CStory:__init(story_id) --printf("Creating story [%s]", tostring(story_id)) if not story_ltx:section_exist(story_id) then abort("There is no story [%s] in sound_stories.ltx", tostring(story_id)) end self.replics = {} --' Вычитываем шаблон истории из ini файла local n = story_ltx:line_count(story_id) local id, value = "","" for i=0,n-1 do result, id, value = story_ltx:r_line(story_id,i,"","") local t = parse_names(value) if t[1] ~= "teller" and t[1] ~= "reaction" and t[1] ~= "reaction_all" then abort("Wrong fist field [%s] in story [%s]", tostring(t[1]), tostring(story_id)) end self.replics = {who = t[1], theme = t[2], timeout = t[3]} end self.id = tostring(story_id) self.max_phrase_count = n-1 self.next_phrase = 0 --print_table(self.replics) end --' Закончена ли история function CStory:is_finished() return self.next_phrase > self.max_phrase_count end --' Ресет истории function CStory:reset_story() self.next_phrase = 0 end --' Возвращает следующую фразу function CStory:get_next_phrase() local phrase = self.replics[self.next_phrase] self.next_phrase = self.next_phrase + 1 return phrase end --' Класс "легенда". Содержит дерево фраз. У каждой фразы указано должен ли ее говорить рассказчик или слушатели. class "CLegend" function CLegend:__init(legend_id) --printf("Creating story [%s]", tostring(legend_id)) if not story_ltx:section_exist(legend_id) then abort("There is no story [%s] in sound_stories.ltx", tostring(legend_id)) end self.replics = {} --' Вычитываем шаблон истории из ini файла local n = story_ltx:line_count(legend_id) local id, value = "","" for i=0,n-1 do result, id, value = story_ltx:r_line(legend_id,i,"","") local t = parse_names(value) if t[1] ~= "teller" and t[1] ~= "reaction" and t[1] ~= "reaction_all" then abort("Wrong fist field [%s] in story [%s]", tostring(t[1]), tostring(legend_id)) end self.replics = {who = t[1], theme = t[2], timeout = t[3]} end self.id = tostring(legend_id) self.max_phrase_count = n-1 self.next_phrase = 0 --print_table(self.replics) end --' Закончена ли история function CLegend:is_finished() return self.next_phrase > self.max_phrase_count end --' Ресет истории function CLegend:reset_story() self.next_phrase = 0 end --' Возвращает следующую фразу function CLegend:get_next_phrase() local phrase = self.replics[self.next_phrase] self.next_phrase = self.next_phrase + 1 return phrase end В игре (вы будете удивлены) ничего не работает. Не вылетает, но НПС перестали рассказывать даже анекдоты у костра, просто молчат, играют на инструментах, иногда бормочут что-то под нос. Как поправить положение и нормально внедрить механику рассказывания НПС у костра историй с последующими реакциями окружающих НПС? Изменено 10 июня пользователем Бессмертный Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
denis2000 1 069 Опубликовано 9 июня (изменено) Бессмертный Глянул мельком. ВЕЗДЕ в скриптах, где добавляли элементы в таблицу лишние запятые в конце. PS: И используйте тег код, тег спойлер корежит выкладываемый код! Изменено 9 июня пользователем denis2000 Путь во мгле. Связь времен."Он ловко выхватил из-под себя табуретку и очень метко и сильно бросил ее в докладчика..." (Чугунный всадник) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Бессмертный 2 Опубликовано 10 июня 4 часа назад, denis2000 сказал: Бессмертный Глянул мельком. ВЕЗДЕ в скриптах, где добавляли элементы в таблицу лишние запятые в конце. PS: И используйте тег код, тег спойлер корежит выкладываемый код! Хм. Где, например? Если вы про начало скрипта xr_kamp, то я просто копировал строки от story, и если там были запятые, то я тоже их переносил. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Ayden 243 Опубликовано 10 июня (изменено) Напомните пожалуйста, как перемотать время на определенное через триггер? Мне надо, чтобы после выхода с локации было определенное время, чтобы синхронизировать с событиями. Изменено 10 июня пользователем Ayden Волк волку- волк, человек человеку- собутыльник. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Hrust 692 Опубликовано 10 июня 42 минуты назад, Ayden сказал: перемотать время При использовании проводников на локации есть функция перемотки, `level.change_game_time`. А в xr_effects есть две реализации, установка точного времени, или просто изменение по дельте. `xr_effects.set_game_time` и `xr_effects.forward_game_time`. В общем, в ЗП это много где использовалось. 1 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Ayden 243 Опубликовано 10 июня 17 минут назад, Hrust сказал: При использовании проводников на локации есть функция перемотки, `level.change_game_time`. А в xr_effects есть две реализации, установка точного времени, или просто изменение по дельте. `xr_effects.set_game_time` и `xr_effects.forward_game_time`. В общем, в ЗП это много где использовалось. Ну я видел где-то простенький скрипт в вопроснице вроде, но найти не могу, мне надо на определенное время, выйти в 2 часа ночи, чтобы по логике постовые спали и можно было прошмыгнуть, сам крепкий сон я им реализовал. Волк волку- волк, человек человеку- собутыльник. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Hrust 692 Опубликовано 10 июня Тогда сеттером по примеру можно и воспользоваться, но тут функция именно для разговора была сделана: function set_game_time(actor, npc, p) local real_hours = level.get_time_hours() local real_minutes = level.get_time_minutes() local hours = tonumber(p[1]) local minutes = tonumber(p[2]) if p[2] == nil then minutes = 0 end local hours_to_change = hours - real_hours if hours_to_change <= 0 then hours_to_change = hours_to_change + 24 end local minutes_to_change = minutes - real_minutes if minutes_to_change <= 0 then minutes_to_change = minutes_to_change + 60 hours_to_change = hours_to_change - 1 elseif hours == real_hours then hours_to_change = hours_to_change - 24 end level.change_game_time(0,hours_to_change,minutes_to_change) level_weathers.get_weather_manager():forced_weather_change() surge_manager.get_surge_manager().time_forwarded = true printf("set_game_time: time changed to [%d][%d]", hours_to_change, minutes_to_change) end Хотя я сам не знаю, в чём отличие, но можно немного переработать приём аргументов, чтобы вместо `p` было два отдельных. 1 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Ayden 243 Опубликовано 10 июня (изменено) Hrust Спасибо! Насчет level_weathers.get_weather_manager():forced_weather_change() дало идею, а ведь можно и дождь врубить под это, еще аутентичнее будет для костыльного "стелса") Я просто врагов сделал глуховатыми на скрипте спящими, что только стрельба их разбудит, чисто с ними на 5 минут сценка, чтобы напряжение создать) Изменено 10 июня пользователем Ayden 1 Волк волку- волк, человек человеку- собутыльник. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
стрелок_2009 8 Опубликовано 10 июня а какие строчки в конфиге оружия отвечает за расположение в режиме прицеливая? я просто хочу пофиксить кривое расположение прицелов на широковорматном маниторе Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Hrust 692 Опубликовано 10 июня стрелок_2009 ссылка, настраивается в игре через худ аджаст. 1 Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Ayden 243 Опубликовано 10 июня Ребят, еще вопросец, по интерфейсу, как при диалоге с нпс открыть окно ящика, чтобы нпс нес с собой половину лута (например с ограничением в 30 кг)?) Навеяно Гаммой. Волк волку- волк, человек человеку- собутыльник. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Бессмертный 2 Опубликовано 10 июня 8 часов назад, denis2000 сказал: Бессмертный Глянул мельком. ВЕЗДЕ в скриптах, где добавляли элементы в таблицу лишние запятые в конце. PS: И используйте тег код, тег спойлер корежит выкладываемый код! По вашему совету поправил отображение кода скриптов под спойлерами. Не очень понимаю, куда копать в решении вопроса. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
denis2000 1 069 Опубликовано 10 июня Бессмертный Откуда этот странный код вообще? Путь во мгле. Связь времен."Он ловко выхватил из-под себя табуретку и очень метко и сильно бросил ее в докладчика..." (Чугунный всадник) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Gambimo 0 Опубликовано 10 июня При спавне НПС через смарт_террейн командой =create_squad происходит такой вылет, как исправить и что его вызывает? Спойлер FATAL ERROR [error]Expression : fatal error [error]Function : CScriptEngine::lua_error [error]File : X:\GitHub\ixray-1.6-stcop\src\xrScripts\script_engine.cpp [error]Line : 61 [error]Description : <no expression> [error]Arguments : LUA error: [string "sim_board"]:228: attempt to index local 'spawn_smart' (a nil value) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Prostomod 1 446 Опубликовано 10 июня 10 минут назад, Gambimo сказал: ixray-1.6-stcop Зная этот движок, спрошу: в логе есть какие-нибудь записи, которые начинаются со слова ABORT? Можешь приложить лог? Мод в разработке - X-7: Эпицентр Дискорд мода - https://discord.gg/NjnUnKDD Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Бессмертный 2 Опубликовано 10 июня 24 минуты назад, denis2000 сказал: Бессмертный Откуда этот странный код вообще? Это вырезки (брал только те секции, которые копировал и куда вносил изменения по формату "оригинал "story", далее моя секция "legend") из моих скриптов xr_kamp и sound_manager. На их достоверность не претендую, а вовсе наоборот, ищу, в чем ошибка. Попробую по-другому поставить вопрос: может есть возможность не изобретать велосипед и какой-то другой способ заставить неписей рассказывать эти истории и после реагировать на них, как это было в некоторых модах на ТЧ? Так-то можно просто добавить эти истории к одиночным репликам у костра типа "Да-а, еще 3-4 таких похода как вчера, да чтоб хабар не хуже...". Но тогда они будут просто произноситься, без реакции со стороны остальных НПС в лагере. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
denis2000 1 069 Опубликовано 10 июня 33 минуты назад, Бессмертный сказал: Это вырезки ... из моих скриптов xr_kamp и sound_manager. Ладно, не буду спрашивать почему ваш код кардинально отличается от оригинального. Приведите, как у вас до правки и после правки выглядит таблица avail_state например. Путь во мгле. Связь времен."Он ловко выхватил из-под себя табуретку и очень метко и сильно бросил ее в докладчика..." (Чугунный всадник) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Yara 144 Опубликовано 10 июня Бессмертный 15 часов назад, Бессмертный сказал: В игре (вы будете удивлены) ничего не работает. Не вылетает, но НПС перестали рассказывать даже анекдоты у костра, просто молчат, играют на инструментах, иногда бормочут что-то под нос. В зп xr_kamp не используется, и нужно править: \configs\scripts\camp.ltx \scripts\sr_camp.script 1 https://sites.google.com/view/xray-sdk-0-4-smg Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
denis2000 1 069 Опубликовано 10 июня (изменено) 9 минут назад, Yara сказал: В зп xr_kamp не используется Но вполне работает если задействовать. С другой стороны, судя по коду, используется не ЗП, а что вопрошающий скрывает! Изменено 10 июня пользователем denis2000 Путь во мгле. Связь времен."Он ловко выхватил из-под себя табуретку и очень метко и сильно бросил ее в докладчика..." (Чугунный всадник) Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
Бессмертный 2 Опубликовано 10 июня (изменено) 21 минуту назад, denis2000 сказал: Но вполне работает если задействовать. С другой стороны, судя по коду, используется не ЗП, а что вопрошающий скрывает! Вопрошающий не скрывает, вопрошающий ошибся темой... За что приношу извинения. Потерялся в темах и запутал вас. Скрипты у меня, конечно, от ЧН, а не от ЗП. Если еще актуально, то вот, как выглядит avail_state до правок. local avail_state = { idle = {directed = standard_states}, pre_harmonica = {directed = {"wait_harmonica"}, undirected = standard_states}, harmonica = {directed = {"play_harmonica"}, undirected = standard_states}, post_harmonica = {directed = {"wait_harmonica"}, undirected = standard_states}, pre_guitar = {directed = {"wait_guitar"}, undirected = standard_states}, guitar = {directed = {"play_guitar"}, undirected = standard_states}, post_guitar = {directed = {"wait_guitar"}, undirected = standard_states}, story = {directed = {"declarate"}, undirected = standard_states}, } Тем не менее, есть ли способ заставить неписей проигрывать эти "истории" и реагировать на них, просто откопировав часть скриптовых функций от тех же, скажем, анекдотов? Может, есть модификации, где методы реализации можно было бы подсмотреть? Или в ЧН и ЗП логика лагеря устроена принципиально разным образом? Изменено 10 июня пользователем Бессмертный Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты
FacingSlave 121 Опубликовано 10 июня Люди есть скрипт или фича чтобы партикл отражался от нпс? К примеру есть нпс, я хочу повесить партикл типо от него электричеством отдаём. Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты