Jump to content

[LE] Quick Questions, Quick Answers


Recommended Posts

OnItemAdded is an ObjectReference event. This means that containers (which are object references) and Actors (which are a sub-type of object references) can receive the event. Quests and dialog fragments cannot. However, reference aliases pointing to said containers and actors will receive the event.

 

Thus, your dialog fragment can show the gift menu with the associated form list filter and a reference alias on your quest pointing to the actor can listen for the OnItemAdded event in order to remove the item.

 

You should use a global variable and modify its value when the player gives an appropriate item. Then in the OnItemAdded event remove said item only when that global variable is at that value. Once the item has been removed, reset the variable. Why? The player could give the follower a stack of one or more valid items just to carry around for them. Without something to prevent removal outside of the designated time frame, any addition of valid items by the player would trigger the removal.

Link to comment
Share on other sites

OnItemAdded is an ObjectReference event. This means that containers (which are object references) and Actors (which are a sub-type of object references) can receive the event. Quests and dialog fragments cannot. However, reference aliases pointing to said containers and actors will receive the event.

 

Thus, your dialog fragment can show the gift menu with the associated form list filter and a reference alias on your quest pointing to the actor can listen for the OnItemAdded event in order to remove the item.

 

You should use a global variable and modify its value when the player gives an appropriate item. Then in the OnItemAdded event remove said item only when that global variable is at that value. Once the item has been removed, reset the variable. Why? The player could give the follower a stack of one or more valid items just to carry around for them. Without something to prevent removal outside of the designated time frame, any addition of valid items by the player would trigger the removal.

Ok, I do have a variable for that good to know. I'll edit some things and see what happens. thank you.

 

EDIT Ok I BELIEVE I have it fixed as it does not give me any compiling errors. The code might be not well optimized as I am flying by the seat of my pants and the CK scripts page. I wanted to make a single function for all the Gift Types but it kept giving me errors when trying to go by If statments so I tried this.

 

 

 

ScriptName Dan_GiveGifts Extends Quest
Quest Property Dan_Gifts Auto

FormList Property Dan_HatedGifts Auto
FormList Property Dan_LikedGifts Auto
FormList Property Dan_DislikedGifts Auto
FormList Property Dan_LovedGifts Auto
GlobalVariable Property Dan_RelPoints Auto
GlobalVariable Property Dan_GiftLove Auto
GlobalVariable Property Dan_GiftLike Auto
GlobalVariable Property Dan_GiftDislike Auto
GlobalVariable Property Dan_GiftHate Auto
ObjectReference akSpeaker
Actor Property PlayerRef Auto
Actor Property Dan Auto

Function GiftGive()
            akSpeaker.AddInventoryEventFilter(Dan_LikedGifts)
            Dan_GiftLike.Mod(1)
            akSpeaker.AddInventoryEventFilter(Dan_LovedGifts)
            Dan_GiftLove.Mod(1)
            akSpeaker.AddInventoryEventFilter(Dan_DislikedGifts)
            Dan_GiftDislike.Mod(1)
            akSpeaker.AddInventoryEventFilter(Dan_HatedGifts)
            Dan_GiftHate.Mod(1)
            Dan.ShowGiftMenu(true)
EndFunction

