Jump to content

[LE] I need a non-SKSE method for controlling gear based on class


Shadohz

Recommended Posts

I have a follower that I only want to wear clothing and wield a dagger. I need a script that can control her inventory so that she removes any gear or weapons that I do not fit my requirements.

Short-term objective:
As I see it there's two possible methods for monitoring her equipment: 1) is to register the script on a timer and alter the gear based on armortype or 2) verify what is equipped based on changes to the NPC container event.

The problem I'm having is I keep screwing up how to detect the armortype. I could use GetArmorRating to see if anything is higher than 0 but that doesn't solve my weapon problem. I can't seem to figure out how to get the HasKeyword function working with IsEquipped.

Wait, dangit. Argh. Okay I think I'm having one of those epiphany moments when I start figuring something out as I ask for help. Okay "GetEquippedItemType" will allow me to address the shield and weapon problem. That problem is out of the way but I still need to figure out how to spot the best clothing to force wear on the follower.

Long-term objective:
Using a solution from the first what I want to do is create a generic script for public-use that will allow players to set a Combat Style (existing or new) and the NPC will only wear gear pre-defined for that class that is attached by the Actor script. So for my follower who is an alchemist, she'd only wear clothing and wield a dagger. For a witchhunter a bow and clothing, so on and so forth.

Link to comment
Share on other sites

Start from here, there are at least 3 different ways posted that can help you start building what you want.



* Small advice: simplify things, a big complicated script does not always mean better, better is making the complicated thing as simple as possible.


Have a happy modding.

Link to comment
Share on other sites

I don't believe your end goal is doable without SKSE -- setting things on an ActorBase for the most part requires it, and, particularly, that is true of combat styles.

 

However, there are some things you can do without that portion. It is possible to 'lock' equipment so that it is never unequipped; this does not require SKSE, but it will also stop it from ever changing, even if other, better items are added. Some additional scripting could be done to listen for gear being added to, or removed from, their inventory, upon which you might be able to update what is equipped or not. This would unfortunately mean that they would also always have their weapon(s) equipped, which could be a problem.

 

Checking a full inventory without SKSE is possible but very much not recommended, because it is both prone to error, visible to the user if done on an NPC/the player, and very slow. Since you can't access it directly the only way I know of is to call a RemoveAll() to another container, catch all the OnItemRemoved() events (or, have a separate script on the destination container listening for OnItemAdded() events) to build a list, and then call RemoveAll() on that container to bring them all back. With actors this will result in them being naked while the thing runs, and in all cases (especially on e.g. the player) is vulnerable to stack dumping and thus giving inaccurate results, even if the Papyrus code is exactly correct.

 

I would strongly recommend, given your desired goal, that you consider incorporating SKSE's tools here.

Link to comment
Share on other sites

Thanks maxarturo but I had already exhausted those options. That was the part of the reason I reached out looking for alternative solutions. I needed it specifically designed this way to be flexible with identifying by armor type. I knew that I could SKSE and have this done in half a day but I didn't want to use that particular method.

 

foamyesque "I would strongly recommend..." I know that tone. I use it all the time. Thanks for the feedback and potential pitfalls. Part of my follower script is below. I tried other methods. What I intended as a last ditch attempt was to create a formlist then cycle through each possible option until there's a hit. For example for "clothing" formlist a loop would cycle until hits on a valid item in the NPC inventory. Eventually it would hit something so it's not a problem if it's only clothing where all armor rating is 0 (the value of the items is not so much a factor so no comparison needed). In the case of light armor or heavy armor value and AR comes into play and that's where I obviously run into the problem. I would basically have to prioritize all armor based on AR in the formlist and allow the loop to work it's way through until it hits something. This of course isn't the optimal choice because there are just too many armor to account for and there surely had to be a better method micro-targeting inventory changes.

 

I saw the SKSE options and knew right away it would fix all my problems in an instant (for the functionality I wanted). Ugggh. Bethesda why couldn't you just use old DnD rules and segregate armor use based on class like every other RPG that's been out since my childhood? I'm just going to pass on this and move onto my next project.

 

 

 

 

;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;This is a setting that dialogue will use for determining if the cloak should be used or not
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
GlobalVariable Property Clara_CloakUse  Auto  
 
Event OnInit()
Clara_Followquest.setstage(5)
RegisterForUpdateGameTime(0.0245)
EndEvent
 
 
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Event: OnUpdateGameTime
;Purpose: This event will tick/trigger ~every 15 in-game minutes.
; It will go through a variety of checks for NPC dynamic behavior
;
;Parameters: None - UpdateGameTime is just a timer for the in-game clock
;Returns: Events don't return anything
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
Event OnUpdateGameTime()
;Debug.MessageBox("Test")
Clara_ClaraCompanionForUpdate = ClaraRef.GetActorRef()
bool NativeFile01 = Game.GetFormFromFile (0x000D62, "Clara.esp")  ; Detect if Clara is loaded
If (NativeFile01 == false)
; If (Clara_ClaraCompanionForUpdate == None)
Debug.MessageBox("We have a Problem. Unable to detect necessary file. Performing uninstall procedure.")
;We have to unregister for updates.  This check was done to make sure the game still had a NPC to work with
UnregisterForUpdateGameTime()
Clara_FollowQuest.Stop()
ElseIf ((Clara_Followquest.GetStage()== 10) || (Clara_Followquest.GetState() > 10))
;Perform check for Clara on Accessories logic
 
