Jump to content

Fallout New Vegas GECK & Scripting Help 101


Recommended Posts

Posted

On dumping arrays and strings:

You have to remember they are nor array and string, but array_var and string_var.  I think OBSE named them like because internally, like every other var, they are just a number.

 

By any chance does Print works outside of SetConsoleEcho ?

 

As for localization, that's a hard one, the binary are the same, at least except for gore/no_gore, so we need a form that can guarantee identify a given language. That's basically Form.GetName == "something" no ?

 

Posted

If you mean FONV ini, there are functions to get and set the values, and to refresh it

Posted

Yes it's in the ini file(s) (fallout_default.ini and fallout.ini) but it's a string; the FOSE command doc doesn't list a function to get a string value, only numeric. Same with the console get/set ini commands. In testing (con_* functions) it doesn't work, just returns NOT FOUND or something like that.

Posted

Odessa would it be 'good enough' to know during mod install? Short of adding an NX or NVSE function, I could give you something that would work in a fomod script. To get the data in-game it could create a new numeric value in the INI that you could then read back with the NVSE functions.

Posted

Yes it's in the ini file(s) (fallout_default.ini and fallout.ini) but it's a string; the FOSE command doc doesn't list a function to get a string value, only numeric. Same with the console get/set ini commands. In testing (con_* functions) it doesn't work, just returns NOT FOUND or something like that.

 

I think con_getinisetting only prints out to the console. Considering the function's originally for console debugging etc. My guess is the set variant should stick, and GetNumericIniSetting shouldn't be affected & return a proper number.

Posted

I'm not sure I follow.. GetNumericIniSetting can work with the fomod thing I described or some other method, but on its own doesn't help, since the setting in the INI is a string, not numeric.

 

Here's a simple (untested) snippet for a fomod script.cs. Would work in OnActivate().

 

 

    // we will use this for a custom section in the ini.
    string mymodKey = "MyModName";

    // Get the language from the ini.
    string slang = GetFalloutIniString("General", "sLanguage");
    
    // Backstop to english
    int iLang = 1;
    
    switch (slang.ToLower())
    {
      case 'english':
        iLang = 1;
      break;

      case 'russian':
        iLang = 2;
      break;
      
      case 'french':
        iLang = 3;
      break;
    }
    
    // Set our custom value
    SetFalloutIniInt(mymodKey, iLang);

 

Posted

You can get the language from the INI file; it's in [General], sLanguage. So we just need a function to get a value from the INI.

 

Then try GetStringGameSetting "sLanguage", it should find it.

Posted

Yeah, not talking about the string thing, just speculating at why con_getinisetting wouldn't work.

 

It does'nt return anything, just output it on screen  :) The fact that one of the answer could be a string is most likely why.

Posted

@jaam: "Print" works fine without SetConsoleEcho, "Con_SQV" does not (which nvse documentation states, but I tested it anyway)

 

GetStringGameSetting "sLanguage"

 

returns an empty string. According to my Fallout.ini: "sLanguage=ENGLISH". I notice OBSE has "GetStringINISetting" but this isn't in NVSE- although its not that important because as you said, you can tell a localization is not English from the form names anyway, which is good enough for me.

 

@Prideslayer: (on using a FOMOD script) interesting, I'll bear that in mind.

Posted

The engine is not very logical with all those console echo. :(

Anyway PrintD should not be too complex to create from Print.

Posted

I've done some testing with BuildRef, created a quest script that runs on 0.1 second delay, starting ten seconds after game starts, with this:

 

(Does a build ref with random numbers 1000 times per second)

 

 

scn BuildRefTestScript

int iTotalMods
int iModIndex
int iForm
ref SomeRef
int iLoop
int iInit

Begin GameMode

    if iInit < 100
        let iInit += 1
    elseif iInit == 100
        con_SCOF "random-build-refing.txt"
        let iTotalMods := GetNumLoadedMods
        let iInit := 101
    endif

    let iLoop := 0
    while (iLoop += 1) < 100
        let iModIndex := Rand 0, iTotalMods
        let iForm := Rand 2780, 100000
        let SomeRef := BuildRef iModIndex, iForm
        if eval !(IsFormValid SomeRef)
            ;Print "not valid form"
            continue
        elseif eval !(IsReference SomeRef)
            Print "Valid non reference from " + $(GetNthModName iModIndex) + " of type: " + $(GetType SomeRef)
            continue
        else
            Print "Valid ref on loop" + $iLoop + " from " + $(GetNthModName iModIndex) + " " + $iForm
            Print "Name of SomeRef is: " + $SomeRef + " from : " + (GetFormIDString SomeRef)
            MessageEx "SomeRef %n" SomeRef
            SomeRef.MoveTo PlayerREF, 500
            Print "Same Cell? " + $(SomeRef.GetInSameCell PlayerREF)
            if eval SomeRef.IsActor
                Print "Actor! AV: " + $(SomeRef.GetAV "Strength")
                Print "Dead/Disabled? " + $(SomeRef.GetDead) + " " + $(SomeRef.GetDisabled)
                SomeRef.AddItem Vodka, 1
                SomeRef.CIOS CazadorPoison
                SomeRef.EquipItem Vodka
                Print "Equipped item upper = " + $(SomeRef.GetEquippedObject 2)
            endif
        endif
    loop
End

 

 

 

Some interesting things:

- This will not crash the game

- This doesn't even lag the game on my system, which is an old core 2.

 

Conclusion: if you make sure to use IsFormValid and a type check, then BuildRef is perfectly safe.

 

Give this .esp a try, its pretty amusing: post-158171-0-64277700-1406023569_thumb.jpg

 

 

BuildRef-Test.esp

Guest tomm434
Posted

Can I somehow clear the reference?

 

When I tried this code

ref MyRef


let MyRef :=GetCrosshairRef

If MyRef.getinfaction supermutant faction
MyRef.startconversation player
else
let MyRef :=0
endif

script breaks. I know that I can set ref to something else(apple) but is there any way to clear the reference so it is set to nothing?

Posted

You can set it to an empty variable. I define a global constant to mean "empty ref"

 

int None == 0

---

let MyRef := None

 

works fine.

Posted

Tomm I remember I used somethig like that. Could it be that it breaks because there's a space on supermutant faction? or it's simply a typo re-writing the code here?

Guest tomm434
Posted

typo rewriting. I remember that when I deleted that line, code started working. Recently(a month ago) I realised there is not any magic about references since they are just contain particular number so I decided to that I can set it to 0 to clear it.

 

 

 

int None == 0

---

let MyRef := None

Ok, I'll try it. So "isFormValid" or "GetType" should return 0 after I set a reference to a int variable. right?

Posted

why not simply declare a ref that you never initialize ?

 

Surprising "let MyRef := None",  if "let MyRef := 0". Probably a case of one being interpreted at compile time when the other is only interpreted at runtime.

 

Posted

I'm wondering if I maybe used Set instead of Let, it was days I was still mixing the two syntax... huh, nevermind

 

But then, Jaam, this means that Letting a reference to 0 works correctly if you use a CO?

Posted

Personally I used a "ref Nothing" that's never initialized.

 

EDIT: CO could works too. I'll try next time I open the GECK.

 

The thing about allowing an integer to be assigned to a ref is kind of a bug, probably a necessary one for the way the engine convert things around. :) I would hate to have the bug "corrected" somewhere down the line and making this no longer work.

 

 