Event OnItemAdded(Form akBaseItem, int aiItemCount, ObjectReference akItemReference, ObjectReference akSourceContainer)
            If akSourceContainer == PlayerREF
                If Dan_GiftLike.GetValueInt()
                akSpeaker.RemoveItem(akBaseItem,aiItemCount) ;he likes it so he'll keep it
                Dan_RelPoints.Mod(1)
                Dan_GiftLike.Mod(0)
                EndIf
            EndIf
            If akSourceContainer == PlayerREF
                If Dan_GiftLove.GetValueInt()
                akSpeaker.RemoveItem(akBaseItem,aiItemCount) ;he likes it so he'll keep it
                Dan_RelPoints.Mod(1)
                Dan_GiftLove.Mod(0)
                EndIf
            EndIf
            If akSourceContainer == PlayerREF
                If Dan_GiftDislike.GetValueInt()
                akSpeaker.RemoveItem(akBaseItem,aiItemCount) ;he likes it so he'll keep it
                Dan_RelPoints.Mod(1)
                Dan_GiftDislike.Mod(0)
                EndIf        
            EndIf
            If akSourceContainer == PlayerREF
                If Dan_GiftHate.GetValueInt()
                akSpeaker.RemoveItem(akBaseItem,aiItemCount) ;he likes it so he'll keep it
                Dan_RelPoints.Mod(1)
                Dan_GiftHate.Mod(0)
                EndIf
            EndIf
EndEvent

 

 

 

reference alias on your quest pointing to the actor can listen for the OnItemAdded event

 

Alright I'm feeling so dumb rn but I can't figure this out. I have a reference in the quest alias pointing to the follower. I've been able to find GetEventData in the Conditionals menu in the dialogue, but it winds up empty and won't let me fill in anything from the associated drop down.(Just made a new reference to player ad item by putting it as the event type in the quest data page). This so far seems to be only thing I can think of that you are referring to. Unless I put something in the script itself but I'm not seeing anything in the CK site that would fit that need?Unless I'm SUPER overthinking this.

Link to comment
Share on other sites

Okay. I will show what I was thinking. You can make changes to fit your needs after confirming that it works.

 

NPC dialog fragment should contain:

myGiftStatus.SetValue(1.0)
ShowGiftMenu(True, myGiftList, False, False)
  • Create the global variable record with a default value of 0
  • Create the dialog fragment by entering the code and commenting out each line with a semi-colon ';' and compiling.
  • Add the property for the form list and the property for the global variable.
  • Remove the semi-colon and compile again.
  • Then go back and assign the correct data to the properties via the properties window.

 

On your quest with an alias that points to your NPC add the following script to the alias:

 

 

ScriptName TestGiftSystemAliasScript Extends ReferenceAlias
 
FormList Property myGiftList Auto
GlobalVariable Property myGiftStatus Auto
 
Event OnItemAdded(Form akBaseItem, int aiItemCount, ObjectReference akItemReference, ObjectReference akSourceContainer)
  If akSourceContainer == Game.GetPlayer() ; is it the player adding the item
    If (myGiftList.HasForm(akBaseItem)) && (myGiftStatus.GetValue() != 0)
      Self.GetReference().RemoveItem(akBaseItem,aiItemCount)
      myGiftStatus.SetValue(0)
    EndIf
  EndIf
EndEvent

After compiling be sure to go back and add the correct data to the properties via the properties window.

 

The global variable used here is to only indicate if the player has initiated the gift giving and is meant to be a toggle (1 or 0).

Link to comment
Share on other sites

Okay. I will show what I was thinking. You can make changes to fit your needs after confirming that it works.

 

NPC dialog fragment should contain:

myGiftStatus.SetValue(1.0)
ShowGiftMenu(True, myGiftList, False, False)
  • Create the global variable record with a default value of 0
  • Create the dialog fragment by entering the code and commenting out each line with a semi-colon ';' and compiling.
  • Add the property for the form list and the property for the global variable.
  • Remove the semi-colon and compile again.
  • Then go back and assign the correct data to the properties via the properties window.

 

On your quest with an alias that points to your NPC add the following script to the alias:

 

 

ScriptName TestGiftSystemAliasScript Extends ReferenceAlias
 
FormList Property myGiftList Auto
GlobalVariable Property myGiftStatus Auto
 