int hoodValue = ShouldWearHood(Clara_ClaraCompanionForUpdate)
int cloakLogic = Clara_CloakUse.GetValue() as INT
 
If (cloakLogic < 2)
If (hoodValue == 0)
;No Hood Time
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Backpack)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodDown)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodUp)
; Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Gloves)
; Re-equip gear
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_HelmetInv)))
Clara_ClaraCompanionForUpdate.EquipItem(Claras_HelmetInv)
ElseIf (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Boots2)))
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Boots2)
ElseIf (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Gloves)))
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Gloves)
ElseIf (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Clothes2)))
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Clothes2)
EndIf
 
ElseIf (hoodValue == 1)
;Remove the hooded version
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodUp)
 
;Handle Backpack first
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Backpack)))
;We need to add the hood and equip
;------Clara_ClaraCompanionForUpdate.AddItem(Claras_Backpack)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Backpack)
EndIf
;Handle Cape Hood Down next
; If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_CapeHoodDown)))
; Clara_ClaraCompanionForUpdate.AddItem(Claras_CapeHoodDown)
; Clara_ClaraCompanionForUpdate.EquipItem(Claras_CapeHoodDown)
; EndIf
;Handle Gloves
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Gloves)))
;---------Clara_ClaraCompanionForUpdate.AddItem(Claras_Gloves)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Gloves)
EndIf
;Handle Clothes
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Clothes2)))
;--------Clara_ClaraCompanionForUpdate.AddItem(Claras_Clothes2)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Clothes2)
EndIf
;Handle Boots
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Boots2)))
;---------Clara_ClaraCompanionForUpdate.AddItem(Claras_Boots2)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Boots2)
EndIf
;Handle Helmet
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_HelmetInv)))
Clara_ClaraCompanionForUpdate.EquipItem(Claras_HelmetInv)
EndIf
 
ElseIf (hoodValue == 2)
;Remove the non-hooded version
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodDown)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Backpack)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_HelmetInv)
 
;Handle Backpack first
; If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Backpack)))
; ;We need to add the hood and equip
; ;---------Clara_ClaraCompanionForUpdate.AddItem(Claras_Backpack)
; Clara_ClaraCompanionForUpdate.EquipItem(Claras_Backpack)
; EndIf
;Check Cape Hood Up
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_CapeHoodUp)))
;We need to add the hood and equip
;----------Clara_ClaraCompanionForUpdate.AddItem(Claras_CapeHoodUp)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_CapeHoodUp)
EndIf
;Handle Gloves
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Gloves)))
;------------Clara_ClaraCompanionForUpdate.AddItem(Claras_Gloves)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Gloves)
EndIf
;Handle Clothes
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Clothes2)))
;---------Clara_ClaraCompanionForUpdate.AddItem(Claras_Clothes2)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Clothes2)
EndIf
;Handle Boots
If (!(Clara_ClaraCompanionForUpdate.IsEquipped(Claras_Boots2)))
;-----------Clara_ClaraCompanionForUpdate.AddItem(Claras_Boots2)
Clara_ClaraCompanionForUpdate.EquipItem(Claras_Boots2)
EndIf
Else
;We are just eating the -1 for the Do Nothing call
EndIf
 
Elseif (cloakLogic == 2)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Backpack) 
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodDown)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_CapeHoodUp)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Gloves)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Clothes2)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_Boots2)
Clara_ClaraCompanionForUpdate.RemoveItem(Claras_HelmetInv)
EndIf

 


Link to comment
Share on other sites

Hey, as maxaturo said, keep things simple. I think you can achieve what you want without skse by using keywords and the OnObjectEquipped event. I wouldn't use a constant running Update loop, as that can be bad for performance. Here's an example script:

 

Scriptname MyFollowerScript extends Actor  

Keyword Property VendorItemClothing Auto
Keyword Property ArmorCuirass Auto
Keyword Property WeapTypeDagger Auto
Armor Property DefaultClothes Auto 
ObjectReference Property FollowerStorageChest Auto

Form CurrentDagger

Event OnObjectEquipped(Form akBaseObject, ObjectReference akReference)
    If akBaseObject as Armor && akBaseObject.HasKeyword(VendorItemClothing) == false
        Self.UnequipItem(akBaseObject) 
        Self.RemoveItem(akBaseObject, 1, 1, FollowerStorageChest) ; remove item and put it in chest
        If akBaseObject.HasKeyword(ArmorCuirass)
            Self.EquipItem(DefaultClothes)
        Endif 
    Elseif akBaseObject as Weapon 
        If akBaseObject.HasKeyword(WeapTypeDagger) 
            CurrentDagger = akBaseObject 
        Else 
            Self.UnequipItem(akBaseObject) 
            Self.RemoveItem(akBaseObject, 1, 1, FollowerStorageChest) ; remove item and put it in chest
            Self.EquipItem(CurrentDagger)
        Endif 
    Elseif akBaseObject as Spell 
        Self.UnequipItem(akBaseObject)
    Endif 
    
EndEvent
Edited by dylbill
Link to comment
Share on other sites

  • Recently Browsing   0 members

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