Using the event interface for making popups

vetiarvind

Prince
Joined
Oct 20, 2013
Messages
329
Location
Chennai, South India
What I am trying to achieve is a system where the user clicks a button in a python screen that opens a popup. I then get the user input text from the popup and call the dll with this value.

I used the event system to do this and the popup opening worked fine, but now it no longer does after I added a second event following the patter below. I don't know if it's because I don't get the event routing system, but if there's a simpler way of getting user input in text and calling the dll with it from python do let me know. (so far documentation on event routing and popups are few and far between)

So here is what I did:

I created a custom event in CvUtil.py:
Code:
MyEvent = 8888
In my python click event handler, I trigger the event:
Code:
CvEventInterface.beginEvent(CvUtil.MyEvent)
In CvEventManager.py:
I added the following property to self.Events for the event routing system:
Code:
CvUtil.MyEvent: ('MyEventName', self.doMyEventApply, self.doMyEventBegin),

which declare the callback and start methods for the corresponding event respectively. These are supposed to be called automatically from the CvEventManager.py class when I called the "beginEvent" method (see above). The actual content of these two methods look like:
Code:
#this creates a popup
def doSaveTradeGroupsBegin(self, argslist): 
    popup = CyPopup(CvUtil.MyEvent, EventContextTypes.EVENTCONTEXT_ALL, True)		
    popup.setHeaderString("hello".upper(), CvUtil.FONT_LEFT_JUSTIFY) 
    popup.createEditBox ("txtUserInput", 1)		
    popup.launch(true, PopupStates.POPUPSTATE_IMMEDIATE)

# do something on callback with popupReturn object's user entered values	
def doMyEventApply(self, playerID, userData, popupReturn):
I have checked\rechecked the code a few times, so now I'm wondering if using the CvEventInterface like this is good practice or not. (I read on sourceforge that you're not supposed to import any *Interface modules directly) so maybe that's the reason why I'm getting inconsistent results.
 
This might be completely irrelevant as I don't understand popups but I know that Kael made a thread to explain using popups http://forums.civfanatics.com/showthread.php?t=183126

Thanks, I have seen Kael's popup tutorial. However, he describes the CvPopupInfo class whereas I am working on the more powerful(and apparently harder to code) CvPopup. The difference seems to be that the former is only for output whereas the latter does I\O. However, I haven't seen any code for this online and hence my questions. Anyway, I will post to this thread if I figure out how to do this properly incase no further help is forthcoming.
 
What I am trying to achieve is a system where the user clicks a button in a python screen that opens a popup. I then get the user input text from the popup and call the dll with this value.
I made a DLL based window where clicking certain buttons opens a new DLL based window (specifically subprofessions in M:C). That turned out to be rather easy. The concept is closing the window and then open a new one.

I wonder if it is possible to do something like that here as well. Click the button, send arguments to the DLL and close the window. The DLL then opens a new python window, which allows you to write text. That window then closes and sends the result to the DLL. Maybe it is possible to close the window and open a new one in python alone, but since that appears to be the unreliable part, I wrote that it could go through the DLL.

Bug warning
Making the user click something, which changes game data is a high risk operation regarding network stability. If the result of the click should be known by other computers (like say disband unit), the result of the click should be transmitted through the network. Failure to do so can result in network desyncs.
 
Thanks for your input guys. I got this working, although I had to take a different route than doing it all in python. I also tried doing some stuff with python callbacks to callback inside python after a popup gets value entered, but that lead to no-man's land...Anyway back to the stuff that works:

So the trick is to open up a new popup in python and pass it over to the dll for it to perform the creation of the input boxes and event handling in the C++.

So you python will be:
Code:
popupInfo = CyPopupInfo()		
popupInfo.setText("Nuclear launch code key.Shh!")
popupInfo.setButtonPopupType(ButtonPopupTypes.BUTTONPOPUP_YOUR_NEW_SHINY_POPUP)
CyInterface().addPopup(popupInfo, gc.getGame().getActivePlayer(), true, false)

C++
In CvEnums.h,
register
Code:
BUTTONPOPUP_YOUR_NEW_SHINY_POPUP
and in CyEnumsInterface.cpp
add a mapping:
Code:
.value("BUTTONPOPUP_YOUR_NEW_SHINY_POPUP", BUTTONPOPUP_YOUR_NEW_SHINY_POPUP)

Now, we need to process the actual launch and event handling of the popup:
This is done in CvDLLButtonPopup.cpp. In launchButtonPopup() method, add a switch case for BUTTONPOPUP_YOUR_NEW_SHINY_POPUP:

where you do the launch
Code:
gDLL->getInterfaceIFace()->popupSetHeaderString(pPopup, "POPUP WEARING A CRUMPLED HAT");
//This is for the textbox
gDLL->getInterfaceIFace()->popupCreateEditBox(pPopup);
gDLL->getInterfaceIFace()->popupLaunch(pPopup, true, POPUPSTATE_IMMEDIATE);

For the event go to the OnOKClicked() method where you can similarly create a switch case for your new popup and access the user entered value using:
Code:
pPopupReturn->getEditBoxString(0)

You can access the hidden data that we passed from python code into a string using:
Code:
 CvString str(info.getText().c_str());
 
Back
Top Bottom