Sign in to follow this  
djh269

Scripting Help

Recommended Posts

Hello all, 

I was tinkering with the Endar Spire script that specifically places class custom items within the initial Footlocker (k_pend_area01.ncs). 

For some reason whenever I try and use an If statement to check whether the player has a certain skill, it will then place an item within the Footlocker, but regardless of whether I have any points in the skill it still spawns the item and I can't see why. Please see the Important section below as the main script is pretty big: 

 

	}
	if (GetHasSkill(2, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_35, object1, 1);
	}

	if (GetHasSkill(0, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_36, object1, 2);
	}
	if (GetHasSkill(1, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_37, object1, 2);
	}
	if (GetHasSkill(5, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_38, object1, 2);
	}
	if (GetHasSkill(6, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_39, object1, 2);
	}
	if (GetHasSkill(7, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_40, object1, 2);
	}
}
// Globals
	int intGLOB_1 = 0;
	int intGLOB_2 = 1;
	int intGLOB_3 = 2;
	int intGLOB_4 = 3;
	int intGLOB_5 = 4;
	int intGLOB_6 = 5;
	int intGLOB_7 = 6;
	int intGLOB_8 = 7;
	int intGLOB_9 = 8;
	int intGLOB_10 = 9;
	int intGLOB_11 = 10;
	int intGLOB_12 = 11;
	int intGLOB_13 = 12;
	int intGLOB_14 = 13;
	int intGLOB_15 = 14;
	int intGLOB_16 = 15;
	int intGLOB_17 = 16;
	int intGLOB_18 = 17;
	int intGLOB_19 = 18;
	int intGLOB_20 = 19;
	int intGLOB_21 = 1100;
	int intGLOB_22 = (-6);
	int intGLOB_23 = (-5);
	int intGLOB_24 = (-4);
	int intGLOB_25 = (-2);
	int intGLOB_26 = (-1);
	int intGLOB_27 = 0;
	int intGLOB_28 = 1;
	int intGLOB_29 = 2;
	int intGLOB_30 = 3;
	int intGLOB_31 = 4;
	int intGLOB_32 = 5;
	int intGLOB_33 = 6;
	int intGLOB_34 = 3;
	int intGLOB_35 = 4;
	int intGLOB_36 = 5;
	int intGLOB_37 = 6;
	int intGLOB_38 = 7;
	int intGLOB_39 = 1;
	int intGLOB_40 = 2;
	int intGLOB_41 = 3;
	int intGLOB_42 = 4;
	int intGLOB_43 = 5;
	int intGLOB_44 = 6;
	int intGLOB_45 = 7;
	int intGLOB_46 = 8;
	int intGLOB_47 = 9;
	int intGLOB_48 = 10;
	int intGLOB_49 = 11;
	int intGLOB_50 = 12;
	int intGLOB_51 = 13;
	int intGLOB_52 = 14;
	int intGLOB_53 = 15;
	int intGLOB_54 = 16;
	int intGLOB_55 = 17;
	int intGLOB_56 = 18;
	int intGLOB_57 = 19;
	int intGLOB_58 = 20;
	int intGLOB_59 = 21;
	int intGLOB_60 = 22;
	int intGLOB_61 = 23;
	int intGLOB_62 = 24;
	int intGLOB_63 = 25;
	int intGLOB_64 = 26;
	int intGLOB_65 = 27;
	int intGLOB_66 = 28;
	int intGLOB_67 = 29;
	int intGLOB_68 = 30;
	int intGLOB_69 = 59;
	int intGLOB_70 = 0;
	int intGLOB_71 = 1;
	int intGLOB_72 = 2;
	int intGLOB_73 = 29;
	int intGLOB_74 = 30;
	int intGLOB_75 = 34;
	int intGLOB_76 = 35;
	int intGLOB_77 = 36;
	int intGLOB_78 = 37;
	int intGLOB_79 = 38;
	int intGLOB_80 = 39;
	int intGLOB_81 = 41;
	int intGLOB_82 = 42;
	int intGLOB_83 = 46;
	int intGLOB_84 = 47;
	int intGLOB_85 = 15;
	int intGLOB_86 = 10;
	int intGLOB_87 = 5;
	int intGLOB_88 = 2;
	int intGLOB_89;
	int intGLOB_90;
	int intGLOB_91;
	object objectGLOB_1;
	int intGLOB_92;
	int intGLOB_93;
	int intGLOB_94;
	int intGLOB_95;
	int intGLOB_96;
	int intGLOB_97;
	int intGLOB_98 = 1;
	int intGLOB_99 = 2;
	int intGLOB_100 = 3;
	int intGLOB_101 = 20;
	int intGLOB_102 = 21;
	int intGLOB_103 = 22;
	int intGLOB_104 = 23;
	int intGLOB_105 = 24;
	int intGLOB_106 = 25;
	int intGLOB_107 = 26;
	int intGLOB_108 = 27;
	int intGLOB_109 = 28;
	int intGLOB_110 = 31;
	int intGLOB_111 = 32;
	int intGLOB_112 = 33;
	int intGLOB_113 = 40;
	int intGLOB_114 = 43;
	int intGLOB_115 = 44;
	int intGLOB_116 = 45;
	int intGLOB_117 = 48;
	int intGLOB_118 = 49;
	int intGLOB_119 = 50;
	int intGLOB_120 = 51;
	int intGLOB_121 = 52;
	int intGLOB_122 = 53;
	int intGLOB_123 = 54;
	int intGLOB_124 = 55;
	int intGLOB_125 = 56;
	int intGLOB_126 = 57;
	int intGLOB_127 = 58;
	int intGLOB_128 = 60;
	int intGLOB_129 = 61;
	int intGLOB_130 = 62;
	int intGLOB_131 = 63;
	int intGLOB_132 = 64;
	int intGLOB_133 = 65;
	int intGLOB_134 = 66;
	int intGLOB_135 = 67;
	int intGLOB_136 = 68;
	int intGLOB_137 = 69;
	int intGLOB_138 = 70;
	int intGLOB_139 = 71;
	int intGLOB_140 = 72;
	int intGLOB_141 = 1;
	int intGLOB_142 = 2;
	int intGLOB_143 = 3;
	int intGLOB_144 = 4;
	string stringGLOB_1 = "end_trask";
	string stringGLOB_2 = "endwp_tarsk01";
	string stringGLOB_3 = "Carth";

	string stringGLOB_4 = "g_w_blstrrfl001";
	string stringGLOB_5 = "g_i_adrnaline003";
	string stringGLOB_6 = "g_i_medeqpmnt01";

	string stringGLOB_7 = "g_w_blstrpstl004";
	string stringGLOB_8 = "g_i_belt003";
	string stringGLOB_9 = "g_i_implant101";

	string stringGLOB_10 = "g_i_medeqpmnt01";
	string stringGLOB_11 = "g_i_secspike01";
	string stringGLOB_12 = "g_i_progspike01";

	string stringGLOB_13 = "g_i_medeqpmnt02";
	string stringGLOB_14 = "g_w_iongren01";
	string stringGLOB_15 = "g_w_fraggren01";
	string stringGLOB_16 = "g_w_stungren01";
	string stringGLOB_17 = "g_i_adrnaline001";
	string stringGLOB_18 = "g_i_cmbtshot001";
	string stringGLOB_19 = "g_i_belt001";

	string stringGLOB_20 = "g_w_adhsvgren001";
	string stringGLOB_21 = "g_w_iongren01";
	string stringGLOB_22 = "g_w_stungren01";
	string stringGLOB_23 = "g_i_adrnaline002";
	string stringGLOB_24 = "g_i_progspike01";
	string stringGLOB_25 = "g_i_parts01";
	string stringGLOB_26 = "g_i_secspike01";
	string stringGLOB_27 = "g_i_medeqpmnt01";

	string stringGLOB_28 = "g_i_secspike02";
	string stringGLOB_29 = "g_w_adhsvgren001";
	string stringGLOB_30 = "g_i_gauntlet05";
	string stringGLOB_31 = "g_w_stungren01";
	string stringGLOB_32 = "g_i_parts01";
	string stringGLOB_33 = "g_i_mask20";

	int intGLOB_145 = 3;
	int intGLOB_146 = 4;
	int intGLOB_147 = 2;
	int intGLOB_148 = (-1);
	int intGLOB_149 = 0;
	int intGLOB_150 = 1;
	int intGLOB_151 = 2;
	int intGLOB_152 = 3;
	int intGLOB_153 = 4;
	int intGLOB_154 = 5;
	int intGLOB_155 = 6;
	int intGLOB_156 = 7;
	int intGLOB_157 = 8;
	int intGLOB_158 = 9;
	int intGLOB_159 = 10;
	int intGLOB_160 = 11;
	int intGLOB_161 = 12;
	int intGLOB_162 = 13;
	int intGLOB_163 = 14;
	int intGLOB_164 = 15;
	int intGLOB_165 = 16;
	int intGLOB_166 = 17;
	int intGLOB_167 = 18;
	int intGLOB_168 = 19;
	int intGLOB_169 = 20;
	int intGLOB_170 = 21;
	int intGLOB_171 = 22;
	int intGLOB_172 = 28;
	int intGLOB_173 = 29;
	int intGLOB_174 = 30;
	int intGLOB_175 = 31;
	string stringGLOB_34 = "end_locker01";
	string stringGLOB_35 = "g_i_belt010";
	string stringGLOB_36 = "g_i_progspike01";
	string stringGLOB_37 = "g_w_cryobgren001";
	string stringGLOB_38 = "g_i_parts01";
	string stringGLOB_39 = "g_i_secspike01";
	string stringGLOB_40 = "g_i_medeqpmnt01";