Event OnItemAdded(Form akBaseItem, int aiItemCount, ObjectReference akItemReference, ObjectReference akSourceContainer)
  If akSourceContainer == Game.GetPlayer() ; is it the player adding the item
    If (myGiftList.HasForm(akBaseItem)) && (myGiftStatus.GetValue() != 0)
      Self.GetReference().RemoveItem(akBaseItem,aiItemCount)
      myGiftStatus.SetValue(0)
    EndIf
  EndIf
EndEvent

After compiling be sure to go back and add the correct data to the properties via the properties window.

 

The global variable used here is to only indicate if the player has initiated the gift giving and is meant to be a toggle (1 or 0).

Ok So I was able to get the base code you gave me to work fine. The only thing I had to do was add akSpeaker.ShowGiftMenu(etc) to the fragment other wise it did not like the function. Now, is there an easier way to be able to use multiple form lists since I have different types of gifts to use? I'm going to assume I can just make another myGiftList2 or something and just use it in the same way with the other form lists. EDIT Yep that's what I did and it seems to be show multiple windows lol. I wonder if I can make it so if the player has an item that matches the formlist it will show the required menu...but i dont think that will alleviate the issue.

Link to comment
Share on other sites

You want multiple form lists to be available in the gift menu? Try creating a form list of form lists and using that master list in the gift menu. Not sure if that will work, but it is worth testing.

 

EDIT: If that fails, create a master list that contains all the items found in the individual lists. That will allow the gift menu to show acceptable items no matter what smaller list they might be on. Use the smaller lists in your OnItemAdded event to handle any differentiation of tasks.

Edited by IsharaMeradin
Link to comment
Share on other sites

You want multiple form lists to be available in the gift menu? Try creating a form list of form lists and using that master list in the gift menu. Not sure if that will work, but it is worth testing.

 

EDIT: If that fails, create a master list that contains all the items found in the individual lists. That will allow the gift menu to show acceptable items no matter what smaller list they might be on. Use the smaller lists in your OnItemAdded event to handle any differentiation of tasks.

Ok, so far I have gotten all of that to work with little to no issue now. But one problem I'm having is after I give the item I want the character to react to it appropriately. I wonder if it's because it pulls up a menu, but after giving an item it doesn't go to my next topic even though I've linked it in the DV, and set it so if the formlist is A give response A etc. Though the latter might not be working since I'm doing it in Conditionals and need to do it the End Event of the one where we pull up the menu??

 

The other problem I'm having is that I want to set the Global Variable RelPoints to itself +/- depending on what the player gives. I tried using mod() and SetValue() with variations of +/- and = but the script dose not like those being inserted. I even tried setting RelPoints to an Int value but it didn't like that either. Reason being, the points are going to work with a custom Ranking system outside of Skyrim's own since I'm picky. Then I can put a bunch of quests in before you can get the follower ranking or romance or whatever I want with it. Here's an example that isn't working currently but I haven't put it in yet. It does have its own quest though.

 

 

 

Scriptname Dan_RelationshipScript extends Quest

GlobalVariable Property Dan_RelPoints Auto
GlobalVariable Property Dan_RelRank Auto

Function Dan_RelTrack()
	Dan_RelPoints.GetValueInt()
	Dan_RelRank.GetValueInt()
	
	while Dan_RelPoints >= 0 && Dan_RelPoints = 50 && !Dan_RelPoints < 50 ;so it doesn't use less than the req #?? idk
		Dan_RelRank.Mod(0)
	Endwhile
	while Dan_RelPoints >= 50 && Dan_RelPoints = 100 && !Dan_RelPoints > 100 ;so it doesn't use less than the req #?? idk
		Dan_RelRank.Mod(1)
	Endwhile
	while Dan_RelPoints >= 100 && Dan_RelPoints = 150 && !Dan_RelPoints > 150 ;so it doesn't use less than the req #?? idk
		Dan_RelRank.Mod(2)
	Endwhile
	while Dan_RelPoints >= 150 && Dan_RelPoints = 200 && !Dan_RelPoints > 250 ;so it doesn't use less than the req #?? idk
		Dan_RelRank.Mod(3)
	Endwhile
	while Dan_RelPoints >= 250 && Dan_RelPoints = 300 && !Dan_RelPoints > 350 ;so it doesn't use less than the req #?? idk
		Dan_RelRank.Mod(4)
	Endwhile
