From 80d0bda206028c1dea3f72d8b5bd53a2a362f7ea Mon Sep 17 00:00:00 2001 From: Clownacy Date: Sat, 9 Feb 2019 01:52:36 +0000 Subject: [PATCH 1/4] Fixed Japanese build --- Makefile | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/Makefile b/Makefile index 87c4b2bc..d382e707 100644 --- a/Makefile +++ b/Makefile @@ -1,21 +1,23 @@ ifeq ($(RELEASE), 1) CXXFLAGS := -O3 -s -FILENAME ?= release +FILENAME_DEF = release else CXXFLAGS := -O0 -g -FILENAME ?= debug +FILENAME_DEF = debug endif ifeq ($(JAPANESE), 1) CXXFLAGS += -DJAPANESE LIBS += -liconv ifeq ($(RELEASE), 1) - FILENAME ?= releasejp + FILENAME_DEF = releasejp else - FILENAME ?= debugjp + FILENAME_DEF = debugjp endif endif +FILENAME ?= FILENAME_DEF + ifeq ($(FIX_BUGS), 1) CXXFLAGS += -DFIX_BUGS endif From 5719c5aabdbbb06874a86d22f5d59b29da7b948f Mon Sep 17 00:00:00 2001 From: Clownacy Date: Sat, 9 Feb 2019 13:35:39 +0000 Subject: [PATCH 2/4] Fixed Makefile Derp --- Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile b/Makefile index d382e707..c00d707d 100644 --- a/Makefile +++ b/Makefile @@ -16,7 +16,7 @@ LIBS += -liconv endif endif -FILENAME ?= FILENAME_DEF +FILENAME ?= $(FILENAME_DEF) ifeq ($(FIX_BUGS), 1) CXXFLAGS += -DFIX_BUGS From 3934705d3fbe521921f95a898769f8038e392d19 Mon Sep 17 00:00:00 2001 From: Clownacy Date: Sat, 9 Feb 2019 13:44:19 +0000 Subject: [PATCH 3/4] More NPCs --- src/NpcAct.h | 19 +- src/NpcAct260.cpp | 102 ++++ src/NpcAct280.cpp | 1433 +++++++++++++++++++++++++++++++++++++++++++++ src/NpcAct300.cpp | 67 +++ src/NpcTbl.cpp | 32 +- 5 files changed, 1634 insertions(+), 19 deletions(-) diff --git a/src/NpcAct.h b/src/NpcAct.h index 0729d1e9..47c15459 100644 --- a/src/NpcAct.h +++ b/src/NpcAct.h @@ -281,16 +281,29 @@ void ActNpc275(NPCHAR *npc); void ActNpc276(NPCHAR *npc); void ActNpc277(NPCHAR *npc); void ActNpc278(NPCHAR *npc); - +void ActNpc279(NPCHAR *npc); +void ActNpc280(NPCHAR *npc); +void ActNpc281(NPCHAR *npc); +void ActNpc282(NPCHAR *npc); +void ActNpc283(NPCHAR *npc); +void ActNpc284(NPCHAR *npc); +void ActNpc285(NPCHAR *npc); +void ActNpc286(NPCHAR *npc); +void ActNpc287(NPCHAR *npc); +void ActNpc288(NPCHAR *npc); +void ActNpc289(NPCHAR *npc); +void ActNpc290(NPCHAR *npc); +void ActNpc291(NPCHAR *npc); void ActNpc292(NPCHAR *npc); - +void ActNpc293(NPCHAR *npc); +void ActNpc294(NPCHAR *npc); void ActNpc295(NPCHAR *npc); void ActNpc296(NPCHAR *npc); void ActNpc297(NPCHAR *npc); void ActNpc298(NPCHAR *npc); void ActNpc299(NPCHAR *npc); void ActNpc300(NPCHAR *npc); - +void ActNpc301(NPCHAR *npc); void ActNpc302(NPCHAR *npc); void ActNpc303(NPCHAR *npc); void ActNpc304(NPCHAR *npc); diff --git a/src/NpcAct260.cpp b/src/NpcAct260.cpp index 9c3f4afa..cf84aa58 100644 --- a/src/NpcAct260.cpp +++ b/src/NpcAct260.cpp @@ -2101,3 +2101,105 @@ void ActNpc278(NPCHAR *npc) break; } } + +//Falling block (large) +void ActNpc279(NPCHAR *npc) +{ + RECT rc[2]; + + rc[0] = {0, 16, 32, 48}; + rc[1] = {16, 0, 32, 16}; + + switch (npc->act_no) + { + case 0: + switch (npc->direct) + { + case 0: + npc->act_no = 100; + npc->bits |= 4; + npc->ani_no = 0; + break; + case 1: + npc->ani_no = 0; + npc->act_no = 10; + break; + case 2: + npc->act_no = 100; + npc->bits |= 4; + npc->ani_no = 1; + npc->view.back = 0x1000; + npc->view.front = 0x1000; + npc->view.top = 0x1000; + npc->view.bottom = 0x1000; + npc->hit.back = 0x1000; + npc->hit.front = 0x1000; + npc->hit.top = 0x1000; + npc->hit.bottom = 0x1000; + break; + } + + if (npc->direct != 1) + break; + // Fallthrough + case 10: + npc->act_no = 11; + npc->act_wait = 16; + // Fallthrough + case 11: + npc->act_wait -= 2; + + if (npc->act_wait <= 0) + { + npc->act_no = 100; + npc->bits |= 4; + } + + break; + + case 100: + npc->ym += 0x40; + if (npc->ym > 0x700) + npc->ym = 0x700; + + if (npc->y > 0x10000) + npc->bits &= ~8; + + if (npc->flag & 8) + { + npc->ym = -0x200; + npc->act_no = 110; + npc->bits |= 8; + PlaySoundObject(26, 1); + SetQuake(10); + + for (int i = 0; i < 4; ++i) + SetNpChar(4, npc->x + (Random(-12, 12) * 0x200), npc->y + 0x2000, Random(-341, 341), Random(-0x600, 0), 0, 0, 0x100); + } + + break; + + case 110: + npc->ym += 0x40; + + if (npc->y > (gMap.length + 2) * 0x2000) + npc->cond = 0; + + break; + } + + if (gMC.y > npc->y) + npc->damage = 10; + else + npc->damage = 0; + + npc->y += npc->ym; + npc->rect = rc[npc->ani_no]; + + if (npc->act_no == 11) + { + npc->rect.top += npc->act_wait; + npc->rect.bottom -= npc->act_wait; + npc->view.top = (16 - npc->act_wait) * 0x200; + } +} diff --git a/src/NpcAct280.cpp b/src/NpcAct280.cpp index b64d9763..1ce3747f 100644 --- a/src/NpcAct280.cpp +++ b/src/NpcAct280.cpp @@ -9,6 +9,1351 @@ #include "Back.h" #include "Triangle.h" #include "Frame.h" +#include "Map.h" +#include "Boss.h" + +//Sue (being teleported by Misery) +void ActNpc280(NPCHAR *npc) +{ + RECT rcLeft[2]; + RECT rcRight[2]; + + rcLeft[0] = {112, 32, 128, 48}; + rcLeft[1] = {144, 32, 160, 48}; + + rcRight[0] = {112, 48, 128, 64}; + rcRight[1] = {144, 48, 160, 64}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->ani_no = 0; + npc->ani_wait = 0; + npc->x += 0xC00; + npc->tgt_x = npc->x; + PlaySoundObject(29, 1); + // Fallthrough + case 1: + if (++npc->act_wait == 64) + { + npc->act_no = 2; + npc->act_wait = 0; + } + + break; + + case 2: + npc->ani_no = 0; + + if (npc->flag & 8) + { + npc->act_no = 4; + npc->act_wait = 0; + npc->ani_no = 1; + PlaySoundObject(23, 1); + } + + break; + } + + if (npc->act_no > 1) + { + npc->ym += 0x20; + if (npc->ym > 0x5FF) + npc->ym = 0x5FF; + + npc->y += npc->ym; + } + + if (npc->direct == 0) + npc->rect = rcLeft[npc->ani_no]; + else + npc->rect = rcRight[npc->ani_no]; + + if (npc->act_no == 1) + { + npc->rect.bottom = npc->rect.top + npc->act_wait / 4; + + if (npc->act_wait / 2 & 1) + npc->x = npc->tgt_x; + else + npc->x = npc->tgt_x + 0x200; + } +} + +//Doctor (red energy form) +void ActNpc281(NPCHAR *npc) +{ + RECT rc = {0, 0, 0, 0}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + break; + + case 10: + npc->act_no = 11; + npc->act_wait = 0; + // Fallthrough + case 11: + ++npc->act_wait; + + SetNpChar(270, npc->x, npc->y + 0x10000, 0, 0, 2, npc, 0x100); + + if (npc->act_wait > 150) + npc->act_no = 12; + + break; + + case 20: + npc->act_no = 21; + npc->act_wait = 0; + // Fallthrough + case 21: + if (++npc->act_wait > 250) + { + DeleteNpCharCode(270, 0); + npc->act_no = 22; + } + + break; + } + + npc->rect = rc; +} + +//Mini Undead Core (active) +void ActNpc282(NPCHAR *npc) +{ + RECT tc[3]; + + tc[0] = {256, 80, 320, 120}; + tc[1] = {256, 0, 320, 40}; + tc[2] = {256, 120, 320, 160}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 20; + npc->tgt_y = npc->y; + + if (Random(0, 100) & 1) + npc->ym = -0x100; + else + npc->ym = 0x100; + // Fallthrough + case 20: + npc->xm = -0x200; + + if (npc->x < -0x8000) + npc->cond = 0; + + if (npc->tgt_y < npc->y) + npc->ym -= 0x10; + if (npc->tgt_y > npc->y) + npc->ym += 0x10; + + if (npc->ym > 0x100) + npc->ym = 0x100; + if (npc->ym < -0x100) + npc->ym = -0x100; + + if (gMC.flag & 8 && gMC.y < npc->y - 0x800 && gMC.x > npc->x - 0x3000 && gMC.x < npc->x + 0x3000) + { + npc->tgt_y = 0x12000; + npc->ani_no = 2; + } + else if (npc->ani_no != 1) + { + npc->ani_no = 0; + } + + if (gMC.flag & 1 && gMC.x < npc->x - npc->hit.back && gMC.x > npc->x - npc->hit.back - 0x1000 && gMC.hit.bottom + gMC.y > npc->y - npc->hit.top && gMC.y - gMC.hit.top < npc->hit.bottom + npc->y) + { + npc->bits &= ~0x40; + npc->ani_no = 1; + } + else if (gMC.flag & 4 && gMC.x > npc->hit.back + npc->x && gMC.x < npc->x + npc->hit.back + 0x1000 && gMC.hit.bottom + gMC.y > npc->y - npc->hit.top && gMC.y - gMC.hit.top < npc->hit.bottom + npc->y) + { + npc->bits &= ~0x40; + npc->ani_no = 1; + } + else if (gMC.flag & 2 && gMC.y < npc->y - npc->hit.top && gMC.y > npc->y - npc->hit.top - 0x1000 && gMC.hit.front + gMC.x > npc->x - npc->hit.back && gMC.x - gMC.hit.back < npc->hit.front + npc->x) + { + npc->bits &= ~0x40; + npc->ani_no = 1; + } + else if (gMC.flag & 8 && gMC.y > npc->y + npc->hit.bottom - 0x800 && gMC.y < npc->y + npc->hit.bottom + 0x1800 && gMC.hit.front + gMC.x > npc->x - npc->hit.back - 0x800 && gMC.x - gMC.hit.back < npc->x + npc->hit.front + 0x800) + { + npc->bits &= ~0x40; + npc->ani_no = 1; + } + } + + npc->x += npc->xm; + npc->y += npc->ym; + + npc->rect = tc[npc->ani_no]; +} + +//Misery (transformed) +void ActNpc283(NPCHAR *npc) +{ + RECT rcLeft[11]; + RECT rcRight[11]; + + rcLeft[0] = {0, 64, 32, 96}; + rcLeft[1] = {32, 64, 64, 96}; + rcLeft[2] = {64, 64, 96, 96}; + rcLeft[3] = {96, 64, 128, 96}; + rcLeft[4] = {128, 64, 160, 96}; + rcLeft[5] = {160, 64, 192, 96}; + rcLeft[6] = {192, 64, 224, 96}; + rcLeft[7] = {224, 64, 256, 96}; + rcLeft[8] = {0, 0, 0, 0}; + rcLeft[9] = {256, 64, 288, 96}; + rcLeft[10] = {288, 64, 320, 96}; + + rcRight[0] = {0, 96, 32, 128}; + rcRight[1] = {32, 96, 64, 128}; + rcRight[2] = {64, 96, 96, 128}; + rcRight[3] = {96, 96, 128, 128}; + rcRight[4] = {128, 96, 160, 128}; + rcRight[5] = {160, 96, 192, 128}; + rcRight[6] = {192, 96, 224, 128}; + rcRight[7] = {224, 96, 256, 128}; + rcRight[8] = {0, 0, 0, 0}; + rcRight[9] = {256, 96, 288, 128}; + rcRight[10] = {288, 96, 320, 128}; + + if (npc->act_no < 100 && (gBoss[0].cond == 0 || npc->life < 400)) + npc->act_no = 100; + + int x; + int y; + int direct; + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->y -= 0x1000; + PlaySoundObject(29, 1); + // Fallthrough + case 1: + if (++npc->act_wait / 2 & 1) + npc->ani_no = 9; + else + npc->ani_no = 0; + + break; + + case 10: + npc->act_no = 11; + npc->ani_no = 9; + break; + + case 20: + gSuperXpos = 0; + npc->act_no = 21; + npc->act_wait = 0; + npc->ani_no = 0; + npc->ani_wait = 0; + // Fallthrough + case 21: + npc->xm = 7 * npc->xm / 8; + npc->ym = 7 * npc->ym / 8; + + if (++npc->ani_wait > 20) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 1) + npc->ani_no = 0; + + if (++npc->act_wait > 100) + npc->act_no = 30; + + if (gMC.x > npc->x) + npc->direct = 2; + else + npc->direct = 0; + + break; + + case 30: + npc->act_no = 31; + npc->act_wait = 0; + npc->ani_no = 2; + npc->count2 = npc->life; + // Fallthrough + case 31: + if (++npc->ani_wait > 1) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 3) + npc->ani_no = 2; + + if (npc->flag & 8) + npc->ym = -0x200; + + if (gBoss[0].x < npc->x) + npc->xm -= 0x20; + else + npc->xm += 0x20; + + if (gMC.y < npc->y) + npc->ym -= 0x10; + else + npc->ym += 0x10; + + if (npc->xm > 0x200) + npc->xm = 0x200; + if (npc->xm < -0x200) + npc->xm = -0x200; + + if (npc->ym > 0x200) + npc->ym = 0x200; + if (npc->ym < -0x200) + npc->ym = -0x200; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + + if (++npc->act_wait > 150 && (npc->life < npc->count2 - 20 || gSuperXpos)) + { + gSuperXpos = 0; + npc->act_no = 40; + } + + if (gBoss[0].ani_no && npc->act_wait > 250) + npc->act_no = 50; + + break; + + case 40: + npc->act_no = 41; + npc->act_wait = 0; + npc->xm = 0; + npc->ym = 0; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + + PlaySoundObject(103, 1); + + if (gMC.y < 0x14000) + npc->count2 = 290; + else + npc->count2 = 289; + // Fallthrough + case 41: + if (++npc->act_wait / 2 & 1) + npc->ani_no = 4; + else + npc->ani_no = 5; + + if (npc->act_wait % 6 == 1) + { + if ( npc->count2 == 289 ) + { + x = npc->x + (Random(-0x40, 0x40) * 0x200); + y = npc->y + (Random(-0x20, 0x20) * 0x200); + } + else + { + x = npc->x + (Random(-0x20, 0x20) * 0x200); + y = npc->y + (Random(-0x40, 0x40) * 0x200); + } + + if (x < 0x4000) + x = 0x4000; + if (x > (gMap.width - 2) * 0x2000) + x = (gMap.width - 2) * 0x2000; + + if (y < 0x4000) + y = 0x4000; + if (y > (gMap.length - 2) * 0x2000) + y = (gMap.length - 2) * 0x2000; + + PlaySoundObject(39, 1); + SetNpChar(npc->count2, x, y, 0, 0, 0, 0, 0x100); + } + + if (npc->act_wait > 50) + { + npc->act_no = 42; + npc->act_wait = 0; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + } + + break; + + case 42: + ++npc->act_wait; + npc->ani_no = 6; + + if (npc->act_wait > 50) + { + npc->ym = -0x200; + + if (npc->direct == 0) + npc->xm = 0x200; + else + npc->xm = -0x200; + + npc->act_no = 30; + } + + break; + + case 50: + npc->act_no = 51; + npc->act_wait = 0; + npc->xm = 0; + npc->ym = 0; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + + PlaySoundObject(103, 1); + // Fallthrough + case 51: + if (++npc->act_wait / 2 & 1) + npc->ani_no = 4; + else + npc->ani_no = 5; + + if (gMC.equip & 0x20) + { + if (npc->act_wait % 10 == 1) + { + if (npc->direct == 0) + { + x = npc->x + 0x1400; + y = npc->y; + + switch (npc->act_wait / 6 % 4) + { + case 0: + direct = 0xD8; + break; + case 1: + direct = 0xEC; + break; + case 2: + direct = 0x14; + break; + case 3: + direct = 0x28; + break; + } + } + else + { + x = npc->x - 0x1400; + y = npc->y; + + switch (npc->act_wait / 6 % 4) + { + case 0: + direct = 0x58; + break; + case 1: + direct = 0x6C; + break; + case 2: + direct = 0x94; + break; + case 3: + direct = 0xA8; + break; + } + } + + PlaySoundObject(39, 1); + SetNpChar(301, x, y, 0, 0, direct, 0, 0x100); + } + } + else if (npc->act_wait % 24 == 1) + { + if (npc->direct == 0) + { + x = npc->x + 0x1400; + y = npc->y; + + switch (npc->act_wait / 6 % 4) + { + case 0: + direct = 0xD8; + break; + case 1: + direct = 0xEC; + break; + case 2: + direct = 0x14; + break; + case 3: + direct = 0x28; + break; + } + } + else + { + x = npc->x - 0x1400; + y = npc->y; + + switch (npc->act_wait / 6 % 4) + { + case 0: + direct = 0x58; + break; + case 1: + direct = 0x6C; + break; + case 2: + direct = 0x94; + break; + case 3: + direct = 0xA8; + break; + } + } + + PlaySoundObject(39, 1); + SetNpChar(301, x, y, 0, 0, direct, 0, 0x100); + } + + if (npc->act_wait > 50) + { + npc->act_no = 42; + npc->act_wait = 0; + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + } + + break; + + case 99: + npc->xm = 0; + npc->ym = 0; + npc->ani_no = 9; + npc->bits &= ~0x20; + break; + + case 100: + npc->act_no = 101; + npc->ani_no = 9; + npc->damage = 0; + npc->bits &= ~0x20; + npc->bits |= 8; + npc->ym = -0x200; + npc->shock += 50; + npc->hit.bottom = 0x1800; + ++gBoss[0].ani_no; + // Fallthrough + case 101: + npc->ym += 0x20; + + if (npc->y > 0x1B000 - npc->hit.bottom) + { + npc->y = 0x1B000 - npc->hit.bottom; + npc->act_no = 102; + npc->ani_no = 10; + npc->xm = 0; + npc->ym = 0; + } + + break; + } + + npc->y += npc->ym; + + if (npc->shock) + npc->x += npc->xm / 2; + else + npc->x += npc->xm; + + if (npc->direct == 0) + npc->rect = rcLeft[npc->ani_no]; + else + npc->rect = rcRight[npc->ani_no]; +} + +//Sue (transformed) +void ActNpc284(NPCHAR *npc) +{ + RECT rcLeft[13]; + RECT rcRight[13]; + + rcLeft[0] = {0, 128, 32, 160}; + rcLeft[1] = {32, 128, 64, 160}; + rcLeft[2] = {64, 128, 96, 160}; + rcLeft[3] = {96, 128, 128, 160}; + rcLeft[4] = {128, 128, 160, 160}; + rcLeft[5] = {160, 128, 192, 160}; + rcLeft[6] = {192, 128, 224, 160}; + rcLeft[7] = {224, 128, 256, 160}; + rcLeft[8] = {0, 0, 0, 0}; + rcLeft[9] = {256, 128, 288, 160}; + rcLeft[10] = {288, 128, 320, 160}; + rcLeft[11] = {224, 64, 256, 96}; + rcLeft[12] = {208, 32, 224, 48}; + + rcRight[0] = {0, 160, 32, 192}; + rcRight[1] = {32, 160, 64, 192}; + rcRight[2] = {64, 160, 96, 192}; + rcRight[3] = {96, 160, 128, 192}; + rcRight[4] = {128, 160, 160, 192}; + rcRight[5] = {160, 160, 192, 192}; + rcRight[6] = {192, 160, 224, 192}; + rcRight[7] = {224, 160, 256, 192}; + rcRight[8] = {0, 0, 0, 0}; + rcRight[9] = {256, 160, 288, 192}; + rcRight[10] = {288, 160, 320, 192}; + rcRight[11] = {224, 96, 256, 128}; + rcRight[12] = {208, 48, 224, 64}; + + if (npc->act_no < 100 && (gBoss[0].cond == 0|| npc->life < 500)) + npc->act_no = 100; + + unsigned char deg; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->y -= 0x800; + PlaySoundObject(29, 1); + npc->count2 = npc->life; + // Fallthrough + case 1: + if (++npc->act_wait / 2 & 1) + { + npc->view.top = 0x2000; + npc->view.back = 0x2000; + npc->view.front = 0x2000; + npc->ani_no = 11; + } + else + { + npc->view.top = 0x600; + npc->view.back = 0x1000; + npc->view.front = 0x1000; + npc->ani_no = 12; + } + + if (npc->act_wait > 50) + npc->act_no = 10; + + break; + + case 10: + npc->act_no = 11; + npc->ani_no = 11; + npc->view.top = 0x2000; + npc->view.back = 0x2000; + npc->view.front = 0x2000; + DeleteNpCharCode(257, 1); + break; + + case 20: + npc->act_no = 21; + npc->act_wait = 0; + npc->ani_no = 0; + npc->ani_wait = 0; + npc->damage = 0; + npc->bits |= 0x20; + npc->bits &= ~8; + // Fallthrough + case 21: + npc->xm = 7 * npc->xm / 8; + npc->ym = 7 * npc->ym / 8; + + if (++npc->ani_wait > 20) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 1) + npc->ani_no = 0; + + if (++npc->act_wait > 80) + npc->act_no = 30; + + if (gMC.x > npc->x) + npc->direct = 2; + else + npc->direct = 0; + + if (npc->life < npc->count2 - 50) + { + npc->count2 = npc->life; + gSuperXpos = 10; + } + + break; + + case 30: + npc->act_no = 31; + npc->act_wait = 0; + npc->ani_no = 2; + npc->xm = 0; + npc->ym = 0; + // Fallthrough + case 31: + if (++npc->act_wait > 16) + { + ++npc->count1; + npc->count1 %= 4; + + switch (npc->count1) + { + case 1: + case 3: + npc->act_no = 34; + break; + case 0: + npc->act_no = 32; + break; + case 2: + npc->act_no = 32; + break; + } + } + + break; + + case 32: + npc->act_no = 33; + npc->act_wait = 0; + npc->bits &= ~0x20; + + if (gMC.x < npc->x) + npc->tgt_x = gMC.x - 0x14000; + else + npc->tgt_x = gMC.x + 0x14000; + + npc->tgt_y = gMC.y; + + deg = GetArktan(npc->x - npc->tgt_x, npc->y - npc->tgt_y); + npc->xm = 3 * GetCos(deg); + npc->ym = 3 * GetSin(deg); + npc->bits &= ~8; + + if (npc->x < (gMap.width * 0x2000) / 2 && npc->xm > 0) + { + if (npc->y < (gMap.length * 0x2000) / 2 && npc->ym > 0) + npc->bits |= 8; + if (npc->y > (gMap.length * 0x2000) / 2 && npc->ym < 0) + npc->bits |= 8; + } + if (npc->x > (gMap.width * 0x2000) / 2 && npc->xm < 0) + { + if (npc->y < (gMap.length * 0x2000) / 2 && npc->ym > 0) + npc->bits |= 8; + if (npc->y > (gMap.length * 0x2000) / 2 && npc->ym < 0) + npc->bits |= 8; + } + + if (npc->xm > 0) + npc->direct = 2; + else + npc->direct = 0; + // Fallthrough + case 33: + if (++npc->act_wait / 2 & 1) + npc->ani_no = 3; + else + npc->ani_no = 8; + + if (npc->act_wait > 50 || npc->flag & 5) + npc->act_no = 20; + + break; + + case 34: + npc->act_no = 35; + npc->act_wait = 0; + npc->damage = 4; + + npc->tgt_x = gMC.x; + npc->tgt_y = gMC.y; + + deg = GetArktan(npc->x - npc->tgt_x, npc->y - npc->tgt_y); + npc->ym = 3 * GetSin(deg); + npc->xm = 3 * GetCos(deg); + npc->bits &= ~8; + + if (npc->x < (gMap.width * 0x2000) / 2 && npc->xm > 0) + { + if (npc->y < (gMap.length * 0x2000) / 2 && npc->ym > 0) + npc->bits |= 8; + if (npc->y > (gMap.length * 0x2000) / 2 && npc->ym < 0) + npc->bits |= 8; + } + + if (npc->x > (gMap.width * 0x2000) / 2 && npc->xm < 0) + { + if (npc->y < (gMap.length * 0x2000) / 2 && npc->ym > 0) + npc->bits |= 8; + if (npc->y > (gMap.length * 0x2000) / 2 && npc->ym < 0) + npc->bits |= 8; + } + + if (npc->xm > 0) + npc->direct = 2; + else + npc->direct = 0; + // Fallthrough + case 35: + if (++npc->act_wait > 20 && npc->shock) + { + npc->act_no = 40; + } + else if (npc->act_wait > 50 || npc->flag & 5) + { + npc->act_no = 20; + } + + if (++npc->ani_wait > 1) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 7) + npc->ani_no = 4; + + if (npc->act_wait % 5 == 1) + PlaySoundObject(109, 1); + + break; + + case 40: + npc->act_no = 41; + npc->act_wait = 0; + npc->ani_no = 2; + npc->damage = 0; + npc->bits &= ~8; + // Fallthrough + case 41: + npc->xm = 7 * npc->xm / 8; + npc->ym = 7 * npc->ym / 8; + + if (++npc->act_wait > 6) + { + npc->act_no = 42; + npc->act_wait = 0; + npc->ym = -0x200; + + if (npc->direct == 0) + npc->xm = 0x200; + else + npc->xm = -0x200; + } + + break; + + case 42: + npc->ani_no = 9; + + if (npc->flag & 8) + { + npc->act_no = 43; + npc->act_wait = 0; + npc->ani_no = 2; + + if (gMC.x > npc->x) + npc->direct = 2; + else + npc->direct = 0; + } + + npc->ym += 0x20; + if (npc->ym > 0x5FF) + npc->ym = 0x5FF; + + break; + + case 43: + if (++npc->act_wait > 16) + npc->act_no = 20; + + break; + + case 99: + npc->xm = 0; + npc->ym = 0; + npc->ani_no = 9; + npc->bits &= ~0x20; + break; + + case 100: + npc->act_no = 101; + npc->ani_no = 9; + npc->damage = 0; + npc->bits &= ~0x20; + npc->bits |= 8; + npc->ym = -0x200; + npc->shock += 50; + ++gBoss[0].ani_no; + // Fallthrough + case 101: + npc->ym += 0x20; + + if (npc->y > 0x1B000 - npc->hit.bottom) + { + npc->y = 0x1B000 - npc->hit.bottom; + npc->act_no = 102; + npc->ani_no = 10; + npc->xm = 0; + npc->ym = 0; + } + + break; + } + + npc->y += npc->ym; + + if (npc->shock) + npc->x += npc->xm / 2; + else + npc->x += npc->xm; + + if (npc->direct == 0) + npc->rect = rcLeft[npc->ani_no]; + else + npc->rect = rcRight[npc->ani_no]; +} + +//Undead Core spiral projectile +void ActNpc285(NPCHAR *npc) +{ + RECT rc = {232, 104, 248, 120}; + + if (npc->x < 0 || npc->x > gMap.width * 0x2000) + { + VanishNpChar(npc); + return; + } + + unsigned char deg; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->tgt_x = npc->x; + npc->tgt_y = npc->y; + npc->count1 = npc->direct / 8; + npc->direct &= 7; + // Fallthrough + case 1: + npc->count1 += 24; + npc->count1 &= 0xFF; + + deg = npc->count1; + + if (npc->act_wait < 128) + ++npc->act_wait; + + if (npc->direct == 0) + npc->xm -= 21; + else + npc->xm += 21; + + npc->tgt_x += npc->xm; + + npc->x = npc->tgt_x + 4 * GetCos(deg); + npc->y = npc->tgt_y + 6 * GetSin(deg); + + SetNpChar(286, npc->x, npc->y, 0, 0, 0, 0, 0x100); + } + + npc->rect = rc; +} + +//Undead Core spiral shot trail +void ActNpc286(NPCHAR *npc) +{ + RECT rc[3]; + + rc[0] = {232, 120, 248, 136}; + rc[1] = {232, 136, 248, 152}; + rc[2] = {232, 152, 248, 168}; + + if (++npc->ani_wait > 0) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 2) + npc->cond = 0; + else + npc->rect = rc[npc->ani_no]; +} + +//Orange smoke +void ActNpc287(NPCHAR *npc) +{ + RECT rcLeft[7]; + + rcLeft[0] = {0, 224, 16, 240}; + rcLeft[1] = {16, 224, 32, 240}; + rcLeft[2] = {32, 224, 48, 240}; + rcLeft[3] = {48, 224, 64, 240}; + rcLeft[4] = {64, 224, 80, 240}; + rcLeft[5] = {80, 224, 96, 240}; + rcLeft[6] = {96, 224, 112, 240}; + + if (npc->act_no == 0) + { + npc->xm = Random(-4, 4) * 0x200; + npc->act_no = 1; + } + else + { + npc->xm = 20 * npc->xm / 21; + npc->ym = 20 * npc->ym / 21; + + npc->x += npc->xm; + npc->y += npc->ym; + } + + if (++npc->ani_wait > 1) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 6) + npc->cond = 0; + else + npc->rect = rcLeft[npc->ani_no]; +} + +//Undead Core exploding rock +void ActNpc288(NPCHAR *npc) +{ + RECT rc[5]; + + rc[0] = {232, 72, 248, 88}; + rc[1] = {232, 88, 248, 104}; + rc[2] = {232, 0, 256, 24}; + rc[3] = {232, 24, 256, 48}; + rc[4] = {232, 48, 256, 72}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->xm = -0x200; + // Fallthrough + case 1: + if (npc->direct == 1) + { + npc->ym -= 0x20; + if (npc->ym < -0x5FF) + npc->ym = -0x5FF; + + if (npc->flag & 2) + npc->act_no = 2; + } + else if (npc->direct == 3) + { + npc->ym += 0x20; + if (npc->ym > 0x5FF) + npc->ym = 0x5FF; + + if (npc->flag & 8) + npc->act_no = 2; + } + + if (++npc->ani_wait > 3) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 1) + npc->ani_no = 0; + + break; + + case 2: + PlaySoundObject(44, 1); + npc->act_no = 3; + npc->act_wait = 0; + npc->bits |= 8; + npc->ym = 0; + + if (gMC.x < npc->x) + npc->xm = -0x400; + else + npc->xm = 0x400; + + npc->view.back = 0x1800; + npc->view.front = 0x1800; + npc->view.top = 0x1800; + npc->view.bottom = 0x1800; + // Fallthrough + case 3: + if (++npc->ani_no > 4) + npc->ani_no = 2; + + if (++npc->act_wait % 4 == 1) + { + if (npc->direct == 1) + SetNpChar(287, npc->x, npc->y, 0, 0x400, 0, 0, 0x100); + else + SetNpChar(287, npc->x, npc->y, 0, -0x400, 0, 0, 0x100); + } + + if (npc->x < 0x2000 || npc->x > (gMap.width * 0x2000) - 0x2000) + npc->cond = 0; + + break; + } + + npc->x += npc->xm; + npc->y += npc->ym; + + npc->rect = rc[npc->ani_no]; +} + +//Critter (orange, Misery) +void ActNpc289(NPCHAR *npc) +{ + RECT rcLeft[3]; + RECT rcRight[3]; + + rcLeft[0] = {160, 32, 176, 48}; + rcLeft[1] = {176, 32, 192, 48}; + rcLeft[2] = {192, 32, 208, 48}; + + rcRight[0] = {160, 48, 176, 64}; + rcRight[1] = {176, 48, 192, 64}; + rcRight[2] = {192, 48, 208, 64}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->ani_no = 2; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + // Fallthrough + case 1: + if (++npc->act_wait > 16) + { + npc->act_no = 10; + npc->view.top = 0x1000; + npc->view.bottom = 0x1000; + npc->damage = 2; + npc->bits |= 0x20; + } + + break; + + case 10: + if (npc->flag & 8) + { + npc->act_no = 11; + npc->ani_no = 0; + npc->act_wait = 0; + npc->xm = 0; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + } + + break; + + case 11: + if (++npc->act_wait > 10) + { + if (++npc->count1 > 4) + npc->act_no = 12; + else + npc->act_no = 10; + + PlaySoundObject(30, 1); + npc->ym = -0x600; + + if (npc->direct == 0) + npc->xm = -0x200; + else + npc->xm = 0x200; + + npc->ani_no = 2; + } + + break; + + case 12: + npc->bits |= 8; + + if (npc->y > gMap.length * 0x2000) + VanishNpChar(npc); + + break; + } + + if (npc->act_no >= 10) + npc->ym += 0x40; + + if (npc->ym > 0x5FF) + npc->ym = 0x5FF; + + npc->x += npc->xm; + npc->y += npc->ym; + + if (npc->direct == 0) + npc->rect = rcLeft[npc->ani_no]; + else + npc->rect = rcRight[npc->ani_no]; + + if (npc->act_no == 1) + { + npc->rect.top += 8 - npc->act_wait / 2; + npc->rect.bottom -= npc->act_wait / 2 + 8; + npc->view.top = (npc->act_wait * 0x200) / 2; + npc->view.bottom = (npc->act_wait * 0x200) / 2; + } +} + +//Bat (Misery) +void ActNpc290(NPCHAR *npc) +{ + RECT rcLeft[3]; + RECT rcRight[3]; + + rcLeft[0] = {112, 32, 128, 48}; + rcLeft[1] = {128, 32, 144, 48}; + rcLeft[2] = {144, 32, 160, 48}; + + rcRight[0] = {112, 48, 128, 64}; + rcRight[1] = {128, 48, 144, 64}; + rcRight[2] = {144, 48, 160, 64}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->ani_no = 2; + + if (gMC.x < npc->x) + npc->direct = 0; + else + npc->direct = 2; + // Fallthrough + case 1: + if (++npc->act_wait > 16) + { + npc->act_no = 10; + npc->view.top = 0x1000; + npc->view.bottom = 0x1000; + npc->damage = 2; + npc->bits |= 0x20; + npc->tgt_y = npc->y; + npc->ym = 0x400; + } + + break; + + case 10: + if (++npc->ani_wait > 2) + { + npc->ani_wait = 0; + ++npc->ani_no; + } + + if (npc->ani_no > 2) + npc->ani_no = 0; + + if (npc->tgt_y > npc->y) + npc->ym += 0x40; + else + npc->ym -= 0x40; + + if (npc->direct == 0) + npc->xm -= 0x10; + else + npc->xm += 0x10; + + if (npc->x < 0 || npc->y < 0 || npc->x > gMap.width * 0x2000 || npc->y > gMap.length * 0x2000) + { + VanishNpChar(npc); + return; + } + + break; + } + + npc->x += npc->xm; + npc->y += npc->ym; + + if (npc->direct == 0) + npc->rect = rcLeft[npc->ani_no]; + else + npc->rect = rcRight[npc->ani_no]; + + if (npc->act_no == 1) + { + npc->rect.top += 8 - npc->act_wait / 2; + npc->rect.bottom -= npc->act_wait / 2 + 8; + npc->view.top = (npc->act_wait * 0x200) / 2; + npc->view.bottom = (npc->act_wait * 0x200) / 2; + } +} + +//Mini Undead Core (inactive) +void ActNpc291(NPCHAR *npc) +{ + RECT tc[2]; + + tc[0] = {256, 80, 320, 120}; + tc[1] = {256, 0, 320, 40}; + + if (npc->act_no == 0) + { + npc->act_no = 20; + + if (npc->direct == 2) + { + npc->bits &= ~0x40; + npc->ani_no = 1; + } + } + + npc->rect = tc[npc->ani_no]; +} //Quake void ActNpc292(NPCHAR *npc) @@ -18,6 +1363,94 @@ void ActNpc292(NPCHAR *npc) SetQuake(10); } +//Undead Core giant energy shot +void ActNpc293(NPCHAR *npc) +{ + RECT rect[2]; + + rect[0] = {240, 200, 280, 240}; + rect[1] = {280, 200, 320, 240}; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + // Fallthrough + case 1: + if (++npc->ani_no > 1) + npc->ani_no = 0; + + SetNpChar(4, npc->x + (Random(0, 0x10) * 0x200), npc->y + (Random(-0x10, 0x10) * 0x200), 0, 0, 0, 0, 0x100); + + npc->x -= 0x1000; + + if (npc->x < -0x4000) + npc->cond = 0; + + break; + } + + npc->rect = rect[npc->ani_no]; +} + +//Quake + falling block generator +void ActNpc294(NPCHAR *npc) +{ + switch (npc->act_no) + { + case 0: + if (gMC.x < (gMap.width - 6) * 0x2000) + { + npc->act_no = 1; + npc->act_wait = 0; + } + + break; + + case 1: + ++npc->act_wait; + + if (gMC.equip & 0x20) + { + npc->x = gMC.x + 0x8000; + + if (npc->x < 0x34000) + npc->x = 0x34000; + } + else + { + npc->x = gMC.x + 0xC000; + + if (npc->x < 0x2E000) + npc->x = 0x2E000; + } + + if (npc->x > (gMap.width - 10) * 0x2000) + npc->x = (gMap.width - 10) * 0x2000; + + if (npc->act_wait > 24) + { + int x; + + if (gMC.equip & 0x20) + x = npc->x + (Random(-14, 14) * 0x2000); + else + x = npc->x + (Random(-11, 11) * 0x2000); + + const int y = gMC.y - 0x1C000; + + if (Random(0, 10) & 1) + SetNpChar(279, x, y, 0, 0, 0, 0, 0x100); + else + SetNpChar(279, x, y, 0, 0, 2, 0, 0x100); + + npc->act_wait = Random(0, 15); + } + + break; + } +} + //Cloud void ActNpc295(NPCHAR *npc) { diff --git a/src/NpcAct300.cpp b/src/NpcAct300.cpp index 7783deae..0e2f7078 100644 --- a/src/NpcAct300.cpp +++ b/src/NpcAct300.cpp @@ -35,6 +35,73 @@ void ActNpc300(NPCHAR *npc) npc->rect = rc[0]; } +//Fish missile (Misery) +void ActNpc301(NPCHAR *npc) +{ + RECT rect[8]; + + rect[0] = {144, 0, 160, 16}; + rect[1] = {160, 0, 176, 16}; + rect[2] = {176, 0, 192, 16}; + rect[3] = {192, 0, 208, 16}; + rect[4] = {144, 16, 160, 32}; + rect[5] = {160, 16, 176, 32}; + rect[6] = {176, 16, 192, 32}; + rect[7] = {192, 16, 208, 32}; + + int dir; + + switch (npc->act_no) + { + case 0: + npc->act_no = 1; + npc->count1 = npc->direct; + // Fallthrough + case 1: + npc->xm = 2 * GetCos(npc->count1); + npc->ym = 2 * GetSin(npc->count1); + + npc->y += npc->ym; + npc->x += npc->xm; + + dir = GetArktan(npc->x - gMC.x, npc->y - gMC.y); + + if (dir < npc->count1) + { + if (npc->count1 - dir < 0x80) + --npc->count1; + else + ++npc->count1; + } + else + { + if (dir - npc->count1 < 0x80) + ++npc->count1; + else + --npc->count1; + } + + if (npc->count1 > 0xFF) + npc->count1 -= 0x100; + if (npc->count1 < 0) + npc->count1 += 0x100; + + break; + } + + if (++npc->ani_wait > 2) + { + npc->ani_wait = 0; + SetCaret(npc->x, npc->y, 7, 4); + } + + npc->ani_no = (npc->count1 + 0x10) / 0x20; + if (npc->ani_no > 7) + npc->ani_no = 7; + + npc->rect = rect[npc->ani_no]; +} + //Camera focus marker void ActNpc302(NPCHAR *npc) { diff --git a/src/NpcTbl.cpp b/src/NpcTbl.cpp index 6ad4b126..11e1e7dd 100644 --- a/src/NpcTbl.cpp +++ b/src/NpcTbl.cpp @@ -335,29 +335,29 @@ NPCFUNCTION gpNpcFuncTbl[361] = ActNpc276, ActNpc277, ActNpc278, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, - nullptr, + ActNpc279, + ActNpc280, + ActNpc281, + ActNpc282, + ActNpc283, + ActNpc284, + ActNpc285, + ActNpc286, + ActNpc287, + ActNpc288, + ActNpc289, + ActNpc290, + ActNpc291, ActNpc292, - nullptr, - nullptr, + ActNpc293, + ActNpc294, ActNpc295, ActNpc296, ActNpc297, ActNpc298, ActNpc299, ActNpc300, - nullptr, + ActNpc301, ActNpc302, ActNpc303, ActNpc304, From 10f69d115b4deaf5026d6f3d0853f4e25118152b Mon Sep 17 00:00:00 2001 From: Clownacy Date: Sat, 9 Feb 2019 14:47:20 +0000 Subject: [PATCH 4/4] Added Undead Core and more NPCs --- Makefile | 1 + src/Boss.cpp | 3 +- src/BossAlmo2.cpp | 737 ++++++++++++++++++++++++++++++++++++++++++++++ src/BossAlmo2.h | 3 + 4 files changed, 743 insertions(+), 1 deletion(-) create mode 100644 src/BossAlmo2.cpp create mode 100644 src/BossAlmo2.h diff --git a/Makefile b/Makefile index c00d707d..e3d2cbd9 100644 --- a/Makefile +++ b/Makefile @@ -44,6 +44,7 @@ SOURCES = \ Back \ Boss \ BossAlmo1 \ + BossAlmo2 \ BossFrog \ BossIronH \ BossLife \ diff --git a/src/Boss.cpp b/src/Boss.cpp index aada7853..eee22014 100644 --- a/src/Boss.cpp +++ b/src/Boss.cpp @@ -5,6 +5,7 @@ #include "Boss.h" #include "BossAlmo1.h" +#include "BossAlmo2.h" #include "BossFrog.h" #include "BossIronH.h" #include "BossOhm.h" @@ -196,7 +197,7 @@ BOSSFUNCTION gpBossFuncTbl[10] = ActBossChar_Core, ActBossChar_Ironhead, ActBossChar_Twin, - nullptr, //ActBossChar_Undead, + ActBossChar_Undead, nullptr, //ActBossChar_Press, nullptr, //ActBossChar_Ballos }; diff --git a/src/BossAlmo2.cpp b/src/BossAlmo2.cpp new file mode 100644 index 00000000..6335ac08 --- /dev/null +++ b/src/BossAlmo2.cpp @@ -0,0 +1,737 @@ +#include "BossAlmo2.h" + +#include "Boss.h" +#include "Flash.h" +#include "Frame.h" +#include "Game.h" +#include "Map.h" +#include "MyChar.h" +#include "NpChar.h" +#include "Sound.h" +#include "Triangle.h" +#include "WindowsWrapper.h" + +static void ActBossCharA_Head(NPCHAR *npc) +{ + RECT rect[4]; + + rect[0] = {0, 0, 72, 112}; + rect[1] = {0, 112, 72, 224}; + rect[2] = {160, 0, 232, 112}; + rect[3] = {0, 0, 0, 0}; + + switch (npc->act_no) + { + case 10: + npc->act_no = 11; + npc->ani_no = 2; + npc->bits = 8; + npc->view.front = 0x4800; + npc->view.top = 0x7000; + // Fallthrough + case 11: + npc->x = gBoss[0].x - 0x4800; + npc->y = gBoss[0].y; + break; + + case 50: + npc->act_no = 51; + npc->act_wait = 112; + // Fallthrough + case 51: + if (--npc->act_wait == 0) + { + npc->act_no = 100; + npc->ani_no = 3; + } + + break; + + case 100: + npc->ani_no = 3; + break; + } + + npc->rect = rect[npc->ani_no]; + + if (npc->act_no == 51) + npc->rect.bottom = npc->act_wait + npc->rect.top; +} + +static void ActBossCharA_Tail(NPCHAR *npc) +{ + RECT rect[3]; + + rect[0] = {72, 0, 160, 112}; + rect[1] = {72, 112, 160, 224}; + rect[2] = {0, 0, 0, 0}; + + switch (npc->act_no) + { + case 10: + npc->act_no = 11; + npc->ani_no = 0; + npc->bits = 8; + npc->view.front = 0x5800; + npc->view.top = 0x7000; + // Fallthrough + case 11: + npc->x = gBoss[0].x + 0x5800; + npc->y = gBoss[0].y; + break; + + case 50: + npc->act_no = 51; + npc->act_wait = 112; + // Fallthrough + case 51: + if (--npc->act_wait == 0) + { + npc->act_no = 100; + npc->ani_no = 2; + } + + break; + + case 100: + npc->ani_no = 2; + break; + } + + npc->rect = rect[npc->ani_no]; + + if (npc->act_no == 51) + npc->rect.bottom = npc->act_wait + npc->rect.top; +} + +static void ActBossCharA_Face(NPCHAR *npc) +{ + RECT rect[5]; + + rect[0] = {0, 0, 0, 0}; + rect[1] = {160, 112, 232, 152}; + rect[2] = {160, 152, 232, 192}; + rect[3] = {160, 192, 232, 232}; + rect[4] = {248, 160, 320, 200}; + + switch (npc->act_no) + { + case 0: + npc->ani_no = 0; + break; + + case 10: + npc->ani_no = 1; + break; + + case 20: + npc->ani_no = 2; + break; + + case 30: + npc->act_no = 31; + npc->ani_no = 3; + npc->act_wait = 100; + // Fallthrough + case 31: + if (++npc->act_wait > 300) + npc->act_wait = 0; + + if (npc->act_wait > 250 && (npc->act_wait & 0xF) == 1) + PlaySoundObject(26, 1); + + if (npc->act_wait > 250 && (npc->act_wait & 0xF) == 7) + { + SetNpChar(293, npc->x, npc->y, 0, 0, 0, 0, 0x80); + PlaySoundObject(101, 1); + } + + if (npc->act_wait == 200) + PlaySoundObject(116, 1); + + if (npc->act_wait > 200 && npc->act_wait % 2) + npc->ani_no = 4; + else + npc->ani_no = 3; + + break; + } + + npc->view.back = 0x4800; + npc->view.front = 0x4800; + npc->view.top = 0x2800; + + npc->x = gBoss[0].x - 0x4800; + npc->y = gBoss[0].y + 0x800; + + npc->bits = 8; + + npc->rect = rect[npc->ani_no]; +} + +static void ActBossCharA_Mini(NPCHAR *npc) +{ + RECT rect[3]; + + rect[0] = {256, 0, 320, 40}; + rect[1] = {256, 40, 320, 80}; + rect[2] = {256, 80, 320, 120}; + + if (npc->cond) + { + npc->life = 1000; + + switch (npc->act_no) + { + case 0: + npc->bits &= ~0x20; + break; + + case 5: + npc->ani_no = 0; + npc->bits &= ~0x20; + ++npc->count2; + npc->count2 &= 0xFF; + break; + + case 10: + npc->ani_no = 0; + npc->bits &= ~0x20; + npc->count2 += 2; + npc->count2 &= 0xFF; + break; + + case 20: + npc->ani_no = 1; + npc->bits &= ~0x20; + npc->count2 += 2; + npc->count2 &= 0xFF; + break; + + case 30: + npc->ani_no = 0; + npc->bits &= ~0x20; + npc->count2 += 4; + npc->count2 &= 0xFF; + break; + + case 200: + npc->act_no = 201; + npc->ani_no = 2; + npc->xm = 0; + npc->ym = 0; + // Fallthrough + case 201: + npc->xm += 0x20; + + npc->x += npc->xm; + + if (npc->x > (gMap.width + 2) * 0x2000) + npc->cond = 0; + + break; + } + + if (npc->act_no < 50) + { + int deg; + + if (npc->count1) + deg = npc->count2 + 0x80; + else + deg = npc->count2 + 0x180; + + npc->x = npc->pNpc->x + 0x30 * GetCos(deg / 2) - 0x1000; + npc->y = npc->pNpc->y + 0x50 * GetSin(deg / 2); + } + + npc->rect = rect[npc->ani_no]; + } +} + +static void ActBossCharA_Hit(NPCHAR *npc) +{ + switch (npc->count1) + { + case 0: + npc->x = gBoss[0].x; + npc->y = gBoss[0].y - 0x4000; + break; + + case 1: + npc->x = gBoss[0].x + 0x3800; + npc->y = gBoss[0].y; + break; + + case 2: + npc->x = gBoss[0].x + 0x800; + npc->y = gBoss[0].y + 0x4000; + break; + + case 3: + npc->x = gBoss[0].x - 0x3800; + npc->y = gBoss[0].y + 0x800; + break; + } +} + +void ActBossChar_Undead(void) +{ + static int life; + static unsigned char flash; + + BOOL bShock = FALSE; + + switch (gBoss[0].act_no) + { + case 1: + gBoss[0].act_no = 10; + gBoss[0].exp = 1; + gBoss[0].cond = 0x80; + gBoss[0].bits = 0x800C; + gBoss[0].life = 700; + gBoss[0].hit_voice = 114; + gBoss[0].x = 0x4A000; + gBoss[0].y = 0xF000; + gBoss[0].xm = 0; + gBoss[0].ym = 0; + gBoss[0].code_event = 1000; + gBoss[0].bits |= 0x200; + + gBoss[3].cond = 0x80; + gBoss[3].act_no = 0; + + gBoss[4].cond = 0x80; + gBoss[4].act_no = 10; + + gBoss[5].cond = 0x80; + gBoss[5].act_no = 10; + + gBoss[8].cond = 0x80; + gBoss[8].bits = 8; + gBoss[8].view.front = 0; + gBoss[8].view.top = 0; + gBoss[8].hit.back = 0x5000; + gBoss[8].hit.top = 0x2000; + gBoss[8].hit.bottom = 0x2000; + gBoss[8].count1 = 0; + + gBoss[9] = gBoss[8]; + gBoss[9].hit.back = 0x4800; + gBoss[9].hit.top = 0x3000; + gBoss[9].hit.bottom = 0x3000; + gBoss[9].count1 = 1; + + gBoss[10] = gBoss[8]; + gBoss[10].hit.back = 0x5800; + gBoss[10].hit.top = 0x1000; + gBoss[10].hit.bottom = 0x1000; + gBoss[10].count1 = 2; + + gBoss[11] = gBoss[8]; + gBoss[11].cond |= 0x10; + gBoss[11].hit.back = 0x2800; + gBoss[11].hit.top = 0x2800; + gBoss[11].hit.bottom = 0x2800; + gBoss[11].count1 = 3; + + gBoss[1].cond = 0x80; + gBoss[1].act_no = 0; + gBoss[1].bits = 40; + gBoss[1].life = 1000; + gBoss[1].hit_voice = 54; + gBoss[1].hit.back = 0x3000; + gBoss[1].hit.top = 0x2000; + gBoss[1].hit.bottom = 0x2000; + gBoss[1].view.front = 0x4000; + gBoss[1].view.top = 0x2800; + gBoss[1].pNpc = gBoss; + + gBoss[2] = gBoss[1]; + gBoss[2].count2 = 0x80; + + gBoss[6] = gBoss[1]; + gBoss[6].count1 = 1; + + gBoss[7] = gBoss[1]; + gBoss[7].count1 = 1; + gBoss[7].count2 = 0x80; + + life = gBoss[0].life; + + break; + + case 15: + gBoss[0].act_no = 16; + bShock = TRUE; + gBoss[0].direct = 0; + gBoss[3].act_no = 10; + gBoss[4].ani_no = 0; + break; + + case 20: + gBoss[0].act_no = 210; + bShock = TRUE; + gBoss[0].direct = 0; + gBoss[1].act_no = 5; + gBoss[2].act_no = 5; + gBoss[6].act_no = 5; + gBoss[7].act_no = 5; + break; + + case 200: + gBoss[0].act_no = 201; + gBoss[0].act_wait = 0; + gBoss[3].act_no = 0; + gBoss[4].ani_no = 2; + gBoss[5].ani_no = 0; + gBoss[8].bits &= ~4; + gBoss[9].bits &= ~4; + gBoss[10].bits &= ~4; + gBoss[11].bits &= ~0x20; + gSuperYpos = 0; + CutNoise(); + bShock = TRUE; + // Fallthrough + case 201: + ++gBoss[0].act_wait; + + if ((gBoss[0].direct == 2 || gBoss[0].ani_no > 0 || gBoss[0].life < 200) && gBoss[0].act_wait > 200) + { + ++gBoss[0].count1; + PlaySoundObject(115, 1); + + if (gBoss[0].life < 200) + { + gBoss[0].act_no = 230; + } + else + { + if ( gBoss[0].count1 <= 2 ) + gBoss[0].act_no = 210; + else + gBoss[0].act_no = 220; + } + } + + break; + + case 210: + gBoss[0].act_no = 211; + gBoss[0].act_wait = 0; + gBoss[3].act_no = 10; + gBoss[8].bits |= 4; + gBoss[9].bits |= 4; + gBoss[10].bits |= 4; + gBoss[11].bits |= 0x20; + life = gBoss[0].life; + bShock = TRUE; + // Fallthrough + case 211: + ++flash; + + if (gBoss[0].shock && (flash >> 1) & 1) + { + gBoss[4].ani_no = 1; + gBoss[5].ani_no = 1; + } + else + { + gBoss[4].ani_no = 0; + gBoss[5].ani_no = 0; + } + + if (++gBoss[0].act_wait % 100 == 1) + { + gCurlyShoot_wait = Random(80, 100); + gCurlyShoot_x = gBoss[11].x; + gCurlyShoot_y = gBoss[11].y; + } + + if (gBoss[0].act_wait < 300) + { + if (gBoss[0].act_wait % 120 == 1) + SetNpChar(288, gBoss[0].x - 0x4000, gBoss[0].y - 0x2000, 0, 0, 1, 0, 0x20); + + if (gBoss[0].act_wait % 120 == 61) + SetNpChar(288, gBoss[0].x - 0x4000, gBoss[0].y + 0x2000, 0, 0, 3, 0, 0x20); + } + + if (gBoss[0].life < life - 50 || gBoss[0].act_wait > 400) + gBoss[0].act_no = 200; + + break; + + case 220: + gBoss[0].act_no = 221; + gBoss[0].act_wait = 0; + gBoss[0].count1 = 0; + gSuperYpos = 1; + gBoss[3].act_no = 20; + gBoss[8].bits |= 4; + gBoss[9].bits |= 4; + gBoss[10].bits |= 4; + gBoss[11].bits |= 0x20; + SetQuake(100); + life = gBoss[0].life; + bShock = TRUE; + // Fallthrough + case 221: + if (++gBoss[0].act_wait % 40 == 1) + { + int x; + int y; + + switch (Random(0, 3)) + { + case 0: + x = gBoss[1].x; + y = gBoss[1].y; + break; + case 1: + x = gBoss[2].x; + y = gBoss[2].y; + break; + case 2: + x = gBoss[6].x; + y = gBoss[6].y; + break; + case 3: + x = gBoss[7].x; + y = gBoss[7].y; + break; + } + + PlaySoundObject(25, 1); + SetNpChar(285, x - 0x2000, y, 0, 0, 0, 0, 0x100); + SetNpChar(285, x - 0x2000, y, 0, 0, 0x400, 0, 0x100); + } + + ++flash; + + if (gBoss[0].shock && (flash >> 1) & 1) + { + gBoss[4].ani_no = 1; + gBoss[5].ani_no = 1; + } + else + { + gBoss[4].ani_no = 0; + gBoss[5].ani_no = 0; + } + + if (gBoss[0].life < life - 150 || gBoss[0].act_wait > 400 || gBoss[0].life < 200) + gBoss[0].act_no = 200; + + break; + + case 230: + gBoss[0].act_no = 231; + gBoss[0].act_wait = 0; + gBoss[3].act_no = 30; + gBoss[8].bits |= 4; + gBoss[9].bits |= 4; + gBoss[10].bits |= 4; + gBoss[11].bits |= 0x20; + PlaySoundObject(25, 1); + SetNpChar(285, gBoss[3].x - 0x2000, gBoss[3].y, 0, 0, 0, 0, 0x100); + SetNpChar(285, gBoss[3].x - 0x2000, gBoss[3].y, 0, 0, 0x400, 0, 0x100); + SetNpChar(285, gBoss[3].x, gBoss[3].y - 0x2000, 0, 0, 0, 0, 0x100); + SetNpChar(285, gBoss[3].x, gBoss[3].y - 0x2000, 0, 0, 0x400, 0, 0x100); + SetNpChar(285, gBoss[3].x, gBoss[3].y + 0x2000, 0, 0, 0, 0, 0x100); + SetNpChar(285, gBoss[3].x, gBoss[3].y + 0x2000, 0, 0, 0x400, 0, 0x100); + life = gBoss[0].life; + bShock = TRUE; + // Fallthrough + case 231: + ++flash; + + if (gBoss[0].shock && (flash >> 1) & 1) + { + gBoss[4].ani_no = 1; + gBoss[5].ani_no = 1; + } + else + { + gBoss[4].ani_no = 0; + gBoss[5].ani_no = 0; + } + + if (++gBoss[0].act_wait % 100 == 1) + { + gCurlyShoot_wait = Random(80, 100); + gCurlyShoot_x = gBoss[11].x; + gCurlyShoot_y = gBoss[11].y; + } + + if (gBoss[0].act_wait % 120 == 1) + SetNpChar(288, gBoss[0].x - 0x4000, gBoss[0].y - 0x2000, 0, 0, 1, 0, 0x20); + + if (gBoss[0].act_wait % 120 == 61) + SetNpChar(288, gBoss[0].x - 0x4000, gBoss[0].y + 0x2000, 0, 0, 3, 0, 0x20); + + break; + + case 500: + CutNoise(); + gBoss[0].act_no = 501; + gBoss[0].act_wait = 0; + gBoss[0].xm = 0; + gBoss[0].ym = 0; + gBoss[3].act_no = 0; + gBoss[4].ani_no = 2; + gBoss[5].ani_no = 0; + gBoss[1].act_no = 5; + gBoss[2].act_no = 5; + gBoss[6].act_no = 5; + gBoss[7].act_no = 5; + SetQuake(20); + + for (int i = 0; i < 100; ++i) + SetNpChar(4, gBoss[0].x + (Random(-0x80, 0x80) * 0x200), gBoss[0].y + (Random(-0x40, 0x40) * 0x200), Random(-0x80, 0x80) * 0x200, Random(-0x80, 0x80) * 0x200, 0, 0, 0); + + DeleteNpCharCode(282, 1); + gBoss[11].bits &= ~0x20; + + for (int i = 0; i < 12; ++i) + gBoss[i].bits &= ~4; + // Fallthrough + case 501: + if (++gBoss[0].act_wait & 0xF) + SetNpChar(4, gBoss[0].x + (Random(-0x40, 0x40) * 0x200), gBoss[0].y + (Random(-0x20, 0x20) * 0x200), Random(-0x80, 0x80) * 0x200, Random(-0x80, 0x80) * 0x200, 0, 0, 0x100); + + gBoss[0].x += 0x40; + gBoss[0].y += 0x80; + + if (gBoss[0].act_wait > 200) + { + gBoss[0].act_wait = 0; + gBoss[0].act_no = 1000; + } + + break; + + case 1000: + SetQuake(100); + + if (++gBoss[0].act_wait % 8 == 0) + PlaySoundObject(44, 1); + + SetDestroyNpChar(gBoss[0].x + (Random(-0x48, 0x48) * 0x200), gBoss[0].y + (Random(-0x40, 0x40) * 0x200), 1, 1); + + if (gBoss[0].act_wait > 100) + { + gBoss[0].act_wait = 0; + gBoss[0].act_no = 1001; + SetFlash(gBoss[0].x, gBoss[0].y, 1); + PlaySoundObject(35, 1); + } + + break; + + case 1001: + SetQuake(40); + + if (++gBoss[0].act_wait > 50) + { + for (int i = 0; i < 20; ++i) + gBoss[i].cond = 0; + + DeleteNpCharCode(158, 1); + DeleteNpCharCode(301, 1); + } + + break; + } + + if (bShock) + { + SetQuake(20); + + if (gBoss[0].act_no == 201) + { + gBoss[7].act_no = 10; + gBoss[6].act_no = 10; + gBoss[2].act_no = 10; + gBoss[1].act_no = 10; + } + + if (gBoss[0].act_no == 221) + { + gBoss[7].act_no = 20; + gBoss[6].act_no = 20; + gBoss[2].act_no = 20; + gBoss[1].act_no = 20; + } + + if (gBoss[0].act_no == 231) + { + gBoss[7].act_no = 30; + gBoss[6].act_no = 30; + gBoss[2].act_no = 30; + gBoss[1].act_no = 30; + } + + PlaySoundObject(26, 1); + + for (int i = 0; i < 8; ++i) + SetNpChar(4, gBoss[4].x + (Random(-0x20, 0x10) * 0x200), gBoss[4].y, Random(-0x200, 0x200), Random(-0x100, 0x100), 0, 0, 0x100); + } + + if (gBoss[0].act_no >= 200 && gBoss[0].act_no < 300) + { + if (gBoss[0].x < 0x18000) + gBoss[0].direct = 2; + if (gBoss[0].x > (gMap.width - 4) * 0x2000) + gBoss[0].direct = 0; + + if (gBoss[0].direct == 0) + gBoss[0].xm -= 4; + else + gBoss[0].xm += 4; + } + + switch (gBoss[0].act_no) + { + case 201: + case 211: + case 221: + case 231: + if (++gBoss[0].count2 == 150) + { + gBoss[0].count2 = 0; + SetNpChar(282, (gMap.width * 0x2000) + 0x40, (Random(-1, 3) + 10) * 0x2000, 0, 0, 0, 0, 0x30); + } + else if (gBoss[0].count2 == 75) + { + SetNpChar(282, (gMap.width * 0x2000) + 0x40, (Random(-3, 0) + 3) * 0x2000, 0, 0, 0, 0, 0x30); + } + + break; + } + + if (gBoss[0].xm > 0x80) + gBoss[0].xm = 0x80; + if (gBoss[0].xm < -0x80) + gBoss[0].xm = -0x80; + + if (gBoss[0].ym > 0x80) + gBoss[0].ym = 0x80; + if (gBoss[0].ym < -0x80) + gBoss[0].ym = -0x80; + + gBoss[0].x += gBoss[0].xm; + gBoss[0].y += gBoss[0].ym; + + ActBossCharA_Face(&gBoss[3]); + ActBossCharA_Head(&gBoss[4]); + ActBossCharA_Tail(&gBoss[5]); + ActBossCharA_Mini(&gBoss[1]); + ActBossCharA_Mini(&gBoss[2]); + ActBossCharA_Mini(&gBoss[6]); + ActBossCharA_Mini(&gBoss[7]); + ActBossCharA_Hit(&gBoss[8]); + ActBossCharA_Hit(&gBoss[9]); + ActBossCharA_Hit(&gBoss[10]); + ActBossCharA_Hit(&gBoss[11]); +} diff --git a/src/BossAlmo2.h b/src/BossAlmo2.h new file mode 100644 index 00000000..c6921f20 --- /dev/null +++ b/src/BossAlmo2.h @@ -0,0 +1,3 @@ +#pragma once + +void ActBossChar_Undead(void);