// Prototypes
object sub5();
void sub4();
void sub3(object objectParam1, int intParam2, int intParam3);
int sub2(object objectParam1, int intParam2);
int sub1();

object sub5() {
	return GetObjectByTag(stringGLOB_1, 0);
}

void sub4() {
	object object1 = GetObjectByTag(stringGLOB_34, 0);
	int int1 = GetClassByPosition(1, GetFirstPC());
	if ((int1 == 2)) {
		CreateItemOnObject(stringGLOB_10, object1, 4);
		CreateItemOnObject(stringGLOB_11, object1, 5);
		CreateItemOnObject(stringGLOB_12, object1, 4);
		CreateItemOnObject(stringGLOB_28, object1, 5);
		CreateItemOnObject(stringGLOB_29, object1, 1);
		CreateItemOnObject(stringGLOB_30, object1, 1);
		CreateItemOnObject(stringGLOB_31, object1, 4);
		CreateItemOnObject(stringGLOB_32, object1, 4);
		CreateItemOnObject(stringGLOB_33, object1, 1);
	}
	else {
		if ((int1 == 1)) {
			CreateItemOnObject(stringGLOB_7, object1, 1);
			CreateItemOnObject(stringGLOB_8, object1, 1);
			CreateItemOnObject(stringGLOB_9, object1, 1);
			CreateItemOnObject(stringGLOB_20, object1, 4);
			CreateItemOnObject(stringGLOB_21, object1, 2);
			CreateItemOnObject(stringGLOB_22, object1, 2);
			CreateItemOnObject(stringGLOB_23, object1, 2);
			CreateItemOnObject(stringGLOB_24, object1, 5);
			CreateItemOnObject(stringGLOB_25, object1, 5);
			CreateItemOnObject(stringGLOB_26, object1, 2);
			CreateItemOnObject(stringGLOB_27, object1, 4);
		}
		else {
			if ((int1 == 0)) {
				CreateItemOnObject(stringGLOB_4, object1, 1);
				CreateItemOnObject(stringGLOB_5, object1, 2);
				CreateItemOnObject(stringGLOB_6, object1, 5);
                                CreateItemOnObject(stringGLOB_13, object1, 2);
                                CreateItemOnObject(stringGLOB_14, object1, 4);
                                CreateItemOnObject(stringGLOB_15, object1, 4);
                                CreateItemOnObject(stringGLOB_16, object1, 4);
                                CreateItemOnObject(stringGLOB_17, object1, 2);
                                CreateItemOnObject(stringGLOB_18, object1, 4);
                                CreateItemOnObject(stringGLOB_19, object1, 1);
			}
		}
	}
	if (GetHasSkill(2, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_35, object1, 1);
	}
	if (GetHasSkill(0, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_36, object1, 17);
	}
	if (GetHasSkill(1, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_37, object1, 18);
	}
	if (GetHasSkill(5, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_38, object1, 21);
	}
	if (GetHasSkill(6, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_39, object1, 42);
	}
	if (GetHasSkill(7, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_40, object1, 44);
	}
}

