Added Daz's persistent NUI storage

Added Daz's persistent NUI storage.  Added instanced player room at the Inn of the Flying Monkey.  Added PnP cockatrice & dire weasel.  Full compile.
This commit is contained in:
Jaysyn904
2023-02-19 01:10:48 -05:00
parent 5586fbdb40
commit a005da6b51
104 changed files with 19760 additions and 176 deletions

View File

@@ -0,0 +1,52 @@
void main()
{
//:: Declare major variables
object oPC = GetPCSpeaker();
object oBaseArea = GetObjectByTag("IFM_PC_ROOMS");
string sPCName = GetName(oPC);
string sBaseResRef = GetResRef(oBaseArea);
string sBaseName = GetName(oBaseArea);
string sNewTag = sPCName+sBaseResRef;
string sNewName = sPCName+"'s Room at the Flying Monkey";
//:: Create instanced area from player's information
CreateArea(sBaseResRef, sNewTag, sNewName);
//:: Get information about new area instance
object oNewRoom = GetObjectByTag(sNewTag);
string sNewResRef = GetResRef(oNewRoom);
location lEntry = GetLocation(GetObjectByTag("PC_ROOM_MAT"));
//:: Create entry waypoint in new area instance
CreateObject(OBJECT_TYPE_WAYPOINT, "nw_waypoint001", lEntry, FALSE, "WP_"+sNewTag);
//:: Make sure the area is valid
object oTarget;
location lTarget;
oTarget = GetWaypointByTag("WP_"+sNewTag);
lTarget = GetLocation(oTarget);
//only do the jump if the location is valid.
//though not flawless, we just check if it is in a valid area.
//the script will stop if the location isn't valid - meaning that
//nothing put after the teleport will fire either.
//the current location won't be stored, either
if (GetAreaFromLocation(lTarget)==OBJECT_INVALID)
{
SendMessageToPC(oPC, "Warning: Area does not exist!");
return;
}
AssignCommand(oPC, ClearAllActions());
AssignCommand(oPC, ActionJumpToLocation(lTarget));
}

View File

@@ -0,0 +1,10 @@
void main()
{
object oPC = GetClickingObject();
if (!GetIsPC(oPC)) return;
ActionStartConversation(oPC, "");
}

View File

@@ -0,0 +1,10 @@
#include "inc_tictactoe"
void main()
{
object oPlayer = GetExitingObject();
TTT_HandlePlayerExit(oPlayer);
ExecuteScript("prc_onleave", oPlayer);
}

File diff suppressed because it is too large Load Diff

494
_module/nss/inc_examine.nss Normal file
View File