EndFunction

 

 

 

Link to comment
Share on other sites

Dialog is interrupted with the gift menu. The player would need to re-initiate conversation or you would need to make the NPC force greet the player. In that event, you would not reset the gift toggle when the item is removed but rather use it as a dialog condition to help ensure that the correct line of dialog starts and then reset it.

 

An alternative route would be a dialog based gift giving. Rather than opening the menu to let the player pick an item from the list, display valid items that the player is carrying as dialog options. But that is just theory, I'm not sure how to pull that off.

 

As far as the global variable thing in your previous post... I think the logic of the following is sound:

 

 

Scriptname Dan_RelationshipScript extends Quest
 
GlobalVariable Property Dan_RelPoints Auto
GlobalVariable Property Dan_RelRank Auto
Int Property MaxPoints = 400 Auto ;default max relationship points
Int Property PointStep = 50 Auto ;default step to advance relationship
Int PointTest = 0
 
Function Dan_RelTrack()
  Int RelPoints = Dan_RelPoints.GetValueInt()
; Int RelRank = Dan_RelRank.GetValueInt()
 
  While (PointTest < MaxPoints) && (RelPoints > PointTest)
    If RelPoints >= (PointTest + PointStep)
      Dan_RelRank.Mod(1) ;increases value by 1
      PointTest = PointTest + PointStep
    EndIf
  EndWhile
 
EndFunction

Made the property integers so that the values can be changed as desired in the CK without re-compiling the script should testing require an adjustment in the values.

 

Link to comment
Share on other sites

Ok I'll have to look into that. But thanks so far for the help its been much appreciated! This topic/mod I might be able to use for an idea: https://forums.nexusmods.com/index.php?/topic/8364848-serana-dialogue-add-on/page-921?hl=%2Bdialogue+%2Bgift+%2Bgiving&do=findComment&comment=114477103

 

DLC1_NPCMentalModelScript Might be a good thing to look into as well, but given how shitty Beth codes things idk how reliable it is.

 

Ok, ok it seems how the Serana mod does it is it sets a value using an Int to the gift, then puts it in a scene that plays afterward. I'll have to maybe look around more in the scripts and see what else I can glean.

 

It seems to use ontemremoved instead of onitemadded. not too sure what the difference by using one or the other would make but i figure ill note it here for other people. https://www.creationkit.com/index.php?title=OnItemRemoved_-_ObjectReference So I think I can use that with other things to make it work. Found this: http://gamesas.com/global-variables-t256104.html to figure out how to be able to add and the points value for gifts.

Link to comment
Share on other sites

OnItemAdded is triggered when objects are added to the container or actor inventory.

OnItemRemoved is triggered when objects are removed from the container or actor inventory.

 

So in your scenario, OnItemAdded would be triggered when an item is added to the NPC (script on NPC or NPC alias). OnItemRemoved would be triggered when the item comes out of the player inventory (script on player or player alias). Better in this case to go from the NPC perspective and use OnItemAdded rather than from the player perspective. Why? Unless an inventory event filter is in place, OnItemRemoved (or OnItemAdded for that matter) from the player perspective would be triggered with EVERY item being removed or added. Which in turn means unnecessary processing taking place just to find out that there is nothing for that particular script to achieve at that time.

 

Get a lot of such scripts checking every item being added or removed and then do a take all from a very stuffed container or another mod transfers a large number of items and papyrus can get overloaded and dump the stack of scripts. On the surface it may seem fine, but if the wrong script(s) get included in the stack, there may be an issue later on.

Link to comment
Share on other sites

  • Recently Browsing   0 members

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