void sub3(object objectParam1, int intParam2, int intParam3) {
	int nLevel = GetHitDice(GetFirstPC());
	if ((intParam3 == 1)) {
		if (((((intParam2 == intGLOB_12) || (intParam2 == intGLOB_17)) || (intParam2 == intGLOB_18)) || (intParam2 == intGLOB_19))) {
			GiveXPToCreature(GetFirstPC(), (nLevel * 15));
		}
		else {
			if ((((intParam2 == intGLOB_13) || (intParam2 == intGLOB_20)) || (intParam2 == intGLOB_16))) {
				GiveXPToCreature(GetFirstPC(), (nLevel * 20));
			}
			else {
				if (((intParam2 == intGLOB_14) || (intParam2 == intGLOB_15))) {
					GiveXPToCreature(GetFirstPC(), (nLevel * 10));
				}
			}
		}
	}
	if ((((intParam2 >= 0) && (intParam2 <= 19)) && GetIsObjectValid(objectParam1))) {
		if (((intParam3 == 1) || (intParam3 == 0))) {
			SetLocalBoolean(objectParam1, intParam2, intParam3);
		}
	}
}

int sub2(object objectParam1, int intParam2) {
	int nLocalBool;
	if ((((intParam2 >= 0) && (intParam2 <= 19)) && GetIsObjectValid(objectParam1))) {
		nLocalBool = GetLocalBoolean(objectParam1, intParam2);
		if ((nLocalBool > 0)) {
			return 1;
		}
	}
	return 0;
}

int sub1() {
	int int1;
	if ((sub2(OBJECT_SELF, intGLOB_10) == 0)) {
		int1 = 1;
		sub3(OBJECT_SELF, intGLOB_10, 1);
	}
	return int1;
}

void main() {
	if (GetIsPC(GetEnteringObject())) {
		if (sub1()) {
			SetGlobalFadeOut(0.0, 0.0, 0.0, 0.0, 0.0);
			PlayMovie("01A");
			SetReturnStrref(0, 32228, 0);
			SetGlobalNumber("K_CURRENT_PLANET", 5);
			sub4();
			SetGlobalFadeOut(0.0, 0.0, 0.0, 0.0, 0.0);
			SetGlobalFadeIn(3.0, 1.5, 0.0, 0.0, 0.0);
			DelayCommand(0.1, AssignCommand(sub5(), ActionStartConversation(GetFirstPC(), "m01aa_c01", 0, 0, 1, "", "", "", "", "", "", 0)));
			SetMinOneHP(GetFirstPC(), 1);
		}
	}
}

 

  • Like 1

Share this post


Link to post
Share on other sites