@@ -0,0 +1,494 @@
/*
Examine NUI Windows
Created By: Daz
*/
#include "inc_nui"
#include "inc_util"
const string EXAMINE_NUI_WINDOW_ID = "EXAMINEWINDOW";
const string EXAMINE_WINDOW_GEOMETRY_JSON = "EXAMINE_WINDOW_GEOMETRY_JSON";
const string EXAMINE_GENERIC_WINDOW_JSON = "EXAMINE_GENERIC_WINDOW_JSON";
const string EXAMINE_ITEM_WINDOW_JSON = "EXAMINE_ITEM_WINDOW_JSON";
const string EXAMINE_CURRENT_WINDOW_TYPE = "EXAMINE_CURRENT_WINDOW_TYPE";
const string EXAMINE_CURRENT_OBJECT = "EXAMINE_CURRENT_OBJECT";
const float EXAMINE_GENERIC_WINDOW_WIDTH = 500.0f;
const float EXAMINE_GENERIC_WINDOW_HEIGHT = 255.0f;
const float EXAMINE_ITEM_WINDOW_WIDTH = 500.0f;
const float EXAMINE_ITEM_WINDOW_HEIGHT = 400.0f;
void Examine_DisablePanels(object oPlayer);
json Examine_GetWindowJson(int nPanel);
json Examine_GetGenericWindowJson();
json Examine_GetItemWindowJson();
float Examine_GetWindowWidth(int nPanel);
float Examine_GetWindowHeight(int nPanel);
void Examine_HandleGUIEvents(object oPlayer, object oTarget, int nPanel);
void Examine_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex);
void Examine_SetData(object oPlayer, int nToken, object oTarget, int nPanel);
void Examine_SetGenericData(object oPlayer, int nToken, object oTarget, int nPanel);
string Examine_GetItemPropertyString(itemproperty ip);
void Examine_SetItemData(object oPlayer, int nToken, object oItem);
void Examine_DisablePanels(object oPlayer)
{
SetGuiPanelDisabled(oPlayer, GUI_PANEL_EXAMINE_CREATURE, TRUE);
SetGuiPanelDisabled(oPlayer, GUI_PANEL_EXAMINE_ITEM, TRUE);
SetGuiPanelDisabled(oPlayer, GUI_PANEL_EXAMINE_PLACEABLE, TRUE);
SetGuiPanelDisabled(oPlayer, GUI_PANEL_EXAMINE_DOOR, TRUE);
}
json Examine_GetWindowJson(int nPanel)
{
json jWindow;
switch (nPanel)
{
case GUI_PANEL_EXAMINE_CREATURE:
case GUI_PANEL_EXAMINE_PLACEABLE:
case GUI_PANEL_EXAMINE_DOOR:
jWindow = Examine_GetGenericWindowJson();
break;
case GUI_PANEL_EXAMINE_ITEM:
jWindow = Examine_GetItemWindowJson();
break;
}
return jWindow;
}
json Examine_GetGenericWindowJson()
{
json jRoot = GetLocalJson(GetModule(), EXAMINE_GENERIC_WINDOW_JSON);
if (jRoot == JsonNull())
{
json jCol = JsonArray(), jRow;
jRow = JsonArray();
{
json jSubCol, jSubRow;
jSubCol = JsonArray();
// Image
jSubRow = JsonArray();
{
json jImage = NuiImage(NuiBind("image_1"), JsonInt(NUI_ASPECT_EXACTSCALED), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
jImage = NuiWidth(jImage, 64.0f);
jImage = NuiHeight(jImage, 100.0f);
jSubRow = JsonArrayInsert(jSubRow, jImage);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Spacer
jSubRow = JsonArray();
{
jSubRow = JsonArrayInsert(jSubRow, NuiSpacer());
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
jRow = JsonArrayInsert(jRow, NuiCol(jSubCol));
jSubCol = JsonArray();
// Description Label
jSubRow = JsonArray();
{
json jHeader = NuiHeader(JsonString("Description"));
jSubRow = JsonArrayInsert(jSubRow, jHeader);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Description Text
jSubRow = JsonArray();
{
json jDescription = NuiText(NuiBind("description"));
jDescription = NuiHeight(jDescription, 160.0f);
jSubRow = JsonArrayInsert(jSubRow, jDescription);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Spacer
jSubRow = JsonArray();
{
jSubRow = JsonArrayInsert(jSubRow, NuiSpacer());
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
jRow = JsonArrayInsert(jRow, NuiCol(jSubCol));
}
jCol = NuiInsertRow(jCol, jRow);
jRoot = NuiCol(jCol);
SetLocalJson(GetModule(), EXAMINE_GENERIC_WINDOW_JSON, jRoot);
}
return jRoot;
}
json Examine_GetItemWindowJson()
{
json jRoot = GetLocalJson(GetModule(), EXAMINE_ITEM_WINDOW_JSON);
if (jRoot == JsonNull())
{
json jCol = JsonArray(), jRow;
jRow = JsonArray();
{
json jSubCol, jSubRow;
jSubCol = JsonArray();
// Image
jSubRow = JsonArray();
{
json jImage = NuiImage(NuiBind("image_1"), JsonInt(NUI_ASPECT_EXACTSCALED), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
json jRect = NuiRect(0.0f, 0.0f, 64.0f, 192.0f);
json jDrawList = JsonArray();
jDrawList = JsonArrayInsert(jDrawList, NuiDrawListImage(NuiBind("complex_item"), NuiBind("image_2"), jRect, JsonInt(NUI_ASPECT_EXACTSCALED), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP)));
jDrawList = JsonArrayInsert(jDrawList, NuiDrawListImage(NuiBind("complex_item"), NuiBind("image_3"), jRect, JsonInt(NUI_ASPECT_EXACTSCALED), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP)));
jImage = NuiDrawList(jImage, JsonBool(TRUE), jDrawList);
jImage = NuiWidth(jImage, 64.0f);
jImage = NuiHeight(jImage, 192.0f);
jSubRow = JsonArrayInsert(jSubRow, jImage);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Button?
jSubRow = JsonArray();
{
json jButton = NuiButton(JsonString("Button?"));
jButton = NuiId(jButton, "btn_button");
jButton = NuiWidth(jButton, 64.0f);
jButton = NuiHeight(jButton, 35.0f);
jSubRow = JsonArrayInsert(jSubRow, jButton);
}
//jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Spacer
jSubRow = JsonArray();
{
jSubRow = JsonArrayInsert(jSubRow, NuiSpacer());
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
jRow = JsonArrayInsert(jRow, NuiCol(jSubCol));
jSubCol = JsonArray();
// Description Label
jSubRow = JsonArray();
{
json jHeader = NuiHeader(JsonString("Description"));
jSubRow = JsonArrayInsert(jSubRow, jHeader);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Description Text
jSubRow = JsonArray();
{
json jDescription = NuiText(NuiBind("description"));
jDescription = NuiHeight(jDescription, 160.0f);
jSubRow = JsonArrayInsert(jSubRow, jDescription);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Item Properties Label
jSubRow = JsonArray();
{
json jHeader = NuiHeader(JsonString("Item Properties"));
jSubRow = JsonArrayInsert(jSubRow, jHeader);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Item Properties List
jSubRow = JsonArray();
{
json jListTemplate = JsonArray();
{
json jLabel = NuiLabel(NuiBind("property"), JsonInt(NUI_HALIGN_LEFT), JsonInt(NUI_VALIGN_MIDDLE));
jLabel = NuiStyleForegroundColor(jLabel, NuiBind("color"));
jListTemplate = JsonArrayInsert(jListTemplate, NuiListTemplateCell(jLabel, 0.0f, TRUE));
}
json jList = NuiList(jListTemplate, NuiBind("property"), 16.0f);
jList = NuiHeight(jList, 105.0f);
jSubRow = JsonArrayInsert(jSubRow, jList);
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
// Spacer
jSubRow = JsonArray();
{
jSubRow = JsonArrayInsert(jSubRow, NuiSpacer());
}
jSubCol = NuiInsertRow(jSubCol, jSubRow);
jRow = JsonArrayInsert(jRow, NuiCol(jSubCol));
}
jCol = NuiInsertRow(jCol, jRow);
jRoot = NuiCol(jCol);
SetLocalJson(GetModule(), EXAMINE_ITEM_WINDOW_JSON, jRoot);
}
return jRoot;
}
float Examine_GetWindowWidth(int nPanel)
{
float fWidth;
switch (nPanel)
{
case GUI_PANEL_EXAMINE_CREATURE:
case GUI_PANEL_EXAMINE_PLACEABLE:
case GUI_PANEL_EXAMINE_DOOR:
fWidth = EXAMINE_GENERIC_WINDOW_WIDTH;
break;
case GUI_PANEL_EXAMINE_ITEM:
fWidth = EXAMINE_ITEM_WINDOW_WIDTH;
break;
}
return fWidth;
}
float Examine_GetWindowHeight(int nPanel)
{
float fHeight;
switch (nPanel)
{
case GUI_PANEL_EXAMINE_CREATURE:
case GUI_PANEL_EXAMINE_PLACEABLE:
case GUI_PANEL_EXAMINE_DOOR:
fHeight = EXAMINE_GENERIC_WINDOW_HEIGHT;
break;
case GUI_PANEL_EXAMINE_ITEM:
fHeight = EXAMINE_ITEM_WINDOW_HEIGHT;
break;
}
return fHeight;
}
void Examine_HandleGUIEvents(object oPlayer, object oTarget, int nPanel)
{
json jGeometry = GetLocalJson(oPlayer, EXAMINE_WINDOW_GEOMETRY_JSON);
int nToken = NuiFindWindow(oPlayer, EXAMINE_NUI_WINDOW_ID);
if (nToken)
{
if (GetLocalObject(oPlayer, EXAMINE_CURRENT_OBJECT) == oTarget)
return;
int bIsItemExamine = nPanel == GUI_PANEL_EXAMINE_ITEM;
int nCurrentWindowType = GetLocalInt(oPlayer, EXAMINE_CURRENT_WINDOW_TYPE);
if (bIsItemExamine && nCurrentWindowType != GUI_PANEL_EXAMINE_ITEM)
{
NuiSetGroupLayout(oPlayer, nToken, NUI_WINDOW_ROOT_GROUP, Examine_GetWindowJson(nPanel));
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, NuiSetRectHeight(jGeometry, Examine_GetWindowHeight(nPanel)));
}
else if (!bIsItemExamine && nCurrentWindowType == GUI_PANEL_EXAMINE_ITEM)
{
NuiSetGroupLayout(oPlayer, nToken, NUI_WINDOW_ROOT_GROUP, Examine_GetWindowJson(nPanel));
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, NuiSetRectHeight(jGeometry, Examine_GetWindowHeight(nPanel)));
}
Examine_SetData(oPlayer, nToken, oTarget, nPanel);
SetLocalInt(oPlayer, EXAMINE_CURRENT_WINDOW_TYPE, nPanel);
SetLocalObject(oPlayer, EXAMINE_CURRENT_OBJECT, oTarget);
return;
}
json jRoot = Examine_GetWindowJson(nPanel);
json jWindow = NuiWindow(jRoot, NuiBind(NUI_WINDOW_TITLE_BIND), NuiBind(NUI_WINDOW_GEOMETRY_BIND), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
float fWidth = Examine_GetWindowWidth(nPanel);
float fHeight = Examine_GetWindowHeight(nPanel);
if (jGeometry == JsonNull())
jGeometry = NuiGetCenteredGeometryRect(oPlayer, fWidth, fHeight);
else
{
jGeometry = NuiSetRectWidth(jGeometry, fWidth);
jGeometry = NuiSetRectHeight(jGeometry, fHeight);
}
nToken = NuiCreate(oPlayer, jWindow, EXAMINE_NUI_WINDOW_ID);
NuiSetBindWatch(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, TRUE);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, jGeometry);
Examine_SetData(oPlayer, nToken, oTarget, nPanel);
SetLocalInt(oPlayer, EXAMINE_CURRENT_WINDOW_TYPE, nPanel);
SetLocalObject(oPlayer, EXAMINE_CURRENT_OBJECT, oTarget);
}
void Examine_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex)
{
if (sType == NUI_EVENT_CLOSE)
{
DeleteLocalInt(oPlayer, EXAMINE_CURRENT_WINDOW_TYPE);
DeleteLocalObject(oPlayer, EXAMINE_CURRENT_OBJECT);
}
else if (sType == NUI_EVENT_WATCH)
{
if (sElement == NUI_WINDOW_GEOMETRY_BIND)
{
SetLocalJson(oPlayer, EXAMINE_WINDOW_GEOMETRY_JSON, NuiGetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND));
}
}
}
int Examine_HandleIdentifyItem(object oPlayer, object oItem)
{
int bIdentified = GetIdentified(oItem);
if (!bIdentified)
{
int nIdentifySkillRank = GetSkillRank(SKILL_LORE, oPlayer);
if (nIdentifySkillRank < 0)
return FALSE;
if (nIdentifySkillRank > 55)
{
SetIdentified(oItem, TRUE);
return TRUE;
}
int nMaxItemGPValue = StringToInt(Get2DAString("skillvsitemcost", "DeviceCostMax", nIdentifySkillRank));
SetIdentified(oItem, TRUE);
bIdentified = GetGoldPieceValue(oItem) <= nMaxItemGPValue;
SetIdentified(oItem, bIdentified);
}
return bIdentified;
}
void Examine_SetData(object oPlayer, int nToken, object oTarget, int nPanel)
{
Examine_SetGenericData(oPlayer, nToken, oTarget, nPanel);
if (nPanel == GUI_PANEL_EXAMINE_ITEM)
Examine_SetItemData(oPlayer, nToken, oTarget);
}
void Examine_SetGenericData(object oPlayer, int nToken, object oTarget, int nPanel)
{
string sTitle, sDescription;
json jImage1, jImage2, jImage3;
int bComplexItem = FALSE;
switch (nPanel)
{
case GUI_PANEL_EXAMINE_CREATURE:
case GUI_PANEL_EXAMINE_PLACEABLE:
case GUI_PANEL_EXAMINE_DOOR:
{
sTitle = GetName(oTarget);
jImage1 = JsonString(GetPortraitResRef(oTarget) + "m");
sDescription = GetDescription(oTarget);
break;
}
case GUI_PANEL_EXAMINE_ITEM:
{
int bIdentified = Examine_HandleIdentifyItem(oPlayer, oTarget);
int nBaseItemType = GetBaseItemType(oTarget);
sTitle = Util_GetItemName(oTarget, bIdentified);
json jItem = ObjectToJson(oTarget);
json jComplexIconData = Util_GetComplexIconData(jItem, nBaseItemType);
if (JsonGetType(jComplexIconData))
{
jImage1 = JsonObjectGet(jComplexIconData, "bottom");
jImage2 = JsonObjectGet(jComplexIconData, "middle");
jImage3 = JsonObjectGet(jComplexIconData, "top");
bComplexItem = TRUE;
}
else
{
jImage1 = JsonString(Util_GetIconResref(oTarget, jItem, nBaseItemType));
}
sDescription = GetDescription(oTarget, FALSE, bIdentified);
int nStatsStrRef = StringToInt(Get2DAString("baseitems", "BaseItemStatRef", nBaseItemType));
if (nStatsStrRef)
{
sDescription += "\n\n" + GetStringByStrRef(nStatsStrRef);
}
break;
}
}
NuiSetBind(oPlayer, nToken, NUI_WINDOW_TITLE_BIND, JsonString(sTitle));
NuiSetBind(oPlayer, nToken, "image_1", jImage1);
if (bComplexItem)
{
NuiSetBind(oPlayer, nToken, "image_2", jImage2);
NuiSetBind(oPlayer, nToken, "image_3", jImage3);
}
NuiSetBind(oPlayer, nToken, "complex_item", JsonBool(bComplexItem));
NuiSetBind(oPlayer, nToken, "description", JsonString(sDescription));
}
string Examine_GetItemPropertyString(itemproperty ip)
{
int nType = GetItemPropertyType(ip);
string sName = GetStringByStrRef(StringToInt(Get2DAString("itempropdef", "GameStrRef", nType)));
int nSubType = GetItemPropertySubType(ip);
if(nSubType != -1)
{
string sSubTypeResRef = Get2DAString("itempropdef", "SubTypeResRef", nType);
int nStrRef = StringToInt(Get2DAString(sSubTypeResRef, "Name", nSubType));
if(nStrRef)
sName += " " + GetStringByStrRef(nStrRef);
}
int nParam1 = GetItemPropertyParam1(ip);
if(nParam1 != -1)
{
string sParamResRef = Get2DAString("iprp_paramtable", "TableResRef", nParam1);
string sSubTypeResRef = Get2DAString("itempropdef", "SubTypeResRef", nType);
string sTableResRef = Get2DAString(sSubTypeResRef, "TableResRef", nParam1);
int nStrRef = StringToInt(Get2DAString(sParamResRef, "Name", GetItemPropertyParam1Value(ip)));
if(nStrRef)
sName += " " + GetStringByStrRef(nStrRef);
}
int nCostTable = GetItemPropertyCostTable(ip);
if(nCostTable != -1)
{
string sCostTableResRef = Get2DAString("iprp_costtable", "Name", nCostTable);
int nStrRef = StringToInt(Get2DAString(sCostTableResRef, "Name", GetItemPropertyCostTableValue(ip)));
if(nStrRef)
sName += " " + GetStringByStrRef(nStrRef);
}
return sName;
}
void Examine_SetItemData(object oPlayer, int nToken, object oItem)
{
int bIdentified = GetIdentified(oItem);
json jProperties = JsonArray();
json jColors = JsonArray();
if (bIdentified)
{
itemproperty ip = GetFirstItemProperty(oItem);
while (GetIsItemPropertyValid(ip))
{
jProperties = JsonArrayInsert(jProperties, JsonString(Examine_GetItemPropertyString(ip)));
jColors = JsonArrayInsert(jColors, GetItemPropertyDurationType(ip) == DURATION_TYPE_TEMPORARY ? NuiColor(0, 0, 255) : NuiColor(255, 255, 255));
ip = GetNextItemProperty(oItem);
}
}
NuiSetBind(oPlayer, nToken, "property", jProperties);
NuiSetBind(oPlayer, nToken, "color", jColors);
}

300
_module/nss/inc_gennui.nss Normal file
View File

@@ -0,0 +1,300 @@
/*
Generic NUI Windows
Created By: Daz
*/
#include "inc_nui"
const string GNW_WINDOW_PREFIX = "GNW";
const string GNW_OK_CANCEL_WINDOW = "OKCANCEL";
const string GNW_OPTIONS_WINDOW = "OPTIONS";
const string GNW_INFO_WINDOW = "INFO";
const string GNW_MENU_WINDOW = "MENU";
// Call this in your EVENT_SCRIPT_MODULE_ON_NUI_EVENT script
void GNW_HandleNUIEvents();
void GNW_ShowOkCancelWindow(object oPlayer, string sText, string sOkAction, string sCancelAction);
json GNW_AddOption(json jOptions, string sLabel, string sVarName, object oTarget);
void GNW_ShowOptionsWindow(object oPlayer, string sTitle, json jOptions);
void GNW_ShowInfoWindow(object oPlayer, string sTitle, string sText);
void GNW_HandleNUIEvents()
{
object oPlayer = NuiGetEventPlayer();
int nToken = NuiGetEventWindow();
string sWindowId = NuiGetWindowId(oPlayer, nToken);
if (GetStringLeft(sWindowId, GetStringLength(GNW_WINDOW_PREFIX)) != GNW_WINDOW_PREFIX)
return;
string sType = NuiGetEventType();
string sElement = NuiGetEventElement();
if (sWindowId == GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW)
{
if (sType == "click")
{
if (sElement == "btn_ok")
{
ExecuteScriptChunk(GetLocalString(oPlayer, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW + "_OKACTION"), oPlayer);
NuiDestroy(oPlayer, nToken);
}
else if (sElement == "btn_cancel")
{
ExecuteScriptChunk(GetLocalString(oPlayer, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW + "_CANCELACTION"), oPlayer);
NuiDestroy(oPlayer, nToken);
}
}
else if (sType == "close")
{
ExecuteScriptChunk(GetLocalString(oPlayer, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW + "_CANCELACTION"), oPlayer);
}
}
else if (sWindowId == GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW)
{
if (sType == "click")
{
if (sElement == "btn_ok")
{
NuiDestroy(oPlayer, nToken);
}
}
else if (sType == "watch")
{
json jOptions = GetLocalJson(oPlayer, GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW);
json jChecked = NuiGetBind(oPlayer, nToken, "checked");
int nOption, nNumOptions = JsonGetLength(jOptions);
for (nOption = 0; nOption < nNumOptions; nOption++)
{
json jOption = JsonArrayGet(jOptions, nOption);
string sVarName = JsonGetString(JsonObjectGet(jOption, "varname"));
object oTarget = StringToObject(JsonGetString(JsonObjectGet(jOption, "target")));
int bCurrentValue = GetLocalInt(oTarget, sVarName);
int bNewValue = JsonGetInt(JsonArrayGet(jChecked, nOption));
if (bCurrentValue != bNewValue)
{
SetLocalInt(oTarget, sVarName, bNewValue);
SendMessageToPC(oPlayer, "Setting '" + sVarName + "' on " + GetName(oTarget) + " to " + IntToString(bNewValue));
}
}
}
}
else if (sWindowId == GNW_WINDOW_PREFIX + GNW_INFO_WINDOW)
{
if (sType == "click")
{
if (sElement == "btn_ok")
{
NuiDestroy(oPlayer, nToken);
}
}
}
else if (sWindowId == GNW_WINDOW_PREFIX + GNW_MENU_WINDOW)
{
if (sType == "click")
{
if (sElement == "btn_menu")
{
int bSelected = JsonGetInt(NuiGetBind(oPlayer, nToken, "btn_menu"));
SendMessageToPC(oPlayer, "Menu: " + (bSelected ? "Open" : "Close"));
}
}
}
}
void GNW_ShowOkCancelWindow(object oPlayer, string sText, string sOkAction, string sCancelAction)
{
object oModule = GetModule();
json jWindow = GetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW);
if (jWindow == JsonNull())
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
json jText = NuiText(NuiBind("text"));
jRow = JsonArrayInsert(jRow, jText);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{
json jButtonCancel = NuiButton(JsonString("Cancel"));
jButtonCancel = NuiId(jButtonCancel, "btn_cancel");
jButtonCancel = NuiWidth(jButtonCancel, 100.0f);
jButtonCancel = NuiHeight(jButtonCancel, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonCancel);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonOK = NuiButton(JsonString("OK"));
jButtonOK = NuiId(jButtonOK, "btn_ok");
jButtonOK = NuiWidth(jButtonOK, 100.0f);
jButtonOK = NuiHeight(jButtonOK, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonOK);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, JsonBool(FALSE), NuiRect(-1.0f, -1.0f, 400.0f, 200.0f), JsonBool(FALSE), JsonBool(FALSE), JsonBool(FALSE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW, jWindow);
}
int nToken = NuiCreate(oPlayer, jWindow, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW);
NuiSetBind(oPlayer, nToken, "text", JsonString(sText));
SetLocalString(oPlayer, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW + "_OKACTION", sOkAction);
SetLocalString(oPlayer, GNW_WINDOW_PREFIX + GNW_OK_CANCEL_WINDOW + "_CANCELACTION", sCancelAction);
}
json GNW_AddOption(json jOptions, string sLabel, string sVarName, object oTarget)
{
json jOption = JsonObject();
jOption = JsonObjectSet(jOption, "label", JsonString(sLabel));
jOption = JsonObjectSet(jOption, "varname", JsonString(sVarName));
jOption = JsonObjectSet(jOption, "target", JsonString(ObjectToString(oTarget)));
return JsonArrayInsert(jOptions, jOption);
}
void GNW_ShowOptionsWindow(object oPlayer, string sTitle, json jOptions)
{
object oModule = GetModule();
json jWindow = GetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW);
if (jWindow == JsonNull())
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
json jListTemplate = JsonArray();
{
json jCheck = NuiCheck(NuiBind("labels"), NuiBind("checked"));
jListTemplate = JsonArrayInsert(jListTemplate, NuiListTemplateCell(jCheck, 0.0f, TRUE));
}
jRow = JsonArrayInsert(jRow, NuiList(jListTemplate, NuiBind("checked"), 15.0f));
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonOK = NuiButton(JsonString("OK"));
jButtonOK = NuiId(jButtonOK, "btn_ok");
jButtonOK = NuiWidth(jButtonOK, 100.0f);
jButtonOK = NuiHeight(jButtonOK, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonOK);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, NuiBind("title"), NuiRect(-1.0f, -1.0f, 350.0f, 300.0f), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW, jWindow);
}
int nToken = NuiCreate(oPlayer, jWindow, GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW);
SetLocalJson(oPlayer, GNW_WINDOW_PREFIX + GNW_OPTIONS_WINDOW, jOptions);
NuiSetBind(oPlayer, nToken, "title", JsonString(sTitle));
json jLabels = JsonArray();
json jChecked = JsonArray();
int nOption, nNumOptions = JsonGetLength(jOptions);
for (nOption = 0; nOption < nNumOptions; nOption++)
{
json jOption = JsonArrayGet(jOptions, nOption);
json jLabel = JsonObjectGet(jOption, "label");
string sVarName = JsonGetString(JsonObjectGet(jOption, "varname"));
object oTarget = StringToObject(JsonGetString(JsonObjectGet(jOption, "target")));
jLabels = JsonArrayInsert(jLabels, jLabel);
jChecked = JsonArrayInsert(jChecked, JsonBool(GetLocalInt(oTarget, sVarName)));
}
NuiSetBind(oPlayer, nToken, "labels", jLabels);
NuiSetBind(oPlayer, nToken, "checked", jChecked);
NuiSetBindWatch(oPlayer, nToken, "checked", TRUE);
}
void GNW_ShowInfoWindow(object oPlayer, string sTitle, string sText)
{
object oModule = GetModule();
json jWindow = GetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_INFO_WINDOW);
if (jWindow == JsonNull())
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
json jText = NuiText(NuiBind("text"));
jRow = JsonArrayInsert(jRow, jText);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonOK = NuiButton(JsonString("OK"));
jButtonOK = NuiId(jButtonOK, "btn_ok");
jButtonOK = NuiWidth(jButtonOK, 100.0f);
jButtonOK = NuiHeight(jButtonOK, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonOK);
jRow = JsonArrayInsert(jRow, NuiSpacer());
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, NuiBind("title"), NuiRect(-1.0f, -1.0f, 400.0f, 200.0f), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_INFO_WINDOW, jWindow);
}
int nToken = NuiCreate(oPlayer, jWindow, GNW_WINDOW_PREFIX + GNW_INFO_WINDOW);
NuiSetBind(oPlayer, nToken, "title", JsonString(sTitle));
NuiSetBind(oPlayer, nToken, "text", JsonString(sText));
}
void GNW_ShowMenuButton(object oPlayer)
{
object oModule = GetModule();
json jWindow = GetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_MENU_WINDOW);
if (jWindow == JsonNull())
{
json jButton = NuiButtonSelect(JsonString("Menu"), NuiBind("btn_menu"));
jButton = NuiId(jButton, "btn_menu");
jButton = NuiMargin(jButton, 0.0f);
jButton = NuiWidth(jButton, 72.0f);
jButton = NuiHeight(jButton, 28.0f);
jButton = NuiGroup(jButton, FALSE, NUI_SCROLLBARS_NONE);
jButton = NuiMargin(jButton, 0.0f);
jWindow = NuiWindow(jButton, JsonBool(FALSE), NuiBind(NUI_WINDOW_GEOMETRY_BIND), JsonBool(FALSE), JsonBool(FALSE), JsonBool(FALSE), JsonBool(TRUE), JsonBool(FALSE));
SetLocalJson(oModule, GNW_WINDOW_PREFIX + GNW_INFO_WINDOW, jWindow);
}
int nToken = NuiCreate(oPlayer, jWindow, GNW_WINDOW_PREFIX + GNW_MENU_WINDOW);
float fGuiScale = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_SCALE)) / 100.0f;
float fX = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_WIDTH)) - (80.0f * fGuiScale);
float fY = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_HEIGHT)) - (166.0f * fGuiScale);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, NuiRect(fX, fY, 80.0f, 36.0f));
}

