Difference between revisions of "Scripting Tutorial: Working with FormLists"

no edit summary
imported>Omzy
imported>Omzy
 
(10 intermediate revisions by the same user not shown)
Line 1: Line 1:
{{Incomplete}}
This article is a WIP. I'll try to finish it in the next few days.--[[User:Omzy|Omzy]] 00:50, 1 August 2009 (UTC)
==IMPORTANT==
==IMPORTANT==
'''You will need [[Fallout Script Extender|Fallout Script Extender (FOSE)]] for this tutorial.'''
'''You will need [[Fallout Script Extender|Fallout Script Extender (FOSE)]] for this tutorial.'''
Line 81: Line 78:
*You can use the [[ListGetCount]] function.
*You can use the [[ListGetCount]] function.


==Using Lists to Create Floating Text==
=Using Lists to Create Floating Text=
This example goes beyond what a casual modder might attempt to accomplish, but it displays the abilities of lists quite well.
This example goes beyond what a casual modder might attempt to accomplish, but it displays the abilities of lists quite well.


Line 92: Line 89:
*Our names are (courtesy of FF7):
*Our names are (courtesy of FF7):
#Cloud
#Cloud
#Barret
#Tifa
#Tifa
#Barret
#Aeris
#Aeris
#Red XIII
#Red XIII
Line 101: Line 98:
#Cid
#Cid


So, let us create a [[FormList]] for each name that contains the letters of that name
Let us create a [[FormList]] for each name that contains the letters of that name. The name of each list will be ''nameX'' where ''X'' is the name (e.g. ''nameCloud''). If we try dragging and dropping ''B, a, r, r, e, t'' into a FormList for the name Barret, we will not be able to add the second ''r'' because dragging and dropping allows us only to add base forms to a FormList once, since they have the same FormID. So, we must add the letters as references via a script using [[ListAddReference]] OR by placing the letters into the world in a cell somewhere and dragging their references from the Cell View window. For this example, lets assume we've added them to a test cell somewhere so we can use [[MoveTo]] to relocate them to their destinations. We will add the letters so that the first letter of each name is at index 0.
As it would seem, a FormList is also an object in the editor, which has its own FormID. That makes a FormList a Form. What this means is that FormLists can contain other FormLists. This may seem a bit confusing if you've never learned any mid-level programming before, so lets look at the following script and see what it does:
 
===Inefficient Script===
If we wish to print these names into the world somewhere, we can use the [[Label]]/[[GoTo]] loop, one loop for each FormList of letters:
  scn floatingNamesScript
  ;vars (not listed for brevity)
  Begin GameMode
    ;set first letter's position
    set firstLetterPosX to 1000
    set firstLetterPosY to 1000
    set firstLetterPosZ to 1000
    ;initialize current letter's position
    set letterPosX to firstLetterPosX
    set letterPosY to firstLetterPosY
    set letterPosZ to firstLetterPosZ
    ;distance to the next letter
    set letterOffsetX to 0
    set letterOffsetY to 5
    set letterOffsetZ to 0
    ;distance to the next name
    set nameOffsetX to 0
    set nameOffsetY to 0
    set nameOffsetZ to 10   
    ;PRINT FIRST NAME
    set letterList to nameCloud
    Label 1
      set currentLetter to ListGetNthForm letterList count1
      currentLetter.MoveTo Player
      currentLetter.SetPos X letterPosX
      currentLetter.SetPos Y letterPosY
      currentLetter.SetPos Z letterPosZ
      ;add offsets for next letter
      set letterPosX to letterPosX + letterOffsetX
      set letterPosY to letterPosY + letterOffsetY
      set letterPosZ to letterPosZ + letterOffsetZ
      set count1 to count1 + 1
    if count1 < ListGetCount letterList
      GoTo 1
    endif
    ;set position of next name's first letter
    set letterPosX to firstLetterPosX
    set letterPosY to firstLetterPosY
    set letterPosZ to firstLetterPosZ
    set letterPosX to letterPosX + nameOffsetX
    set letterPosY to letterPosY + nameOffsetY
    set letterPosZ to letterPosZ + nameOffsetZ
    ;PRINT SECOND NAME
    set letterList to nameBarret
    Label 2
      set currentLetter to ListGetNthForm letterList count2
      currentLetter.MoveTo Player
      currentLetter.SetPos X letterPosX
      currentLetter.SetPos Y letterPosY
      currentLetter.SetPos Z letterPosZ
      ;add offsets for next letter
      set letterPosX to letterPosX + letterOffsetX
      set letterPosY to letterPosY + letterOffsetY
      set letterPosZ to letterPosZ + letterOffsetZ
      set count2 to count2 + 1
    if count2 < ListGetCount letterList
      GoTo 2
    endif
    (etc)
  End
 
The script was cut short because it is a bit tedious, since we have 9 names to print. The script could also quickly get long if we put more instructions into each loop, like angle and scale information.
 
===Lists of Lists===
As it would seem, a FormList is also an object in the editor, which has its own FormID. That makes a FormList a Form. What this means is that FormLists can contain other FormLists. Lets use this to our advantage by making another FormList named ''namesList''. Now we will drag and drop all 9 of our name FormLists into this new FormList.
 
===Efficient Script===
Our script just got a whole lot shorter:
  scn floatingNamesScript
  ;vars (not listed for brevity)
  Begin GameMode
    ;set first letter's position
    set firstLetterPosX to 1000
    set firstLetterPosY to 1000
    set firstLetterPosZ to 1000
    ;initialize current letter's position
    set letterPosX to firstLetterPosX
    set letterPosY to firstLetterPosY
    set letterPosZ to firstLetterPosZ
    ;distance to the next letter
    set letterOffsetX to 0
    set letterOffsetY to 5
    set letterOffsetZ to 0
    ;distance to the next name
    set nameOffsetX to 0
    set nameOffsetY to 0
    set nameOffsetZ to 10   
    ;PRINT NAMES
    Label 1
      set letterList to ListGetNthForm namesList countNames
      set countLetters to 0
      Label 2
        set currentLetter to ListGetNthForm letterList countLetters
        currentLetter.MoveTo Player
        currentLetter.SetPos X letterPosX
        currentLetter.SetPos Y letterPosY
        currentLetter.SetPos Z letterPosZ
        ;add offsets for next letter
        set letterPosX to letterPosX + letterOffsetX
        set letterPosY to letterPosY + letterOffsetY
        set letterPosZ to letterPosZ + letterOffsetZ
        set countLetters to countLetters + 1
      if countLetters < ListGetCount letterList
        GoTo 2
      endif
      set countNames to countNames + 1
      ;set position of next name's first letter
      set letterPosX to firstLetterPosX + nameOffsetX * countNames
      set letterPosY to firstLetterPosY + nameOffsetY * countNames
      set letterPosZ to firstLetterPosZ + nameOffsetZ * countNames
    if countNames < ListGetCount namesList
      GoTo 1
    endif
  End
 
That was the entire script to print all 9 names in a cell. If these initial positions are changed, this script can print these names anywhere in the game world. If we add more names or want to change the names, this can easily be done in the editor without modifying the script.


(script here)
The moral of the story is: '''there is a lot you can accomplish by working with FormLists'''.


(add more scripting tricks/uses)
[[Category:Scripting]]
[[Category:Tutorials]]
[[Category:Advanced_Modding_Techniques]]
Anonymous user