If you want to gate via a specific skill rank, then you need to check for that instead:

// 315: Get the number of ranks that oTarget has in nSkill.
// - nSkill: SKILL_*
// - oTarget
// * Returns -1 if oTarget doesn't have nSkill.
// * Returns 0 if nSkill is untrained.
int GetSkillRank(int nSkill, object oTarget=OBJECT_SELF);

By the way, your script is bloated because of the Include guff. The cleaned up original script is:

#include "k_inc_end"

void main() {
    
    if (GetIsPC(GetEnteringObject()))
        {
            if (HasNeverTriggered())
                {
                    SetGlobalFadeOut();
                    PlayMovie("01A");
                    SetReturnStrref(FALSE, 32228, 0); //String 32228 is "Return To Hideout". Should instead be 38550, "Transit Disabled".
                    SetGlobalNumber("K_CURRENT_PLANET", 5);
                    SpawnStartingEquipment();
                    SetGlobalFadeOut();
                    SetGlobalFadeIn(3.0, 1.5);
                    DelayCommand(0.1, AssignCommand(GetTrask(), ActionStartConversation(GetFirstPC(), "m01aa_c01", FALSE, CONVERSATION_TYPE_CINEMATIC, TRUE)));
                    SetMinOneHP(GetFirstPC(), TRUE);
                }
        }
}

You just want to replace the SpawnStartingEquipment function with your own custom one, but presumably the rest can be pulled from the Includes at compile. However, K1CP made some minor adjustments to the script to fix the player being visible before the first cutscene starts, so I would suggest using that version as a basis instead - https://github.com/KOTORCommunityPatches/K1_Community_Patch/blob/master/Source/k_pend_area01.nss

  • Like 1

Share this post


Link to post
Share on other sites

Thanks for such a quick response!

Yeah the original script is very messy, where does the function: 

SpawnStartingEquipment()

Pull from? From your include script or nwsscript.nss? 

It'll be more concise if I used the include function definitely, I'll also use the getskillrank function as my original line just checked whether you had the skill and not a specific number rank. I just found it odd the original check which gave you a stealth field generator was the only function that actually carried out a check or not. So strange haha. 

Share this post


Link to post
Share on other sites

Okay I'll look into both scripts involved!

Where'd you learn to script so well? The Nwn Lexicon, Lucasforums or anything like that? Most people have backgrounds in programming like Stoffe to get to such such a high level of understanding of scripting, pretty sure its C++ am I right?

Share this post


Link to post
Share on other sites

NWScript is C-like - https://en.wikipedia.org/wiki/NWScript#Syntax

As to my scripting abilities, they are fairly meagre, but enough to brute force a solution most of the time. To my own regret, I avoided scripting for most of the time I have been modding. I dabbled on the odd occasion when scripting was the only solution, but typically relied heavily on outside assistance for even the most basic of tasks. It wasn't until I got involved with K1CP that I really started to wrap my head around how scripting works. Almost entirely out of necessity, since probably 80-90% of the content is partially or entirely script-based. I owe a lot to JCarter426 for shepherding me along and answering all my noobish questions along the way. You could say I now know enough to be dangerous.

The best way to wrap your head around things is to just look at vanilla scripts and examine how and why they do what they do to achieve their desired outcome. Obviously only global scripts have original source available, and most of those aren't commented particularly well, so initially it can be a bit overwhelming when looking at decompiled module scripts. But eventually you'll start to recognise familiar Include functions and drill down to the meat of a given script. And K1CP has all its source available to peruse, so it's worth having a look at some of those to see how we went about fixing things.

  • Like 1

Share this post


Link to post
Share on other sites

The copy and paste function has been my best friend with scripting in the past but I'll definitely keep researching to become better, I'll peruse the K1CP nss files.

I archived all the scripts I could find on Lucasforums years ago but I never set up account recovery on my old email and lost them all haha. 

Thanks for the advice! 🙏

Share this post


Link to post
Share on other sites
3 hours ago, djh269 said:

Where'd you learn to script so well? The Nwn Lexicon, Lucasforums or anything like that? Most people have backgrounds in programming like Stoffe to get to such such a high level of understanding of scripting, pretty sure its C++ am I right?

Maybe see if you get your hands on the old Versus Books 'Neverwinter Nights World Builder Guide', it's got a nice tutorial on nwscript. Different game, obviously, but the language is the same.

Share this post


Link to post
Share on other sites

Hahaha, seems a better option than £24.95 on Amazon hahaha. 

Okay I finally get to implement this within the script: 

}

    if(GetHasSkill(SKILL_STEALTH,GetFirstPC()))
    {
        CreateItemOnObject(STEALTH_UNIT,oLocker);
    }

Instead of: 

}
	if (GetHasSkill(2, GetFirstPC())) {
		CreateItemOnObject(stringGLOB_35, object1, 1);
	}

But why doesn't the vanilla script for k_pend_area01.ncs actually use the include for k_inc_end.ncs?

I can't find it referenced in k_pend_area02.ncs either. Weird. 

Share this post


Link to post
Share on other sites
1 hour ago, djh269 said:

But why doesn't the vanilla script for k_pend_area01.ncs actually use the include for k_inc_end.ncs?

