Alpha Game: Vortex The Pretty


Well I got it running, but I cannot escape into the game, I,m stuck, and when I try to hit the "load profile bar, the game will crash. did I do something wrong? oh I almost forgot the key mapper itself gave me a warning Some thing like

“Using dummy save- and load- callbacks. Bindings and profiles will not be said or loaded!”

Theoretically, it shouldn’t break the logic of something like Roaming Ralph–it should pretty much just replace it. However, I of course don’t know what else you’re doing in your code, and thus how the two might interact.

Note that KeyMapper has more than just the “KEYMAP_HELD_KEY” method of handling a control–it can also call arbitrary methods (as with an event). (If you want an example of this in use, look at “KeyMapperTester.py”.)

I… don’t recommend that. It sounds like something that’s likely to introduce bugs, and seems likely to be more complicated than is called for.

Just hide the KeyMapper’s “guiRoot”–it’s a DirectGUI object, and can be treated as such. You could even attach it to other UI elements that you may already have.

(The example game that comes with KeyMapper does something like this, as I recall.)

Ah, right, I’d forgotten about that: in short, there’s an issue in DirectOptionMenu in which it crashes when the user attempts to open a menu with no entries. Since you presumably have no profiles yet with which to fill the menu, it crashes. (I have an open pull request on GitHub that’s related to this, I believe.)

To work around it, just save a profile (via the “Add new” button). Once you have at least one profile available, the menu should be fine.

Sorry about that!

As noted above, KeyMapper doesn’t handle saving and loading of profiles out-of-the-box; that’s left for you to implement. That warning is intended to let you know that you don’t currently have anything handling that.

However, overall, if it’s going to be a problem to integrate KeyMapper, maybe it would be easier to just go with your previous idea of reading key-mappings from a file?

1 Like

Thaumaturge, oh no, it is not a problem, it is the first attempt after all, for what it is the results came out pretty good, I just need to tune it that is all, which was why I was asking.

1 Like

Okay hiding the gui like you said worked, hmm, well about the “Load profile” and “Add new” gui elements, is there any commands to hide those, maybe change them to something like “Continue”?



Well I got rid of the error message that pops up and the two buttons that will cause error with your advice and peeking at your code, everything is looking good at the moment, I would like to ask how I would add a new button saying “Looks good…” pertaining that the player is fine with the selected controls.

Then give that button the command to hide the gui as you suggested earlier, preferably in the same spot as the two buttons I just hid.

Fair enough! If you’re happy to keep going, then so am I. :slight_smile:

Well done on that. :slight_smile:

I would suggest looking at how I created the “Add new” button for an idea of how to construct your button. The short version is that KeyMapper’s GUI just uses DirectGUI, and thus you should be able to attach new DirectGUI controls to it as per normal with DirectGUI.

As to having the button hide the GUI, the simplest way might be to just set the button’s “command” keyword-parameter to be the “hide” method of the KeyMapper-object’s gui-root. (Or, if you attach the KeyMapper to another GUI-object, then the “hide” method of that object.)

I,m not educated on panda3d’s GUI functions (never needed them up to this point), so I’ll try to closely copy button code I examined that displayed the “Load profile” I,m just wondering how I can give it the effect of hiding the gui when it is pressed.

But I guess I can get back to you on that when done writing the code copy block in a minute or few.

The “Load Profile” control is a popup-menu control, so I don’t recommend looking at that one. I’d suggest looking at the “Add new” button, instead.

When you look at the button-code in order to construct your button, note the parameter labelled “command”–that should specify a method or function to be run when the button is clicked. This works much like a key-event: you simply give it a reference to a method or function.

In your case, you could simply assign that to the “hide” method of the KeyMapper gui-root object–that is, “self.whateverYouCalledYourKeyMapperObject.guiRoot.hide”.

okay, thanks for guidance.

1 Like

So I did the copy, but I had to alter a few things, like the frameBounds wouldn’t work at first so I had to create my own local variable frameBounds and point it to “self.keyMapper.list[“frameSize”]”, and so I got it to show, but as soon as clicked on it I got a error.

