diff --git a/resources/config2/items.json b/resources/config2/items.json index fc94623..f9e226f 100644 --- a/resources/config2/items.json +++ b/resources/config2/items.json @@ -3,7 +3,7 @@ { "id": "phone", "name": "Телефон", - "description": "Я не могу себе представить жизнь без своего телефона", + "description": "Я не могу себе представить жизнь без своего телефона.", "icon": "resources/fire2.png" }, { @@ -23,6 +23,24 @@ "name": "Книга", "description": "Это книга о манасчи Жусупе Мамае.", "icon": "resources/fire2.png" + }, + { + "id": "note_spell", + "name": "Записка", + "description": "Тут написано \"Прочитай вслух когда настанет ночь, сквозь двери сможешь ты пройти.\" и текст заклинания.", + "icon": "resources/fire2.png" + }, + { + "id": "report_card", + "name": "Зачетка Бегимай", + "description": "Это зачетная книжка Бегимай. Сюда нужно поставить оценку за курсовую работу.", + "icon": "resources/fire2.png" + }, + { + "id": "coursework", + "name": "Курсовая Бегимай", + "description": "Это курсовая работа Бегимай, из-за которой она выбросилась из окна.", + "icon": "resources/fire2.png" } ] } diff --git a/resources/config2/npcs_dorm.json b/resources/config2/npcs_dorm.json index 6815b50..05950ad 100644 --- a/resources/config2/npcs_dorm.json +++ b/resources/config2/npcs_dorm.json @@ -30,7 +30,7 @@ }, "positionX": 4.03298, "positionY": 0.0, - "positionZ": -3.61801, + "positionZ": 0.61801, "facingAngle" : 0, "walkSpeed": 1.8, "rotationSpeed": 8.0, @@ -39,6 +39,34 @@ "modelCorrectionRotY": 180.0, "modelCorrectionRotZ": 0.0, "interactionRadius": 2.0 + }, + { + "id": "npc_alik", + "name": "Алик", + "animationIdlePath": "resources/w/jam/man_stand_idle002.anim", + "animationWalkPath": "resources/w/jam/man_walk002.anim", + "meshTextures": { + "Body": "resources/w/jam/male_packed0_diffuse.png", + "Bottoms": "resources/w/jam/male_packed1_diffuse.png", + "Eyelashes": "resources/w/jam/male_packed0_diffuse.png", + "Eyes": "resources/w/jam/male_packed0_diffuse.png", + "Eyewear": "resources/w/jam/male_packed0_diffuse.png", + "Gloves": "resources/w/jam/male_packed1_diffuse.png", + "Hair": "resources/w/jam/male_packed0_diffuse.png", + "Shoes": "resources/w/jam/male_packed1_diffuse.png", + "Tops": "resources/w/jam/male_packed2_diffuse.png" + }, + "positionX": -6.33478, + "positionY": 0.0, + "positionZ": -15.0382, + "facingAngle" : 3.141592, + "walkSpeed": 1.5, + "rotationSpeed": 8.0, + "modelScale": 0.0001, + "modelCorrectionRotX": 0.0, + "modelCorrectionRotY": 180.0, + "modelCorrectionRotZ": 0.0, + "interactionRadius": 2.0 } ] } \ No newline at end of file diff --git a/resources/dialogue/dorm_dialogues.json b/resources/dialogue/dorm_dialogues.json index ed3d7ec..e09fc74 100644 --- a/resources/dialogue/dorm_dialogues.json +++ b/resources/dialogue/dorm_dialogues.json @@ -133,6 +133,216 @@ "type": "End" } ] + }, + { + "id": "dialog_female_student001", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бермет", + "portrait": "resources/w/avatar_girl.png", + "text": "Бекзат отстань!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_female_student002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Алтынай", + "portrait": "resources/w/avatar_girl.png", + "text": "Бекзат ты почему на пары не ходишь?!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_alik001", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Привет Бекзат! Давно я не видел тебя на парах!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_alik002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Привет Бекзат!", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Привет Алик! Разговор есть.", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "С тобой на курсе училась Бегимай, ты ее помнишь?", + "next": "line_4" + }, + { + "id": "line_4", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Конечно помню! Я тебе даже больше расскажу.", + "next": "line_5" + }, + { + "id": "line_5", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "В тот день она принесла свою курсовую, чтобы сдать.", + "next": "line_6" + }, + { + "id": "line_6", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Но в тот день в учительской происходила генеральная уборка.", + "next": "line_7" + }, + { + "id": "line_7", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "И получилось так, что ее курсовая оказалась в стопке бумаг на выброс.", + "next": "line_8" + }, + { + "id": "line_8", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Курсовая работа пропала, Бегимай получила за нее ноль баллов, и не прошла отбор в Германию.", + "next": "line_9" + }, + { + "id": "line_9", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Поэтому с горя она выпрыгнула из окна лекционного зала и убилась.", + "next": "line_10" + }, + { + "id": "line_10", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "А ты откуда все это знаешь?", + "next": "line_11" + }, + { + "id": "line_11", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Я видел как ее курсовую уносили вместе с другой макулатурой из учительской.", + "next": "line_12" + }, + { + "id": "line_12", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "И где сейчас ее курсовая работа?", + "next": "line_13" + }, + { + "id": "line_13", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "За зданием универа есть контейнер с кучей бумажного мусора и макулатурой.", + "next": "line_14" + }, + { + "id": "line_14", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Скорее всего, курсовая до сих пор лежит где-то там.", + "next": "line_15" + }, + { + "id": "line_15", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Спасибо Алик! Ты мне очень помог.", + "next": "line_16" + }, + { + "id": "line_16", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Да без проблем! Обращайся если что.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_alik003", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Алик", + "portrait": "resources/w/avatar_student.png", + "text": "Привет Бекзат! Надеюсь ты нашел то что ищешь.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] } ], "cutscenes": [{ diff --git a/resources/dialogue/uni_exterior_dialogues.json b/resources/dialogue/uni_exterior_dialogues.json index 8d5a6ed..0816348 100644 --- a/resources/dialogue/uni_exterior_dialogues.json +++ b/resources/dialogue/uni_exterior_dialogues.json @@ -35,6 +35,40 @@ "type": "End" } ] + }, + { + "id": "dialog_contaier002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Если Алик не соврал, курсовая работа Бегимай лежит где-то тут.", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "[Копается в куче мусора]", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Ага, нашел! Вот и она!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] } ], "cutscenes": [ diff --git a/resources/dialogue/uni_interior_dialogues.json b/resources/dialogue/uni_interior_dialogues.json index 57ec484..72b44a8 100644 --- a/resources/dialogue/uni_interior_dialogues.json +++ b/resources/dialogue/uni_interior_dialogues.json @@ -149,6 +149,40 @@ "type": "End" } ] + }, + { + "id": "aiperi_dialog002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Айпери", + "portrait": "resources/w/avatar_girlfriend.png", + "text": "Я не знаю какие у тебя там дела, Бекзат,", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Айпери", + "portrait": "resources/w/avatar_girlfriend.png", + "text": "Но ты должен вернуть мне нож поскорее, а то я тебе голову оторву!", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Я обещаю, сейчас я один вопрос решу и верну тебе нож.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] }, { "id": "door_dialog001", @@ -319,6 +353,122 @@ "type": "End" } ] + }, + { + "id": "teacher_dialog004", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Аида Дженибековна, Бегимай хотела вам курсовую сдать, вы помните?", + "next": "line_2" + }, + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Я принес вам ее курсовую, можете посмотреть?", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Хорошо, давай посмотрим.", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Да, это ее курсовая работа, я вижу.", + "next": "line_4" + }, + { + "id": "line_4", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Там в шкафу лежат зачетки, найди мне зачетку и принеси мне.", + "next": "line_5" + }, + { + "id": "line_5", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Хорошо!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "teacher_dialog005", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Аида Дженибековна, Бегимай хотела вам курсовую сдать, вы помните?", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Я принес вам ее зачетку и ее курсовую работу, посмотрите пожалуйста.", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Хорошо, давай посмотрим.", + "next": "line_4" + }, + { + "id": "line_4", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Да, я вижу что курсовая написана хорошо, я ставлю ей максимальный балл.", + "next": "line_5" + }, + { + "id": "line_5", + "type": "Line", + "speaker": "Аида Дженибековна", + "portrait": "resources/w/avatar_teacher.png", + "text": "Вот держи зачетку с оценкой, положи ее обратно в шкаф.", + "next": "line_6" + }, + { + "id": "line_6", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Хорошо!", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] }, { "id": "book_dialog001", @@ -421,7 +571,7 @@ { "id": "line_3", "type": "Line", - "speaker": "Призрак", + "speaker": "Бегимай", "portrait": "resources/w/avatar_ghost.png", "text": "Меня зовут Бегимай, мне нужно сдать курсовую по манасоведению.", "next": "line_4" @@ -429,7 +579,7 @@ { "id": "line_4", "type": "Line", - "speaker": "Призрак", + "speaker": "Бегимай", "portrait": "resources/w/avatar_ghost.png", "text": "Я появляюсь здесь каждую ночь, чтобы сдать курсовую.", "next": "line_5" @@ -445,7 +595,7 @@ { "id": "line_6", "type": "Line", - "speaker": "Призрак", + "speaker": "Бегимай", "portrait": "resources/w/avatar_ghost.png", "text": "Я уйду на покой только когда увиду оценку по курсовой в своей зачетке.", "next": "line_7" @@ -453,9 +603,9 @@ { "id": "line_7", "type": "Line", - "speaker": "Призрак", + "speaker": "Бегимай", "portrait": "resources/w/avatar_ghost.png", - "text": "Я уйду из этого мира только когда я сдам курсовую. Поэтому я появляюсь здесь каждую ночь.", + "text": "А до тех пор, я буду появлятся здесь каждую ночь.", "next": "line_8" }, { @@ -471,6 +621,114 @@ "type": "End" } ] + }, + { + "id": "dialog_with_ghost002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Я Бегимай, мне нужно сдать курсовую по манасоведению.", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Я появляюсь здесь каждую ночь, чтобы сдать курсовую.", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Я уйду на покой только когда увиду оценку по курсовой в своей зачетке.", + "next": "line_4" + }, + { + "id": "line_4", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Ладно, я что-нибудь придумаю.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_with_ghost003", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Эй простыня, посмотри сюда.", + "next": "line_2" + }, + { + "id": "line_2", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Что это?", + "next": "line_3" + }, + { + "id": "line_3", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Это твоя зачетка.", + "next": "line_4" + }, + { + "id": "line_4", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Тебе поставили за курсовую максимальный балл!", + "next": "line_5" + }, + { + "id": "line_5", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Неужели! Наконец-то, мое предназначение исполнено.", + "next": "line_6" + }, + { + "id": "line_6", + "type": "Line", + "speaker": "Бегимай", + "portrait": "resources/w/avatar_ghost.png", + "text": "Теперь я могу уйти на покой.", + "next": "line_7" + }, + { + "id": "line_7", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Давай, иди отдыхай.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] }, { "id": "note_dialog001", @@ -533,6 +791,42 @@ "type": "End" } ] + }, + { + "id": "dialog_report_card002", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Здесь лежит зачетка Бегимай. Я пожалуй, возьму ее.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] + }, + { + "id": "dialog_report_card003", + "start": "line_1", + "nodes": [ + { + "id": "line_1", + "type": "Line", + "speaker": "Бекзат", + "portrait": "resources/w/gg/gg2_s_podsvetkoy5.png", + "text": "Мне еще рано возвращать зачетку Бегимай обратно в шкаф.", + "next": "end_1" + }, + { + "id": "end_1", + "type": "End" + } + ] } ], "cutscenes": [ @@ -625,99 +919,48 @@ ] }, { - "id": "test_cutscene_pan_01", - "background": "resources/first_cutscene.png", - "durationMs": 12000, - "cameraTrack": [ + "id": "darklands_exit001", + "background": "resources/test_cutscene001.png", + "durationMs": 5000, + "fadeOutMs": 500, + "fadeInMs": 500, + "endFadeOutMs": 500, + "endFadeInMs": 500, + "cameraTrack": [ + { + "durationMs": 3000, + "from": { "focusX": 0.3, "focusY": 0.50, "zoom": 1.10, "rotationDeg": 0.0 }, + "to": { "focusX": 0.7, "focusY": 0.50, "zoom": 1.00, "rotationDeg": 0.0 }, + "easing": "EaseInOutSine" + }, + { + "durationMs": 3000, + "from": { "focusX": 0.3, "focusY": 0.50, "zoom": 1.0, "rotationDeg": 0.0 }, + "to": { "focusX": 0.7, "focusY": 0.50, "zoom": 1.1, "rotationDeg": 0.0 }, + "easing": "EaseInOutCubic" + } + ], + "lines": [ + { + "speaker": "Бекзат", + "portrait": "resources/hero.png", + "text": "Кажется, после того как я умер, я очнулся.", + "durationMs": 3000 + }, + { + "speaker": "Бекзат", + "portrait": "resources/hero.png", + "text": "Жесть вообще, хочу спать.", + "durationMs": 3000 + }, { - "durationMs": 1200, - "from": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "to": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "easing": "Linear" - }, - { - "durationMs": 2500, - "from": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "to": { "anchor": "TopLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - }, - { - "durationMs": 2600, - "from": { "anchor": "TopLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "to": { "anchor": "TopRight", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - }, - { - "durationMs": 1800, - "from": { "anchor": "TopRight", "zoom": 1.55, "rotationDeg": 0.0 }, - "to": { "anchor": "BottomRight", "zoom": 1.72, "rotationDeg": 0.0 }, - "easing": "EaseInCubic" - }, - { - "durationMs": 3900, - "from": { "anchor": "BottomRight", "zoom": 1.72, "rotationDeg": 0.0 }, - "to": { "anchor": "BottomLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - } - ], - "lines": [ - { - "speaker": "Narrator", - "portrait": "resources/hero.png", - "text": "The memory begins in silence.", - "durationMs": 2200 - }, - { - "speaker": "Narrator", - "portrait": "resources/hero.png", - "text": "Something is drawing your eyes across the whole scene.", - "durationMs": 2800 - }, - { - "speaker": "Ghost", - "portrait": "resources/ghost_avatar.png", - "text": "Do not look away.", - "durationMs": 2400 - } - ] - }, - { - "id": "test_cutscene_pan_02", - "background": "resources/first_cutscene.png", - "durationMs": 12000, - "cameraTrack": [ - { - "durationMs": 1200, - "from": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "to": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "easing": "Linear" - }, - { - "durationMs": 2500, - "from": { "anchor": "Center", "zoom": 1.00, "rotationDeg": 0.0 }, - "to": { "anchor": "TopLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - }, - { - "durationMs": 2600, - "from": { "anchor": "TopLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "to": { "anchor": "TopRight", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - }, - { - "durationMs": 1800, - "from": { "anchor": "TopRight", "zoom": 1.55, "rotationDeg": 0.0 }, - "to": { "anchor": "BottomRight", "zoom": 1.72, "rotationDeg": 0.0 }, - "easing": "EaseInCubic" - }, - { - "durationMs": 3900, - "from": { "anchor": "BottomRight", "zoom": 1.72, "rotationDeg": 0.0 }, - "to": { "anchor": "BottomLeft", "zoom": 1.55, "rotationDeg": 0.0 }, - "easing": "EaseInOutSine" - } - ], - "lines": [] - } + "speaker": "Бекзат", + "portrait": "resources/hero.png", + "text": "Который час?", + "durationMs": 2000, + "background": "resources/test_cutscene001.png" + } + ] + } ] } diff --git a/resources/start_dorm.lua b/resources/start_dorm.lua index ba0c2e3..0a0bb03 100644 --- a/resources/start_dorm.lua +++ b/resources/start_dorm.lua @@ -17,6 +17,27 @@ game_api.start_dialogue("dialog_start001") phone_picked_up = false journal_picked_up = false +function on_npc_interact(npc_index) + if npc_index == 2 then + local player_alik_aware = game_api.getIntValue("player_alik_aware") + local player_container_aware = game_api.getIntValue("player_container_aware") + if player_container_aware == 1 then + game_api.start_dialogue("dialog_alik003") + elseif player_alik_aware == 1 then + game_api.start_dialogue("dialog_alik002") + game_api.setIntValue("player_container_aware", 1) + else + game_api.start_dialogue("dialog_alik001") + end + end + if npc_index == 0 then + game_api.start_dialogue("dialog_female_student001") + end + if npc_index == 1 then + game_api.start_dialogue("dialog_female_student002") + end +end + function on_phone_pickup() game_api.pickup_item("phone") diff --git a/resources/start_uni_exterior.lua b/resources/start_uni_exterior.lua index 0c947b4..0cef056 100644 --- a/resources/start_uni_exterior.lua +++ b/resources/start_uni_exterior.lua @@ -21,8 +21,15 @@ function darklands_exit001_enter_callback() end function on_container_clicked() +local player_container_aware = game_api.getIntValue("player_container_aware") +if player_container_aware == 1 then +game_api.start_dialogue("dialog_contaier002") +game_api.pickup_item("coursework") +game_api.setIntValue("player_has_coursework", 1) +else game_api.start_dialogue("dialog_contaier001") end +end game_api.set_darklands_callbacks( nil, diff --git a/resources/start_uni_interior.lua b/resources/start_uni_interior.lua index ae47bca..11df525 100644 --- a/resources/start_uni_interior.lua +++ b/resources/start_uni_interior.lua @@ -15,6 +15,8 @@ player_in_darklands = false player_ghost_aware = false +ghost_gone = false + function lection_hall_zone001_enter_callback() --game_api.start_dialogue("") --Start cutscene @@ -104,22 +106,56 @@ function on_npc_interact(npc_index) print("[Lua] NPC interaction! Index: " .. tostring(npc_index)) if npc_index == 1 then if (player_ghost_aware) then - game_api.start_dialogue("aiperi_dialog001") + local player_alik_aware = game_api.getIntValue("player_alik_aware") + if player_alik_aware ==1 then + game_api.start_dialogue("aiperi_dialog002") + else + game_api.start_dialogue("aiperi_dialog001") + game_api.setIntValue("player_alik_aware", 1) + end else - game_api.start_dialogue("knife_dialog001") + game_api.start_dialogue("knife_dialog001") end end if npc_index == 0 then if (player_ghost_aware) then - game_api.start_dialogue("teacher_dialog003") + --game_api.setIntValue("player_has_coursework", 1) + local player_has_coursework = game_api.getIntValue("player_has_coursework") + local player_has_report_card = game_api.getIntValue("player_has_report_card") + local report_card_signed = game_api.getIntValue("report_card_signed") + + if (report_card_signed == 1) then + game_api.start_dialogue("teacher_dialog002") + elseif (player_has_coursework == 1 and player_has_report_card==1) then + game_api.start_dialogue("teacher_dialog005") + game_api.remove_item("coursework") + game_api.setIntValue("report_card_signed", 1) + elseif (player_has_coursework == 1) then + game_api.start_dialogue("teacher_dialog004") + else + game_api.start_dialogue("teacher_dialog003") + end else - game_api.start_dialogue("teacher_dialog001") + game_api.start_dialogue("teacher_dialog001") end - --game_api.set_trigger_zone_enabled(2, false) end if npc_index == 2 then + if (player_ghost_aware) then + local report_card_signed = game_api.getIntValue("report_card_signed") + if (report_card_signed==1) then + game_api.start_dialogue("dialog_with_ghost003") + ghost_gone = true + game_api.set_npc_enabled(2, false) + game_api.set_npc_enabled(3, false) + game_api.set_npc_enabled(4, false) + game_api.set_npc_enabled(5, false) + else + game_api.start_dialogue("dialog_with_ghost002") + end + else game_api.start_dialogue("dialog_with_ghost001") player_ghost_aware = true + end end end @@ -236,7 +272,10 @@ game_api.set_cutscene_callback("test_cutscene_02", function() --game_api.set_trigger_zone_enabled(1, false) game_api.set_npc_enabled(0, false) game_api.switch_navigation(5) - game_api.rotate_object("Room_N_2_Leaf001", 90, 0.01, nil) + game_api.set_object_rotation("Room_N_2_Leaf001", 0) + game_api.set_object_rotation("Hall_Leaf001", 0) + game_api.set_object_rotation("Room_S_2_Leaf001", 0) + game_api.activate_interactive_object("Room_Cover_Corridor_001") game_api.activate_interactive_object("Room_Cover_Main_Hall_001") game_api.activate_interactive_object("Room_Cover_North_1_001") @@ -244,10 +283,10 @@ game_api.set_cutscene_callback("test_cutscene_02", function() game_api.activate_interactive_object("Room_Cover_South_1_001") game_api.activate_interactive_object("Room_Cover_South_2_001") game_api.activate_interactive_object("Room_Cover_South_3_001") - game_api.fade_object("Room_Cover_Corridor_001", 1, 0.01, nil) - game_api.fade_object("Room_Cover_South_3_001", 1, 0.01, nil) - game_api.fade_object("Room_Cover_North_1_001", 1, 0.01, nil) - game_api.fade_object("Room_Cover_Main_Hall_001", 1, 0.01, nil) + game_api.set_object_alpha("Room_Cover_Corridor_001", 1) + game_api.set_object_alpha("Room_Cover_South_3_001", 1) + game_api.set_object_alpha("Room_Cover_North_1_001", 1) + game_api.set_object_alpha("Room_Cover_Main_Hall_001", 1) game_api.activate_interactive_object("Note001") end) @@ -259,20 +298,59 @@ game_api.deactivate_interactive_object("Note001") end function on_report_card_pickup() + +if player_ghost_aware then + + local player_has_report_card = game_api.getIntValue("player_has_report_card") + local report_card_signed = game_api.getIntValue("report_card_signed") + + if (player_has_report_card == 1) then + game_api.start_dialogue("dialog_report_card003") -- Еще рано возвращать зачетку обратно в шкаф + else + game_api.start_dialogue("dialog_report_card002") -- Я пожалуй возьму зачетку + game_api.pickup_item("report_card") + game_api.deactivate_interactive_object("ReportCard001") + game_api.setIntValue("player_has_report_card", 1) + end +else game_api.start_dialogue("dialog_report_card001") end +end function on_bookshelf_teacher_clicked() -game_api.start_dialogue("dialog_report_card001") +on_report_card_pickup() end +first_time_darklands = true game_api.set_darklands_callbacks( function() - game_api.start_dialogue("ghost_dialog001") - game_api.set_npc_enabled(2, true) - game_api.set_npc_enabled(3, true) - game_api.set_npc_enabled(4, true) - game_api.set_npc_enabled(5, true) + if (first_time_darklands) then + game_api.start_dialogue("ghost_dialog001") + first_time_darklands = false + end + + game_api.set_npc_enabled(0, false) + game_api.set_npc_enabled(1, false) + + if (ghost_gone) then + game_api.set_npc_enabled(2, false) + game_api.set_npc_enabled(3, false) + game_api.set_npc_enabled(4, false) + game_api.set_npc_enabled(5, false) + else + game_api.set_npc_enabled(2, true) + game_api.set_npc_enabled(3, true) + game_api.set_npc_enabled(4, true) + game_api.set_npc_enabled(5, true) + + game_api.npc_set_hp(3, 35) + game_api.npc_set_hp(4, 35) + game_api.npc_set_hp(5, 35) + + game_api.npc_set_position(3, 0,0,-6.4) + game_api.npc_set_position(4, -5.0,0,12) + game_api.npc_set_position(5, 5.0,0,12) + end game_api.switch_navigation(6) player_in_darklands = true @@ -280,16 +358,18 @@ game_api.set_darklands_callbacks( end, function() player_in_darklands = false - game_api.start_cutscene("test_cutscene_03") - game_api.set_npc_enabled(2, false) + game_api.start_cutscene("darklands_exit001") + game_api.set_npc_enabled(0, false) + game_api.set_npc_enabled(1, false) game_api.set_npc_enabled(2, false) game_api.set_npc_enabled(3, false) game_api.set_npc_enabled(4, false) game_api.set_npc_enabled(5, false) - game_api.switch_navigation(3) + game_api.switch_navigation(0) -- todo fix game_api.setIntValue("day", 1) game_api.setIntValue("need_sleep", 1) game_api.set_player_hp(10) + setDay1MorningSetup() end ) @@ -304,20 +384,29 @@ game_api.set_trigger_zone_callbacks("book_dialog_zone001", book_dialog_zone001_exit_callback ) +function setDay0setup() game_api.deactivate_interactive_object("Room_Cover_Corridor_001") game_api.deactivate_interactive_object("Room_Cover_North_1_001") game_api.deactivate_interactive_object("Note001") - game_api.set_npc_enabled(0, false) game_api.set_npc_enabled(1, false) game_api.set_npc_enabled(2, false) game_api.set_npc_enabled(3, false) game_api.set_npc_enabled(4, false) game_api.set_npc_enabled(5, false) +end function setDay1setup() - game_api.switch_navigation(5) + game_api.set_object_alpha("Room_Cover_North_1_001", 1) + game_api.set_object_alpha("Room_Cover_North_2_001", 1) + game_api.set_object_alpha("Room_Cover_North_3_001", 1) + game_api.set_object_alpha("Room_Cover_South_1_001", 1) + game_api.set_object_alpha("Room_Cover_South_2_001", 1) + game_api.set_object_alpha("Room_Cover_South_3_001", 1) + game_api.set_object_alpha("Room_Cover_Corridor_001", 1) + game_api.set_object_alpha("Room_Cover_Main_Hall_001", 1) + game_api.deactivate_interactive_object("Room_Cover_Corridor_001") game_api.deactivate_interactive_object("Room_Cover_Main_Hall_001") game_api.deactivate_interactive_object("Room_Cover_North_1_001") @@ -326,6 +415,15 @@ function setDay1setup() game_api.activate_interactive_object("Room_Cover_South_1_001") game_api.activate_interactive_object("Room_Cover_South_2_001") game_api.deactivate_interactive_object("Room_Cover_South_3_001") + + game_api.set_object_rotation("Room_N_0_Leaf001", 0) + game_api.set_object_rotation("Room_N_1_Leaf001", 0) + game_api.set_object_rotation("Room_N_2_Leaf001", -90) + game_api.set_object_rotation("Room_S_0_Leaf001", 0) + game_api.set_object_rotation("Room_S_1_Leaf001", 0) + game_api.set_object_rotation("Room_S_2_Leaf001", 90) + game_api.set_object_rotation("Hall_Leaf001", 90) + game_api.set_npc_enabled(0, true) game_api.set_npc_enabled(1, true) game_api.set_npc_enabled(2, false) @@ -334,19 +432,61 @@ function setDay1setup() game_api.set_npc_enabled(5, false) end +function setDay1MorningSetup() +game_api.deactivate_interactive_object("Room_Cover_North_1_001") +game_api.activate_interactive_object("Room_Cover_North_2_001") +game_api.activate_interactive_object("Room_Cover_North_3_001") +game_api.activate_interactive_object("Room_Cover_South_1_001") +game_api.activate_interactive_object("Room_Cover_South_2_001") +game_api.activate_interactive_object("Room_Cover_South_3_001") +game_api.deactivate_interactive_object("Room_Cover_Corridor_001") +game_api.activate_interactive_object("Room_Cover_Main_Hall_001") + + game_api.set_object_rotation("Room_N_0_Leaf001", 0) + game_api.set_object_rotation("Room_N_1_Leaf001", 0) + game_api.set_object_rotation("Room_N_2_Leaf001", 0) + game_api.set_object_rotation("Room_S_0_Leaf001", 0) + game_api.set_object_rotation("Room_S_1_Leaf001", 0) + game_api.set_object_rotation("Room_S_2_Leaf001", 0) + game_api.set_object_rotation("Hall_Leaf001", 0) + + + game_api.set_object_alpha("Room_Cover_North_1_001", 1) + game_api.set_object_alpha("Room_Cover_North_2_001", 1) + game_api.set_object_alpha("Room_Cover_North_3_001", 1) + game_api.set_object_alpha("Room_Cover_South_1_001", 1) + game_api.set_object_alpha("Room_Cover_South_2_001", 1) + game_api.set_object_alpha("Room_Cover_South_3_001", 1) + game_api.set_object_alpha("Room_Cover_Corridor_001", 1) + game_api.set_object_alpha("Room_Cover_Main_Hall_001", 1) + +game_api.set_npc_enabled(0, false) +game_api.set_npc_enabled(1, false) +game_api.set_npc_enabled(2, false) +game_api.set_npc_enabled(3, false) +game_api.set_npc_enabled(4, false) +game_api.set_npc_enabled(5, false) +end game_api.set_location_callbacks( function() print("Enter location uni interior") local hp = game_api.getFloatValue("player_hp") game_api.set_player_hp(hp) ---[[ + local need_sleep = game_api.getIntValue("need_sleep") local day = game_api.getIntValue("day") - if (day==1) then + if (day>0) and (need_sleep==1) then + setDay1MorningSetup() + game_api.switch_navigation(0) + elseif (day>0) then setDay1setup() - end]] + game_api.switch_navigation(5) + else + setDay0setup() + game_api.switch_navigation(0) + end end, function() print("Exit location uni interior") diff --git a/src/Character.cpp b/src/Character.cpp index b963c51..75e11cd 100644 --- a/src/Character.cpp +++ b/src/Character.cpp @@ -7,6 +7,7 @@ #include "GameConstants.h" #include "Environment.h" + namespace ZL { const float ATTACK_COOLDOWN_TIME = 1.6f; diff --git a/src/Game.cpp b/src/Game.cpp index 879ec2a..5ed4e21 100644 --- a/src/Game.cpp +++ b/src/Game.cpp @@ -188,7 +188,6 @@ namespace ZL ItemRegistry::instance().loadFromJson("resources/config2/items.json", CONST_ZIP_FILE); - globalFloats["player_hp"] = 200; LocationSetup uniInteriorParams; diff --git a/src/Location.cpp b/src/Location.cpp index d705cd9..9e84153 100644 --- a/src/Location.cpp +++ b/src/Location.cpp @@ -78,7 +78,6 @@ namespace ZL player->loadBinaryAnimation(AnimationState::DEATH_IDLE, "resources/w/gg/new/gg_die_idle001.anim", CONST_ZIP_FILE); - player->weaponTexture = renderer.textureManager.LoadFromPng("resources/w/white.png", CONST_ZIP_FILE); player->weaponMesh.data = LoadFromTextFile02("resources/w/gg/knife002.txt", CONST_ZIP_FILE); player->weaponMesh.data.Scale(0.1f); diff --git a/src/ScriptEngine.cpp b/src/ScriptEngine.cpp index 5f8bee8..15223e4 100644 --- a/src/ScriptEngine.cpp +++ b/src/ScriptEngine.cpp @@ -101,6 +101,28 @@ namespace ZL { std::cerr << "[script] activate_interactive_object: not found: " << objectName << std::endl; }); + api.set_function("set_object_rotation", [game](const std::string& objectName, float value) { + for (auto& intObj : game->interactiveObjects) { + if (intObj.loadedObject.name == objectName) { + intObj.rotationY = value; + std::cout << "[script] set_object_rotation: " << objectName << " " << value << std::endl; + return; + } + } + std::cerr << "[script] set_object_rotation: not found: " << objectName << std::endl; + }); + + api.set_function("set_object_alpha", [game](const std::string& objectName, float value) { + for (auto& intObj : game->interactiveObjects) { + if (intObj.loadedObject.name == objectName) { + intObj.alpha = value; + std::cout << "[script] set_object_alpha: " <getCount(); @@ -209,7 +231,14 @@ namespace ZL { api.set_function("set_player_hp", [game](float value) { if (game->player) + { game->player->hp = value; + if (game->player->currentState == AnimationState::ACTION_TO_DEATH || game->player->currentState == AnimationState::DEATH_IDLE) + { + game->player->currentState = AnimationState::STAND; + game->player->resetAnim = true; + } + } }); // get_player_hp() → float (0 if no player) api.set_function("get_player_hp", @@ -254,6 +283,42 @@ namespace ZL { }); + // npc_set_hp(index, value) — sets an NPC's current HP directly. + api.set_function("npc_set_hp", + [game](int index, float value) { + auto& npcs = game->npcs; + if (index < 0 || index >= static_cast(npcs.size())) { + std::cerr << "[script] npc_set_hp: index " << index << " out of range\n"; + return; + } + npcs[index]->hp = value; + }); + + // npc_set_position(index, x, y, z) — teleports an NPC instantly, no walking. + api.set_function("npc_set_position", + [game](int index, float x, float y, float z) { + auto& npcs = game->npcs; + if (index < 0 || index >= static_cast(npcs.size())) { + std::cerr << "[script] npc_set_position: index " << index << " out of range\n"; + return; + } + Eigen::Vector3f pos(x, y, z); + npcs[index]->position = pos; + npcs[index]->setTarget(pos); + }); + + // npc_set_rotation(index, angle) — sets NPC facing angle around Y axis (radians). + api.set_function("npc_set_rotation", + [game](int index, float angle) { + auto& npcs = game->npcs; + if (index < 0 || index >= static_cast(npcs.size())) { + std::cerr << "[script] npc_set_rotation: index " << index << " out of range\n"; + return; + } + npcs[index]->facingAngle = angle; + npcs[index]->targetFacingAngle = angle; + }); + // set_npc_enabled(index, enabled) api.set_function("set_npc_enabled", [game](int index, bool value) { @@ -263,6 +328,14 @@ namespace ZL { return; } npcs[index]->enabled = value; + npcs[index]->attack = 0; + npcs[index]->attack_cooldown = 0; + npcs[index]->currentState = AnimationState::STAND; + if (npcs[index]->canAttack) + { + npcs[index]->attackTarget = game->player.get(); + } + npcs[index]->battle_state = 0; }); // move_object(name, x, y, z, duration_sec [, on_complete]) diff --git a/src/items/InteractiveObject.cpp b/src/items/InteractiveObject.cpp index b30cef7..4068a3d 100644 --- a/src/items/InteractiveObject.cpp +++ b/src/items/InteractiveObject.cpp @@ -107,7 +107,10 @@ namespace ZL { // Snap to exact target position = task.targetPos; rotationY = task.targetRotY; - scale = task.targetScale; + if (task.type == AnimTask::Type::Fade) + alpha = task.targetScale; // targetScale reused to hold targetAlpha for Fade + else + scale = task.targetScale; std::function cb = std::move(task.onComplete); animTask.reset();