I can't find it referenced in k_pend_area02.ncs either. Weird. 

Are you sure you aren't mistaken? No source exists for either k_pend_area01.ncs or k_pend_area02.ncs; did you reverse compile them? If so, that would explain why you don't see includes.

There could be a number of reasons why a script exists but is unused. For example, rushing to meet the deadline and forgetting to delete the unused script...

Share this post


Link to post
Share on other sites
1 hour ago, djh269 said:

But why doesn't the vanilla script for k_pend_area01.ncs actually use the include for k_inc_end.ncs?

It does. That's what the giant list of variables and functions is. Calling stuff externally via includes is just for the source to make it easier to parse. When the script is compiled, all those functions are pulled into the NCS.

Share this post


Link to post
Share on other sites
2 minutes ago, DarthParametric said:

It does. That's what the giant list of variables and functions is. Calling stuff externally via includes is just for the source to make it easier to parse. When the script is compiled, all those functions are pulled into the NCS.

Oh okay, thanks for the clarification!

If I used this if statement and I was also a Consular and a Soldier, would it still spawn items? If I was technically both?

    else if(nClass == CLASS_TYPE_SOLDIER)
    {
        CreateItemOnObject(SOLDIER_WEAPON,oLocker);

I'm concerned with compatibility with Jedi from the start mod

Share this post


Link to post
Share on other sites

Putting commonly/repeatedly used functions into includes makes for less work. Rather than add it directly to the script you are working on, you can just call it via a linked include. You can see the difference in size this can make for even a very simple script when you compare what DeNCS spits out vs the cleaned up version I posted above. Albeit the Bioware compiler adds a bunch of unnecessary guff not actually used in the script. This is why I said above that eventually you'll start to recognise commonly functions. Take a look at sub3 for example. As soon as you spot those cascading GiveXPToCreature calls, you know that's UT_SetPlotBooleanFlag from k_inc_utility, one of the most commonly used functions you'll encounter. So as you comb through those functions and ID them, you can start to change the function names, remove the superfluous function blocks, and rely on linking the relevant include/s.

Share this post


Link to post
Share on other sites

Thanks for all the excellent advice, I will try and be more concise with my scripting and learn to commonly used functions from the various include files! 

Why doesn't the k_inc_end.nss compile? So annoying haha!

Share this post


Link to post
Share on other sites

I'm pretty sure I remember Stoffe modifying her own nss files when she used her high level Force powers mod and they weren't compiled, thanks for the info!!

Share this post


Link to post
Share on other sites

Hey all, 

I've modified the k_inc_end.nss file and used the below k_pend_area01.ncs file and the script won't work, please see the bottom code for the modified version of k_inc_end.nss

On 10/18/2021 at 6:11 PM, DarthParametric said:

 


#include "k_inc_end"

void main() {
    
    if (GetIsPC(GetEnteringObject()))
        {
            if (HasNeverTriggered())
                {
                    SetGlobalFadeOut();
                    PlayMovie("01A");
                    SetReturnStrref(FALSE, 32228, 0); //String 32228 is "Return To Hideout". Should instead be 38550, "Transit Disabled".
                    SetGlobalNumber("K_CURRENT_PLANET", 5);
                    SpawnStartingEquipment();
                    SetGlobalFadeOut();
                    SetGlobalFadeIn(3.0, 1.5);
                    DelayCommand(0.1, AssignCommand(GetTrask(), ActionStartConversation(GetFirstPC(), "m01aa_c01", FALSE, CONVERSATION_TYPE_CINEMATIC, TRUE)));
                    SetMinOneHP(GetFirstPC(), TRUE);
                }
        }
}

 

#include "k_inc_utility"
#include "k_inc_generic"

string sTraskTag = "end_trask";
string sTraskWP = "endwp_tarsk01";
string sCarthTag = "Carth";

string SOLDIER_WEAPON = "g_w_blstrrfl001";
string SOLDIER_ITEM01 = "g_i_adrnaline003";
string SOLDIER_ITEM02 = "g_i_medeqpmnt01";
string SOLDIER_ITEM03 = "g_i_medeqpmnt02";
string SOLDIER_ITEM04 = "g_w_iongren01";
string SOLDIER_ITEM05 = "g_w_fraggren01";
string SOLDIER_ITEM06 = "g_w_stungren01";
string SOLDIER_ITEM07 = "g_i_adrnaline001";
string SOLDIER_ITEM08 = "g_i_cmbtshot001";
string SOLDIER_ITEM09 = "g_i_belt001";

string SCOUT_WEAPON = "g_w_blstrpstl004";
string SCOUT_ITEM01 = "g_i_belt003";
string SCOUT_ITEM02 = "g_i_implant101";
string SCOUT_ITEM03 = "g_w_adhsvgren001";
string SCOUT_ITEM04 = "g_w_iongren01";
string SCOUT_ITEM05 = "g_w_stungren01";
string SCOUT_ITEM06 = "g_i_adrnaline002";
string SCOUT_ITEM07 = "g_i_progspike01";
string SCOUT_ITEM08 = "g_i_parts01";
string SCOUT_ITEM09 = "g_i_secspike01";
string SCOUT_ITEM10 = "g_i_medeqpmnt01";

string SCOUNDREL_WEAPON = "g_i_medeqpmnt01";
string SCOUNDREL_ITEM01 = "g_i_secspike01";
string SCOUNDREL_ITEM02 = "g_i_progspike01";
string SCOUNDREL_ITEM03 = "g_i_secspike02";
string SCOUNDREL_ITEM04 = "g_w_adhsvgren001";
string SCOUNDREL_ITEM05 = "g_i_gauntlet05";
string SCOUNDREL_ITEM06 = "g_w_stungren01";
string SCOUNDREL_ITEM07 = "g_i_parts01";
string SCOUNDREL_ITEM08 = "g_i_mask20";

int ROOM3_DEAD = 3;
int ROOM5_DEAD = 4;
int ROOM7_DEAD = 2;

int TRASK_DEFAULT = -1;
int TRASK_MUST_GET_GEAR = 0;
int TRASK_GEAR_DONE = 1;
int TRASK_TARGET_DONE = 2;
int TRASK_MUST_EQUIP = 3;
int TRASK_EQUIP_DONE = 4;
int TRASK_MUST_MAP = 5;
int TRASK_MAP_DONE = 6;
int TRASK_MUST_SWITCH = 7;
int TRASK_SWITCH_DONE = 8;
int TRASK_SWITCH_REMIND = 9;
int TRASK_CARTH_BRIDGE = 10;
int TRASK_BRIDGE_DONE = 11;
int TRASK_MUST_DOOR = 12;
int TRASK_DOOR_DONE = 13;
int TRASK_ROOM3_DONE = 14;
int TRASK_MUST_MEDPACK = 15;
int TRASK_COMBAT_WARNING = 16;
int TRASK_COMBAT_WARNING2 = 17;
int TRASK_COMPUTER_DONE = 18;
int TRASK_MUST_DROID = 19;
int TRASK_DROID_DONE = 20;
int TRASK_MUST_MAP_02 = 21;
int TRASK_NOTHING_02 = 22;
//int TRASK_COMBAT_WARNING = 27;
int TRASK_LEVEL_INIT = 28;
int TRASK_MUST_LEVEL = 29;
int TRASK_PARTY_LEVEL = 30;
int TRASK_LEVEL_DONE = 31;

string LOCKER_TAG = "end_locker01";
string STEALTH_UNIT = "g_i_belt010";
string COMP_PART = "g_i_progspike01";
string DEM_MINE = "g_w_cryobgren001";
string REP_PARTS = "g_i_parts01";
string SEC_SPIKES = "g_i_secspike01";
string MED_PAC = "g_i_medeqpmnt01";

//returns Trask's object id
object GetTrask();

// checks if the conditions for passing the healing stage have been met
int HealingDone();

// returns Carth's object id
object GetCarth();

// checks if this has never been done before. uses sw 10
int HasNeverTriggered();

// Has Trask initiate with the pc at any distance
void TalkTrask();

// returns the effect from the corridor explosion
effect CorridorExplosion();

//spawns equipment into the first locker dependent on the players class
void SpawnStartingEquipment();

// returns if the door has been sliced (uses plot 2)
int GetIsSecureDoorSliced(object oDoor = OBJECT_SELF);

// sets the slice state of the door (uses plot 2)
void SetSecureDoorSliced(int bState, object oDoor = OBJECT_SELF);

// returns if the door has been repaired (uses plot 3)
int GetIsDamagedDoorRepaired(object oDoor = OBJECT_SELF);

// sets the repaired state of the door (uses plot 3)
void SetDamagedDoorRepaired(int bState, object oDoor = OBJECT_SELF);

// returns the value of the trask dialouge state global
int GetTraskState();

//sets the trask dialouge global
void SetTraskState(int nValue);

// returns true if there is somethin equipped in the weapon or body slots
int GetHasEquippedSomething();

// Checks if Trask is already waiting to initiate
int GetTraskWillInitiate();

// Sets the flag for Trask waiting to initiate
void SetTraskWillInitiate(int nValue);

//returns Carth dialgue state
int GetCarthState();

//sets Carth dialogue state
void SetCarthState(int nValue);

// plays an explosion
void PlayExplosion(string sWP = "end_explode01", int bWithShake = TRUE, int bWithRumble = TRUE);

//returns a cutscene invisible placeable based on the given number
object GetCutsceneObject(int nObjectNumber);
//////////////////////////////////////////////////////////////////////////


object GetTrask()
{
    return GetObjectByTag(sTraskTag);
}

int HealingDone()
{
    int bDone;
    object oPC = GetFirstPC();
    int bHasMedPack = GetIsObjectValid(GetItemPossessedBy(oPC,"g_i_medeqpmnt01"));
    int bFullHitPoints = GetCurrentHitPoints(oPC) == GetMaxHitPoints(oPC);
    if(bFullHitPoints || bHasMedPack == FALSE)
    {

        bDone = TRUE;
    }
    return bDone;
}

object GetCarth()
{
    return GetObjectByTag("Carth");
}

int HasNeverTriggered()
{
    int bReturn;
    if(UT_GetPlotBooleanFlag(OBJECT_SELF,SW_PLOT_BOOLEAN_10) == FALSE)
    {
        bReturn = TRUE;
        UT_SetPlotBooleanFlag(OBJECT_SELF,SW_PLOT_BOOLEAN_10,TRUE);
    }
    return bReturn;
}

void TalkTrask()
{
    object oTrask = GetTrask();
    if(GetPartyMemberByIndex(0) == oTrask)
    {
        SetPartyLeader(NPC_PLAYER);
    }
   // AurPostString("Trask trying to talk" + IntToString(GetTraskState()),5,5,5.0);
    NoClicksFor(0.5);
    DelayCommand(0.1,SignalEvent(oTrask,EventUserDefined(50)));
}

effect CorridorExplosion()
{
    effect eZap = EffectBeam(VFX_BEAM_LIGHTNING_DARK_L,GetObjectByTag("end_zap01"),BODY_NODE_CHEST);
    return EffectLinkEffects(EffectDamage(5),eZap);
}

object GetSpeaker()
{
    return GetPartyMemberByIndex(1);
}

object GetListener()
{
    return GetPartyMemberByIndex(0);
}

void SpawnStartingEquipment()
{
    object oLocker = GetObjectByTag(LOCKER_TAG);
    int nClass = GetClassByPosition(1,GetFirstPC());
    if(nClass == CLASS_TYPE_SCOUNDREL)
    {
        CreateItemOnObject(SCOUNDREL_WEAPON,oLocker, 4);
        CreateItemOnObject(SCOUNDREL_ITEM01,oLocker, 5);
        CreateItemOnObject(SCOUNDREL_ITEM02,oLocker, 4);
        CreateItemOnObject(SCOUNDREL_ITEM03,oLocker, 5);
        CreateItemOnObject(SCOUNDREL_ITEM04,oLocker);
        CreateItemOnObject(SCOUNDREL_ITEM05,oLocker);
        CreateItemOnObject(SCOUNDREL_ITEM06,oLocker, 4);
        CreateItemOnObject(SCOUNDREL_ITEM07,oLocker, 4);
        CreateItemOnObject(SCOUNDREL_ITEM08,oLocker);
    }
    else if(nClass == CLASS_TYPE_SCOUT)
    {
        CreateItemOnObject(SCOUT_WEAPON,oLocker);
        CreateItemOnObject(SCOUT_ITEM01,oLocker);
        CreateItemOnObject(SCOUT_ITEM02,oLocker);
        CreateItemOnObject(SCOUT_ITEM03,oLocker, 4);
        CreateItemOnObject(SCOUT_ITEM04,oLocker, 2);
        CreateItemOnObject(SCOUT_ITEM05,oLocker, 2);
        CreateItemOnObject(SCOUT_ITEM06,oLocker, 2);
        CreateItemOnObject(SCOUT_ITEM07,oLocker, 5);
        CreateItemOnObject(SCOUT_ITEM08,oLocker, 5);
        CreateItemOnObject(SCOUT_ITEM09,oLocker, 2);
        CreateItemOnObject(SCOUT_ITEM10,oLocker, 4);
    }
    else if(nClass == CLASS_TYPE_SOLDIER)
    {
        CreateItemOnObject(SOLDIER_WEAPON,oLocker);
        CreateItemOnObject(SOLDIER_ITEM01,oLocker, 2);
        CreateItemOnObject(SOLDIER_ITEM02,oLocker, 5);
        CreateItemOnObject(SOLDIER_ITEM03,oLocker, 5);
        CreateItemOnObject(SOLDIER_ITEM04,oLocker, 4);
        CreateItemOnObject(SOLDIER_ITEM05,oLocker, 4);
        CreateItemOnObject(SOLDIER_ITEM06,oLocker, 4);
        CreateItemOnObject(SOLDIER_ITEM07,oLocker, 2);
        CreateItemOnObject(SOLDIER_ITEM08,oLocker, 4);
        CreateItemOnObject(SOLDIER_ITEM09,oLocker);
          
                    }

    if(GetHasSkill(SKILL_STEALTH,GetFirstPC()))
    {
        CreateItemOnObject(STEALTH_UNIT,oLocker);
    }
    if(GetHasSkill(SKILL_COMPUTER_USE,GetFirstPC()))
    {
        CreateItemOnObject(COMP_PART,oLocker, 2);
    }
    if(GetHasSkill(SKILL_DEMOLITIONS,GetFirstPC()))
    {
        CreateItemOnObject(DEM_MINE,oLocker, 2);
    }
    if(GetHasSkill(SKILL_REPAIR,GetFirstPC()))
    {
        CreateItemOnObject(REP_PARTS,oLocker, 2);
    }
    if(GetHasSkill(SKILL_SECURITY,GetFirstPC()))
    {
        CreateItemOnObject(SEC_SPIKES,oLocker, 2);
    }
    if(GetHasSkill(SKILL_TREAT_INJURY,GetFirstPC()))
    {
        CreateItemOnObject(MED_PAC,oLocker, 2);
    }
}

int GetIsSecureDoorSliced(object oDoor = OBJECT_SELF)
{
    return UT_GetPlotBooleanFlag(oDoor,SW_PLOT_BOOLEAN_02);
}

void SetSecureDoorSliced(int bState, object oDoor = OBJECT_SELF)
{
    UT_SetPlotBooleanFlag(oDoor,SW_PLOT_BOOLEAN_02,bState);
}

int GetIsDamagedDoorRepaired(object oDoor = OBJECT_SELF)
{
    return UT_GetPlotBooleanFlag(oDoor,SW_PLOT_BOOLEAN_03);
}

void SetDamagedDoorRepaired(int bState, object oDoor = OBJECT_SELF)
{
    UT_SetPlotBooleanFlag(oDoor,SW_PLOT_BOOLEAN_03,bState);
}

int GetTraskState()
{
    return GetGlobalNumber("END_TRASK_DLG");
}

void SetTraskState(int nValue)
{
  //  AurPostString("New State" + IntToString(nValue),5,7,2.0);
    SetGlobalNumber("END_TRASK_DLG",nValue);
   // AurPostString("Set: " + IntToString(nValue),5,10,3.0);
}

int GetHasEquippedSomething()
{
    int bItemEquipped = FALSE;
    object oPC = GetFirstPC();
    if(GetIsObjectValid(GetItemInSlot(INVENTORY_SLOT_RIGHTWEAPON,oPC)) ||
       GetIsObjectValid(GetItemInSlot(INVENTORY_SLOT_LEFTWEAPON,oPC)) ||
       GetIsObjectValid(GetItemInSlot(INVENTORY_SLOT_BODY,oPC)) )
    {
            bItemEquipped = TRUE;
    }
    return bItemEquipped;
}

int GetTraskWillInitiate()
{
    return UT_GetPlotBooleanFlag(GetTrask(),SW_PLOT_BOOLEAN_03);
}

void SetTraskWillInitiate(int nValue)
{
    UT_SetPlotBooleanFlag(GetTrask(),SW_PLOT_BOOLEAN_03,nValue);
}

int GetCarthState()
{
    return GetGlobalNumber("END_CARTH_DLG");
}

void SetCarthState(int nValue)
{
    SetGlobalNumber("END_CARTH_DLG",nValue);
}

void PlayExplosion(string sWP = "end_explode01", int bWithShake = TRUE, int bWithRumble = TRUE)
{
    location lExplode = GetLocation(GetNearestObjectByTag(sWP));
    effect eExplode = EffectVisualEffect(VFX_FNF_GRENADE_FRAGMENTATION);
    effect eShake = EffectVisualEffect(VFX_IMP_SCREEN_SHAKE);
    ApplyEffectAtLocation(DURATION_TYPE_INSTANT,eExplode,lExplode);
    if(bWithShake)
    {
        ApplyEffectToObject(DURATION_TYPE_INSTANT,eShake,GetFirstPC());
    }
    if(bWithRumble)
    {
        PlayRumblePattern(14);
    }
}

object GetCutsceneObject(int nObjectNumber)
{
    return GetObjectByTag("end01_sceneobj0" + IntToString(nObjectNumber));
}

 

Do I need to compile either of the scripts in a specific folder with the include script also?

Share this post


Link to post
Share on other sites

I was being an idiot, I basically wasn't compiling the k_pend_area01.nss file with the k_inc_end.nss file into the Override folder, and it's actually working. But weirdly this function still isn't working: 

}
    if(GetHasSkill(SKILL_COMPUTER_USE,GetFirstPC()))
    {
        CreateItemOnObject(COMP_PART,oLocker, 2);
    }

