Ren'Py Making a player stats menu. Really need a fresh perspective.

Avalonica

Newbie
Oct 11, 2017
40
20
Hello. I have for hours non-stop trying to "make it work", but Goggle give me outdated code or examples that don't really "hit the spot".

I would love to "inject" into my alpha VN project a "status menu" for the MC. Please, don't stop reading... I know there are 100+ posts all over the Internet on this topic, but as mentioned none of them are relevant in this case.

1. Firstly I would love to have some code that lets the player press the Z key (or S key) in order to bring up the actual stat menu. Cheat Menu's made by D.S.-sama for many VN's open up in-game when one press the Z key. It's a wonderful feature. Here is the code I think is relevant (got it by reading the code in one of his Cheat Menu's):

You don't have permission to view the spoiler content. Log in or register now.

This might be a bit overkill, but I would not say no to also have the "main menu" when *in the game* to also have a button for "Statistics" so the player can reach it that way. If the Z-key idea is not doable, then at least that could be a good "backup plan". But as a complement it could be nice too...


2. The "Statistics Page" content should be filled out with some working examples like the one from the Code example, just... that it "should" work out-of-the-box if possible with some formatting examples.
You don't have permission to view the spoiler content. Log in or register now.


3. for the actual "Statistics Page" it should be like a "fresh" full screen that one can have a nice background image on, not a tiny winy little box. And that huge full screen box should also have a imagebutton that is clickable that closes the full screen box and returns the player back to exactly where she/he was when pressing the Z key.


I am so sorry for asking so much, but my entire project is hanging on this status display, becouse it will be too many characters and statistics going around that a player must be able to see it all on a status display. And I am totally new on Ren'Py so please if posting code examples, make them very complete and easy to understand and above all portable into Ren'py from the start.

Thank you all for any kind assistance.
 

anne O'nymous

I'm not grumpy, I'm just coded that way.
Modder
Donor
Respected User
Jun 10, 2017
10,302
15,172
This might be a bit overkill, but I would not say no to also have the "main menu" when *in the game* to also have a button for "Statistics" so the player can reach it that way.
Python:
init python:

    def myAction():
        #  If the screen is already opened, then close it...
        if not renpy.get_screen( "myScreen" ) is None:
            renpy.hide_screen( "myScreen" )
        # else open it.
        else:
            renpy.show_screen( "myScreen" )
        #  Then ask Ren'py to restart the interaction, which will,
        # among other things, redraw all the screens, and then
        # show yours, or hide it.
        renpy.restart_interaction()

    #  Add the key to bind to the action.
    config.keymap["myAction"] = "K_z"
    #  And link the action to the this key.
    config.underlay[0].keymap["myAction"] = myAction


screen myScreen():
    #  Ensure that the screen will be shown on top off all the others.
    zorder 100
    #  And make it modal, so the player can't break the game by clicking
    # outside of the screen.
    modal True
    text "{color=#F00}{b}opened{/b}{/color}"
By order or appearance : , , , , ; config.underlay being undocumented. As for zorder and modal, it's in .

You can found more about the syntax for the keys, in and in .
But be careful, Ren'py already use a lot of keys, and some are added time to time. So when you update the version of the SDK, always check [path to SDK]/renpy/common/00keymap.rpy to verify that this new version don't use the same key(s) than you.


The rest of the questions are more "styling" than "coding", I'll let people better than me on this field answer.
 

Avalonica

Newbie
Oct 11, 2017
40
20
This is amazing. The code you gave me worked directly! :geek:

With the Z-key I can clearly see how it open/closes as I press the button. Now, before I even start "messing" with your wonderful code I just want to confirm some important things for future reference as I am far to green to 100% understand things as of this moment.

1. Let's say I want to "add" a background image to the window I now can open with the Z-key, where in the code approximate would I start writing that code in order to not break anything?

2. I know this is a style issue, but would it be okay to also (just as an example) to have an example on a formatting on screen with some "text" in this window that is on-top of the background image, like this:
Statistics
STR: 9
DEX: 12
CON: 8
INT: 15
CHA: 18
As a bonus it would be great if the formatting would align all the "stats" under each other like in a table so the number dont look so misaligned under each other.

3. A little "button" made from a imagemap (just write in a bogus png name will do perfect as a guide for now) that is placed on the screen somewhere that's clickable that will "close" the screen when pressed.