68
_module/nss/inc_nui.nss Normal file
View File

@@ -0,0 +1,68 @@
/*
Various NUI Helpers
Created By: Daz
*/
#include "nw_inc_nui"
const string NUI_WINDOW_ROOT_GROUP = "_window_";
const string NUI_WINDOW_TITLE_BIND = "wd_title";
const string NUI_WINDOW_GEOMETRY_BIND = "wd_geometry";
const string NUI_EVENT_OPEN = "open";
const string NUI_EVENT_CLOSE = "close";
const string NUI_EVENT_CLICK = "click";
const string NUI_EVENT_WATCH = "watch";
const string NUI_EVENT_MOUSEDOWN = "mousedown";
const string NUI_EVENT_MOUSEUP = "mouseup";
const string NUI_EVENT_MOUSESCROLL = "mousescroll";
json NuiGetCenteredGeometryRect(object oPlayer, float fWindowWidth, float fWindowHeight);
json NuiSetRectWidth(json jRect, float fWidth);
json NuiSetRectHeight(json jRect, float fHeight);
json NuiInsertRow(json jCol, json jRow);
json NuiHeader(json jHeader, float fHeight = 24.0f, float fWidth = 0.0f);
float NuiGetMouseScrollDelta(json jPayload);
json NuiGetCenteredGeometryRect(object oPlayer, float fWindowWidth, float fWindowHeight)
{
float fGuiScale = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_SCALE)) / 100.0f;
float fX = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_WIDTH) / 2) - ((fWindowWidth * 0.5f) * fGuiScale);
float fY = IntToFloat(GetPlayerDeviceProperty(oPlayer, PLAYER_DEVICE_PROPERTY_GUI_HEIGHT) / 2) - ((fWindowHeight * 0.5f) * fGuiScale);
return NuiRect(fX, fY, fWindowWidth, fWindowHeight);
}
json NuiSetRectWidth(json jRect, float fWidth)
{
return JsonObjectSet(jRect, "w", JsonFloat(fWidth));
}
json NuiSetRectHeight(json jRect, float fHeight)
{
return JsonObjectSet(jRect, "h", JsonFloat(fHeight));
}
json NuiInsertRow(json jCol, json jRow)
{
return JsonArrayInsert(jCol, NuiRow(jRow));
}
json NuiHeader(json jHeader, float fHeight = 24.0f, float fWidth = 0.0f)
{
json jLabel = NuiLabel(jHeader, JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_MIDDLE));
jLabel = NuiGroup(jLabel, TRUE, NUI_SCROLLBARS_NONE);
jLabel = NuiHeight(jLabel, fHeight);
if (fWidth > 0.0f)
jLabel = NuiWidth(jLabel, fWidth);
return jLabel;
}
float NuiGetMouseScrollDelta(json jPayload)
{
return JsonGetFloat(JsonObjectGet(JsonObjectGet(jPayload, "mouse_scroll"), "y"));
}

View File