My PC doesn't have Computer Use, but I still get the computer parts in the footlocker. Weird!

Share this post


Link to post
Share on other sites

Try changing the check to:

if (GetSkillRank(SKILL_COMPUTER_USE, GetFirstPC())) > 0
   {
     CreateItemOnObject(COMP_PART,oLocker, 2);
   }

I would assume that inherently the GetHasSkill check should already be checking for a skill rank greater than zero, but perhaps not. I'm pretty sure I suggested this already the last time this came up.

Share this post


Link to post
Share on other sites
On 10/18/2021 at 6:11 PM, DarthParametric said:

If you want to gate via a specific skill rank, then you need to check for that instead:


// 315: Get the number of ranks that oTarget has in nSkill.
// - nSkill: SKILL_*
// - oTarget
// * Returns -1 if oTarget doesn't have nSkill.
// * Returns 0 if nSkill is untrained.
int GetSkillRank(int nSkill, object oTarget=OBJECT_SELF);

 

I've seen people advise others on scripting functions before, like above. But I don't know how to go from the above to have the script lines ready like below 😀

 

3 hours ago, DarthParametric said:

Try changing the check to:


if (GetSkillRank(SKILL_COMPUTER_USE, GetFirstPC())) > 0
   {
     CreateItemOnObject(COMP_PART,oLocker, 2);
   }

 

 

Share this post


Link to post
Share on other sites

Whoops, syntax error on my part. The If statements have their closing brackets in the wrong place. The example I posted above should be:

if (GetSkillRank(SKILL_COMPUTER_USE, GetFirstPC()) > 0)
   {
     CreateItemOnObject(COMP_PART,oLocker, 2);
   }

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this