Help on creating an array of stored units.
Moderator: Forum Moderators
Forum rules
- Please use [code] BBCode tags in your posts for embedding WML snippets.
- To keep your code readable so that others can easily help you, make sure to indent it following our conventions.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Help on creating an array of stored units.
I would like to create an array of stored units that can be unstored via an option menu.
Here's what I have so far, (I just placed this at the end of Athermaw scenario for testing)
Edit: this is a continuation of a topic from here:
https://forums.wesnoth.org/viewtopic.ph ... 68#p662268
This thread focuses on the core desired function instead of having everything all mixed up in the middle of an unfinished mod.
Here's what I have so far, (I just placed this at the end of Athermaw scenario for testing)
Code: Select all
[event]
name=start
[set_menu_item] # store units
id=store_unit
description= _ "Store unit"
[command]
[message]
[option]
message= _ "Store unit"
[command]
[store_unit]
[filter]
id=$unit.id
side=$side_number
[/filter]
variable=a_unit
kill=yes
[/store_unit]
[set_variables]
name=stored_units
mode=append
[value]
description="$a_unit[0].name"
[command]
[message]
message="$a_unit[0].type"
[/message]
[/command]
[/value]
[/set_variables]
[/command]
[/option]
[option]
message= _ "Cancel"
speaker=narrator
[/option]
[/message]
[/command]
[/set_menu_item]
[set_menu_item] # unstore units
id=unstore_units
description= _ "unstore units"
[filter]
side=$side_number
[/filter]
[command]
[message]
[option]
[insert_tag]
name=options
variable=stored_units
[/insert_tag]
[/option]
[option]
message= _ "Cancel"
speaker=narrator
[/option]
[/message]
[/command]
[/set_menu_item]
[/event]
https://forums.wesnoth.org/viewtopic.ph ... 68#p662268
This thread focuses on the core desired function instead of having everything all mixed up in the middle of an unfinished mod.
Last edited by Legend_Rider on February 3rd, 2021, 2:30 am, edited 1 time in total.
- skeptical_troll
- Posts: 500
- Joined: August 31st, 2015, 11:06 pm
Re: Help on creating an array of stored units.
I had something similar in a scenario of Return from the Abyss, basically using an array of units to choose which one to hire. I remember I wasn't able to figure out a way of having a variable number of 'options' inside a message. You could try with a
You'd need to use this inside the
and you need to build all the variables
These are the lines I had in my scenario which may be useful for you (or if you feel brave you can check the code around line 1000 of scenario 16 in my campaign):
Last, note that in your first menu item your filter won't work, if you check the
[for]
tag inside it but I doubt it would work. The other way is to insert manually the maximum number of options you want to allow, and use a [show_if]
to check the array length and only show the first options accordingly. You'd need to use this inside the
[message]
Code: Select all
[insert_tag]
name = option # this must be a supported tag inside the 'message' tag, so 'options' is not... an option
value = variable_you_have_defined_1
[/insert_tag]
variable_you_have_defined_1
somewhere else, which you could do through a loop. They must be structured variable with the content of the option
. These are the lines I had in my scenario which may be useful for you (or if you feel brave you can check the code around line 1000 of scenario 16 in my campaign):
Spoiler:
set_menu_filter
doc it only supports filter_location
and there is no unit
variable associated, so you must use x1,y1
. Also, I think you need mode = append
inside store_unit
too. Hope this helps, good luck!- Pentarctagon
- Project Manager
- Posts: 5564
- Joined: March 22nd, 2009, 10:50 pm
- Location: Earth (occasionally)
Re: Help on creating an array of stored units.
[insert_tag] should work on each element of an array, so this should do the same thing:
Code: Select all
{FOREACH mercenaries i} # vector of units I defined somewhere else
[set_variables]
name=my_options
mode=append
[value]
label=$mercenaries[$i].name
description=$mercenaries[$i].description
image=$mercenaries[$i].image|~CROP(17,10,40,50)~SCALE(0.5,0.5)
[command]
{HIRE_MERCENARY mercenaries[$i] 51 37} # command to unstore/place unit. In my case defined in a macro
[/command]
[/value]
[/set_variables]
{NEXT i}
[message]
speaker=narrator
caption= _ "Mercenaries Available"
message= _ "Important! All mercenaries are loyal, but will work for you only in this scenario. Each time one of them dies while in mission for you, you will have to pay 40 gold pieces for funeral expenses and family compensation. No refunding."
# I had 7 options
[insert_tag]
name=option
variable=my_options
[/insert_tag]
[option]
message= _ "Quit the tavern."
[command]
{VARIABLE get_out yes}
[/command]
[/option]
[/message]
99 little bugs in the code, 99 little bugs
take one down, patch it around
-2,147,483,648 little bugs in the code
take one down, patch it around
-2,147,483,648 little bugs in the code
- skeptical_troll
- Posts: 500
- Joined: August 31st, 2015, 11:06 pm
Re: Help on creating an array of stored units.
niiiiiice! I wish I realized it at the time!! Do you mind if I edit the wiki to specify this case with arrays? Or if you're unsure do you prefer that I check beforehand that it works as you're suggesting?Pentarctagon wrote: ↑February 1st, 2021, 9:21 pm [insert_tag] should work on each element of an array, so this should do the same thing
- Pentarctagon
- Project Manager
- Posts: 5564
- Joined: March 22nd, 2009, 10:50 pm
- Location: Earth (occasionally)
Re: Help on creating an array of stored units.
I'm pretty confident, but it never hurts to check first.
99 little bugs in the code, 99 little bugs
take one down, patch it around
-2,147,483,648 little bugs in the code
take one down, patch it around
-2,147,483,648 little bugs in the code
Re: Help on creating an array of stored units.
You are not storing the unit or variable correctly, and in unstore menu you wrote options.
Test the following. There might be better alternatives too.
Edit: your use of command message and speaker is confusing the hell out of me! I cleaned it up a bit.
Test the following. There might be better alternatives too.
Code: Select all
[event]
name=prestart
[set_menu_item] # boarding ships
id=embark
description= _ "Board ship"
[show_if]
[have_unit]
x,y=$x1,$y1
[/have_unit]
[/show_if]
[command] # embark
[message]
speaker=narrator
message="Board ship"
[option]
label= _ "Board $unit.name"
[command]
[set_variables]
name=shipventory
mode=append
[value]
label="$unit.name"
[command]
[for]
array=a_unit
reverse=yes
[do]
[if]
{VARIABLE_CONDITIONAL a_unit[$|i].name equals $unit.name}
[then]
[unstore_unit]
variable=a_unit[$|i]
x,y=$|x1,$|y1
[/unstore_unit]
{CLEAR_VARIABLE a_unit[$|i]}
[/then]
[/if]
[/do]
[/for]
[for]
array=shipventory
reverse=yes
[do]
[if]
{VARIABLE_CONDITIONAL shipventory[$|i].label equals $unit.name}
[then]
{CLEAR_VARIABLE shipventory[$|i]}
[/then]
[/if]
[/do]
[/for]
[/command]
[/value]
[/set_variables]
[store_unit]
[filter]
x,y=$x1,$y1
[/filter]
variable=a_unit
kill=yes
mode=append
[/store_unit]
[/command]
[/option]
[option]
label= _ "Cancel"
[command][/command]
[/option]
[/message]
[/command]
[/set_menu_item]
[set_menu_item] # disembark
id=disembark
description= _ "Disembark units from ship"
[command] # disembark
[message]
speaker=narrator
message="Disembark"
[insert_tag]
name=option
variable=shipventory
[/insert_tag]
[option]
label= _ "Cancel"
[command][/command]
[/option]
[/message]
[/command]
[/set_menu_item]
[/event]
Edit: your use of command message and speaker is confusing the hell out of me! I cleaned it up a bit.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
Thank you all for your very helpful replies!
I’m going to try these out!
I really dove in deeper than my experience level with this, (that’s how you learn though, I guess)
I will update the post with the current version I have after testing these solutions, so we’ll be on the same page.
I’m going to try these out!
I really dove in deeper than my experience level with this, (that’s how you learn though, I guess)
I did clean up some of the command message stuff a little bit too.
I will update the post with the current version I have after testing these solutions, so we’ll be on the same page.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
Ah, yes! all these little things, can be trick to catch as a beginner, thanks for pointing that one out!skeptical_troll wrote: ↑February 1st, 2021, 9:02 pm You'd need to use this inside the[message]
Code: Select all
[insert_tag] name = option # this must be a supported tag inside the 'message' tag, so 'options' is not... an option value = variable_you_have_defined_1 [/insert_tag]
Very helpful! Thanks a bundle!skeptical_troll wrote: ↑February 1st, 2021, 9:02 pm Last, note that in your first menu item your filter won't work, if you check theset_menu_filter
doc it only supportsfilter_location
and there is nounit
variable associated, so you must usex1,y1
. Also, I think you needmode = append
insidestore_unit
too. Hope this helps, good luck!
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
WOW! That did it!vghetto wrote: ↑February 2nd, 2021, 4:34 am You are not storing the unit or variable correctly, and in unstore menu you wrote options.
Test the following. There might be better alternatives too.
Code: Select all
[event] name=prestart [set_menu_item] # boarding ships id=embark description= _ "Board ship" [show_if] [have_unit] x,y=$x1,$y1 [/have_unit] [/show_if] [command] # embark [message] speaker=narrator message="Board ship" [option] label= _ "Board $unit.name" [command] [set_variables] name=shipventory mode=append [value] label="$unit.name" [command] [for] array=a_unit reverse=yes [do] [if] {VARIABLE_CONDITIONAL a_unit[$|i].name equals $unit.name} [then] [unstore_unit] variable=a_unit[$|i] x,y=$|x1,$|y1 [/unstore_unit] {CLEAR_VARIABLE a_unit[$|i]} [/then] [/if] [/do] [/for] [for] array=shipventory reverse=yes [do] [if] {VARIABLE_CONDITIONAL shipventory[$|i].label equals $unit.name} [then] {CLEAR_VARIABLE shipventory[$|i]} [/then] [/if] [/do] [/for] [/command] [/value] [/set_variables] [store_unit] [filter] x,y=$x1,$y1 [/filter] variable=a_unit kill=yes mode=append [/store_unit] [/command] [/option] [option] label= _ "Cancel" [command][/command] [/option] [/message] [/command] [/set_menu_item] [set_menu_item] # disembark id=disembark description= _ "Disembark units from ship" [command] # disembark [message] speaker=narrator message="Disembark" [insert_tag] name=option variable=shipventory [/insert_tag] [option] label= _ "Cancel" [command][/command] [/option] [/message] [/command] [/set_menu_item] [/event]
Now that the storing function is working, I will have to add the proper locations to unstore the units to etc... but that should be relatively easy
I can't express how much I appreciate you all helping me through this! It certainly helped in my WML journey, and helps immensely in my ability to learn as well!
When I finish this mod, I would very much like to credit all of you who helped me in this, because I couldn't have possibly done it without you.
Thanks a bundle!
Re: Help on creating an array of stored units.
What I wrote works but problematic.
You need to refine it in order to pinpoint the unit you want to store or unstore.
Going only by the unit name will break if 2 or more units have the same name.
It won't work with nameless walking corpses or ghosts either.
You're likely to lose units with the above method.
You need to refine it in order to pinpoint the unit you want to store or unstore.
Going only by the unit name will break if 2 or more units have the same name.
It won't work with nameless walking corpses or ghosts either.
You're likely to lose units with the above method.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
Ah, yes... that would be problematic.vghetto wrote: ↑February 3rd, 2021, 9:35 am What I wrote works but problematic.
You need to refine it in order to pinpoint the unit you want to store or unstore.
Going only by the unit name will break if 2 or more units have the same name.
It won't work with nameless walking corpses or ghosts either.
You're likely to lose units with the above method.
I'll see what I can do.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
Would this work?
Added
I changed the variable
Added
variable=$unit.id
in [value]
instead of using the label=$unit.name
hopefully avoiding any issues with the name being the same, and also keeping the "id" from being seen in game when choosing the units to unstore.Code: Select all
[set_variables]
name=ship_inventory
mode=append
[value]
label="$unit.name"
image=$unit.image
variable=$unit.id # instead of the "label=$unit.name" $unit.id is unique, avoiding the problems with using names?
[command]
[for]
array=a_unit
reverse=yes
[do]
[if]
{VARIABLE_CONDITIONAL a_unit[$|i].id equals $unit.id} # changed these from "name" to "id"
[then]
[unstore_unit]
variable=a_unit[$|i]
x,y=$|x1,$|y1
[/unstore_unit]
[/then]
[/if]
[/do]
[/for]
[for]
array=ship_inventory
reverse=yes
[do]
[if]
{VARIABLE_CONDITIONAL ship_inventory[$|i].label equals $unit.name} # show name when choosing unit
[then]
{CLEAR_VARIABLE ship_inventory[$|i]}
[/then]
[/if]
[/do]
[/for]
[/command]
[/value]
[/set_variables]
shipventory
to ship_inventory
to be more understandable.Re: Help on creating an array of stored units.
Maybe.
I'd change
and i'd change
to
Start with that and see where it gets you.
Edit: Actually, changing the variable to ship_id might be even better than id. Remember ship_inventory will get inserted into a [message] and we don't want all of its values to get processed by the [message] tag filters.
I'd change
variable=$unit.id
to id=$unit.id
and i'd change
Code: Select all
{VARIABLE_CONDITIONAL ship_inventory[$|i].label equals $unit.name} # show name when choosing unit
Code: Select all
{VARIABLE_CONDITIONAL ship_inventory[$|i].id equals $unit.id}
Edit: Actually, changing the variable to ship_id might be even better than id. Remember ship_inventory will get inserted into a [message] and we don't want all of its values to get processed by the [message] tag filters.
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
I need to somehow create any number of arrays, and give them each a unique id.
What I'm thinking, is that I can basically tie the ID of a ship
Create a
And maybe when a ship is recruited, that's when the array is created? and the array would simply connect to the ships id at that point.
Here's my up to date version of the mod that I'm working with.
What I'm thinking, is that I can basically tie the ID of a ship
id=$unit.id
to the array.Create a
variable
? to allow multiple arrays.And maybe when a ship is recruited, that's when the array is created? and the array would simply connect to the ships id at that point.
Here's my up to date version of the mod that I'm working with.
- Attachments
-
- ships_mod.zip
- (5.91 KiB) Downloaded 156 times
- Legend_Rider
- Posts: 35
- Joined: June 20th, 2018, 4:51 pm
Re: Help on creating an array of stored units.
I just noticed a bug... Apparently if units disembark from the ship, embark again, then disembark, they duplicate.