@@ -0,0 +1,561 @@
/*
NUI Persistent Chest System
Created By: Daz
*/
#include "inc_nui"
#include "inc_util"
//void main (){}
const string PC_NUI_WINDOW_ID = "PCWINDOW";
const string PC_NUI_GOLD_WINDOW_ID = "PCGOLDWINDOW";
const string PC_UUID_ARRAY = "PC_UUID_ARRAY";
const string PC_WINDOW_JSON = "PC_WINDOW_JSON";
const string PC_GOLD_WINDOW_JSON = "PC_GOLD_WINDOW_JSON";
const string PC_TARGETING_MODE = "PC_TARGETING_MODE";
const string PC_GEOMETRY_JSON = "PC_GEOMETRY_JSON";
const string PC_SEARCH_STRING = "PC_SEARCH_STRING";
const int PC_MAX_ITEMS = 500; // The max number of items a player can store in their chest
const int PC_ITEM_WITHDRAW_BATCH = 5; // How many items to deserialize at the same time
const float PC_ITEM_WITHDRAW_DELAY = 0.25f; // The delay between deserialization batches
const int PC_USE_SEARCH_BUTTON = FALSE; // Set to true to use a Search button instead of searching on text change
const int PC_SAVE_ITEM_OBJECT_STATE = TRUE; // Save local variables / temporary itemproperties when serializing items
const int PC_OPEN_INVENTORY_WINDOW = TRUE; // Open the inventory when opening a persistent chest
string PC_GetDatabaseName(object oPlayer);
string PC_GetTableName(object oPlayer);
void PC_InitializeDatabase(object oPlayer);
void PC_CreateNUIWindow(object oPlayer, int bOpenInventory = PC_OPEN_INVENTORY_WINDOW);
void PC_EnterDepositMode(object oPlayer);
void PC_HandleNUIEvents(object oPlayer, string sWindowId, int nToken, string sType, string sElement, int nArrayIndex);
int PC_GetStoredItemAmount(object oPlayer);
void PC_HandleDepositEvent(object oPlayer, object oItem, vector vPosition);
void PC_UpdateItemList(object oPlayer, int nToken);
void PC_WithdrawItems(object oPlayer, int nToken);
int PC_GetStoredGold(object oPlayer);
void PC_SetStoredGold(object oPlayer, int nGold);
void PC_ModifyStoredGold(object oPlayer, int nAmount);
void PC_UpdateGoldData(object oPlayer, int nToken);
void PC_CreateNUIGoldWindow(object oPlayer);
string PC_GetDatabaseName(object oPlayer)
{
return "PC_" + GetPCPublicCDKey(oPlayer, TRUE);
}
string PC_GetTableName(object oPlayer)
{
return "PC_ITEMS";
}
void PC_InitializeDatabase(object oPlayer)
{// Boring database stuff
string sDatabase = PC_GetDatabaseName(oPlayer);
string sTable = PC_GetTableName(oPlayer);
string sQuery = "SELECT name FROM sqlite_master WHERE type='table' AND name=@table;";
sqlquery sql = SqlPrepareQueryCampaign(sDatabase, sQuery);
SqlBindString(sql, "@table", sTable);
if (!SqlStep(sql))
{
string sQuery = "CREATE TABLE IF NOT EXISTS " + sTable + " (" +
"item_uuid TEXT NOT NULL, " +
"item_name TEXT NOT NULL, " +
"item_baseitem INTEGER NOT NULL, " +
"item_stacksize INTEGER NOT NULL, " +
"item_iconresref TEXT NOT NULL, " +
"item_data TEXT_NOT NULL, " +
"PRIMARY KEY(item_uuid));";
sqlquery sql = SqlPrepareQueryCampaign(sDatabase, sQuery);
SqlStep(sql);
}
}
void PC_CreateNUIWindow(object oPlayer, int bOpenInventory = PC_OPEN_INVENTORY_WINDOW)
{
if (NuiFindWindow(oPlayer, PC_NUI_WINDOW_ID))
return;// Don't re-open the window if it is already open
PC_InitializeDatabase(oPlayer);
json jWindow = GetLocalJson(GetModule(), PC_WINDOW_JSON);
if (jWindow == JsonNull())
{// For efficiency, we only build the window json once and store it in a local json on the module
json jCol;// Our main column to hold all the rows
json jRow;// A reusable row
jCol = JsonArray();// Create an array to hold our rows
jRow = JsonArray();// Create an array to hold our row elements
{// Our first row only has a progress bar to indicate the amount of items stored
json jProgress = NuiProgress(NuiBind("progress"));// The actual progress of the progress bar is bound to 'progress'
jProgress = NuiTooltip(jProgress, NuiBind("progress_tooltip"));// Here we add a tooltip and its bind to update it
jRow = JsonArrayInsert(jRow, jProgress);
json jButtonGold = NuiButtonImage(JsonString("iit_gold_001"));
jButtonGold = NuiTooltip(jButtonGold, NuiBind("gold_tooltip"));
jButtonGold = NuiId(jButtonGold, "btn_gold");
jButtonGold = NuiWidth(jButtonGold, 35.0f);
jButtonGold = NuiHeight(jButtonGold, 35.0f);
//jRow = JsonArrayInsert(jRow, jButtonGold);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));// Add the row to the column
jRow = JsonArray();
{// The second row has the search bar, a clear button, and if enabled, a search button
json jSearch = NuiTextEdit(JsonString("Search..."), NuiBind("search"), 64, FALSE);// A simple search bar, we bind whatever the user types to 'search'
jRow = JsonArrayInsert(jRow, jSearch);
json jClearButton = NuiButton(JsonString("X"));
jClearButton = NuiId(jClearButton, "btn_clear");// We give the button an id so we can get its click event
jClearButton = NuiEnabled(jClearButton, NuiBind("btn_clear"));// Here we enable the enabling or disabling of the button.. :D bound to 'btn_clear'
jClearButton = NuiWidth(jClearButton, 35.0f);// Width...
jClearButton = NuiHeight(jClearButton, 35.0f);// Height...
jRow = JsonArrayInsert(jRow, jClearButton);
if (PC_USE_SEARCH_BUTTON)
{
json jSearchButton = NuiButton(JsonString("Search"));
jSearchButton = NuiId(jSearchButton, "btn_search");
jSearchButton = NuiWidth(jSearchButton, 100.0f);
jSearchButton = NuiHeight(jSearchButton, 35.0f);
jRow = JsonArrayInsert(jRow, jSearchButton);
}
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{// The third row has the item list, here we also create the template for every list item to use
json jListTemplate = JsonArray();
{
json jImage = NuiImage(NuiBind("icons"), JsonInt(NUI_ASPECT_FIT100), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
jImage = NuiMargin(jImage, 0.0f);
jImage = NuiTooltip(jImage, NuiBind("tooltips"));
jImage = NuiGroup(jImage, TRUE, NUI_SCROLLBARS_NONE);
jListTemplate = JsonArrayInsert(jListTemplate, NuiListTemplateCell(jImage, 32.0f, FALSE));
json jCheck = NuiCheck(NuiBind("names"), NuiBind("selected"));
jListTemplate = JsonArrayInsert(jListTemplate, NuiListTemplateCell(jCheck, 0.0f, TRUE));
}
json jList = NuiList(jListTemplate, NuiBind("icons"), 32.0f);
jRow = JsonArrayInsert(jRow, jList);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{// The final row has a bunch of buttons, exciting
json jButtonWithdraw = NuiButton(JsonString("Withdraw"));
jButtonWithdraw = NuiId(jButtonWithdraw, "btn_withdraw");
jButtonWithdraw = NuiEnabled(jButtonWithdraw, NuiBind("btn_withdraw"));
jButtonWithdraw = NuiWidth(jButtonWithdraw, 100.0f);
jButtonWithdraw = NuiHeight(jButtonWithdraw, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonWithdraw);
json jButtonDeposit = NuiButton(JsonString("Deposit"));
jButtonDeposit = NuiId(jButtonDeposit, "btn_deposit");
jButtonDeposit = NuiEnabled(jButtonDeposit, NuiBind("btn_deposit"));
jButtonDeposit = NuiWidth(jButtonDeposit, 100.0f);
jButtonDeposit = NuiHeight(jButtonDeposit, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonDeposit);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonClose = NuiButton(JsonString("Close"));
jButtonClose = NuiId(jButtonClose, "btn_close");
jButtonClose = NuiWidth(jButtonClose, 100.0f);
jButtonClose = NuiHeight(jButtonClose, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonClose);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);// Turn our column variable into a column
// Bind the window title and geometry, disable resizing and set collapsed to false
jWindow = NuiWindow(jRoot, NuiBind(NUI_WINDOW_TITLE_BIND), NuiBind(NUI_WINDOW_GEOMETRY_BIND), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(GetModule(), PC_WINDOW_JSON, jWindow);// Store the created window for reuse
}
// We let the user move the window and it'll save the position in a local
// In the case of the local not existing we position the window in its default position
json jGeometry = GetLocalJson(oPlayer, PC_GEOMETRY_JSON);
if (jGeometry == JsonNull())
jGeometry = NuiRect(400.0f, 0.0f, 400.0f, 500.0f);
// Actually create the window for the player!
int nToken = NuiCreate(oPlayer, jWindow, PC_NUI_WINDOW_ID);
// If the search button is not enabled we watch the search bind for changes in the search box
NuiSetBindWatch(oPlayer, nToken, "search", !PC_USE_SEARCH_BUTTON);
// Watch for players moving the window
NuiSetBindWatch(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, TRUE);
// Here we set the initial window position, either to the default position or wherever the player last left it
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, jGeometry);
// Setting the window title
NuiSetBind(oPlayer, nToken, NUI_WINDOW_TITLE_BIND, JsonString(GetName(oPlayer) + "'s Persistent Chest"));
// We clear the search bar, this'll invoke the watch event, if enabled, where we do some other stuff
NuiSetBind(oPlayer, nToken, "search", JsonString(""));
// Enable or disable the clear button depending on if we have the search button enabled
// If the search button is disabled we only enable it if the search bar actually has text
NuiSetBind(oPlayer, nToken, "btn_clear", JsonBool(PC_USE_SEARCH_BUTTON));
if (PC_USE_SEARCH_BUTTON)
{
DeleteLocalString(oPlayer, PC_SEARCH_STRING);
PC_UpdateItemList(oPlayer, nToken);
}
PC_UpdateGoldData(oPlayer, nToken);
if (bOpenInventory)
PopUpGUIPanel(oPlayer, GUI_PANEL_INVENTORY);
}
void PC_EnterDepositMode(object oPlayer)
{
SetLocalInt(oPlayer, PC_TARGETING_MODE, TRUE);
EnterTargetingMode(oPlayer, OBJECT_TYPE_ITEM);
}
void PC_HandleNUIEvents(object oPlayer, string sWindowId, int nToken, string sType, string sElement, int nArrayIndex)
{
if (sWindowId == PC_NUI_WINDOW_ID)
{
if (sType == NUI_EVENT_CLICK)
{
if (sElement == "btn_withdraw")
{// The withdraw button is clicked, withdraw some items
PC_WithdrawItems(oPlayer, nToken);
}
else if (sElement == "btn_deposit")
{// The deposit button is clicked, enter deposit mode
PC_EnterDepositMode(oPlayer);
}
else if (sElement == "btn_close")
{// Murder the poor window
NuiDestroy(oPlayer, nToken);
nToken = NuiFindWindow(oPlayer, PC_NUI_GOLD_WINDOW_ID);
if (nToken)
NuiDestroy(oPlayer, nToken);
}
else if (sElement == "btn_search")
{// Handle the search button if enabled
SetLocalString(oPlayer, PC_SEARCH_STRING, JsonGetString(NuiGetBind(oPlayer, nToken, "search")));
PC_UpdateItemList(oPlayer, nToken);
}
else if (sElement == "btn_clear")
{// Handle the clear button
NuiSetBind(oPlayer, nToken, "search", JsonString(""));
if (PC_USE_SEARCH_BUTTON)
{
DeleteLocalString(oPlayer, PC_SEARCH_STRING);
PC_UpdateItemList(oPlayer, nToken);
}
}
else if (sElement == "btn_gold")
{
PC_CreateNUIGoldWindow(oPlayer);
}
}
else if (sType == NUI_EVENT_WATCH)
{
if (sElement == NUI_WINDOW_GEOMETRY_BIND)
{// Whenever the geometry of the window changes this watch event will fire, we just get the bind's value and store it in a local
SetLocalJson(oPlayer, PC_GEOMETRY_JSON, NuiGetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND));
}
else if (sElement == "search")
{// Whenever the player types in the search bar this watch event fires, we enable or disable the clear button depending on string length and set the search string in a local
string sSearch = JsonGetString(NuiGetBind(oPlayer, nToken, "search"));
NuiSetBind(oPlayer, nToken, "btn_clear", JsonBool(GetStringLength(sSearch)));
SetLocalString(oPlayer, PC_SEARCH_STRING, sSearch);
PC_UpdateItemList(oPlayer, nToken);
}
}
else if (sType == NUI_EVENT_CLOSE)
{
nToken = NuiFindWindow(oPlayer, PC_NUI_GOLD_WINDOW_ID);
if (nToken)
NuiDestroy(oPlayer, nToken);
}
}
else if (sWindowId == PC_NUI_GOLD_WINDOW_ID)
{
if (sType == NUI_EVENT_CLICK)
{
if (sElement == "btn_deposit")
{
//SendMessageToPC(oPlayer, "Depositing: " + JsonGetString(NuiGetBind(oPlayer, nToken, "amount")) + " gold");
}
else if (sElement == "btn_close")
{
NuiDestroy(oPlayer, nToken);
}
}
}
}
int PC_GetStoredItemAmount(object oPlayer)
{// Wrapper to get the number of stored items
string sQuery = "SELECT COUNT(*) FROM " + PC_GetTableName(oPlayer);
sqlquery sql = SqlPrepareQueryCampaign(PC_GetDatabaseName(oPlayer), sQuery);
return SqlStep(sql) ? SqlGetInt(sql, 0) : 0;
}
void PC_HandleDepositEvent(object oPlayer, object oItem, vector vPosition)
{// This function is fired in the module on player target event
if (!GetLocalInt(oPlayer, PC_TARGETING_MODE))// Make sure it only fires if we're actually depositing an item
return;
DeleteLocalInt(oPlayer, PC_TARGETING_MODE);
if (!GetIsObjectValid(oItem) || GetLocalInt(oItem, "PC_ITEM_DESTROYED") || GetObjectType(oItem) != OBJECT_TYPE_ITEM)
return;// Check the validness of the item
if (GetItemPossessor(oItem) != oPlayer)
{// Check if we actually own the item
SendMessageToPC(oPlayer, "You do not own '" + GetName(oItem) + "'");
return;
}
int nStoredItems = PC_GetStoredItemAmount(oPlayer);
if (nStoredItems >= PC_MAX_ITEMS)
{// Check if we have space...
SendMessageToPC(oPlayer, "Your persistent chest is full, withdraw an item first.");
return;
}
// Here we grab a bunch of data and actually store stuff in the database
// We store the item as json because we need that to get some additional icon data anyway
string sItemUUID = GetObjectUUID(oItem);
int nItemBaseItem = GetBaseItemType(oItem);
string sItemName = Util_GetItemName(oItem, GetIdentified(oItem));
int nItemStackSize = GetItemStackSize(oItem);
json jItemData = ObjectToJson(oItem, PC_SAVE_ITEM_OBJECT_STATE);
string sItemIconResRef = Util_GetIconResref(oItem, jItemData, nItemBaseItem);
string sQuery = "INSERT INTO " + PC_GetTableName(oPlayer) +
"(item_uuid, item_name, item_baseitem, item_stacksize, item_iconresref, item_data) " +
"VALUES(@item_uuid, @item_name, @item_baseitem, @item_stacksize, @item_iconresref, @item_data);";
sqlquery sql = SqlPrepareQueryCampaign(PC_GetDatabaseName(oPlayer), sQuery);
SqlBindString(sql, "@item_uuid", sItemUUID);
SqlBindString(sql, "@item_name", sItemName);
SqlBindInt(sql, "@item_baseitem", nItemBaseItem);
SqlBindInt(sql, "@item_stacksize", nItemStackSize);
SqlBindString(sql, "@item_iconresref", sItemIconResRef);
SqlBindJson(sql, "@item_data", jItemData);
SqlStep(sql);
int nToken = NuiFindWindow(oPlayer, PC_NUI_WINDOW_ID);
if (nToken)
{// Check if the window is still open, if so update the item list and enter targeting mode again if we still have space
PC_UpdateItemList(oPlayer, nToken);
if(++nStoredItems != PC_MAX_ITEMS)
{
PC_EnterDepositMode(oPlayer);
}
}
// Dunno if this is needed but maybe somehow the player clicks on an item before it is destroyed, we'll try to prevent that
SetLocalInt(oItem, "PC_ITEM_DESTROYED", TRUE);
DestroyObject(oItem);
}
void PC_UpdateItemList(object oPlayer, int nToken)
{
json jUUIDArray = JsonArray();// This array is stored on the player so we can map an array index to an items UUID
json jNamesArray = JsonArray();// This array is for the list and stores all the names of the items
json jTooltipArray = JsonArray();// This array is for the list and stores all the baseitem tooltips of the items
json jIconsArray = JsonArray();// This array is for the list and stores all the icons of the items
json jSelectedArray = JsonArray();// This array is for the list and stores wether an item is selected or not
int nNumItems = PC_GetStoredItemAmount(oPlayer);
string sSearch = GetLocalString(oPlayer, PC_SEARCH_STRING);
string sQuery = "SELECT item_uuid, item_name, item_baseitem, item_stacksize, item_iconresref FROM " +
PC_GetTableName(oPlayer) + (sSearch != "" ? " WHERE item_name LIKE @search" : "") +" ORDER BY item_baseitem ASC, item_name ASC;";
sqlquery sql = SqlPrepareQueryCampaign(PC_GetDatabaseName(oPlayer), sQuery);
if (sSearch != "")
SqlBindString(sql, "@search", "%" + sSearch + "%");
while (SqlStep(sql))
{// Loop all items
string sUUID = SqlGetString(sql, 0);
string sName = SqlGetString(sql, 1);
int nBaseItem = SqlGetInt(sql, 2);
int nStackSize = SqlGetInt(sql, 3);
string sIconResRef = SqlGetString(sql, 4);
jUUIDArray = JsonArrayInsert(jUUIDArray, JsonString(sUUID));// Store its UUId
jNamesArray = JsonArrayInsert(jNamesArray, JsonString(sName + (nStackSize > 1 ? " (x" + IntToString(nStackSize) + ")" : "")));// Store its name and stacksize if >1
jTooltipArray = JsonArrayInsert(jTooltipArray, JsonString(GetStringByStrRef(StringToInt(Get2DAString("baseitems", "Name", nBaseItem)))));// Store the tooltip
jIconsArray = JsonArrayInsert(jIconsArray, JsonString(sIconResRef));// Store the icon
jSelectedArray = JsonArrayInsert(jSelectedArray, JsonBool(FALSE));// Set the item as not selected
}
SetLocalJson(oPlayer, PC_UUID_ARRAY, jUUIDArray);// We save this array on the player for later use
// Set the list binds to the new arrays
NuiSetBind(oPlayer, nToken, "icons", jIconsArray);
NuiSetBind(oPlayer, nToken, "names", jNamesArray);
NuiSetBind(oPlayer, nToken, "tooltips", jTooltipArray);
NuiSetBind(oPlayer, nToken, "selected", jSelectedArray);
// Update our progress tracker and its tooltip
NuiSetBind(oPlayer, nToken, "progress", JsonFloat(IntToFloat(nNumItems) / IntToFloat(PC_MAX_ITEMS)));
NuiSetBind(oPlayer, nToken, "progress_tooltip", JsonString(IntToString(nNumItems) + " / " + IntToString(PC_MAX_ITEMS) + " Items Stored"));
// Disable or enable the withdraw and deposit buttons depending on item amounts
NuiSetBind(oPlayer, nToken, "btn_withdraw", JsonBool(nNumItems > 0));
NuiSetBind(oPlayer, nToken, "btn_deposit", JsonBool(nNumItems < PC_MAX_ITEMS));
}
void VoidJsonToObject(json jObject, location locLocation, object oOwner = OBJECT_INVALID, int bLoadObjectState = FALSE)
{
JsonToObject(jObject, locLocation, oOwner, bLoadObjectState);
}
void PC_WithdrawItems(object oPlayer, int nToken)
{
json jSelected = NuiGetBind(oPlayer, nToken, "selected");// This gets the array of selected items
int nNumItems = JsonGetLength(jSelected);
if (!nNumItems)// Why bother doing anything if we have no items stored
return;
string sDatabase = PC_GetDatabaseName(oPlayer);
string sTable = PC_GetTableName(oPlayer);
string sSelectQuery = "SELECT item_data FROM " + sTable + " WHERE item_uuid=@uuid;";
string sDeleteQuery = "DELETE FROM " + sTable + " WHERE item_uuid=@uuid;";
json jUUIDs = GetLocalJson(oPlayer, PC_UUID_ARRAY);// Get our array index <-> uuid map
location locPlayer = GetLocation(oPlayer);
int nItem, nWithdrawnItems = 0;
float fDelay = PC_ITEM_WITHDRAW_DELAY;
sqlquery sql;
for (nItem = 0; nItem < nNumItems; nItem++)
{// Loop all items, this will need improving for big amounts of items
if (JsonGetInt(JsonArrayGet(jSelected, nItem)))
{// Check if the item is selected, if so we withdraw it
string sUUID = JsonGetString(JsonArrayGet(jUUIDs, nItem));// Use the index of the item to get its uuid from the array we stored earlier
sql = SqlPrepareQueryCampaign(sDatabase, sSelectQuery);
SqlBindString(sql, "@uuid", sUUID);
if (SqlStep(sql))
{
json jItem = SqlGetJson(sql, 0);
sql = SqlPrepareQueryCampaign(sDatabase, sDeleteQuery);// Delete the database entry of the item
SqlBindString(sql, "@uuid", sUUID);
SqlStep(sql);
DelayCommand(fDelay, VoidJsonToObject(jItem, locPlayer, oPlayer, PC_SAVE_ITEM_OBJECT_STATE));
nWithdrawnItems++;
}
}
if (nWithdrawnItems == PC_ITEM_WITHDRAW_BATCH)
{// Here we do some stuff to not withdraw all items at once
nWithdrawnItems = 0;
fDelay += PC_ITEM_WITHDRAW_DELAY;
}
}
// Finally update the item list again
PC_UpdateItemList(oPlayer, nToken);
}
int PC_GetStoredGold(object oPlayer)
{
return GetCampaignInt(PC_GetTableName(oPlayer), "PC_GOLD");
}
void PC_SetStoredGold(object oPlayer, int nGold)
{
SetCampaignInt(PC_GetTableName(oPlayer), "PC_GOLD", nGold);
}
void PC_ModifyStoredGold(object oPlayer, int nAmount)
{
PC_SetStoredGold(oPlayer, PC_GetStoredGold(oPlayer) + nAmount);
}
void PC_UpdateGoldData(object oPlayer, int nToken)
{
NuiSetBind(oPlayer, nToken, "gold_tooltip", JsonString("Gold: " + IntToString(PC_GetStoredGold(oPlayer))));
}
void PC_CreateNUIGoldWindow(object oPlayer)
{
if (NuiFindWindow(oPlayer, PC_NUI_GOLD_WINDOW_ID))
return;
json jWindow = GetLocalJson(GetModule(), PC_GOLD_WINDOW_JSON);
if (jWindow == JsonNull())
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
json jTextEdit = NuiTextEdit(JsonString("Amount..."), NuiBind("amount"), 10, FALSE);
jTextEdit = NuiWidth(jTextEdit, 110.0f);
jRow = JsonArrayInsert(jRow, jTextEdit);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonWithdraw = NuiButton(JsonString("Withdraw"));
jButtonWithdraw = NuiId(jButtonWithdraw, "btn_withdraw");
jButtonWithdraw = NuiEnabled(jButtonWithdraw, NuiBind("btn_withdraw"));
jButtonWithdraw = NuiWidth(jButtonWithdraw, 90.0f);
jButtonWithdraw = NuiHeight(jButtonWithdraw, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonWithdraw);
json jButtonDeposit = NuiButton(JsonString("Deposit"));
jButtonDeposit = NuiId(jButtonDeposit, "btn_deposit");
jButtonDeposit = NuiEnabled(jButtonDeposit, NuiBind("btn_deposit"));
jButtonDeposit = NuiWidth(jButtonDeposit, 90.0f);
jButtonDeposit = NuiHeight(jButtonDeposit, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonDeposit);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jRow = JsonArray();
{
json jImage = NuiImage(JsonString("iit_gold_001"), JsonInt(NUI_ASPECT_FIT100), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
jImage = NuiGroup(jImage, FALSE, NUI_SCROLLBARS_NONE);
jImage = NuiWidth(jImage, 35.0f);
jImage = NuiHeight(jImage, 35.0f);
jRow = JsonArrayInsert(jRow, jImage);
json jLabel = NuiLabel(JsonString("Gold: "), JsonInt(NUI_HALIGN_LEFT), JsonInt(NUI_VALIGN_MIDDLE));
jLabel = NuiWidth(jLabel, 40.0f);
jRow = JsonArrayInsert(jRow, jLabel);
json jAmount = NuiLabel(NuiBind("stored_gold"), JsonInt(NUI_HALIGN_LEFT), JsonInt(NUI_VALIGN_MIDDLE));
jAmount = NuiWidth(jAmount, 100.0f);
jRow = JsonArrayInsert(jRow, jAmount);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonDeposit = NuiButton(JsonString("Close"));
jButtonDeposit = NuiId(jButtonDeposit, "btn_close");
jButtonDeposit = NuiWidth(jButtonDeposit, 90.0f);
jButtonDeposit = NuiHeight(jButtonDeposit, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonDeposit);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, JsonBool(FALSE), NuiRect(-1.0f, -1.0f, 375.0f, 135.0f), JsonBool(FALSE), JsonBool(FALSE), JsonBool(FALSE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(GetModule(), PC_GOLD_WINDOW_JSON, jWindow);
}
int nToken = NuiCreate(oPlayer, jWindow, PC_NUI_GOLD_WINDOW_ID);
NuiSetBind(oPlayer, nToken, "stored_gold", JsonString("5000000"));
}

View File

@@ -0,0 +1,660 @@
/*
Multiplayer TicTacToe NUI Game
Created By: Daz
*/
#include "inc_nui"
#include "inc_util"
const string TTT_WINDOW_ID = "TTT_GAME";
const string TTT_WINDOW_JSON = "TTT_WINDOW_JSON";
const string TTT_WINDOW_GEOMETRY = "TTT_WINDOW_GEOMETRY";
const float TTT_WINDOW_WIDTH = 400.0f;
const float TTT_WINDOW_HEIGHT = 340.0f;
const float TTT_LINE_LENGTH = 50.0f;
const float TTT_LINE_THICKNESS = 10.0f;
const string TTT_GRID_LINE_LEFT = "ttt_ll";
const string TTT_GRID_LINE_RIGHT = "ttt_lr";
const string TTT_GRID_LINE_TOP = "ttt_lt";
const string TTT_GRID_LINE_BOTTOM = "ttt_lb";
const string TTT_GRID_LINE_CENTER = "ttt_lc";
const string TTT_GRID_LINE_VERTICAL = "ttt_lmv";
const string TTT_GRID_LINE_HORIZONTAL = "ttt_lmh";
const string TTT_BIND_HEADER_TEXT = "header_text";
const string TTT_BIND_PORTRAIT_ONE = "po_player1";
const string TTT_BIND_PORTRAIT_TWO = "po_player2";
const string TTT_BIND_INFO_TEXT = "info_text";
const string TTT_BIND_BUTTON_RESTART = "btn_restart";
const string TTT_IMAGE_BLANK = "ttt_blank";
const string TTT_IMAGE_CIRCLE = "ttt_circle";
const string TTT_IMAGE_CROSS = "ttt_cross";
const string TTT_CELL_PREFIX = "ttt_cell_";
const int TTT_NUM_CELLS = 9;
const string TTT_CELL_VALUE_BLANK = "";
const string TTT_CELL_VALUE_CIRCLE = "O";
const string TTT_CELL_VALUE_CROSS = "X";
const string TTT_BOARD = "TTT_BOARD";
const string TTT_PLAYER_ID = "TTT_PLAYER_ID";
const string TTT_PLAYER_ONE = "TTT_PLAYER_ONE";
const string TTT_PLAYER_TWO = "TTT_PLAYER_TWO";
const string TTT_CURRENT_PLAYER = "TTT_CURRENT_PLAYER";
const string TTT_WIN_CONDITIONS = "TTT_WIN_CONDITIONS";
const string TTT_GRID_STATE = "TTT_GRID_STATE";
const string TTT_GAME_STATE = "TTT_GAME_STATE";
const int TTT_GAME_STATE_NONE = 0;
const int TTT_GAME_STATE_WAITING = 1;
const int TTT_GAME_STATE_PLAYING = 2;
const int TTT_GAME_STATE_GAME_OVER = 3;
string TTT_IntToCellString(int nCell);
json TTT_InsertGridLine(json jCol, string sImage, float fWidth, float fHeight);
json TTT_InsertGridCell(json jCol, int nCell);
json TTT_GetTicTacToeGridJson();
json TTT_GetWindowJson();
void TTT_SetRestartButtonEnabled(object oGame, int bEnabled);
int TTT_GetPlayerWindowToken(object oPlayer);
void TTT_SetGame(object oPlayer, object oGame);
object TTT_GetGame(object oPlayer);
void TTT_DeleteGame(object oPlayer);
void TTT_SetPlayerId(object oPlayer, string sPlayerId);
string TTT_GetPlayerId(object oPlayer);
void TTT_DeletePlayerId(object oPlayer);
void TTT_SetPlayer(object oGame, string sPlayerId, object oPlayer);
object TTT_GetPlayer(object oGame, string sPlayerId);
void TTT_DeletePlayer(object oGame, string sPlayerId);
void TTT_SetCurrentPlayer(object oGame, object oPlayer);
object TTT_GetCurrentPlayer(object oGame);
string TTT_GetCurrentPlayerSymbol(object oGame);
object TTT_GetOpponent(object oGame);
object TTT_GetValidatedPlayer(object oGame, string sPlayerId);
int TTT_GetIsPlayerValid(object oGame, string sPlayerId);
int TTT_GetNumPlayers(object oGame);
string TTT_GetFreePlayerId(object oGame);
object TTT_GetSinglePlayer(object oGame);
void TTT_UpdateBind(object oPlayer, string sBindName, json jValue);
void TTT_UpdateBindsForPlayers(object oGame, string sBindName, json jValue);
int TTT_CreateGameWindow(object oPlayer);
void TTT_UpdateStaticBinds(object oGame);
void TTT_UpdateGridCellBind(object oGame, int nCell, json jImage);
string TTT_GetImageFromSymbol(string sSymbol);
void TTT_UpdateGridBinds(object oGame);
void TTT_UpdateInfoTextBind(object oGame, string sText);
void TTT_AddPlayerToGame(object oPlayer, object oGame = OBJECT_SELF);
void TTT_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex, json jPayload);
json TTT_InsertWinCondition(json jWinConditions, int nValueA, int nValueB, int nValueC);
json TTT_GetWinConditions();
json TTT_GetGridState(object oGame);
void TTT_SetGridState(object oGame, json jGridState);
void TTT_ClearGridState(object oGame);
string TTT_GetGridStateCell(object oGame, int nCell);
void TTT_SetGridStateCell(object oGame, int nCell, string sValue);
int TTT_GetGameState(object oGame);
void TTT_SetGameState(object oGame, int nGameState, string sInfoText);
void TTT_UpdateGameState(object oGame);
int TTT_GetIsDraw(object oGame);
int TTT_GetIsWin(object oGame);
void TTT_RestartGame(object oGame);
void TTT_RemovePlayerFromGame(object oGame, object oPlayer);
void TTT_HandlePlayerExit(object oPlayer);
string TTT_IntToCellString(int nCell)
{
return TTT_CELL_PREFIX + IntToString(nCell);
}
json TTT_InsertGridLine(json jCol, string sImage, float fWidth, float fHeight)
{
json jImage = NuiImage(JsonString(sImage), JsonInt(NUI_ASPECT_EXACT), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_MIDDLE));
jImage = NuiMargin(jImage, 0.0f);
jImage = NuiWidth(jImage, fWidth);
jImage = NuiHeight(jImage, fHeight);
return JsonArrayInsert(jCol, NuiMargin(NuiRow(JsonArrayInsert(JsonArray(), jImage)), 0.0f));
}
json TTT_InsertGridCell(json jCol, int nCell)
{
string sCell = TTT_IntToCellString(nCell);
json jImage = NuiImage(NuiBind(sCell), JsonInt(NUI_ASPECT_EXACT), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_MIDDLE));
jImage = NuiId(jImage, sCell);
jImage = NuiMargin(jImage, 0.0f);
jImage = NuiWidth(jImage, TTT_LINE_LENGTH);
jImage = NuiHeight(jImage, TTT_LINE_LENGTH);
return JsonArrayInsert(jCol, NuiMargin(NuiRow(JsonArrayInsert(JsonArray(), jImage)), 0.0f));
}
json TTT_GetTicTacToeGridJson()
{
json jCol = JsonArray(), jRow;
jRow = JsonArray();
{
json jSubCol, jSubRow;
jSubCol = JsonArray();
jSubCol = TTT_InsertGridCell(jSubCol, 0);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_LEFT, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 3);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_LEFT, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 6);
jRow = JsonArrayInsert(jRow, NuiMargin(NuiCol(jSubCol), 0.0f));
jSubCol = JsonArray();
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_TOP, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_CENTER, TTT_LINE_THICKNESS, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_VERTICAL, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jSubCol = TTT_InsertGridLine(jSubCol,TTT_GRID_LINE_CENTER, TTT_LINE_THICKNESS, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_BOTTOM, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jRow = JsonArrayInsert(jRow, NuiMargin(NuiCol(jSubCol), 0.0f));
jSubCol = JsonArray();
jSubCol = TTT_InsertGridCell(jSubCol, 1);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_HORIZONTAL, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 4);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_HORIZONTAL, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 7);
jRow = JsonArrayInsert(jRow, NuiMargin(NuiCol(jSubCol), 0.0f));
jSubCol = JsonArray();
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_TOP, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_CENTER, TTT_LINE_THICKNESS, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_VERTICAL, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_CENTER, TTT_LINE_THICKNESS, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_BOTTOM, TTT_LINE_THICKNESS, TTT_LINE_LENGTH);
jRow = JsonArrayInsert(jRow, NuiMargin(NuiCol(jSubCol), 0.0f));
jSubCol = JsonArray();
jSubCol = TTT_InsertGridCell(jSubCol, 2);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_RIGHT, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 5);
jSubCol = TTT_InsertGridLine(jSubCol, TTT_GRID_LINE_RIGHT, TTT_LINE_LENGTH, TTT_LINE_THICKNESS);
jSubCol = TTT_InsertGridCell(jSubCol, 8);
jRow = JsonArrayInsert(jRow, NuiMargin(NuiCol(jSubCol), 0.0f));
}
jCol = NuiInsertRow(jCol, jRow);
return NuiCol(jCol);
}
json TTT_GetWindowJson()
{
json jWindow = GetLocalJson(GetModule(), TTT_WINDOW_JSON);
if (jWindow == JsonNull())
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
json jHeader = NuiHeader(NuiBind(TTT_BIND_HEADER_TEXT));
jRow = JsonArrayInsert(jRow, jHeader);
}
jCol = NuiInsertRow(jCol, jRow);
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jPlayer1 = NuiImage(NuiBind(TTT_BIND_PORTRAIT_ONE), JsonInt(NUI_ASPECT_EXACT), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
jPlayer1 = NuiMargin(jPlayer1, 0.0f);
jPlayer1 = NuiGroup(jPlayer1, TRUE, NUI_SCROLLBARS_NONE);
jPlayer1 = NuiWidth(jPlayer1, 64.0f);
jPlayer1 = NuiHeight(jPlayer1, 100.0f);
jRow = JsonArrayInsert(jRow, jPlayer1);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jTicTacToe = TTT_GetTicTacToeGridJson();
jTicTacToe = NuiGroup(jTicTacToe, FALSE, NUI_SCROLLBARS_NONE);
jTicTacToe = NuiWidth(jTicTacToe, 182.0f);
jTicTacToe = NuiHeight(jTicTacToe, 182.0f);
jRow = JsonArrayInsert(jRow, jTicTacToe);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jPlayer2 = NuiImage(NuiBind(TTT_BIND_PORTRAIT_TWO), JsonInt(NUI_ASPECT_EXACT), JsonInt(NUI_HALIGN_CENTER), JsonInt(NUI_VALIGN_TOP));
jPlayer2 = NuiMargin(jPlayer2, 0.0f);
jPlayer2 = NuiGroup(jPlayer2, TRUE, NUI_SCROLLBARS_NONE);
jPlayer2 = NuiWidth(jPlayer2, 64.0f);
jPlayer2 = NuiHeight(jPlayer2, 100.0f);
jRow = JsonArrayInsert(jRow, jPlayer2);
jRow = JsonArrayInsert(jRow, NuiSpacer());
}
jCol = NuiInsertRow(jCol, jRow);
jRow = JsonArray();
{
json jHeader = NuiHeader(NuiBind(TTT_BIND_INFO_TEXT));
jRow = JsonArrayInsert(jRow, jHeader);
}
jCol = NuiInsertRow(jCol, jRow);
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButton = NuiButton(JsonString("Restart"));
jButton = NuiId(jButton, TTT_BIND_BUTTON_RESTART);
jButton = NuiEnabled(jButton, NuiBind(TTT_BIND_BUTTON_RESTART));
jButton = NuiHeight(jButton, 30.0f);
jRow = JsonArrayInsert(jRow, jButton);
jRow = JsonArrayInsert(jRow, NuiSpacer());
}
jCol = NuiInsertRow(jCol, jRow);
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
}
jCol = NuiInsertRow(jCol, jRow);
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, JsonString("TicTacToe"), NuiBind(NUI_WINDOW_GEOMETRY_BIND), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(GetModule(), TTT_WINDOW_JSON, jWindow);
}
return jWindow;
}
void TTT_SetRestartButtonEnabled(object oGame, int bEnabled) { TTT_UpdateBindsForPlayers(oGame, TTT_BIND_BUTTON_RESTART, JsonBool(bEnabled)); }
int TTT_GetPlayerWindowToken(object oPlayer) { return NuiFindWindow(oPlayer, TTT_WINDOW_ID); }
void TTT_SetGame(object oPlayer, object oGame) { SetLocalObject(oPlayer, TTT_BOARD, oGame); }
object TTT_GetGame(object oPlayer) { return GetLocalObject(oPlayer, TTT_BOARD); }
void TTT_DeleteGame(object oPlayer) { DeleteLocalObject(oPlayer, TTT_BOARD); }
void TTT_SetPlayerId(object oPlayer, string sPlayerId) { SetLocalString(oPlayer, TTT_PLAYER_ID, sPlayerId); }
string TTT_GetPlayerId(object oPlayer) { return GetLocalString(oPlayer, TTT_PLAYER_ID); }
void TTT_DeletePlayerId(object oPlayer) { DeleteLocalString(oPlayer, TTT_PLAYER_ID); }
void TTT_SetPlayer(object oGame, string sPlayerId, object oPlayer) { SetLocalObject(oGame, sPlayerId, oPlayer); }
object TTT_GetPlayer(object oGame, string sPlayerId) { return GetLocalObject(oGame, sPlayerId); }
void TTT_DeletePlayer(object oGame, string sPlayerId) { DeleteLocalObject(oGame, sPlayerId); }
void TTT_SetCurrentPlayer(object oGame, object oPlayer) { SetLocalObject(oGame, TTT_CURRENT_PLAYER, oPlayer); }
object TTT_GetCurrentPlayer(object oGame) { return GetLocalObject(oGame, TTT_CURRENT_PLAYER); }
string TTT_GetCurrentPlayerSymbol(object oGame)
{
return TTT_GetPlayerId(TTT_GetCurrentPlayer(oGame)) == TTT_PLAYER_ONE ? TTT_CELL_VALUE_CROSS : TTT_CELL_VALUE_CIRCLE;
}
object TTT_GetOpponent(object oGame)
{
return TTT_GetPlayerId(TTT_GetCurrentPlayer(oGame)) == TTT_PLAYER_ONE ? TTT_GetPlayer(oGame, TTT_PLAYER_TWO) : TTT_GetPlayer(oGame, TTT_PLAYER_ONE);
}
object TTT_GetValidatedPlayer(object oGame, string sPlayerId)
{
return TTT_GetIsPlayerValid(oGame, sPlayerId) ? TTT_GetPlayer(oGame, sPlayerId) : OBJECT_INVALID;
}
int TTT_GetIsPlayerValid(object oGame, string sPlayerId)
{
object oPlayer = TTT_GetPlayer(oGame, sPlayerId);
return GetIsObjectValid(oPlayer) && TTT_GetPlayerWindowToken(oPlayer);
}
int TTT_GetNumPlayers(object oGame)
{
return TTT_GetIsPlayerValid(oGame, TTT_PLAYER_ONE) + TTT_GetIsPlayerValid(oGame, TTT_PLAYER_TWO);
}
string TTT_GetFreePlayerId(object oGame)
{
if (!TTT_GetIsPlayerValid(oGame, TTT_PLAYER_ONE))
return TTT_PLAYER_ONE;
else if (!TTT_GetIsPlayerValid(oGame, TTT_PLAYER_TWO))
return TTT_PLAYER_TWO;
else
return "IF_THIS_HAPPENS_YOU_DID_SOMETHING_WRONG";
}
object TTT_GetSinglePlayer(object oGame)
{
object oPlayer = TTT_GetValidatedPlayer(oGame, TTT_PLAYER_ONE);
if (oPlayer != OBJECT_INVALID)
return oPlayer;
else
{
oPlayer = TTT_GetValidatedPlayer(oGame, TTT_PLAYER_TWO);
if (oPlayer != OBJECT_INVALID)
return oPlayer;
}
return OBJECT_INVALID;
}
void TTT_UpdateBind(object oPlayer, string sBindName, json jValue)
{
if (GetIsObjectValid(oPlayer))
{
int nToken = TTT_GetPlayerWindowToken(oPlayer);
if (nToken)
NuiSetBind(oPlayer, nToken, sBindName, jValue);
}
}
void TTT_UpdateBindsForPlayers(object oGame, string sBindName, json jValue)
{
TTT_UpdateBind(TTT_GetValidatedPlayer(oGame, TTT_PLAYER_ONE), sBindName, jValue);
TTT_UpdateBind(TTT_GetValidatedPlayer(oGame, TTT_PLAYER_TWO), sBindName, jValue);
}
int TTT_CreateGameWindow(object oPlayer)
{
int nToken = NuiCreate(oPlayer, TTT_GetWindowJson(), TTT_WINDOW_ID);
json jGeometry = GetLocalJson(oPlayer, TTT_WINDOW_GEOMETRY);
if (jGeometry == JsonNull())
jGeometry = NuiRect(100.0f, 100.0f, TTT_WINDOW_WIDTH, TTT_WINDOW_HEIGHT);
NuiSetBindWatch(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, TRUE);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, jGeometry);
return nToken;
}
void TTT_UpdateStaticBinds(object oGame)
{
object oPlayerOne = TTT_GetValidatedPlayer(oGame, TTT_PLAYER_ONE);
object oPlayerTwo = TTT_GetValidatedPlayer(oGame, TTT_PLAYER_TWO);
string sNamePlayerOne = oPlayerOne == OBJECT_INVALID ? "???" : GetName(oPlayerOne);
string sNamePlayerTwo = oPlayerTwo == OBJECT_INVALID ? "???" : GetName(oPlayerTwo);
string sHeader = sNamePlayerOne + " vs. " + sNamePlayerTwo;
TTT_UpdateBindsForPlayers(oGame, TTT_BIND_HEADER_TEXT, JsonString(sHeader));
string sPortraitPlayerOne = oPlayerOne == OBJECT_INVALID ? "po_hu_m_99_m" : GetPortraitResRef(oPlayerOne) + "m";
string sPortraitPlayerTwo = oPlayerTwo == OBJECT_INVALID ? "po_hu_m_99_m" : GetPortraitResRef(oPlayerTwo) + "m";
TTT_UpdateBindsForPlayers(oGame, TTT_BIND_PORTRAIT_ONE, JsonString(sPortraitPlayerOne));
TTT_UpdateBindsForPlayers(oGame, TTT_BIND_PORTRAIT_TWO, JsonString(sPortraitPlayerTwo));
}
void TTT_UpdateGridCellBind(object oGame, int nCell, json jImage)
{
TTT_UpdateBindsForPlayers(oGame, TTT_IntToCellString(nCell), jImage);
}
string TTT_GetImageFromSymbol(string sSymbol)
{
return sSymbol == TTT_CELL_VALUE_BLANK ? TTT_IMAGE_BLANK : sSymbol == TTT_CELL_VALUE_CIRCLE ? TTT_IMAGE_CIRCLE : TTT_IMAGE_CROSS;
}
void TTT_UpdateGridBinds(object oGame)
{
json jGridState = TTT_GetGridState(oGame);
int nCell, nNumCells = JsonGetLength(jGridState);
for (nCell = 0; nCell < nNumCells; nCell++)
{
string sImage = TTT_GetImageFromSymbol(JsonGetString(JsonArrayGet(jGridState, nCell)));
TTT_UpdateGridCellBind(oGame, nCell, JsonString(sImage));
}
}
void TTT_UpdateInfoTextBind(object oGame, string sText)
{
TTT_UpdateBindsForPlayers(oGame, TTT_BIND_INFO_TEXT, JsonString(sText));
}
void TTT_AddPlayerToGame(object oPlayer, object oGame = OBJECT_SELF)
{
if (TTT_GetPlayerWindowToken(oPlayer))
{
FloatingTextStringOnCreature("TicTacToe: Player Already In Game", oPlayer, FALSE);
return;
}
int nNumPlayers = TTT_GetNumPlayers(oGame);
if (nNumPlayers == 2)
{
FloatingTextStringOnCreature("TicTacToe: Max Number Of Players Reached", oPlayer, FALSE);
return;
}
if (!nNumPlayers)
{
TTT_ClearGridState(oGame);
TTT_SetGameState(oGame, TTT_GAME_STATE_NONE, "");
TTT_DeletePlayer(oGame, TTT_PLAYER_ONE);
TTT_DeletePlayer(oGame, TTT_PLAYER_TWO);
}
string sPlayerId = TTT_GetFreePlayerId(oGame);
TTT_SetPlayer(oGame, sPlayerId, oPlayer);
TTT_SetPlayerId(oPlayer, sPlayerId);
TTT_SetGame(oPlayer, oGame);
TTT_CreateGameWindow(oPlayer);
TTT_UpdateStaticBinds(oGame);
TTT_UpdateGridBinds(oGame);
TTT_UpdateGameState(oGame);
}
void TTT_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex, json jPayload)
{
if (sType == NUI_EVENT_MOUSEUP)
{
if (GetStringLeft(sElement, GetStringLength(TTT_CELL_PREFIX)) == TTT_CELL_PREFIX)
{
object oGame = TTT_GetGame(oPlayer);
object oCurrentPlayer = TTT_GetCurrentPlayer(oGame);
int nCell = StringToInt(GetStringRight(sElement, 1));
int nGameState = TTT_GetGameState(oGame);
if (nGameState != TTT_GAME_STATE_PLAYING ||
oCurrentPlayer != oPlayer ||
TTT_GetGridStateCell(oGame, nCell) != TTT_CELL_VALUE_BLANK)
return;
string sSymbol = TTT_GetCurrentPlayerSymbol(oGame);
TTT_SetGridStateCell(oGame, nCell, sSymbol);
TTT_UpdateGridCellBind(oGame, nCell, JsonString(TTT_GetImageFromSymbol(sSymbol)));
if (TTT_GetIsWin(oGame))
TTT_SetGameState(oGame, TTT_GAME_STATE_GAME_OVER, GetName(oCurrentPlayer) + " won!");
else if (TTT_GetIsDraw(oGame))
TTT_SetGameState(oGame, TTT_GAME_STATE_GAME_OVER, "Draw!");
else
{
object oOpponent = TTT_GetOpponent(oGame);
TTT_SetGameState(oGame, TTT_GAME_STATE_PLAYING, GetName(oOpponent) + "'s turn!");
TTT_SetCurrentPlayer(oGame, oOpponent);
}
}
}
else if (sType == NUI_EVENT_CLICK)
{
if (sElement == TTT_BIND_BUTTON_RESTART)
{
object oGame = TTT_GetGame(oPlayer);
if (TTT_GetGameState(oGame) == TTT_GAME_STATE_GAME_OVER)
TTT_RestartGame(oGame);
}
}
else if (sType == NUI_EVENT_CLOSE)
{
if (sElement == NUI_WINDOW_ROOT_GROUP)
{
object oGame = TTT_GetGame(oPlayer);
TTT_RemovePlayerFromGame(oGame, oPlayer);
TTT_RestartGame(oGame);
}
}
else if (sType == NUI_EVENT_WATCH)
{
if (sElement == NUI_WINDOW_GEOMETRY_BIND)
{
SetLocalJson(oPlayer, TTT_WINDOW_GEOMETRY, NuiGetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND));
}
}
}
json TTT_InsertWinCondition(json jWinConditions, int nValueA, int nValueB, int nValueC)
{
json jWinCondition = JsonArray();
jWinCondition = JsonArrayInsert(jWinCondition, JsonInt(nValueA));
jWinCondition = JsonArrayInsert(jWinCondition, JsonInt(nValueB));
jWinCondition = JsonArrayInsert(jWinCondition, JsonInt(nValueC));
return JsonArrayInsert(jWinConditions, jWinCondition);
}
json TTT_GetWinConditions()
{
json jWinConditions = GetLocalJson(GetModule(), TTT_WIN_CONDITIONS);
if (jWinConditions == JsonNull())
{
jWinConditions = JsonArray();
jWinConditions = TTT_InsertWinCondition(jWinConditions, 0, 1, 2);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 3, 4, 5);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 6, 7, 8);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 0, 3, 6);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 1, 4, 7);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 2, 5, 8);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 0, 4, 8);
jWinConditions = TTT_InsertWinCondition(jWinConditions, 2, 4, 6);
SetLocalJson(GetModule(), TTT_WIN_CONDITIONS, jWinConditions);
}
return jWinConditions;
}
json TTT_GetGridState(object oGame)
{
return GetLocalJson(oGame, TTT_GRID_STATE);
}
void TTT_SetGridState(object oGame, json jGridState)
{
SetLocalJson(oGame, TTT_GRID_STATE, jGridState);
}
void TTT_ClearGridState(object oGame)
{
json jGridState = JsonArray();
int nCell;
for (nCell = 0; nCell < TTT_NUM_CELLS; nCell++)
{
jGridState = JsonArrayInsert(jGridState, JsonString(TTT_CELL_VALUE_BLANK));
}
TTT_SetGridState(oGame, jGridState);
}
string TTT_GetGridStateCell(object oGame, int nCell)
{
json jGridState = TTT_GetGridState(oGame);
return JsonGetString(JsonArrayGet(jGridState, nCell));
}
void TTT_SetGridStateCell(object oGame, int nCell, string sValue)
{
json jGridState = TTT_GetGridState(oGame);
jGridState = JsonArraySet(jGridState, nCell, JsonString(sValue));
TTT_SetGridState(oGame, jGridState);
}
int TTT_GetGameState(object oGame)
{
return GetLocalInt(oGame, TTT_GAME_STATE);
}
void TTT_SetGameState(object oGame, int nGameState, string sInfoText)
{
SetLocalInt(oGame, TTT_GAME_STATE, nGameState);
TTT_UpdateInfoTextBind(oGame, sInfoText);
if (nGameState == TTT_GAME_STATE_GAME_OVER)
TTT_SetRestartButtonEnabled(oGame, TRUE);
else
TTT_SetRestartButtonEnabled(oGame, FALSE);
}
void TTT_UpdateGameState(object oGame)
{
int nNumPlayers = TTT_GetNumPlayers(oGame);
if (nNumPlayers == 1)
{
TTT_SetGameState(oGame, TTT_GAME_STATE_WAITING, "Waiting for opponent...");
TTT_SetCurrentPlayer(oGame, TTT_GetSinglePlayer(oGame));
}
else if (nNumPlayers == 2)
{
TTT_SetGameState(oGame, TTT_GAME_STATE_PLAYING, GetName(TTT_GetCurrentPlayer(oGame)) + "'s turn!");
}
}
int TTT_GetIsDraw(object oGame)
{
json jGridState = TTT_GetGridState(oGame);
int nCell, nNumCells = JsonGetLength(jGridState);
for (nCell = 0; nCell < nNumCells; nCell++)
{
if (JsonGetString(JsonArrayGet(jGridState, nCell)) == TTT_CELL_VALUE_BLANK)
return FALSE;
}
return TRUE;
}
int TTT_GetIsWin(object oGame)
{
json jGridState = TTT_GetGridState(oGame);
json jWinConditions = TTT_GetWinConditions();
int nWinCondition, nNumWinConditions = JsonGetLength(jWinConditions);
for(nWinCondition = 0; nWinCondition < nNumWinConditions; nWinCondition++)
{
json jWinCondition = JsonArrayGet(jWinConditions, nWinCondition);
string sValueA = JsonGetString(JsonArrayGet(jGridState, JsonGetInt(JsonArrayGet(jWinCondition, 0))));
string sValueB = JsonGetString(JsonArrayGet(jGridState, JsonGetInt(JsonArrayGet(jWinCondition, 1))));
string sValueC = JsonGetString(JsonArrayGet(jGridState, JsonGetInt(JsonArrayGet(jWinCondition, 2))));
if (sValueA == TTT_CELL_VALUE_BLANK || sValueB == TTT_CELL_VALUE_BLANK ||sValueC == TTT_CELL_VALUE_BLANK)
continue;
if (sValueA == sValueB && sValueB == sValueC)
return TRUE;
}
return FALSE;
}
void TTT_RestartGame(object oGame)
{
TTT_SetGameState(oGame, TTT_GAME_STATE_NONE, "");
TTT_ClearGridState(oGame);
TTT_UpdateStaticBinds(oGame);
TTT_UpdateGridBinds(oGame);
TTT_UpdateGameState(oGame);
}
void TTT_RemovePlayerFromGame(object oGame, object oPlayer)
{
NuiDestroy(oPlayer, TTT_GetPlayerWindowToken(oPlayer));
TTT_DeletePlayer(oGame, TTT_GetPlayerId(oPlayer));
TTT_DeleteGame(oPlayer);
TTT_DeletePlayerId(oPlayer);
}
void TTT_HandlePlayerExit(object oPlayer)
{
if (TTT_GetPlayerWindowToken(oPlayer))
{
object oGame = TTT_GetGame(oPlayer);
TTT_RemovePlayerFromGame(oGame, oPlayer);
TTT_RestartGame(oGame);
}
}

