Jump to content

[LE] Script help for MCM.. half working


Recommended Posts

hey everyone just after a little help with this code...

 

Book[] Property MyBooks Auto
Function AddBooks()
Actor aPlayer = Game.GetPlayer()
int i = MyBooks.Length
while (i > 0)
i -= 1
aPlayer.AddItem(MyBooks, 1)
endWhile
EndFunction
;----------------------------------------- ON OPTION SELECT ---------------------------------------------------------
Event OnOptionSelect(int option)
elseif (option == OIDBooks)
AddBooks = !AddBooks
SetToggleOptionValue(option, AddBooks)
AddBooks()
-----------------------------------------------------------------------------------------------------------------------------------
so this works perfectly for adding the books ive created to a players inventory though a toggle in my MCM menu.. but.. i want to be able to remove them too through the same toggle.. the code to remove the items is this:
Function AddBooks()
Actor aPlayer = Game.GetPlayer()
int i = MyBooks.Length
while (i > 0)
i -= 1
aPlayer.RemoveItem(MyBooks, 1)
endWhile
EndFunction
-------------------------------------------------------
which also works perfectly.. the problem is with my somewhat limited experience i cant intergrate them.. its either one or the other.. papyrus will only allow one instance of AddBooks() and ive tried adding Else, If.. you know to try seperating them but im really struggling..
any help would be greatly appreciated
Link to comment
Share on other sites

Call two separate functions. One to add the books and one to remove the books. You'll have to change up your OnOptionSelect and associated menu functions to use a bool variable to toggle.

 

Something like:

 

 

Book[] Property MyBooks Auto
 
Function AddBooks()
    Actor aPlayer = Game.GetPlayer()
	int i = MyBooks.Length    
	while (i > 0)
		i -= 1
		aPlayer.AddItem(MyBooks[i], 1)
	endWhile
EndFunction

Function RemoveBooks()
    Actor aPlayer = Game.GetPlayer()
	int i = MyBooks.Length    
	while (i > 0)
		i -= 1
		aPlayer.RemoveItem(MyBooks[i], 1)
	endWhile
EndFunction

; on option select example to work with the above functions
Bool BooksAdded = false

Event OnOptionSelect(int option)
	If (option == OIDBooks)
		BooksAdded = !BooksAdded
		SetToggleOptionValue(option, BooksAdded)
		If BooksAdded == True
			AddBooks()
		Else
			RemoveBooks()
		EndIf
	EndIf
EndEvent

However I would take this a step further and avoid doing work during the menu selection process. But rather put it off till the end when the menu is exited. It would be something more like this:

Book[] Property MyBooks Auto
Bool BooksAdded = False

Function AddBooks()
	Actor aPlayer = Game.GetPlayer()
	int i = MyBooks.Length    
	while (i > 0)
		i -= 1
		aPlayer.AddItem(MyBooks[i], 1)
	endWhile
EndFunction

Function RemoveBooks()
	Actor aPlayer = Game.GetPlayer()
	int i = MyBooks.Length    
	while (i > 0)
		i -= 1
		aPlayer.RemoveItem(MyBooks[i], 1)
	endWhile
EndFunction

Event OnOptionSelect(int option)
	If (option == OIDBooks)
		BooksAdded = !BooksAdded
		SetToggleOptionValue(option, BooksAdded)
	EndIf
EndEvent

Event OnConfigClose()
    RegisterForSingleUpdate(0.1)
EndEvent

Event OnUpdate()
	If BooksAdded == True
		AddBooks()
	Else
		RemoveBooks()
	EndIf
EndEvent

Why the suggestion to put off the work until the menu is closed? Some operations take up time and / or will not run until the menu is closed. This can cause the MCM menu system to become unresponsive at times.

 

For an example of the problem that this avoids: See my Aesthetic Bold Quiver (ABQ) mod. That MCM menu does the work when options are selected, if you were to jump to another mod's MCM menu without fully exiting, the next mod's MCM menu will begin to freeze and no longer function. To avoid this I have a warning pop up window when the ABQ MCM menu is accessed. If I were to rebuild that MCM today, I would use something akin to the example immediately above.

 

There would be other things that I would do but I'm not going to open the door on the debate about where and how it is best to refer to the player's data. You obviously knew enough to pass it into a variable rather than constantly using Game.GetPlayer() for every usage and that is "good enough".

 

 

Link to comment
Share on other sites

You can also use a single function and check for the AddBooks variable.

Function AddBooks()
    Actor aPlayer = Game.GetPlayer()
    int i = MyBooks.Length    
    while (i > 0)
        i -= 1
           if Addbooks
              aPlayer.AddItem(MyBooks[i], 1)
           else
              aPlayer.RemoveItem(MyBooks[i], 1)
    endWhile
EndFunction

What if the player removed one or more of the books meanwhile?

Link to comment
Share on other sites

the functions are working perfectly now.... what im trying to do now is to display a different message when the toggle is activated in MCM like so

 

Event OnOptionSelect(int option)
If (option == OIDBooks)
BooksAdded = !BooksAdded
Debug.MessageBox("Books added to inventory")
if BooksAdded == True
Debug.MessageBox("Books removed from inventory")
SetToggleOptionValue(option, BooksAdded)
endif
but its displaying both messages one after eachother on a single toggle
Link to comment
Share on other sites

Calling the functions from OnOptionSelect like this works perfectly:

 

Event OnOptionSelect(int option)

If (option == OIDBooks)

BooksAdded = !BooksAdded

SetToggleOptionValue(option, BooksAdded)

If BooksAdded == True

AddBooks()

Else

RemoveBooks()

EndIf

Endevent

 

But doing it like this is causing issues..

 

Event OnOptionSelect(int option)

If (option == OIDBooks)

BooksAdded = !BooksAdded

SetToggleOptionValue(option, BooksAdded)

EndIf

EndEvent

 

Event OnConfigClose()

RegisterForSingleUpdate(0.1)

EndEvent

 

Event OnUpdate()

If BooksAdded == True

AddBooks()

Else

RemoveBooks()

EndIf

EndEvent

 

Calling the function from OnUpdate makes the menu add the books again automatically everytime the menu is closed

Link to comment
Share on other sites

  • Recently Browsing   0 members

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