Skip to main content

Indie game storeFree gamesFun gamesHorror games
Game developmentAssetsComics
SalesBundles
Jobs
TagsGame Engines

Okay, I give.  It's possible I'm not even messing with the right part of the code (I recently did a giant overhaul of the game's text just for fun before realizing that the text I was working with was obsolete/nonfunctional and just a few lines had been lifted to an entirely different part of the code, which was the part that actually mattered, sigh).  It's possible that I'm overlooking something basic, or that the part of the code I'd actually need to mess with isn't even editable in the user-accessible text-style files, so here I am hoping for answers/guidance.

(Note: I'm a longtime hobbyist coder/game designer, and new to Godot/GDScript, but it's similar to many languages I've used over the years, and most of the basics are easy enough to grasp.  So I expect I might be failing at some core distinctions or underlying foundational details.)

Anyway, so, in StatsTab.gd I found the section where some buttons pop up and you can order them to call you by a new name.  So I figured I'd try to add a button that lets you change their name.  Mostly I'm just copying what seems like a reasonable section of code and changing a few tidbits that seem like they won't break anything.  (I do feel a bit like the classmates I tutored back in college, when I was already skilled in Visual Basic while they were randomly copy-pasting code with no grasp of the underlying structure and then getting confused why it broke.)  It easily created a button, but of course the button doesn't do anything.

So I hunted through a few files, making some educated guesses, and happened across Mansion.tscn (I've only recently dug into files that aren't .gd), which does have the right variable names (callorder, callconfirm).  So I copied some code there, changed names to match the other file, and gave it a shot.  No dice.  Button appears, but does not do anything.

I double-checked that I hadn't misspelled anything, and that all the references match the pattern of the original code ("callorder" becomes "namechange", "callconfirm" becomes "namechangeconfirm").  Nothing looks like it needs a particular uncopyable code (e.g. a unique numerical ID).  It appears that having identical names (like "Label") is fine so long as they're under distinct Nodes.  I finally got smart enough to open all the files collectively in Notepad++ and search for the variable name, and it appears that these are the only two files that reference it, out of the Scripts folder and the Files folder.

And just to test, I went through the original functions and changed the internal parts (not referencing the variable name) and got a functional change-name button.  But changing all the references to "callorder" and "callconfirm" to "blahcallorder" and "blahcallconfirm" breaks the button entirely, so clearly there's something else going on here.

So now I'm stumped.

Here's the original code.  To keep the code here shorter, I've omitted the Anchors and Margins, as I can't imagine they're part of the problem here (and I haven't messed with them, just copied them wholesale hoping the button would show up in the same place).  Again, all I did was change "callorder" to "namechange" and "callconfirm" to "namechangeconfirm" in copied code in the same file:

Part 1 (in Mansion.tscn):
[connection signal="pressed" from="MainScreen/slave_tab/stats/callorder/callconfirm"
to="MainScreen/slave_tab/stats" method="_on_callconfirm_pressed"]
Part 2 (in Mansion.tscn):
[node name="callorder" type="Popup" parent="MainScreen/slave_tab/stats"]
size_flags_vertical = 2
[node name="TextureRect" type="TextureRect" parent="MainScreen/slave_tab/stats/callorder"]
texture = ExtResource( 44 )
expand = true
[node name="Label" type="Label" parent="MainScreen/slave_tab/stats/callorder"]
size_flags_horizontal = 2
size_flags_vertical = 0
text = "How should $name address you?"
align = 1
[node name="callconfirm" type="Button" parent="MainScreen/slave_tab/stats/callorder"]
size_flags_horizontal = 2
size_flags_vertical = 2
text = "Confirm"
[node name="LineEdit" type="LineEdit" parent="MainScreen/slave_tab/stats/callorder"]
size_flags_horizontal = 2
size_flags_vertical = 2
caret_blink = true
Part 3 (in StatsTab.gd):
func callorder():
    get_node("callorder").popup()
    ## Improved phrasing
    get_node("callorder/Label").set_text(person.dictionary("How should $name address you?"))
    get_node("callorder/LineEdit").set_text(person.masternoun)
    get_node("callorder/LineEdit").set_placeholder(person.getMasterNoun())
func _on_callconfirm_pressed():
    get_node("callorder").visible = false
    var text = ""
    ## Improved phrasing plus support for characters who don't speak with their mouths
    if !person.traits.has("Mute"):
        text = "You have ordered $name to call you '$master' from now on. "
    else:
        text = "Since $name cannot speak, you teach $him a way to sign '$master'."
    person.masternoun = get_node("callorder/LineEdit").get_text()
    get_tree().get_current_scene().close_dialogue()
    get_tree().get_current_scene().popup(person.dictionary(text))
Part 4 (in StatsTab.gd):
buttons.append({text = person.dictionary("Order to call you ..."), function = 'callorder'})
SAMPLES OF MY VERSION:
## Testing to see if I can add a button
buttons.append({text = person.dictionary("Change Name"), function = 'namechange'})
#That part worked fine, but the rest doesn't:
[node name="namechange" type="Popup" parent="MainScreen/slave_tab/stats"]
[connection signal="pressed" from="MainScreen/slave_tab/stats/namechange/namechangeconfirm"
to="MainScreen/slave_tab/stats" method="_on_namechangeconfirm_pressed"]
func _on_namechangeconfirm_pressed():

Note: I'm not adding interior line breaks or tabs in the actual code unless they're there in the code I'm working from.  The copy is identical except for the variable name changes, the obvious strings (like "Order to call you..." to "Change Name", which works fine), and a bit of If/Else code (which I'm not having any trouble with elsewhere and doesn't seem to be related to the problem).

Any clue what I'm missing?

(1 edit)

Hello, I basically became the leader of the modding community here after I spent a couple years debugging this game, though I haven't been as active lately. Usually the fastest way to get help is to ask on the Discord (https://itch.io/t/284398/discord), but I try to keep an eye on this site as well.

Godot Script is mostly Python with a little LUA mixed in so the basics should be intuitive to anyone that has messed around with other scripts, but it does a few things in eccentric ways. Most of the files can be edit in text editors, though I recommend using the Debug mod (https://itch.io/t/1137280/debugmod-v10d) for dealing with errors. For general editing of the GUI (scene files .scn and text scene files .tscn) I strongly recommend using the editor provided for the Godot Engine. The game's program folder is mostly the same as the project folder and it uses a version between 3.2 and 3.3 (the latter is likely the closest match).

Strive for Power was created by a beginner programmer so the code can be straightforward to read but messy in design. Large sections of code and even entire files are no longer used, with no clear indications most of the time. This problem was rather low on the priorities list so I haven't gotten around to it.

Scene files are generally used to create GUI that is not expected to dynamically change form or order during run time. Godot provides multiple ways to connect functions to actions such button presses. For buttons created in scene files the standard approach is the stuff you found at the bottom of the file:

[connection signal="pressed" from="MainScreen/slave_tab/stats/callorder/callconfirm" to="MainScreen/slave_tab/stats" method="_on_callconfirm_pressed"]

However, Strive has multiple systems for dynamically creating buttons during runtime and the system relevant to what you are working on is "func dialogue" found in ".../scripts/Mansion.gd". In another function it uses the following code to bind functions to the button presses.

newbutton.connect("pressed", destination, array.function, array.args)

However, this all works pretty well and there's not really anything to worry about besides making certain that you spelled things consistently.


You have excluded some details of your version, so it's not possible for me to determine the exact causes of your problems. My first guess would be that you have not named your name change function exactly 'namechange', put something in the wrong file, or missed renaming something not shown.  I would expect it to be in statstab.gd and look something like this:

func namechange():
    get_node("namechange").popup()

You didn't specify the location and said it works, but I assume your dynamic button data looks similar to this:

buttons.append({text = person.dictionary("Order to call you ..."), function = 'callorder'})
buttons.append({text = person.dictionary("Change Name"), function = 'namechange'})

For clarity, the name of the function should be as you specified in your dynamic button data. The node names and paths for get_node() in your function should be as you specified in mansion.tscn.

Also, while it doesn't appear to cause any errors and you mentioned not adding line breaks, the signal connection lines contain breaks that are not originally present in the file. A bigger problem would be using spaces instead of tabs within your code.

(3 edits)

Yeah, I specified that I didn't change spaces in the actual code because I did add line breaks here (to prevent it going off the side of my screen when I switched it to Code Mode there).  I'm aware that spaces can be functional; they aren't in most of the languages I've used, but since Godot/GDScript uses indentations functionally I presume that all whitespace is potentially functional and I'm careful about not messing with it (my brain is pretty well specced to grasp open/close mechanics such as parentheses and nesting -- that's the very thing that those classmates in college were messing up all the time, pasting code into random spots and breaking the nested logic of the original code).

ETA: And yes, I am very careful about the distinction between tabs and spaces.  I'm using tabs in the code for all the indentations -- they don't just look similar, they are equivalent even in the whitespace.

Here's my code (again omitting Anchors and Margins, for brevity).  Again, these are in the exact same files, matching the original code exactly, including the white space (the line breaks have been added here purely for readability, and are not used in the code); the only thing I have changed is the variable names (carefully matched in logic to the original set of names), obvious Strings, and some If/Then logic that shouldn't impact the buttons themselves, just the text displayed (I even commented it out with a test string instead, to be sure it wasn't screwing things up).

##############################################
#### Testing to see if I can add a button ####
##############################################
[node name="namechange" type="Popup" parent="MainScreen/slave_tab/stats"]
size_flags_horizontal = 2
size_flags_vertical = 2
[node name="TextureRect" type="TextureRect" parent="MainScreen/slave_tab/stats/namechange"]
texture = ExtResource( 44 )
expand = true
[node name="Label" type="Label" parent="MainScreen/slave_tab/stats/namechange"]
size_flags_horizontal = 2
size_flags_vertical = 0
text = "What name should $name respond to?"
align = 1
[node name="namechangeconfirm" type="Button" parent="MainScreen/slave_tab/stats/namechange"]
size_flags_horizontal = 2
size_flags_vertical = 2
text = "Change Their Name"
[node name="LineEdit" type="LineEdit" parent="MainScreen/slave_tab/stats/namechange"]
size_flags_horizontal = 2
size_flags_vertical = 2
caret_blink = true
##################
#### END TEST ####
##################
##############################################
#### Testing to see if I can add a button ####
##############################################
[connection signal="pressed" from="MainScreen/slave_tab/stats/namechange/namechangeconfirm"
to="MainScreen/slave_tab/stats" method="_on_namechangeconfirm_pressed"]
##############################################
#### Testing to see if I can add a button ####
##############################################
#### Function called when new button gets pressed:
func namechange():
get_node("namechange").popup()
get_node("namechange/Label").set_text(person.dictionary("What name should $name respond to?"))
get_node("namechange/LineEdit").set_text(person.name)
get_node("namechange/LineEdit").set_placeholder(person.name)
#### When new button gets pressed:
func _on_namechangeconfirm_pressed():
get_node("namechange").visible = false
var text = ""
text = "Yes, $master."
#if person.obed < 35: ## Not yet broken
# if person.conf > 30:
# text = "— You can't just take my name away!"
# else:
# text = "— Are you really going to take even my name away??"
#elif person.obed > 70: ## Highly obedient
# text = "— Of course, $master.  Every part of me exists to serve your will."
#else: ## Moderate, compelled obedience
# if person.conf > 60:
# text = "— I guess I don't have much choice."
# else:
# text = "— Yes... $master."
person.name = get_node("namechange/LineEdit").get_text()
get_tree().get_current_scene().close_dialogue()
get_tree().get_current_scene().popup(person.dictionary(text))
## Testing to see if I can add a button
buttons.append({text = person.dictionary("Change Name"), function = 'namechange'})

So yeah, I don't think I missed something as simple as using the wrong name.  And since changing the original names (in both files) to blahCallOrder and blahCallOrderConfirm completely broke the original sections that were working, and since none of the other files in either directory reference these variables, it definitely feels like I'm missing a piece that needs to get accounted for elsewhere.

Also, I included the buttons.append line exactly as you quoted, in my "samples of my code" at the end of my first post there.  Just added it to here for completion.  Really wish the code formatting let me include line breaks, this wall of text stuff is killing me.

(3 edits)

I don't see any problems with the code as presented, including the commented out code. Probably due to itch.io formatting you are missing leading whitespace in the functions so I'll have to take your word that it is not an issue. You haven't specified if you are using the Debug mod or the editor, so I can't rule out the possibility of a tangentially related error somehow sabotaging you.

Itch.io code can be formatted but it doesn't play nice with copy and paste. Edit: seems extra lines really don't work, though adding a space to them works.

code
code after extra line break
    code after tab
 
code after extra line break with space


If we assume that there are no errors, then we will have to get creative in looking for the source of the problem. Please verify that you are not editing the files in the "backup" folder for Strive as those files are 100% copies but are not used except to replace the game's files whenever the mod system applies or resets mods. Note that any changes you have made to the non-backup files will be erased if you use the mod system, and the Debug mod doesn't actually use the mod system. Additionally if you have made your own copies of the files, make sure that the game is using files with your latest changes. Finally, I've had people report in some cases that editors like Notepad++ were somehow editing something like copies of files rather than the actual files so their edits had no effect, though I've never had this happen to me.

Using the Debug mod or editor it is possible to use print() to get direct feedback as to the state of the program in functions, which can be more useful than relying on the Game's GUI to behave as expected. The game also has a system designed for file based trace statements in globals.gd, but those are more helpful for dealing with crashes.