View File

@@ -0,0 +1,305 @@
/*
Visual Transform NUI Window
Created By: Daz
*/
#include "inc_nui"
const string VT_WINDOW_ID = "VT";
const string VT_WINDOW_JSON = "VT_WINDOW_JSON";
const string VT_WINDOW_GEOMETRY = "VT_WINDOW_GEOMETRY";
const string VT_VALUE_BIND_PREFIX = "vt_value_";
const string VT_DISPLAY_BIND_PREFIX = "vt_display_";
const string VT_CLEAR_BUTTON_ID_PREFIX = "vt_btn_clear_";
const string VT_TARGET_BUTTON_ID = "vt_btn_target";
const string VT_CURRENT_TARGET = "VT_CURRENT_TARGET";
const string VT_TARGETING_MODE = "VT_TARGETING_MODE";
const float VT_SCALE_MIN = 1.0f;
const float VT_SCALE_MAX = 10.0f;
const float VT_SCALE_STEP = 0.1f;
const float VT_SCALE_DEFAULT = 1.0f;
const float VT_ROTATE_MIN = 0.0f;
const float VT_ROTATE_MAX = 359.0f;
const float VT_ROTATE_STEP = 1.0f;
const float VT_TRANSLATE_MIN = -10.0f;
const float VT_TRANSLATE_MAX = 10.0f;
const float VT_TRANSLATE_STEP = 0.1f;
void VT_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex, json jPayload);
string VT_GetValueBind(int nType);
string VT_GetDisplayBind(int nType);
string VT_GetClearButtonId(int nType);
json VT_CreateVisualTransformRow(string sName, int nType, float fMin, float fMax, float fStep);
void VT_SetValueBindToCurrentValue(object oPlayer, int nToken, int nType);
void VT_ShowWindow(object oPlayer);
void VT_SetCurrentTarget(object oPlayer, object oTarget);
object VT_GetCurrentTarget(object oPlayer);
void VT_DeleteCurrentTarget(object oPlayer);
void VT_EnterTargetMode(object oPlayer);
void VT_HandleTargetEvent(object oPlayer, object oTarget, vector vPosition);
void VT_HandleNUIEvents(object oPlayer, int nToken, string sType, string sElement, int nArrayIndex, json jPayload)
{
if (sType == NUI_EVENT_CLICK)
{
if (sElement == VT_TARGET_BUTTON_ID)
{
VT_EnterTargetMode(oPlayer);
}
else if (GetStringLeft(sElement, GetStringLength(VT_CLEAR_BUTTON_ID_PREFIX)) == VT_CLEAR_BUTTON_ID_PREFIX)
{
int nType = StringToInt(GetStringRight(sElement, 2));
NuiSetBind(oPlayer, nToken, VT_GetValueBind(nType), JsonFloat(nType == OBJECT_VISUAL_TRANSFORM_SCALE ? VT_SCALE_DEFAULT : 0.0f));
}
}
else if (sType == NUI_EVENT_WATCH)
{
if (GetStringLeft(sElement, GetStringLength(VT_VALUE_BIND_PREFIX)) == VT_VALUE_BIND_PREFIX)
{
int nType = StringToInt(GetStringRight(sElement, 2));
float fValue = JsonGetFloat(NuiGetBind(oPlayer, nToken, VT_GetValueBind(nType)));
object oTarget = VT_GetCurrentTarget(oPlayer);
SetObjectVisualTransform(oTarget, nType, fValue);
NuiSetBind(oPlayer, nToken, VT_GetDisplayBind(nType), JsonString(FloatToString(fValue, 2, 1)));
}
else if (sElement == NUI_WINDOW_GEOMETRY_BIND)
{
SetLocalJson(oPlayer, VT_WINDOW_GEOMETRY, NuiGetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND));
}
}
else if (sType == NUI_EVENT_MOUSESCROLL)
{
if (GetStringLeft(sElement, GetStringLength(VT_VALUE_BIND_PREFIX)) == VT_VALUE_BIND_PREFIX)
{
int nType = StringToInt(GetStringRight(sElement, 2));
float fDelta = NuiGetMouseScrollDelta(jPayload);
float fStep;
switch (nType)
{
case OBJECT_VISUAL_TRANSFORM_SCALE:
fStep = VT_SCALE_STEP;
break;
case OBJECT_VISUAL_TRANSFORM_ROTATE_X:
case OBJECT_VISUAL_TRANSFORM_ROTATE_Y:
case OBJECT_VISUAL_TRANSFORM_ROTATE_Z:
fStep = VT_ROTATE_STEP;
break;
case OBJECT_VISUAL_TRANSFORM_TRANSLATE_X:
case OBJECT_VISUAL_TRANSFORM_TRANSLATE_Y:
case OBJECT_VISUAL_TRANSFORM_TRANSLATE_Z:
fStep = VT_TRANSLATE_STEP;
break;
}
float fCurrentValue = JsonGetFloat(NuiGetBind(oPlayer, nToken, sElement));
NuiSetBind(oPlayer, nToken, sElement, JsonFloat(fCurrentValue + (fDelta > 0.0f ? fStep : -fStep)));
}
}
else if (sType == NUI_EVENT_CLOSE)
{
if (sElement == NUI_WINDOW_ROOT_GROUP)
{
VT_DeleteCurrentTarget(oPlayer);
}
}
}
string VT_GetValueBind(int nType)
{
return VT_VALUE_BIND_PREFIX + IntToString(nType);
}
string VT_GetDisplayBind(int nType)
{
return VT_DISPLAY_BIND_PREFIX + IntToString(nType);
}
string VT_GetClearButtonId(int nType)
{
return VT_CLEAR_BUTTON_ID_PREFIX + IntToString(nType);
}
json VT_CreateVisualTransformRow(string sName, int nType, float fMin, float fMax, float fStep)
{
json jRow = JsonArray();
json jLabel = NuiLabel(JsonString(sName), JsonInt(NUI_HALIGN_LEFT), JsonInt(NUI_VALIGN_MIDDLE));
jLabel = NuiWidth(jLabel, 100.0f);
jRow = JsonArrayInsert(jRow, jLabel);
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jSlider = NuiSliderFloat(NuiBind(VT_GetValueBind(nType)), JsonFloat(fMin), JsonFloat(fMax), JsonFloat(fStep));
jSlider = NuiId(jSlider, VT_GetValueBind(nType));
jSlider = NuiWidth(jSlider, 175.0f);
jRow = JsonArrayInsert(jRow, jSlider);
json jText = NuiTextEdit(JsonString(""), NuiBind(VT_GetDisplayBind(nType)), 10, FALSE);
jText = NuiEnabled(jText, JsonBool(FALSE));
jText = NuiWidth(jText, 75.0f);
jRow = JsonArrayInsert(jRow, jText);
json jButtonClear = NuiButton(JsonString("X"));
jButtonClear = NuiId(jButtonClear, VT_GetClearButtonId(nType));
jButtonClear = NuiWidth(jButtonClear, 35.0f);
jButtonClear = NuiHeight(jButtonClear, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonClear);
return NuiRow(jRow);
}
void VT_SetValueBindToCurrentValue(object oPlayer, int nToken, int nType)
{
object oTarget = VT_GetCurrentTarget(oPlayer);
NuiSetBind(oPlayer, nToken, VT_GetValueBind(nType), JsonFloat(GetObjectVisualTransform(oTarget, nType)));
}
void VT_ShowWindow(object oPlayer)
{
int nToken = NuiFindWindow(oPlayer, VT_WINDOW_ID);
if (nToken)
return;
object oModule = GetModule();
json jWindow = GetLocalJson(oModule, VT_WINDOW_JSON);
if (!JsonGetType(jWindow))
{
json jCol;
json jRow;
jCol = JsonArray();
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
json jButtonTarget = NuiButton(JsonString("Target"));
jButtonTarget = NuiId(jButtonTarget, VT_TARGET_BUTTON_ID);
jButtonTarget = NuiWidth(jButtonTarget, 100.0f);
jButtonTarget = NuiHeight(jButtonTarget, 35.0f);
jRow = JsonArrayInsert(jRow, jButtonTarget);
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Scale", OBJECT_VISUAL_TRANSFORM_SCALE, VT_SCALE_MIN, VT_SCALE_MAX, VT_SCALE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Rotate X", OBJECT_VISUAL_TRANSFORM_ROTATE_X, VT_ROTATE_MIN, VT_ROTATE_MAX, VT_ROTATE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Rotate Y", OBJECT_VISUAL_TRANSFORM_ROTATE_Y, VT_ROTATE_MIN, VT_ROTATE_MAX, VT_ROTATE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Rotate Z", OBJECT_VISUAL_TRANSFORM_ROTATE_Z, VT_ROTATE_MIN, VT_ROTATE_MAX, VT_ROTATE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Translate X", OBJECT_VISUAL_TRANSFORM_TRANSLATE_X, VT_TRANSLATE_MIN, VT_TRANSLATE_MAX, VT_TRANSLATE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Translate Y", OBJECT_VISUAL_TRANSFORM_TRANSLATE_Y, VT_TRANSLATE_MIN, VT_TRANSLATE_MAX, VT_TRANSLATE_STEP));
jCol = JsonArrayInsert(jCol, VT_CreateVisualTransformRow("Translate Z", OBJECT_VISUAL_TRANSFORM_TRANSLATE_Z, VT_TRANSLATE_MIN, VT_TRANSLATE_MAX, VT_TRANSLATE_STEP));
jRow = JsonArray();
{
jRow = JsonArrayInsert(jRow, NuiSpacer());
}
jCol = JsonArrayInsert(jCol, NuiRow(jRow));
json jRoot = NuiCol(jCol);
jWindow = NuiWindow(jRoot, NuiBind(NUI_WINDOW_TITLE_BIND), NuiBind(NUI_WINDOW_GEOMETRY_BIND), JsonBool(FALSE), JsonNull(), JsonBool(TRUE), JsonBool(FALSE), JsonBool(TRUE));
SetLocalJson(oModule, VT_WINDOW_JSON, jWindow);
}
nToken = NuiCreate(oPlayer, jWindow, VT_WINDOW_ID);
json jGeometry = GetLocalJson(oPlayer, VT_WINDOW_GEOMETRY);
if (!JsonGetType(jGeometry))
jGeometry = NuiGetCenteredGeometryRect(oPlayer, 450.0f, 425.0f);
VT_SetCurrentTarget(oPlayer, oPlayer);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_SCALE), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_ROTATE_X), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_ROTATE_Y), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_ROTATE_Z), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_TRANSLATE_X), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_TRANSLATE_Y), TRUE);
NuiSetBindWatch(oPlayer, nToken, VT_GetValueBind(OBJECT_VISUAL_TRANSFORM_TRANSLATE_Z), TRUE);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_SCALE);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_X);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_Y);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_Z);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_X);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_Y);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_Z);
NuiSetBindWatch(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, TRUE);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_GEOMETRY_BIND, jGeometry);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_TITLE_BIND, JsonString("Visually Transforming: " + GetName(oPlayer)));
}
void VT_SetCurrentTarget(object oPlayer, object oTarget)
{
SetLocalObject(oPlayer, VT_CURRENT_TARGET, oTarget);
}
object VT_GetCurrentTarget(object oPlayer)
{
return GetLocalObject(oPlayer, VT_CURRENT_TARGET);
}
void VT_DeleteCurrentTarget(object oPlayer)
{
DeleteLocalObject(oPlayer, VT_CURRENT_TARGET);
}
void VT_EnterTargetMode(object oPlayer)
{
SetLocalInt(oPlayer, VT_TARGETING_MODE, TRUE);
EnterTargetingMode(oPlayer, OBJECT_TYPE_CREATURE | OBJECT_TYPE_PLACEABLE | OBJECT_TYPE_DOOR | OBJECT_TYPE_TILE);
}
void VT_HandleTargetEvent(object oPlayer, object oTarget, vector vPosition)
{
if (!GetLocalInt(oPlayer, VT_TARGETING_MODE))
return;
DeleteLocalInt(oPlayer, VT_TARGETING_MODE);
if (!GetIsObjectValid(oTarget))
return;
if (GetArea(oPlayer) == oTarget)
{
oTarget = GetNearestObjectToLocation(OBJECT_TYPE_CREATURE | OBJECT_TYPE_PLACEABLE | OBJECT_TYPE_DOOR, Location(oTarget, vPosition, 0.0f));
if (!GetIsObjectValid(oTarget))
return;
}
else
{
int nObjectType = GetObjectType(oTarget);
if (nObjectType != OBJECT_TYPE_CREATURE &&
nObjectType != OBJECT_TYPE_PLACEABLE &&
nObjectType != OBJECT_TYPE_DOOR)
return;
}
int nToken = NuiFindWindow(oPlayer, VT_WINDOW_ID);
if (!nToken)
return;
VT_SetCurrentTarget(oPlayer, oTarget);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_SCALE);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_X);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_Y);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_ROTATE_Z);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_X);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_Y);
VT_SetValueBindToCurrentValue(oPlayer, nToken, OBJECT_VISUAL_TRANSFORM_TRANSLATE_Z);
NuiSetBind(oPlayer, nToken, NUI_WINDOW_TITLE_BIND, JsonString("Visually Transforming: " + GetName(oTarget)));
}

