Added "win_fill_color" script function

This commit is contained in:
NovaRain
2020-10-24 12:56:26 +08:00
parent 97fde2950c
commit 65c4cf644a
10 changed files with 103 additions and 39 deletions
+2
View File
@@ -294,6 +294,7 @@
#define art_cache_clear sfall_func0("art_cache_clear")
#define attack_is_aimed sfall_func0("attack_is_aimed")
#define car_gas_amount sfall_func0("car_gas_amount")
#define clear_window sfall_func0("win_fill_color")
#define combat_data sfall_func0("combat_data")
#define create_win(winName, x, y, w, h) sfall_func5("create_win", winName, x, y, w, h)
#define create_win_flag(winName, x, y, w, h, flag) sfall_func6("create_win", winName, x, y, w, h, flag)
@@ -384,6 +385,7 @@
#define unjam_lock(obj) sfall_func1("unjam_lock", obj)
#define unset_unique_id(obj) sfall_func2("set_unique_id", obj, -1)
#define unwield_slot(critter, slot) sfall_func2("unwield_slot", critter, slot)
#define win_fill_color(x, y, width, height, color) sfall_func5("win_fill_color", x, y, width, height, color)
#define set_fake_perk_npc(npc, perk, level, image, desc) sfall_func5("set_fake_perk_npc", npc, perk, level, image, desc)
#define set_fake_trait_npc(npc, trait, active, image, desc) sfall_func5("set_fake_trait_npc", npc, trait, active, image, desc)
+7 -2
View File
@@ -732,7 +732,7 @@ optional argument:
- message: the text in the dialog box. Use the '\n' control character to move text to a new line (example: "Hello\nWorld!")
optional arguments:
- flags: mode flags (see MSGBOX_* constants in define_extra.h). Pass -1 to skip setting the flags (default flags are NORMAL and YESNO)
- color1/color2: the color index in Fallout palette. color1 sets the text color for the first line, and color2 for all subsequent lines of text (default color is 145)
- color1/color2: the color index in the game palette. color1 sets the text color for the first line, and color2 for all subsequent lines of text (default color is 145)
> int sfall_func1("get_stat_min", int stat)
> int sfall_func1("get_stat_max", int stat)
@@ -762,7 +762,7 @@ optional arguments:
- text: the text to be printed. Use the '\n' control character to move text to a new line (example: "Hello\nWorld!")
- winType: the type number of the interface window (see WINTYPE_* constants in sfall.h)
- x/y: offset relative to the top-left corner of the window
- color: the color index in Fallout palette. Pass 0 if the text color was previously set by vanilla SetTextColor function
- color: the color index in the game palette. Pass 0 if the text color was previously set by vanilla SetTextColor function
it can also take additional flags (via bwor) for displaying text:
0x0010000 - adds a shadow to the text, the 'textshadow' compiler constant
0x1000000 - prevents immediate redrawing of the interface window, the 'textdirect' compiler constant (works the other way around)
@@ -774,6 +774,11 @@ optional arguments:
- can be used in conjunction with the get_object_data and set_object_data functions
example: sfall_func3("set_object_data", sfall_func0("combat_data"), C_ATTACK_UNUSED, 255);
> int sfall_func0("win_fill_color")
> int sfall_func5("win_fill_color", int x, int y, int width, int height, int color)
- fills the rectangle area of the currently selected script window with the specified color, or clears the entire window with transparent color (called without arguments)
- color: the color index in the game palette (from 0 to 255)
------------------------
------ MORE INFO -------
------------------------
+16 -2
View File
@@ -366,11 +366,25 @@ void DrawToSurface(long width, long height, long fromX, long fromY, long fromWid
}
}
// Fills the specified non-scripted interface window with index color 0 (black color)
// Fills the specified interface window with index color
void WinFillRect(long winID, long x, long y, long width, long height, BYTE indexColor) {
fo::Window* win = fo::func::GNW_find(winID);
BYTE* surf = win->surface + (win->width * y) + x;
long pitch = win->width - width;
while (height--) {
long w = width;
while (w--) *surf++ = indexColor;
surf += pitch;
};
}
// Fills the specified interface window with index color 0 (black color)
void ClearWindow(long winID, bool refresh) {
fo::Window* win = fo::func::GNW_find(winID);
BYTE* surf = win->surface;
for (long i = 0; i < win->height; i++) {
std::memset(win->surface, 0, win->width);
std::memset(surf, 0, win->width);
surf += win->width;
}
if (refresh) {
fo::func::GNW_win_refresh(win, &win->rect, 0);
+4 -1
View File
@@ -115,7 +115,10 @@ void DrawToSurface(long width, long height, long fromX, long fromY, long fromWid
void DrawToSurface(long width, long height, long fromX, long fromY, long fromWidth, BYTE* fromSurf, long toX, long toY, long toWidth, long toHeight, BYTE* toSurf);
// Fills the specified non-scripted interface window with index color 0 (black color)
// Fills the specified interface window with index color
void WinFillRect(long winID, long x, long y, long width, long height, BYTE indexColor);
// Fills the specified interface window with index color 0 (black color)
void ClearWindow(long winID, bool refresh = true);
// Print text to surface
+1
View File
@@ -234,6 +234,7 @@ WRAP_WATCOM_FUNC3(long, register_object_take_out, GameObject*, object, long, hol
WRAP_WATCOM_FUNC3(long, register_object_turn_towards, GameObject*, object, long, tileNum, long, nothing)
WRAP_WATCOM_FUNC2(long, roll_random, long, minValue, long, maxValue)
WRAP_WATCOM_FUNC1(long*, runProgram, Program*, progPtr)
WRAP_WATCOM_FUNC1(long, selectWindowID, long, sWinID)
WRAP_WATCOM_FUNC1(ScriptInstance*, scr_find_first_at, long, elevation)
WRAP_WATCOM_FUNC0(ScriptInstance*, scr_find_next_at)
WRAP_WATCOM_FUNC1(GameObject*, scr_find_obj_from_program, Program*, program)
+43 -26
View File
@@ -188,8 +188,7 @@ struct CombatGcsd {
struct ScriptInstance {
long id;
long next;
// first 3 bits - elevation, rest - tile number
long elevationAndTile;
long elevationAndTile; // first 3 bits - elevation, rest - tile number
long spatialRadius;
long flags;
long scriptIdx;
@@ -205,30 +204,49 @@ struct ScriptInstance {
GameObject *targetObject;
long actionNum;
long scriptOverrides;
char gap_48[4];
long field_48;
long howMuch;
char gap_50[4];
long field_50;
long procedureTable[28];
};
// Script run-time data
struct Program {
const char* fileName;
const char* fileName; // path and file name of the script "scripts\*.int"
long *codeStackPtr;
long gap_8;
long gap_9;
long field_8;
long field_C;
long *codePtr;
long field_14;
long gap_18;
long field_18;
long *dStackPtr;
long *aStackPtr;
long *dStackOffs;
long *aStackOffs;
long gap_2C;
long field_2C;
long *stringRefPtr;
long gap_34;
long *procTablePtr;
long field_34; // procTablePtr
long *procTablePtr; // field_38
long regs[12];
long field_6C;
long field_70;
long field_74;
long field_78;
long field_7C;
union {
long flags;
struct {
char flags1;
char flags2;
char flags3;
char flags4;
};
};
long currentScriptWin; // current window for executing script
long field_88;
};
static_assert(sizeof(Program) == 140, "Incorrect Program definition.");
struct ItemButtonItem {
GameObject* item;
@@ -584,8 +602,7 @@ struct Proto {
long flags;
long flagsExt;
// 0x0Y00XXXX: Y - script type (0=s_system, 1=s_spatial, 2=s_time, 3=s_item, 4=s_critter); XXXX - number in scripts.lst. -1 means no script.
long scriptId;
long scriptId; // 0x0Y00XXXX: Y - script type (0=s_system, 1=s_spatial, 2=s_time, 3=s_item, 4=s_critter); XXXX - number in scripts.lst. -1 means no script.
ItemType type;
union {
@@ -730,14 +747,14 @@ struct Window {
long width;
long height;
long clearColour;
long rand1;
long rand2;
long randX;
long randY;
BYTE *surface; // bytes frame data ref to palette
long *buttonsList;
long unknown5; // buttonptr?
long unknown6;
long buttonT1; // buttonptr?
long buttonT2;
long *menuBar;
long *drawFunc;
long *drawFunc; // trans_buf_to_buf_
};
struct sWindow {
@@ -745,18 +762,18 @@ struct sWindow {
long wID;
long width;
long height;
long unknown1;
long unknown2;
long unknown3;
long unknown4;
long region1;
long region2;
long region3;
long region4;
long *buttons;
long numButtons;
long unknown5;
long unknown6;
long setPositionX;
long setPositionY;
long clearColour;
long flags;
long unknown7;
long unknown8;
float randX;
float randY;
};
struct LSData {
+17 -1
View File
@@ -474,7 +474,7 @@ static fo::FrmFile* LoadArtFile(const char* file, long frame, long direction, fo
fo::FrmFile* frmPtr = nullptr;
if (checkPCX) {
const char* pos = strrchr(file, '.');
if (pos && _stricmp(pos, ".PCX") == 0) {
if (pos && _stricmp(++pos, "PCX") == 0) {
long w, h;
BYTE* data = fo::func::loadPCX(file, &w, &h);
if (!data) return nullptr;
@@ -511,6 +511,7 @@ static long GetArtFIDFile(long fid, const char* &file) {
}
static long DrawImage(OpcodeContext& ctx, bool isScaled) {
fo::func::selectWindowID(ctx.program()->currentScriptWin);
if (*(DWORD*)FO_VAR_currentWindow == -1) {
ctx.printOpcodeError("%s() - no created/selected window for the image.", ctx.getMetaruleName());
return 0;
@@ -782,5 +783,20 @@ void mf_interface_print(OpcodeContext& ctx) { // same as vanilla PrintRect
if (!(color & 0x1000000)) fo::func::GNW_win_refresh(win, &win->rect, 0);
}
void mf_win_fill_color(OpcodeContext& ctx) {
fo::func::selectWindowID(ctx.program()->currentScriptWin);
long iWin = *(DWORD*)FO_VAR_currentWindow;
if (iWin == -1) {
ctx.printOpcodeError("%s() - no created or selected window.", ctx.getMetaruleName());
ctx.setReturn(-1);
return;
}
if (ctx.numArgs() > 0) {
fo::WinFillRect(fo::var::sWindows[iWin].wID, ctx.arg(0).rawValue(), ctx.arg(1).rawValue(), ctx.arg(2).rawValue(), ctx.arg(3).rawValue(), (BYTE)ctx.arg(4).rawValue());
} else {
fo::ClearWindow(fo::var::sWindows[iWin].wID, false); // full clear
}
}
}
}
@@ -119,5 +119,7 @@ void mf_get_window_attribute(OpcodeContext&);
void mf_interface_print(OpcodeContext&);
void mf_win_fill_color(OpcodeContext&);
}
}
@@ -150,6 +150,7 @@ static const SfallMetarule metarules[] = {
{"tile_refresh_display", mf_tile_refresh_display, 0, 0},
{"unjam_lock", mf_unjam_lock, 1, 1, -1, {ARG_OBJECT}},
{"unwield_slot", mf_unwield_slot, 2, 2, -1, {ARG_OBJECT, ARG_INT}},
{"win_fill_color", mf_win_fill_color, 0, 5, -1, {ARG_INT, ARG_INT, ARG_INT, ARG_INT, ARG_INT}},
#ifndef NDEBUG
{"validate_test", mf_test, 2, 5, -1, {ARG_INT, ARG_NUMBER, ARG_STRING, ARG_OBJECT, ARG_ANY}},
#endif
+10 -7
View File
@@ -172,24 +172,27 @@ static bool LoadFrm(Frm* frm) {
return true;
}
static long dialogWinX = 0, dialogWinY = 0;
static struct DialogWinPos {
long x = -1;
long y;
} dialogWinPos;
static void __fastcall DrawHeadFrame(Frm* frm, int frameno) {
if (frm && !frm->broken) {
if (!frm->loaded && !LoadFrm(frm)) goto loadFail;
fo::FrmFrameData* frame = fo::func::frame_ptr((fo::FrmHeaderData*)frm, frameno, 0);
if (dialogWinX == -1) {
if (dialogWinPos.x == -1) {
fo::Window* dialogWin = fo::func::GNW_find(fo::var::dialogueBackWindow);
if (texHighlight) Graphics::SetHighlightTexture(texHighlight, dialogWin->rect.x, dialogWin->rect.y);
dialogWinX = dialogWin->rect.x;
dialogWinY = dialogWin->rect.y;
dialogWinPos.x = dialogWin->rect.x;
dialogWinPos.y = dialogWin->rect.y;
}
Graphics::SetHeadTex(frm->textures[frameno],
frame->width,
frame->height,
frame->x + frm->xshift + dialogWinX,
frame->y + frm->yshift + dialogWinY,
frame->x + frm->xshift + dialogWinPos.x,
frame->y + frm->yshift + dialogWinPos.y,
(frm->showHighlights == 2)
);
showHighlights = frm->showHighlights;
@@ -219,7 +222,7 @@ void __declspec(naked) gdDestroyHeadWindow_hack() {
__asm {
call Graphics::SetDefaultTechnique;
mov showHighlights, 0;
//mov dialogWinX, -1; // uncomment if the dialog window position is supposed to change
//mov dword ptr ds:[dialogWinPos], -1; // uncomment if the dialog window position is supposed to change
pop ebp;
pop edi;
pop edx;