AttributeError: ‘DirectOptionMenu’ object has no attribute ‘minZ’

I suspect because minZ is self to your script therefor I would some how have to make it “self.keyMapper.minZ” because of this, it causes more problems with more variables relating to the script, so I ask what does the variable frameBounds[2] do?


Edit: After looking it over again, no, I think it has something to do with the function I created to hide both the button and gui.

    def keyMapclose(self):
        self.escapeMenu.hide()
        self.keyMapper.guiRoot.hide()

What do you think? these work if I place them in the main code block, however if done in a function like above, I get a crash, I wonder if it is my lack of python knowledge, hmm.

This seems to indicate that you copied the DirectOptionMenu–the popup menu that allows players to select a profile–rather than the DirectButton. It looks like it’s trying to open the popup menu, but failing.

(The variable “minZ” is part of DirectOptionMenu, but may not be available if the menu has no items in its list, if I recall correctly.)

That’s hard to answer, since you defined “frameBounds”–without seeing your definition for it, it’s hard to say what might be in there. ^^;

In general, however, the notation [ <some number> ] is used by Python lists, tuples, etc. to access an item in the list at the index given by “<some number>”.

Let me demonstrate with an example:

# A simple Python list
myList = ["a", "b", "c", "d"]

# Print the first item in the list--remember that
# list indices start with 0, not 1!
print (myList[0])
# This should print "a"

# Print the third item in the list
print (myList[2])
# This should print "c"

Therefore “frameBounds[2]” should correspond to the third item in the list named “frameBounds”.

I don’t think that it’s the method being called. It’s hard to be confident without looking at your code, but as I said above, it looks like you’ve copied the DirectOptionMenu rather than the DirectButton, and that the crash is related to the issue that I described earlier.

[edit]
But let’s check: would you please post the code that you’ve added, specifically the definition of the new button?

you mean the code block for my escape button? sure thing.

self.escapeMenu = DirectOptionMenu(text = "Looks good...", command = self.keyMapclose, scale = self.keyMapper.buttonSize, text_align = TextNode.ACenter, pos = (0, 0, frameBounds[2] - self.keyMapper.buttonSize*2.0), frameSize = (-3, 3, -0.7, 1), parent = self.keyMapper.guiRoot)

Yup, as I thought: you’ve copied the popup-menu, not the button. That’s why it’s producing a crash (it’s the DirectOptionMenu crash that I mentioned earlier).

You’re looking for a DirectButton, not a DirectOptionMenu, in this case, I believe.

1 Like

okay, cool, let me give a try real quick then.


yup that did it, you were right.


now clicking the “Looks good…” button take the gui away, so with the gui functional, it’s time move onto getting the actual keys to work.

1 Like

Excellent–I’m glad that you got it working! :slight_smile:

thanks, I actually almost got the keys to work but I’m still trying to figure out how to get the individual items out from “self.keyMapper.keys.items()”.

You should be able to just reference them via the control-names that you specified in when you called “addKey”. For example:

# When you setup your keys:
self.myKeyMapperObj.addKey("stepForward", "w", InputDevice.DeviceClass.keyboard, KEYMAP_HELD_KEY)

# When you want to access a key:
forwardKeyValue = self.myKeyMapperObj.keys["stepForward"]
1 Like

okay, that did the trick, thanks

1 Like

So I got everything setup, however there is one more issue, when player talks a NPC after some time a tiny icon with the button needed to proceeded is displayed, I would like it to display the key mapped to “ishop”, how would that syntax work? thanks

Edit: to clarify, how would I obtain the character bind to a key in a string?

Something like this:

rawBinding = self.keyMapperObj.keyBindings["ishop"].binding
# Let's skip over the axis business for now...
bindingText = self.keyMapperObj.getBindingName(rawBinding, 0)

(Although in the case of keyboard keys you could probably get away with just the first line above.)

okay, “self.keyMapper.keyBindings[“ishop”].binding” works for me, it looks like some bit of tweaking on where to place this option needs to be done, and I’ll release the next update, thanks Thaumaturge you helped out big.

1 Like