129
_module/nss/inc_util.nss Normal file
View File

@@ -0,0 +1,129 @@
/*
Utility Functions
Created By: Daz
*/
#include "nw_inc_gff"
#include "nw_inc_nui"
string Util_GetIconResref(object oItem, json jItem, int nBaseItem);
string Util_GetIconResref(object oItem, json jItem, int nBaseItem)
{
if (nBaseItem == BASE_ITEM_CLOAK) // Cloaks use PLTs so their default icon doesn't really work
return "iit_cloak";
else if (nBaseItem == BASE_ITEM_SPELLSCROLL || nBaseItem == BASE_ITEM_ENCHANTED_SCROLL)
{// Scrolls get their icon from the cast spell property
if (GetItemHasItemProperty(oItem, ITEM_PROPERTY_CAST_SPELL))
{
itemproperty ip = GetFirstItemProperty(oItem);
while (GetIsItemPropertyValid(ip))
{
if (GetItemPropertyType(ip) == ITEM_PROPERTY_CAST_SPELL)
return Get2DAString("iprp_spells", "Icon", GetItemPropertySubType(ip));
ip = GetNextItemProperty(oItem);
}
}
}
else if (Get2DAString("baseitems", "ModelType", nBaseItem) == "0")
{// Create the icon resref for simple modeltype items
json jSimpleModel = GffGetByte(jItem, "ModelPart1");
if (JsonGetType(jSimpleModel) == JSON_TYPE_INTEGER)
{
string sSimpleModelId = IntToString(JsonGetInt(jSimpleModel));
while (GetStringLength(sSimpleModelId) < 3)// Padding...
{
sSimpleModelId = "0" + sSimpleModelId;
}
string sDefaultIcon = Get2DAString("baseitems", "DefaultIcon", nBaseItem);
switch (nBaseItem)
{
case BASE_ITEM_MISCSMALL:
case BASE_ITEM_CRAFTMATERIALSML:
sDefaultIcon = "iit_smlmisc_" + sSimpleModelId;
break;
case BASE_ITEM_MISCMEDIUM:
case BASE_ITEM_CRAFTMATERIALMED:
case 112:/* Crafting Base Material */
sDefaultIcon = "iit_midmisc_" + sSimpleModelId;
break;
case BASE_ITEM_MISCLARGE:
sDefaultIcon = "iit_talmisc_" + sSimpleModelId;
break;
case BASE_ITEM_MISCTHIN:
sDefaultIcon = "iit_thnmisc_" + sSimpleModelId;
break;
}
int nLength = GetStringLength(sDefaultIcon);
if (GetSubString(sDefaultIcon, nLength - 4, 1) == "_")// Some items have a default icon of xx_yyy_001, we strip the last 4 symbols if that is the case
sDefaultIcon = GetStringLeft(sDefaultIcon, nLength - 4);
string sIcon = sDefaultIcon + "_" + sSimpleModelId;
if (ResManGetAliasFor(sIcon, RESTYPE_TGA) != "")// Check if the icon actually exists, if not, we'll fall through and return the default icon
return sIcon;
}
}
// For everything else use the item's default icon
return Get2DAString("baseitems", "DefaultIcon", nBaseItem);
}
json Util_GetModelPart(string sDefaultIcon, string sType, json jPart)
{
if (JsonGetType(jPart) == JSON_TYPE_INTEGER)
{
string sModelPart = IntToString(JsonGetInt(jPart));
while (GetStringLength(sModelPart) < 3)
{
sModelPart = "0" + sModelPart;
}
string sIcon = sDefaultIcon + sType + sModelPart;
if (ResManGetAliasFor(sIcon, RESTYPE_TGA) != "")
return JsonString(sIcon);
}
return JsonString("");
}
json Util_GetComplexIconData(json jItem, int nBaseItem);
json Util_GetComplexIconData(json jItem, int nBaseItem)
{
if (Get2DAString("baseitems", "ModelType", nBaseItem) == "2")
{
string sDefaultIcon = Get2DAString("baseitems", "DefaultIcon", nBaseItem);
json jComplexIcon = JsonObject();
jComplexIcon = JsonObjectSet(jComplexIcon, "top", Util_GetModelPart(sDefaultIcon, "_t_", GffGetByte(jItem, "ModelPart3")));
jComplexIcon = JsonObjectSet(jComplexIcon, "middle", Util_GetModelPart(sDefaultIcon, "_m_", GffGetByte(jItem, "ModelPart2")));
jComplexIcon = JsonObjectSet(jComplexIcon, "bottom", Util_GetModelPart(sDefaultIcon, "_b_", GffGetByte(jItem, "ModelPart1")));
return jComplexIcon;
}
return JsonNull();
}
string Util_Get2DAStringByStrRef(string s2DA, string sColumn, int nRow);
string Util_Get2DAStringByStrRef(string s2DA, string sColumn, int nRow)
{
return GetStringByStrRef(StringToInt(Get2DAString(s2DA, sColumn, nRow)));
}
string Util_GetItemName(object oItem, int bIdentified);
string Util_GetItemName(object oItem, int bIdentified)
{
return bIdentified ? GetName(oItem) : Util_Get2DAStringByStrRef("baseitems", "Name", GetBaseItemType(oItem)) + " (Unidentified)";
}
void Util_SendDebugMessage(string sMessage);
void Util_SendDebugMessage(string sMessage)
{
object oPlayer = GetFirstPC();
while (oPlayer != OBJECT_INVALID)
{
SendMessageToPC(oPlayer, sMessage);
oPlayer = GetNextPC();
}
}