4. When the game starts the Z-key can open the menu (even in the main game before the actual adventure is started. How would the code look like if we just made that "not possible". I can live with this bug, but if only the Z-key would register "inside" the adventure it could be helpful.


With the above questions addressed I think anyone like me could get things running... Of course there are some more tiny questions but the above ones are the most important ones, and thanks so much for making the code. I am so close now to actually have the GUI in a place where my VN needs it to be.
 

Avalonica

Newbie
Oct 11, 2017
40
20
Despite me being 99.9% new on this I try my best even without guidance and so far it's going mostly well, but there is an issue with a background image. As I press the Z-key I now get my text and test sprite up as intended but I have tried a lot to get a background image to "hide" the normal game window (the one in this case with several colors) with a one called "space.jpg".

Here is the code so far:

You don't have permission to view the spoiler content. Log in or register now.

I have tried lots of syntax for adding space.jpg but either I get crashes or it won't show... Any help would be most welcome

EDIT:
I managed to get a probably "bad" fix to work by adding:

imagebutton:
idle "space" hover "space" xalign 0.0 yalign 0.0

But I don't think you are supposed to post a background-image like that...
 
Last edited:

Avalonica

Newbie
Oct 11, 2017
40
20
Oh, this is important: Since the player can pick from several MC's before the game start, I really need to be able to have one callable stats page for each of them with the Z-key. Would it somehow be possible to not have the display to be started when the game starts but with some sort of "trigger" like:
if PlayerID >= 1:
if PlayerID >= 2:
if PlayerID >= 3:
After the game somehow "know" the ID it will point to the proper menu. So I would love to make one stats page for each MC, but currently since the game starts the menu directly it's impossible :)

EDIT: I try this code:
init python: if PlayerID >= 1: <--- but the game crash
Somehow the game must not be allowed to start the "z-key menu" before I allow it. This way every MC can get their own menu.

EDIT 2: Maybe I do all of this wrong.
What if we *after* this code somehow use the "if PlayerID >= 1:" syntax ?

# And make it modal, so the player can't break the game by clicking
# outside of the screen.
modal True
text "{color=#F00}{b}opened{/b}{/color}"
"if PlayerID >= 1:" ---> Then we "goto" 001
"if PlayerID >= 2:" ---> Then we "goto" 002
"if PlayerID >= 3:" ---> Then we "goto" 004

Sadly I am to new to even figure out how to write this code, but I think my overall idea is presented quite well... I hope :unsure:

Here, I think I got it right but Ren'py thinks otherwise, This will only show the relevant TEXT for the correct player
PHP:
if PlayerID >= 1:
    fixed:
        text "Player 001: [mc_points_one] points" xalign 0.5 yalign 0.1111
elif PlayerID >= 2:
    fixed:
        text "Player 002: [mc_points_two] points" xalign 0.5 yalign 0.1111
elif PlayerID >= 3:
    fixed:
        text "Player 003: [mc_points_three] points" xalign 0.5 yalign 0.1111
else:
    fixed:
        text "Player 004: [mc_points_four] points" xalign 0.5 yalign 0.1111
 
Last edited:

anne O'nymous

I'm not grumpy, I'm just coded that way.
Modder
Donor
Respected User
Jun 10, 2017
10,302
15,172
1. Let's say I want to "add" a background image to the window I now can open with the Z-key, where in the code approximate would I start writing that code in order to not break anything?
In a way, the answer is in the question, you need to use the screen statement. Like, obviously, Ren'py proceed the screen starting by the first line, it should be the first things displayed, to not hide the rest of the screen :
Code:
screen whatever:
    add "images/my background.jpg"
    [...]
He I used directly the name of the file, but you can all use a displayable :
Code:
image myBackground = "images/my background.jpg"

screen whatever:
    add "myBackground"
    [...]

2. I know this is a style issue, but would it be okay to also (just as an example) to have an example on a formatting on screen with some "text" in this window that is on-top of the background image, like this:
Well, it all depend of what you effectively want as result. But it can one of those way :
Code:
style fieldName is default:
    color "#00F"

style fieldValue is default:
    color "#0F0"

screen myScreen():

    vbox:
        text "field a: [myValue]"

        null height 20

        hbox:
           text "field b" style "fieldName"
           text " : "
           text "[myValue]" style "fieldValue"

        null height 20

        grid 2 2:
            text "field c1 " style "fieldName"
            text "[myValue]" style "fieldValue"
            text "field c2 " style "fieldName"
            text "[myValue]" style "fieldValue"

        null height 20

        hbox:
            vbox:
                text "field d1" style "fieldName"
                text "field d2" style "fieldName"
            null width 10
            vbox:
                text "[myValue]" style "fieldValue"
                text "[myValue]" style "fieldValue"
By order of appearance, , , and .


As a bonus it would be great if the formatting would align all the "stats" under each other like in a table so the number dont look so misaligned under each other.
The last two examples do that.


3. A little "button" made from a imagemap (just write in a bogus png name will do perfect as a guide for now) that is placed on the screen somewhere that's clickable that will "close" the screen when pressed.
You don't need an imagemap for that. With the help of the screen action, an will do it perfectly :
Python:
screen whatever:
    text "{color=#F00}{b}opened{/b}{/color}"
    null height 200
    imagebutton:
        # The images can be defined like this
        auto "myCloseButton_%s.png"
 #       # Or like that if you don't have an image by state
#        idle "myCloseButton.png"
        # Here you pass as parameter the name of the screen to hide.
        action Hide( "whatever" )
It can even be a simple :
Code:
screen whatever:
    text "{color=#F00}{b}opened{/b}{/color}"
    null height 200
    textbutton "Close":
        action Hide( "whatever" )

4. When the game starts the Z-key can open the menu (even in the main game before the actual adventure is started. How would the code look like if we just made that "not possible". I can live with this bug, but if only the Z-key would register "inside" the adventure it could be helpful.
I think that there's a flag somewhere to tell if the game is already started, but I fail to remember where. Therefore a little fix to simulate it should do it :
Code:
default gameIsStarted = False

label start:
    $ gameIsStarted = True
    [...]
And you change "myAction" like this :
Code:
init python:

    def myAction():
        if gameIsStarted is False: 
            return
        if not renpy.get_screen( "myScreen" ) is None:
            renpy.hide_screen( "myScreen" )
        else:
            renpy.show_screen( "myScreen" )
        renpy.restart_interaction()
 
  • Like
Reactions: Avalonica

anne O'nymous

I'm not grumpy, I'm just coded that way.
Modder
Donor
Respected User
Jun 10, 2017
10,302
15,172
Oh, this is important: Since the player can pick from several MC's before the game start, I really need to be able to have one callable stats page for each of them with the Z-key.
Why ? As I understand it, once the game is started, the only way to change the MC will be to restart a game. Therefore they can share the same variables to store their values.
 

Avalonica

Newbie
Oct 11, 2017
40
20
Why ? As I understand it, once the game is started, the only way to change the MC will be to restart a game. Therefore they can share the same variables to store their values.
Thanks so much for all your answers, I'll be on this for hours. Oh, I make a different VN. At start the player will be able to pick from serveral characters, and each once will have different stats. After a long time a "new" generation will take over, and this is why every character that the player "plays" must have their own unique stats "saved" since the player will down the road will meet them. In other words, I want to make a RPG/VN. I'll probably use that syntax that also lets Ren'py save externally too. Oh, don't worry, I'll 100% come back here with more questions when the GUI part is finished... :devilish:
 

anne O'nymous

I'm not grumpy, I'm just coded that way.
Modder
Donor
Respected User
Jun 10, 2017
10,302
15,172
Thanks so much for all your answers, I'll be on this for hours. Oh, I make a different VN. At start the player will be able to pick from serveral characters, and each once will have different stats.
It's a little advanced, but there's many way to deal with this, while still having only one screen :
[wrote on the fly, I can have made a typo somewhere]
Python:
# Where the stats are stored
default MCstats = { "strength":0, "charisma": 0, "agility": 0 }
# Will be the list of available states
default actualStats = []

style fieldName is default:
    color "#00F"

style fieldValue is default:
    color "#0F0"

label whatever:
    menu:
        "Choose your mc"

        "This MC":
            $ actualStats = [ "strength", "charisma" ]

        "That MC":
            $ actualStats = [ "charisma", "agility" ]

        "or this MC":
            $ actualStats = [ "strength", "agility" ]


    show screen whatever
    "WAIT"
    jump start

screen whatever:
    vbox:
        # Browse all the valid stats for this MC
        for stat in actualStats:
           # Display the name
           text "[stat] :" style "fieldName"
           # And it's value
           text "{}".format( MCstats[stat] ) style "fieldValue"
Then when you want to works with the stats :
Code:
label whatever:
    if MCstats["strength"] > 10:
       "Wow, you're strong"
   
   $ MCstats["charisma"] += 1

Or if you really need to works with effectively separated variables, you can go for this, with the help of the screen statement :
Code:
screen whatever():
    if playerMC == 1:
        use MC1stats
    elif playerMC == 2:
        use MC2stats
    [...]

screen MC1stats():
    text "strength: [strength]"
    text "charisma: [charisma]"

screen MC2stats():
    text "charisma: [charisma]"
    text "agility: [agility]"
 
  • Like
Reactions: Avalonica