Posted

 

You can get the language from the INI file; it's in [General], sLanguage. So we just need a function to get a value from the INI.

 

Then try GetStringGameSetting "sLanguage", it should find it.

 

 

That was too easy, this one is not converted into setting.

Posted

On Mod Local Data

 

from nvse_whatsnew.txt:

 

 

    OBSE expressions, see http://obse.silverlock.org/obse_command_doc.html#OBSE_Expressions
...
        GetModLocalData        (verified ?)
        SetModLocalData

 

 

The OBSE docs also mention these functions, which are in NVSE too: ModLocalDataExists, RemoveModLocalData, GetAllModLocalData

 

I tested them like:

array_var aData
....
    Print "All Mod Local Data"
    SetModLocalData "sunny", SunnyREF
    Print "Mod data exists: " + $(ModLocalDataExists "sunny") + " " + $(ModLocalDataExists "ratr")
    Print "Local data sunny: " + $(GetModLocalData "sunny")
    let aData := GetAllModLocalData
    Ar_Dump aData
    RemoveModLocalData "sunny"
    Print "Mod data exists: " + $(ModLocalDataExists "sunny") + " " + $(ModLocalDataExists "ratr")
    Print " * End mod local data"

Which gives me console output:

 

 

All Mod Local Data
Mod data exists: 1 0
Local data sunny: 5.27997e-318
Error in script 1c012606
Operator := failed to evaluate to a valid result
    File: SexoutSoliciting.esm Offset: 0x0525 Command: Let
Error in script 1c012606
An expression failed to evaluate to a valid result
    File: SexoutSoliciting.esm Offset: 0x0525 Command: Let
** Dumping Array #0 **
  Array does not exist
Mod data exists: 0 0
 * End mod local data

 

 

Implying (to my limited understanding of NVSE) that:

- GetAllModLocalData is broken

- ModLocalDataExists and RemoveModLocalData work correctly

- SetModLocalData and GetModLocalData sort of work, except the reference I stored appears to have been converted to a number

Guest tomm434
Posted

jaam, can you tell me how can I avoid initializing ref?

 

I made this code for people who can't initiate Mutant greeting via "activate" button. I don't need to set ref to 0 there, I was just curious why that didn't work.

 

I read this article http://geck.bethsoft.com/index.php?title=Tutorial:_String_Variables_2 but I don't see the way without initializing reference.

 

 

 

Scriptname aaquestGreetingKeyQuestScript

ref ActorRef
int stage

begin gamemode

if stage ==0

if isKeyPressed aaquest.GreetingKeyQuestButton
  let ActorRef := GetCrosshairRef
  let stage := 1
  return
endif

elseif stage ==1

if aaquest.aamq01marcusagreed  && ActorRef.getinfaction SupermutantFaction && ActorRef.getisCreature
  if ActorRef.getdead ==0 && ActorRef.getunconscious ==0 && ActorRef.isinCombat ==0 && eval (0 == call fnSexoutActorInuse ActorRef) && ActorRef.getrestrained ==0
    ActorRef.startconversation player Greeting
    let stage := 2
    return
  else
  let stage :=0
  endif
else
let stage :=0
endif

elseif stage ==2

if PlayerRef.GetinSameCell ActorRef ==0
let stage :=0
endif


if ActorRef.GetCurrentAIProcedure != 43 ; if not initiating dialogue
let stage := 0
endif


endif



end

 

 

Posted
ref Nothing
ref something

begin GameMode
  let something := VeronicaRef
;...
  let something := nothing
end


Just declare a ref. Internally it is set to 0.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...