19
_module/nss/mod_gui.nss Normal file
View File

@@ -0,0 +1,19 @@
#include "inc_examine"
void main()
{
object oPlayer = GetLastGuiEventPlayer();
int nType = GetLastGuiEventType();
object oTarget = GetLastGuiEventObject();
int nValue = GetLastGuiEventInteger();
if (nType == GUIEVENT_DISABLED_PANEL_ATTEMPT_OPEN)
{
if (nValue == GUI_PANEL_EXAMINE_CREATURE || nValue == GUI_PANEL_EXAMINE_ITEM ||
nValue == GUI_PANEL_EXAMINE_PLACEABLE || nValue == GUI_PANEL_EXAMINE_DOOR)
{
Examine_HandleGUIEvents(oPlayer, oTarget, nValue);
}
}
}

33
_module/nss/mod_nui.nss Normal file
View File

@@ -0,0 +1,33 @@
#include "inc_perchest"
#include "inc_gennui"
#include "inc_examine"
#include "inc_tictactoe"
#include "inc_blackjack"
#include "inc_transform"
void main()
{
object oPlayer = NuiGetEventPlayer();
int nToken = NuiGetEventWindow();
string sWindowId = NuiGetWindowId(oPlayer, nToken);
string sType = NuiGetEventType();
string sElement = NuiGetEventElement();
int nArrayIndex = NuiGetEventArrayIndex();
json jPayload = NuiGetEventPayload();
//SendMessageToPC(oPlayer, "(" + IntToString(nToken) + ":" + sWindowId + ") T: " + sType + ", E: " + sElement + ", AI: " + IntToString(nArrayIndex) + ", P: " + JsonDump(jPayload));
if (sWindowId == PC_NUI_WINDOW_ID || sWindowId == PC_NUI_GOLD_WINDOW_ID)
PC_HandleNUIEvents(oPlayer, sWindowId, nToken, sType, sElement, nArrayIndex);
else if (sWindowId == EXAMINE_NUI_WINDOW_ID)
Examine_HandleNUIEvents(oPlayer, nToken, sType, sElement, nArrayIndex);
else if (sWindowId == TTT_WINDOW_ID)
TTT_HandleNUIEvents(oPlayer, nToken, sType, sElement, nArrayIndex, jPayload);
else if (sWindowId == BJ_WINDOW_ID)
BJ_HandleNUIEvents(oPlayer, nToken, sType, sElement, nArrayIndex, jPayload);
else if (sWindowId == VT_WINDOW_ID)
VT_HandleNUIEvents(oPlayer, nToken, sType, sElement, nArrayIndex, jPayload);
else
GNW_HandleNUIEvents();
}

View File

@@ -0,0 +1,12 @@
#include "inc_perchest"
#include "inc_transform"
void main()
{
object oPlayer = GetLastPlayerToSelectTarget();
object oTarget = GetTargetingModeSelectedObject();
vector vPosition = GetTargetingModeSelectedPosition();
PC_HandleDepositEvent(oPlayer, oTarget, vPosition);
VT_HandleTargetEvent(oPlayer, oTarget, vPosition);
}

View File

@@ -0,0 +1,8 @@
#include "inc_perchest"
void main()
{
object oPlayer = GetLastUsedBy();
PC_CreateNUIWindow(oPlayer);
}

View File

@@ -0,0 +1,28 @@
/*
Created by Omnifarious
Basically all of this is reverse engineered for my purposes.
I owe lots of credit to the Item Storage Device by Rusty Dios.
https://neverwintervault.org/project/nwn1/prefab/item/item-storage-device
*/
//This works to transfer items between charachters on the same CD key & Login Name.
void main()
{
object oPC = GetLastClosedBy();
string sUnique = (GetPCPublicCDKey(oPC) + GetPCPlayerName(oPC));
DestroyCampaignDatabase("DATA"+sUnique);
int i = 0;
object oLoop = GetFirstItemInInventory();
while(oLoop != OBJECT_INVALID)
{
SetCampaignString("DATA"+sUnique, sUnique+IntToString(i), GetResRef(oLoop), OBJECT_SELF);
SetCampaignInt("DATA"+sUnique, GetResRef(oLoop)+IntToString(i), GetNumStackedItems(oLoop), OBJECT_SELF);
i++;
DestroyObject(oLoop);
SendMessageToPC(oPC, GetName(oLoop) + " has been stored successfully");
oLoop = GetNextItemInInventory();
}
SetCampaignInt("DATA"+sUnique, sUnique, i, OBJECT_SELF);
}

View File

@@ -0,0 +1,25 @@
/*
Created by Omnifarious
Basically all of this is reverse engineered for my purposes.
I owe lots of credit to the Item Storage Device by Rusty Dios.
https://neverwintervault.org/project/nwn1/prefab/item/item-storage-device
*/
//This works to transfer items between charachters on the same CD key & Login Name.
void main()
{
object oPC = GetLastOpenedBy();
string sUnique = (GetPCPublicCDKey(oPC) + GetPCPlayerName(oPC));
int i = 0;
int NumItems = GetCampaignInt("DATA"+sUnique, sUnique, OBJECT_SELF);
if(NumItems > 0)
{
while(i < NumItems)
{
string sResRef = GetCampaignString("DATA"+sUnique, sUnique+IntToString(i), OBJECT_SELF);
CreateItemOnObject(sResRef, OBJECT_SELF, GetCampaignInt("DATA"+sUnique, sResRef+IntToString(i), OBJECT_SELF));
i++;
}
}
}

View File

@@ -0,0 +1,46 @@
// Cockatrice Bite - Item Unique OnHit Script
//
// CON based petrification attack
//
//
#include "prc_inc_spells"
//#include "x2_inc_spellhook"
#include "x2_inc_switches"
void main()
{
//:: Declare major variables
object oNPC = OBJECT_SELF;
object oItem = GetSpellCastItem();
object oTarget = GetSpellTargetObject();
int oFort = GetFortitudeSavingThrow(oTarget);
int nDC = 10 + (GetHitDice(oNPC) / 2) + GetAbilityModifier(ABILITY_CONSTITUTION, oNPC);
int bImmune = GetHasFeat(FEAT_IMMUNE_PETRIFICATION, oTarget);
effect ePetrify = EffectPetrify();
effect ePetrifyVis = EffectVisualEffect(VFX_IMP_FORTITUDE_SAVING_THROW_USE);
effect eImmune = EffectVisualEffect(VFX_IMP_MAGIC_RESISTANCE_USE);
//:: Respect Immunity to Petrification
if (bImmune)
{
//SendMessageToPC(OBJECT_SELF, "This creatrure is immune to petrification");
ApplyEffectToObject(DURATION_TYPE_INSTANT, eImmune, oTarget);
return;
}
//:: Cockatrice's are immune to their own petrification attack.
if (GetName(OBJECT_SELF) == GetName(oTarget))
return;
//:: See if the petrification is resisted.
if (!FortitudeSave(oTarget, nDC, SAVING_THROW_TYPE_ALL, oTarget))
{
ApplyEffectToObject(DURATION_TYPE_INSTANT, ePetrifyVis, oTarget);
ApplyEffectToObject(DURATION_TYPE_PERMANENT, ePetrify, oTarget);
}
}

View File

@@ -1,6 +1,8 @@
#include "prc_inc_racial"
//#include "journal_include"
#include "pqj_inc"
#include "inc_examine"
#include "inc_gennui"
void GivePCWands(object oPC)
@@ -130,9 +132,13 @@ void main()
{
//:: Set Major Variables
object oPC = GetEnteringObject();
//:: NUI Magic by Daz
//Examine_DisablePanels(oPC);
PrintString(GetObjectUUID(oPC));
//:: Restore jounral entries
RebuildJournalQuestEntries(GetEnteringObject());
RebuildJournalQuestEntries(oPC);
// Make sure PC isn't set to Plot, for reasons
SetPlotFlag(oPC, FALSE);

View File

@@ -0,0 +1,8 @@
//Make PC read the description on a placeable when he interacts with it
void main()
{
object oPC=GetLastUsedBy();
object oExamine=OBJECT_SELF;
AssignCommand(oPC,ActionExamine(oExamine));
}

View File

@@ -0,0 +1,7 @@
//Allow PC to see his description.
void main()
{
object oPC=GetLastUsedBy();
AssignCommand(oPC,ActionExamine(OBJECT_SELF));
}

View File

@@ -0,0 +1,8 @@
//Make PC read the description on a door when he interacts with it
void main()
{
object oPC=GetClickingObject();
object oExamine=OBJECT_SELF;
AssignCommand(oPC,ActionExamine(oExamine));
}

View File

@@ -0,0 +1,12 @@
//Gives placeable description when opened
void main()
{
object oSelf=OBJECT_SELF;
string sDes=GetDescription(oSelf);
int nDone=GetLocalInt(oSelf,"SPEAKDONE");
if (nDone==TRUE)
return;
SpeakString(sDes);
}

View File

@@ -154,7 +154,7 @@ void main()
{
effect eNatInvis = EffectInvisibility(4);
eNatInvis = SupernaturalEffect(eNatInvis);
eNatInvis = ExtraordinaryEffect(eNatInvis);
//eNatInvis = ExtraordinaryEffect(eNatInvis);
DelayCommand(0.0f, ApplyEffectToObject(DURATION_TYPE_PERMANENT,eNatInvis,OBJECT_SELF));
}

View File

@@ -38,6 +38,11 @@
#include "x2_inc_restsys"
void main()
{
SetEventScript(GetModule(), EVENT_SCRIPT_MODULE_ON_NUI_EVENT, "mod_nui");
SetEventScript(GetModule(), EVENT_SCRIPT_MODULE_ON_PLAYER_TARGET, "mod_target");
SetEventScript(GetModule(), EVENT_SCRIPT_MODULE_ON_PLAYER_GUIEVENT, "mod_gui");
if (GetGameDifficulty() == GAME_DIFFICULTY_CORE_RULES || GetGameDifficulty() == GAME_DIFFICULTY_DIFFICULT)
{
// * Setting the switch below will enable a seperate Use Magic Device Skillcheck for