View Full Version : [PYTHONCOMP] Civ4lerts: Alert messages about in game events
Dr Elmer Jiggle Jan 31, 2006, 09:40 PM This mod implements on screen alerts for a variety of in-game events such as city growth and the availability of new trade opportunities. The concept is modelled after the CivAssist tool for Civilization 3, and in fact, many of the alerts are the same.
The alerts will not reveal information that would otherwise be unavailable. They are simply intended to call the player's attention to situations as they arise without requiring tedious scanning of the advisor screens on each turn.
The alert messages are integrated with the existing event log. Like those messages, a notification is displayed on screen for a short period of time. Messages that have been cleared from the screen can be recalled by opening the event log. When appropriate, clicking on a message brings the camera focus to the site of the event.
The supported alerts are listed below. The alerts are documented in greater detail in the Features section
City will grow on the next turn
City will become unhealthy on the next turn
City will become angry on the next turn
City has grown
City has become unhealthy
City has become angry
Civilization has significant amount of gold available for trade
Civilization has significant amount of gold per turn available for trade
Future releases will include support for additional alerts and a user interface for configuring options.
Changes:
2006-Aug-11
Updated for Warlords compatibility.
Appears to work with Civ4 version 1.61. No changes necessary.
2006-Mar-12, v1.3
Fixed a bug with determining the user directory when the installation directory has been renamed. Thanks to 12monkeys
2006-Feb-28, v1.2
Fixed the search path for .INI files. The parser was searching the Assets directories instead of their respective parent directories. Thanks to jray
Restored the 6 Boolean state flags to the event handler front end. Thanks to jray
2006-Feb-2, v1.1
Added the CvModName feature to CvConfigParser to allow discovery of the active mod name under certain circumstances.
Fixed exception handling in INI file reader.
Civ4lerts.zip (http://forums.civfanatics.com/downloads.php?do=file&id=2293)
CivFan91 Feb 03, 2006, 11:17 AM Sorry for the mini-bump, but I was wondering if you had any screenshots of the mod working. I'm wondering if it is like CivAssist II where you had to minimize Civ to see it. After all, it takes so long to get back into the game when cIV gets minimized... =/
Dr Elmer Jiggle Feb 03, 2006, 12:06 PM Sorry for the mini-bump, but I was wondering if you had any screenshots of the mod working. I'm wondering if it is like CivAssist II where you had to minimize Civ to see it. After all, it takes so long to get back into the game when cIV gets minimized... =/
I don't have any screenshots, but they wouldn't be very interesting anyway. No, it's not like CivAssist.
You know the messages that show up on screen saying things like "Hinduism has been founded in a far away land" or "India has declared war on the Spanish?" The alerts generated by this mod work the same way.
You'll get a little on-screen message about the event. The message will fade away after about 10 seconds. If you want to recall a message (like maybe you got a whole pile of them at once) you can open the event log that's usually shown in the upper left region of the screen.
Also, think about how the built in message work when a forest is chopped or when a city's cultural borders work. You know how there's a little icon you can click to zoom to the city or the tile that had the forest? Some of the alerts also have a similar icon. It doesn't make sense for all of them (where would you zoom for "Catherine has 63 gold available for trade," but alerts like city growth and health or happiness problems will all zoom to the city.
So, in summary, you might not see any signs that it's working if no city is growing. At the beginning of a game it might take as many as 10 or 20 turns before you see an alert, depending on your game speed, the city quality, and various other factors.
The easiest way to verify that it's working is probably to load an old save from late in a game when everyone is in the modern age and has lots of gold. Then skip to the next turn. The first turn after you load a saved game will always display a lot of trade alerts, because every trading opportunity is "new." That is, let's say Napoleon has 167 gold available. Since you just loaded this game, you haven't been alterted to that situation yet, so as soon as you skip to the next turn, you'll see a trading alert. Since most leaders will have at least 50 gold to trade late in the game, you'll always get a pile of warnings on that first turn.
CivFan91 Feb 03, 2006, 12:09 PM OK. I downloaded it, and I like it. Good job! :)
OblivionOdyssey Feb 04, 2006, 06:05 AM Your Civ4lerts mod looks good, but whenever I try to load it the game says there's a problem with the CvEventInterface file. Any ideas? Thanks.
Dr Elmer Jiggle Feb 04, 2006, 08:20 AM Your Civ4lerts mod looks good, but whenever I try to load it the game says there's a problem with the CvEventInterface file. Any ideas? Thanks.
No idea about what the actual problem is, but I do know how to find out. Open your CivilizationIV.ini file (usually C:\Documents and Settings\User\My Documents\My Games\Sid Meier's Civilization 4\CivilizationIV.ini) and change the "LoggingEnabled" settings as shown below.
LoggingEnabled = 1
Then next time you run the game, it will create various files in the Logs directory (usually C:\Documents and Settings\User\My Documents\My Games\Sid Meier's Civilization 4\Logs). There should be a PythonErr2.log and a PythonErr.log. One or both of those should have some error messages in them. If you post those here, I can probably figure out what's causing the problem.
Thanks.
jray Feb 28, 2006, 10:10 AM Awesome mod!!!
I wonder if you can help me with a problem. When I edit Civ4lerts.ini, I don't see the changes occuring in the game. For example, I set the gold trading notifications to False, but I still see them. (I have Civ4lerts.ini in the usual place, at My Games\Sid Meier's Civilization 4\).
I also have additional problems when I try to merge this mod with Alerum's Unaltered Gameplay. I don't know Python, but I'm a software developer and was pretty careful :cool:. After the merge, the in-game wonder movies and new-tech splash screens (the ones where Leanord Nimoy talks) stop happening. I also get errors in PythonErr.log (see below). I tried Alerum's mod alone, and it worked fine. When I try Civ4lerts alone, I see wonder movies, but they are choppy (actually... there may be another factor involved in this problem, since I think I was using a different Civ4.ini when I tried that... so forget that for now...).
I see the "CvModName import failed" message in the python error logs, but I assume this is expected since I don't have any mods. Everything is in CustomAssets. I'd be glad to send additional files if that would help debug things. Thanks in advance for help!
Below is a paste of the error message I get in PythonErr.log (repeated 6 times) after merging Civ4lerts and Alerum:
Traceback (most recent call last):
File "CvEventInterface", line 23, in onEvent
File "CvCustomEventManager", line 115, in handleEvent
File "CvCustomEventManager", line 126, in _handleDefaultEvent
File "CvEventManager", line 517, in onBuildingBuilt
AttributeError: 'CvCustomEventManager' object has no attribute 'bMultiPlayer'
ERR: Python function onEvent failed, module CvEventInterface
And here is the call at line 23 of CvEventInterface:
def onEvent(argsList):
'Called when a game event happens - return 1 if the event was consumed'
return getEventManager().handleEvent(argsList)
Dr Elmer Jiggle Feb 28, 2006, 10:27 AM I know what the problem is with the exceptions in onBuildingBuilt. I did some "cleanup" in the handleEvent method, but since I don't know Python very well, I think I cleaned up some stuff that was important. Oops! :blush: I'll try to post a fixed version later today.
I'm not sure why your .INI file edits wouldn't be working, but since the defaults are set the way I like them, I don't actually do any overrides myself, so that stuff isn't very well tested. I'll do some experiments and see what I can come up with. It does sound like you have the .INI file in the correct place, and you're right that the error about CvModName doesn't matter (that's a weird hack to help find the .INI file if you install the mod in the Mods directory).
jray Feb 28, 2006, 10:55 AM Thanks for the quick response!
I wonder if you could suggest a way to circumvent your custom parser, so I can try that and see if it's the cause of my .ini problem. Since I have all my .ini's in the same usual place, I don't need the custom parsing.
Dr Elmer Jiggle Feb 28, 2006, 09:33 PM Turns out I was only partly right about the cause. It's in the area of the code I took out, but there was also a change made in Alerum's mod (or someone else's that got merged into his) that is part of the problem. If you change the CvCustomEventManager.handleEvent function as shown below, it should set bMultiPlayer properly. The change is the addition of three new lines at the beginning.
def handleEvent(self, argsList):
"""Handles events by calling all installed handlers."""
self.origArgsList = argsList
flagsIndex = len(argsList) - 6
self.bDbg, self.bMultiPlayer, self.bAlt, self.bCtrl, self.bShift, self.bAllowCheats = argsList[flagsIndex:]
eventType = argsList[0]
return {
"kbdEvent": self._handleConsumableEvent,
"mouseEvent": self._handleConsumableEvent,
"OnSave": self._handleOnSaveEvent,
"OnLoad": self._handleOnLoadEvent
}.get(eventType, self._handleDefaultEvent)(eventType,
argsList[1:flagsIndex])
I don't think the INI files work like you think they do. ;) If you disable the CvConfigParser class in my mod, the INI file won't work at all, no matter where you put it.
The reason all that stuff is in there is that the Civ4 API's don't give mods any way of accessing settings from their INI files. You'll notice that every mod in the Mods directory has its own INI file with stuff like "SinglePlayerOnly," "AllowPublicMaps," "Name," etc. That looks like the perfect place to store all your custom mod settings, right? After all, that file is already read in by the game, so let's just put a few more values in there.
Great idear, but it doesn't actually work. Wherever the game puts that INI file after it reads it, it's not accessible from Python. So that's why I've got that parser class there. I sort of borrowed/stole the idea from the Hall of Fame mod and adapted it a bit to be more general and to have fewer/no hardcoded paths.
I'm about to try some tests to see if I can track down why it isn't working.
Dr Elmer Jiggle Feb 28, 2006, 09:46 PM def handleEvent(self, argsList):
"""Handles events by calling all installed handlers."""
self.origArgsList = argsList
flagsIndex = len(argsList) - 6
self.bDbg, self.bMultiPlayer, self.bAlt, self.bCtrl, self.bShift, self.bAllowCheats = argsList[flagsIndex:]
eventType = argsList[0]
return {
"kbdEvent": self._handleConsumableEvent,
"mouseEvent": self._handleConsumableEvent,
"OnSave": self._handleOnSaveEvent,
"OnLoad": self._handleOnLoadEvent
}.get(eventType, self._handleDefaultEvent)(eventType,
argsList[1:flagsIndex])
Don't make the change shown in the last line (:flagsIndex). Or if you do, make sure you also remove ":len(argsList) - 6" from each of the other handle*Event functions. They're both trying to do the same thing, and they step on each others toes if you have both.
jray Feb 28, 2006, 10:13 PM Yay, it works now without any errors! Thanks so much!
I was also able to manually set the INI stuff in the .py files... was easy to find. But out of curiosity, is the INI file supposed to work if I just put it in the parent folder of CustomAssets and have all my .py files in CustomAssets (instead of MODS)?
FYI, I also merged in TheLopez's Specialist Stacker. I saw that he uses your custom config parser. Probably not a surprise, but I can't get it to read its INI either. But again it was easy to change the .py files directly, so oh well :).
Dr Elmer Jiggle Feb 28, 2006, 10:26 PM is the INI file supposed to work if I just put it in the parent folder of CustomAssets and have all my .py files in CustomAssets (instead of MODS)?
Yes, it's supposed to "just work." I did some testing though, and I saw the same problem you did. After a little investigation, I discovered that it wasn't reading the config file at all (big surprise; you already knew that much :-)). The directory search path was wrong. It was looking in the assets directories instead of in their parents.
I just updated the attachment in the first post of the thread. That has both of these recent fixes. Alternatively, if it's easier for you to just change the code directly, you can change the __init__ method of CvConfigParser as shown below. The change is to the line that initializes filenames. I added "os.path.dirname(dir)" where it previously just said "dir".
def __init__(self, filename = None, *args, **kwargs):
"""Initializes the parser by reading options from the named file."""
super(CvConfigParser, self).__init__(*args, **kwargs)
if (filename != None):
filenames = [os.path.join(os.path.dirname(dir), filename)
for dir in CvPath.assetsPath]
filenames.reverse()
self.read(filenames)
CivFan91 Feb 28, 2006, 10:27 PM IIRC, if you put it in CustomAssets you have to load it in the menu, whereas putting it in the Mods folder loads it automatically
jray Mar 01, 2006, 12:31 AM I just updated the attachment in the first post of the thread. That has both of these recent fixes. Alternatively, if it's easier for you to just change the code directly, you can change the __init__ method of CvConfigParser as shown below. The change is to the line that initializes filenames. I added "os.path.dirname(dir)" where it previously just said "dir".
Awesome, thanks! I appreciate you mentioning the changes since I had already done some merging. I'll let you know if I find any problems. I tried changing the Specialist Stacker INI file since that is faster to see the effects of (at least in my game right now, where I haven't met any competitors yet), and that worked. So I assume your INI will work fine too.
Dual Mar 01, 2006, 02:57 PM Nice work on the mod! :goodjob:
This is very useful to me, because I'm so forgetful during my games. I always end up neglecting to check and see how my populations are doing. :) So this helps me keep track of it all.
A Silly Goose Mar 01, 2006, 05:37 PM IIRC, if you put it in CustomAssets you have to load it in the menu, whereas putting it in the Mods folder loads it automatically
That'd be the other way around, I do believe.
TheLopez Mar 01, 2006, 06:16 PM (that's a weird hack to help find the .INI file if you install the mod in the Mods directory).
It might be a weird hack, but you know what? It has been working very well for me given that they didn't provide ANY way to get the name of the currently loaded mod.
Spocko Mar 02, 2006, 07:49 PM Wow - I loaded this as a standalone mod, and it is exactly what I'm looking for.
Too bad (for me) I have no clue on how to incorporate this into my own fusion mod. I've fused together 28 or so mod components, many that use CvCustomEventManager and I don't know how to adopt Dr Jiggle's code into my hacked CvCustomEventManager.
But still, I'd like to try.
I wonder how I could tweak the following code in my hacked CvCustomEventManager:
def __init__(self):
# initialize base class
self.parent = CvEventManager.CvEventManager
self.parent.__init__(self)
self.Events[7501] = ('FreeTechPopup', self.__eventFreeTechApply , self.__eventFreeTechBegin)
def initValues(self):
self.iProphetID = CvUtil.findInfoTypeNum (gc.getUnitInfo,gc.getNumUnitInfos(),'UNIT_PROPHET ')
etc.
... with respect to Dr Jiggle's code:
class CvCustomEventManager(CvEventManager.CvEventManager , object):
def __init__(self, *args, **kwargs):
super(CvCustomEventManager, self).__init__(*args, **kwargs)
# map the initial EventHandlerMap values into the new data structure
for eventType, eventHandler in self.EventHandlerMap.iteritems():
self.setEventHandler(eventType, eventHandler)
# --> INSERT EVENT HANDLER INITIALIZATION HERE <--
Civ4lerts.Civ4lerts(self)
def addEventHandler(self, eventType, eventHandler):
etc.
I respect the fact that Dr Jiggle's approach is compliant with a sensible way to fuse mods together. Unfortunately, while I have the time and will to fuse mods together, I don't have the time (and thus the will) to grasp the science I would need to fold this into my mod. Is there a way to sidestep the elegance of Dr Jiggle's method, just this once, to fold this into my CvCustomEventManager?
Respectfully,
Spocko
PS - I wonder whether I could reverse my question and learn how to fold my existing CvCustomEventManager into Dr Jiggle's?
Dr Elmer Jiggle Mar 02, 2006, 07:58 PM I'll try to post some details later after I've had a chance to look over your example. It should be easy to do either way -- either fold my alerts into your event manager or install your handlers into my event manager. I had some documentation on doing this at one point, but I don't think I ever fleshed it out. This might motivate me to get back to it.
Spocko Mar 02, 2006, 08:13 PM Thanks for the quick reply, there Dr.
I wonder if it might be smartest for me to learn how to fold mine into yours, so that I'll be better prepared to handle future elegant mods as well as those that I've already learned how to fuse together.
If the technique is "simple" enough to learn, maybe I should think of using the elegant approach to recompile my mod at the time the next patch comes out. I've been sweating it out, wondering just how hard it will be to rebuild my mod for the next patch. It seems the elegant approach in your mod is the way to go to modularize all my forked mods when I port over to the forthcoming new patch.
Anyway, you responded so quickly I wanted to let you know, in a timely way, that I'll appreciate the help you're able to provide.
Thanks!
Spocko
Dr Elmer Jiggle Mar 02, 2006, 09:42 PM As you mentioned, there are two approaches you can take:
use my custom event handler and merge your handlers ito it
use your custom event handler and merge my alerts into it
I'll start with the first option, because as you'll eventually read, it's much easier. The main thing you need to do is register your event manager's handler functions with my event manager. You would do this with calls like in the the example below. Note that although I think these code snippets are correct, I haven't actually run it and tested them, so there may be minor errors and typos.
def __init__(self, eventManager):
# initialize base class
self.parent = CvEventManager.CvEventManager
self.parent.__init__(self)
eventManager.addEventHandler("unitMove", self.onUnitMove)
eventManager.addEventHandler("unitCreated", self.onUnitCreated)
eventManager.addEventHandler("unitKilled", self.onUnitKilled)
# ... repeat for all event handlers ...
eventManager.addEventHandler("religionSpread", self.onReligionSpread)
The string names of the event handlers can be found in the original CvEventManager class where EventHandlerMap is initialized (around line 73-ish). As you can see from the above examples, most of the time the pattern is to remove "on" from the handler function, but that isn't always true, so make sure you check the names. It's particularly inconsistent when you're dealing with the onGame* and Save/Load types of events.
Then call your event manager's constructor from my CvCustomEventManager __init__ function. Let's assume for the sake of discussion that you rename your class to CvSpockoEventManager.
CvSpockoEventManager.CvSpockoEventManager(self)
The only obvious problem I see with this approach, based on a quick scan of your code, is the self.Events[7501] thing you're doing to install the popup handler. The easiest solution would probably be to just stick that line right in my __init__ function. So to sum up, you would wind up with a CvCustomEventManager constructor that looks something like this.
def __init__(self, *args, **kwargs):
super(CvCustomEventManager, self).__init__(*args, **kwargs)
# map the initial EventHandlerMap values into the new data structure
for eventType, eventHandler in self.EventHandlerMap.iteritems():
self.setEventHandler(eventType, eventHandler)
# --> INSERT EVENT HANDLER INITIALIZATION HERE <--
Civ4lerts.Civ4lerts(self)
CvSpockoEventManager.CvSpockoEventManager(self)
self.Events[7501] = ('FreeTechPopup', self.__eventFreeTechApply , self.__eventFreeTechBegin)
I think that's it. Done. It should work.
Alternatively, if you wanted to keep your event manager and call out to my handler functions, you could do that as well. I think that will require more code and/or will be more complicated, but I'm obviously biased. The main reason for the difficulty is that the deep class hierarchy of my alerts, while it makes it easy to add new alerts with a minimal amount of new code, it also makes it somewhat harder to quickly see what event handler functions are used by each alert. It also means that there are quite a few places where you would need to make changes to my code to let them interact with a different event manager.
For example, let's take the CityPendingGrowth alert to start with. That class implements an onCityPendingGrowth function, but that's not a "real" event handler. It's faked by the base class. If you look at the base class, you'll see that it implements an onCityDoTurn function. We'll need to plug that into your event manager. You would need to implement something like this.
def onCityDoTurn(self, argsList):
cityPendingGrowth.onCityDoTurn(argsList)
And at the beginning of your module in the same place where you initialize FreeTech and TechWindow, also create a CityPendingGrowth object.
cityPendingGrowth = Civ4lerts.CityPendingGrowth()
But notice that the CityPendingGrowth constructor expects a single argument -- the event manager. It will use that argument to register its event handlers. So that code needs to be removed in order to let it work with a more conventional event manager. You need to remove the eventManager argument from the AbstractAlert, AbstractCityPendingGrowth, and CityPendingGrowth classes. You also need to remove the addEventHandler call from the AbstractCityPendingGrowth class. You would wind up with an AbstractCityPendingGrowth constructor like this.
def __init__(self, *args, **kwargs):
super(AbstractCityPendingGrowth, self).__init__(*args, **kwargs)
I'm not going to continue this further, because I think I've made my case. Good, bad, for better or for worse, it's just not that easy to make my alerts work with a conventional event manager. I'd recommend the first approach if you want to merge the two.
Basically my event manager is fairly compatible with an old style event manager, but the old style event managers aren't very compatible with my event handlers.
Spocko Mar 05, 2006, 10:45 AM Here are the files I promised in my PM
Elhoim Apr 19, 2006, 09:09 AM It is compatible with 1.61?
THX!
Dr Elmer Jiggle Apr 19, 2006, 09:14 AM Yes. At least I haven't noticed any problems so far.
Elhoim Apr 19, 2006, 09:55 AM THX for your quick reply! Perhaps you should put a notice in the first post... THX again! :goodjob:
DaviddesJ Apr 23, 2006, 11:52 PM Civilization has significant amount of gold available for trade
Why not "Civilization has new technology available for trade"? Is that more difficult to implement?
Denniz Apr 24, 2006, 05:17 AM Why not "Civilization has new technology available for trade"? Is that more difficult to implement?
Having done it for the HOF mod, I would say: Yes. :D But what do I know. :mischief:
Dr Elmer Jiggle Apr 24, 2006, 07:37 AM Why not "Civilization has new technology available for trade"? Is that more difficult to implement?
Yeah, it is, because you need to worry about "visibility." You only want to mention technologies where you have the prerequisites.
The functions to do that are all there, somewhere, in the Python API's, but I haven't spent the time to figure it all out. To be honest, I haven't really been playing Civ4 much lately, so I haven't been very motivated to do the unimplemented alerts. I'm in the middle of a game right now though, and I have to admit that not having a technology alert is driving me nuts. ;-)
Denniz Apr 24, 2006, 03:57 PM Yeah, it is, because you need to worry about "visibility." You only want to mention technologies where you have the prerequisites
The functions to do that are all there, somewhere, in the Python API's, but I haven't spent the time to figure it all out. To be honest, I haven't really been playing Civ4 much lately, so I haven't been very motivated to do the unimplemented alerts..;-)I got most of the visibility logic from the Exotic Foreign Advisor. ;) The other part that was tough was to only alert about "new" techs.
I'm in the middle of a game right now though, and I have to admit that not having a technology alert is driving me nuts. ;-)Take a look at MoreCiv4lerts.py
Dr Elmer Jiggle Apr 24, 2006, 04:18 PM Take a look at MoreCiv4lerts.py
Oh, cool. Thanks. I hadn't noticed that before.
Looks like I have a lot of updating to do once I finish this game. ;-)
Spocko Apr 25, 2006, 06:59 PM Take a look at MoreCiv4lerts.py
Where can I get this file? Thanks!!
Dr Elmer Jiggle Apr 25, 2006, 08:31 PM Where can I get this file? Thanks!!
It's part of the Hall of Fame mod.
http://hof.civfanatics.net/civ4/mod.php
Spocko Apr 25, 2006, 08:38 PM :goodjob:
Thanks Dr Jiggle!
A Silly Goose May 02, 2006, 02:06 PM Now that your event manager has pop-up capability, are there any plans to incorporate them into Civ4lerts? Or is it something that's as simple as pasting variations of a few lines of code into the appropriate locations?
Thanks in advance.
Dr Elmer Jiggle May 02, 2006, 02:19 PM What sort of popup dialogs would you want? Something like "You're city has just grown. [Go to the city screen] [Carry on]"? For the most part I've avoided that, because I find most of the built-in dialogs annoying ("You just built your first archer! Congratulations!" Yeah, yeah, stop nagging me.), but if people want that I don't think it would be hard to do.
FYI, the popup handling was always there. It's build into the standard event manager that comes with the game. All I really added was a function that makes it more obvious how to tap into that capability.
Dual May 02, 2006, 03:29 PM What sort of popup dialogs would you want? Something like "You're city has just grown. [Go to the city screen] [Carry on]"? For the most part I've avoided that, because I find most of the built-in dialogs annoying ("You just built your first archer! Congratulations!" Yeah, yeah, stop nagging me.), but if people want that I don't think it would be hard to do.
FYI, the popup handling was always there. It's build into the standard event manager that comes with the game. All I really added was a function that makes it more obvious how to tap into that capability.
Popups for the city messages would be very nice. As long as the user has the option to turn them on and off.
A Silly Goose May 03, 2006, 09:36 PM What sort of popup dialogs would you want? Something like "You're city has just grown. [Go to the city screen] [Carry on]"? For the most part I've avoided that, because I find most of the built-in dialogs annoying ("You just built your first archer! Congratulations!" Yeah, yeah, stop nagging me.), but if people want that I don't think it would be hard to do.
FYI, the popup handling was always there. It's build into the standard event manager that comes with the game. All I really added was a function that makes it more obvious how to tap into that capability.
What I want it for is to be able to go straight to a city with pending unhappiness or unhealthiness problems, and address the issue immediately, as opposed to forgetting to do so after handling all the other issues that need attention (and it doesn't help when you have a mild case of ADD, either, heh).
At any rate, I should've figured there wasn't an easy answer like, "oh, you just slap a statement, like this generic one here, right into such-and-such a spot." It's about time I ventured from cut-n-paste work to actually enabling myself in Python, though; I knew I'd have to get around to it eventually, and it'll help prepare for cut-n-paste work with the SDK.
Denniz May 04, 2006, 03:46 AM What I want it for is to be able to go straight to a city with pending unhappiness or unhealthiness problems, and address the issue immediately, as opposed to forgetting to do so after handling all the other issues that need attention (and it doesn't help when you have a mild case of ADD, either, heh).Take a look at the Domestic Advisor (F1). You can see the state of those things an click on the icon to left of the city name to just to it. You can work your way through any cities with issues that way. The alerts save you from having to do that every turn.
jonpfl May 10, 2006, 05:22 AM All,
I have this mod installed on my machine and it works fine in single player but when I play multi player it doesn't work.
How do I get it to work with multi player?
Thx
jonpfl
Dr Elmer Jiggle May 10, 2006, 07:03 AM How do I get it to work with multi player?
I don't know. I wasn't aware of any problems with multiplayer, but I only do single player, so it might just be something I've never encountered. If you can turn on logging and post an error message here, that might help figure out the problem.
Set "LoggingEnabled = 1" in your CivilizationIV.ini file (typically C:\Documents and Settings\User\My Documents\My Games\Sid Meier's Civilization 4\CivilizationIV.ini")
Run the game long enough to be sure an alert should have appeared (ex. play until a city grows)
Look at Logs\PythonErr.log and Logs\PythonErr2.log in the same place you found CivilizationIV.ini and see if there's anything that looks like an exception or error message.
jonpfl May 10, 2006, 04:24 PM I don't know. I wasn't aware of any problems with multiplayer, but I only do single player, so it might just be something I've never encountered. If you can turn on logging and post an error message here, that might help figure out the problem.
Set "LoggingEnabled = 1" in your CivilizationIV.ini file (typically C:\Documents and Settings\User\My Documents\My Games\Sid Meier's Civilization 4\CivilizationIV.ini")
Run the game long enough to be sure an alert should have appeared (ex. play until a city grows)
Look at Logs\PythonErr.log and Logs\PythonErr2.log in the same place you found CivilizationIV.ini and see if there's anything that looks like an exception or error message.
Here you go. I had to cut some of it since it was too long.
warning: to-Python converter for class CyPythonMgr already registered; second conversion method ignored.
warning: to-Python converter for enum GameStateTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PopupStates already registered; second conversion method ignored.
warning: to-Python converter for enum CameraLookAtTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CameraMovementSpeeds already registered; second conversion method ignored.
warning: to-Python converter for enum ZoomLevelTypes already registered; second conversion method ignored.
warning: to-Python converter for enum DirectionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CardinalDirectionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ColorTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PlayerColorTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PlotStyles already registered; second conversion method ignored.
warning: to-Python converter for enum PlotLandscapeLayers already registered; second conversion method ignored.
warning: to-Python converter for enum InterfaceModeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum InterfaceMessageTypes already registered; second conversion method ignored.
warning: to-Python converter for enum MinimapModeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum EngineDirtyBits already registered; second conversion method ignored.
warning: to-Python converter for enum InterfaceDirtyBits already registered; second conversion method ignored.
warning: to-Python converter for enum CityTabTypes already registered; second conversion method ignored.
warning: to-Python converter for enum WidgetTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ButtonPopupTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ClimateTypes already registered; second conversion method ignored.
warning: to-Python converter for enum SeaLevelTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CustomMapOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum WorldSizeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TerrainTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PlotTypes already registered; second conversion method ignored.
warning: to-Python converter for enum YieldTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CommerceTypes already registered; second conversion method ignored.
warning: to-Python converter for enum AdvisorTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FlavorTypes already registered; second conversion method ignored.
warning: to-Python converter for enum EmphasizeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GameOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum MultiplayerOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum SpecialOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PlayerOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GraphicOptionTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ForceControlTypes already registered; second conversion method ignored.
warning: to-Python converter for enum VictoryTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FeatureTypes already registered; second conversion method ignored.
warning: to-Python converter for enum BonusTypes already registered; second conversion method ignored.
warning: to-Python converter for enum BonusClassTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ImprovementTypes already registered; second conversion method ignored.
warning: to-Python converter for enum RouteTypes already registered; second conversion method ignored.
warning: to-Python converter for enum RiverTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GoodyTypes already registered; second conversion method ignored.
warning: to-Python converter for enum BuildTypes already registered; second conversion method ignored.
warning: to-Python converter for enum SymbolTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FontSymbols already registered; second conversion method ignored.
warning: to-Python converter for enum HandicapTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GameSpeedTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TurnTimerTypes already registered; second conversion method ignored.
warning: to-Python converter for enum EraTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CivilizationTypes already registered; second conversion method ignored.
warning: to-Python converter for enum LeaderHeadTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ArtStyleTypes already registered; second conversion method ignored.
warning: to-Python converter for enum CitySizeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FootstepAudioTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FootstepAudioTags already registered; second conversion method ignored.
warning: to-Python converter for enum ChatTargetTypes already registered; second conversion method ignored.
warning: to-Python converter for enum VoiceTargetTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TeamTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PlayerTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TraitTypes already registered; second conversion method ignored.
warning: to-Python converter for enum OrderTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TaskTypes already registered; second conversion method ignored.
warning: to-Python converter for enum BuildingClassTypes already registered; second conversion method ignored.
warning: to-Python converter for enum BuildingTypes already registered; second conversion method ignored.
warning: to-Python converter for enum SpecialBuildingTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ProjectTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ProcessTypes already registered; second conversion method ignored.
warning: to-Python converter for enum VoteTypes already registered; second conversion method ignored.
warning: to-Python converter for enum InfoBarTypes already registered; second conversion method ignored.
warning: to-Python converter for enum HealthBarTypes already registered; second conversion method ignored.
warning: to-Python converter for enum MemoryTypes already registered; second conversion method ignored.
warning: to-Python converter for enum AttitudeTypes already registered; second conversion method ignored.
warning: to-Python converter for enum LeaderheadAction already registered; second conversion method ignored.
warning: to-Python converter for enum DiplomacyPowerTypes already registered; second conversion method ignored.
warning: to-Python converter for enum FeatTypes already registered; second conversion method ignored.
warning: to-Python converter for enum SaveGameTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GameType already registered; second conversion method ignored.
warning: to-Python converter for enum GameMode already registered; second conversion method ignored.
warning: to-Python converter for enum InterfaceVisibility already registered; second conversion method ignored.
warning: to-Python converter for enum GenericButtonSizes already registered; second conversion method ignored.
warning: to-Python converter for enum WorldBuilderPopupTypes already registered; second conversion method ignored.
warning: to-Python converter for enum EventType already registered; second conversion method ignored.
warning: to-Python converter for enum LoadType already registered; second conversion method ignored.
warning: to-Python converter for enum FontTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PanelStyles already registered; second conversion method ignored.
warning: to-Python converter for enum ButtonStyles already registered; second conversion method ignored.
warning: to-Python converter for enum TableStyles already registered; second conversion method ignored.
warning: to-Python converter for enum EventContextTypes already registered; second conversion method ignored.
warning: to-Python converter for enum TabGroupTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ReplayMessageTypes already registered; second conversion method ignored.
warning: to-Python converter for enum AudioTag already registered; second conversion method ignored.
warning: to-Python converter for enum CivilopediaPageTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ActionSubTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GameMessageTypes already registered; second conversion method ignored.
warning: to-Python converter for enum PopupControlLayout already registered; second conversion method ignored.
warning: to-Python converter for enum JustificationTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ToolTipAlignTypes already registered; second conversion method ignored.
warning: to-Python converter for enum ActivationTypes already registered; second conversion method ignored.
warning: to-Python converter for enum HitTestTypes already registered; second conversion method ignored.
warning: to-Python converter for enum GraphicLevelTypes already registered; second conversion method ignored.
warning: to-Python converter for class CyGame already registered; second conversion method ignored.
warning: to-Python converter for class CvSpecialUnitInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCivicOptionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCivicInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvUnitClassInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvBuildingInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvSpecialBuildingInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvBuildingClassInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvRouteModelInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCivilizationInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvVictoryInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvHurryInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvHandicapInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvGameSpeedInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvTurnTimerInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvBuildInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvGoodyInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvRouteInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvImprovementBonusInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvImprovementInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvBonusClassInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvBonusInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvFeatureInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCommerceInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvYieldInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvTerrainInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvLeaderHeadInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvProcessInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvVoteInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvProjectInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvReligionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvTraitInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvWorldInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvClimateInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvSeaLevelInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvAssetInfoBase already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoAsset already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoScalableAsset already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoInterface already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoMovie already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoMisc already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoUnit already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoBuilding already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoCivilization already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoLeaderhead already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoBonus already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoImprovement already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoTerrain already registered; second conversion method ignored.
warning: to-Python converter for class CvArtInfoFeature already registered; second conversion method ignored.
warning: to-Python converter for class CvEmphasizeInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvUpkeepInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCultureLevelInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvEraInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvColorInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvPlayerColorInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvGameText already registered; second conversion method ignored.
warning: to-Python converter for class CvDiplomacyTextInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvDiplomacyInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvEffectInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvControlInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvQuestInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvTutorialMessage already registered; second conversion method ignored.
warning: to-Python converter for class CvTutorialInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvAutomateInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvCommandInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvGameOptionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvMPOptionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvForceControlInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvPlayerOptionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CvGraphicOptionInfo already registered; second conversion method ignored.
warning: to-Python converter for class CyReplayInfo already registered; second conversion method ignored.
warning: to-Python converter for class CyHallOfFameInfo already registered; second conversion method ignored.
warning: to-Python converter for class CyCity already registered; second conversion method ignored.
warning: to-Python converter for class CyPlayer already registered; second conversion method ignored.
warning: to-Python converter for class CyUnit already registered; second conversion method ignored.
warning: to-Python converter for class CyPlot already registered; second conversion method ignored.
warning: to-Python converter for class CyGlobalContext already registered; second conversion method ignored.
warning: to-Python converter for class CyPopupReturn already registered; second conversion method ignored.
warning: to-Python converter for class CyPopupInfo already registered; second conversion method ignored.
warning: to-Python converter for class CyPopup already registered; second conversion method ignored.
warning: to-Python converter for class CyFractal already registered; second conversion method ignored.
warning: to-Python converter for enum CvFractal::FracVals already registered; second conversion method ignored.
warning: to-Python converter for enum FInputDevice::InputType already registered; second conversion method ignored.
warning: to-Python converter for enum MOUSE_FLAGS already registered; second conversion method ignored.
warning: to-Python converter for enum FxCheckBox::CheckBoxState already registered; second conversion method ignored.
warning: to-Python converter for class NiMatrix3 already registered; second conversion method ignored.
warning: to-Python converter for enum NotifyCode already registered; second conversion method ignored.
warning: to-Python converter for enum WidgetAnim already registered; second conversion method ignored.
warning: to-Python converter for class CyEngine already registered; second conversion method ignored.
warning: to-Python converter for class CySign already registered; second conversion method ignored.
warning: to-Python converter for class CyCamera already registered; second conversion method ignored.
warning: to-Python converter for class CyDiplomacy already registered; second conversion method ignored.
warning: to-Python converter for class CyUnitEntity already registered; second conversion method ignored.
warning: to-Python converter for class CyUnitSubEntity already registered; second conversion method ignored.
warning: to-Python converter for class CyInterfaceScreen already registered; second conversion method ignored.
warning: to-Python converter for class CyGInterfaceScreen already registered; second conversion method ignored.
warning: to-Python converter for class CyMessageControl already registered; second conversion method ignored.
warning: to-Python converter for class CyInterface already registered; second conversion method ignored.
warning: to-Python converter for class CyUserProfile already registered; second conversion method ignored.
warning: to-Python converter for class CyAudioGame already registered; second conversion method ignored.
warning: to-Python converter for class CyVariableSystem already registered; second conversion method ignored.
warning: to-Python converter for class CyTranslator already registered; second conversion method ignored.
warning: to-Python converter for class CyGTabCtrl already registered; second conversion method ignored.
warning: to-Python converter for class CyGFlyoutMenu already registered; second conversion method ignored.
warning: to-Python converter for class CyGlobeLayer already registered; second conversion method ignored.
warning: to-Python converter for class CyGlobeLayerManager already registered; second conversion method ignored.
warning: to-Python converter for class CyStatistics already registered; second conversion method ignored.
sys.path = ['ASSETS\\PYTHON\\SYSTEM\\email', 'ASSETS\\PYTHON\\SYSTEM\\encodings', 'ASSETS\\PYTHON\\SYSTEM\\wx', 'ASSETS\\PYTHON\\SYSTEM\\wx\\build', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib', 'ASSETS\\PYTHON\\SYSTEM\\wx\\py', 'ASSETS\\PYTHON\\SYSTEM\\wx\\tools', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\colourchooser', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\editor', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\floatcanvas', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\masked', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\mixins', 'ASSETS\\PYTHON\\SYSTEM\\wx\\lib\\ogl', 'ASSETS\\PYTHON\\SYSTEM\\wx\\py\\tests', 'ASSETS\\PYTHON\\SYSTEM\\wx\\tools\\XRCed', 'ASSETS\\PYTHON\\SYSTEM']
sys.modules = {'zipimport': <module 'zipimport' (built-in)>, 'signal': <module 'signal' (built-in)>, '__builtin__': <module '__builtin__' (built-in)>, 'sys': <module 'sys' (built-in)>, '__main__': <module '__main__' (built-in)>, 'exceptions': <module 'exceptions' (built-in)>, 'CvPythonExtensions': <module 'CvPythonExtensions' (built-in)>}
sys.builtin_module_names = ('CvPythonExtensions', 'CvPythonExtensions', '__builtin__', '__main__', '_bisect', '_codecs', '_codecs_cn', '_codecs_hk', '_codecs_iso2022', '_codecs_jp', '_codecs_kr', '_codecs_tw', '_csv', '_heapq', '_hotshot', '_locale', '_multibytecodec', '_random', '_sre', '_subprocess', '_symtable', '_weakref', '_winreg', 'array', 'audioop', 'binascii', 'cPickle', 'cStringIO', 'cmath', 'collections', 'datetime', 'errno', 'exceptions', 'gc', 'imageop', 'imp', 'itertools', 'marshal', 'math', 'md5', 'mmap', 'msvcrt', 'nt', 'operator', 'parser', 'regex', 'rgbimg', 'sha', 'signal', 'strop', 'struct', 'sys', 'thread', 'time', 'xxsubtype', 'zipimport')
load_module CvEventInterface
load_module CvUtil
load_module traceback
load_module CvEventManager
load_module CvScreensInterface
load_module CvMainInterface
load_module ScreenInput
load_module CvScreenEnums
load_module time
load_module CvDomesticAdvisor
load_module PyHelpers
load_module CvTechChooser
load_module CvForeignAdvisor
load_module math
load_module CvMilitaryAdvisor
load_module re
load_module CvFinanceAdvisor
load_module CvReligionScreen
load_module CvCivicsScreen
load_module string
load_module CvVictoryScreen
load_module CvOptionsScreen
load_module CvReplayScreen
load_module CvHallOfFameScreen
load_module CvDanQuayle
load_module CvGameUtils
load_module CvUnVictoryScreen
load_module CvDawnOfMan
load_module CvTechSplashScreen
load_module CvTopCivs
load_module random
load_module CvInfoScreen
load_module CvIntroMovieScreen
load_module CvVictoryMovieScreen
load_module CvWonderMovieScreen
load_module CvEraMovieScreen
load_module CvPediaMain
load_module CvPediaScreen
load_module CvScreen
load_module CvPediaTech
load_module CvPediaUnit
load_module CvPediaBuilding
load_module CvPediaPromotion
load_module CvPediaUnitChart
load_module CvPediaBonus
load_module CvPediaTerrain
load_module CvPediaFeature
load_module CvPediaImprovement
load_module CvPediaCivic
load_module CvPediaCivilization
load_module CvPediaLeader
load_module CvPediaSpecialist
load_module CvPediaHistory
load_module CvPediaProject
load_module CvPediaReligion
load_module CvWorldBuilderScreen
load_module Popup
load_module CvWorldBuilderDiplomacyScreen
load_module CvDebugTools
load_module CvDebugInfoScreen
load_module CvMapGeneratorUtil
load_module CvGFCScreen
load_module CvPopupInterface
load_module CvScreenUtilsInterface
load_module CvScreenUtils
load_module CvWBPopups
load_module CvCameraControls
load_module CvAdvisorUtils
PY:OnInit
load_module CvAppInterface
Dr Elmer Jiggle May 10, 2006, 04:35 PM Here you go. I had to cut some of it since it was too long.
That all looks normal and/or unrelated to the alerts. I don't know what all that stuff is about enum conversions, but it's not anything I did.
Do any mods work in multiplayer? I'm thinking the game might automatically ignore customizations as an anti-cheating measure. Of course, I don't think an alert about city growth is actually cheating, but the game doesn't know that. I just sees a custom Python module.
I'm thinking that's the problem. Looking through that list of loaded modules, I don't see any of the modules for my mod. None of them. It looks like they're completely ignored.
jonpfl May 10, 2006, 04:53 PM D*mn
Your mod is so helpful. I guess they don't allow stuff like this to work.
Any other ideas what I might be missing? It works fine in single player. I am just clicking the icon on my desktop to start it.
Does anyone else use this mod for mplayer????
goodyhut May 12, 2006, 03:05 PM As I posted in the main Creation & customization forum, I wish to add this mod with the sdksixmapsizes mod (http://www.civfanatics.net/uploads11/sdksixmapsizes.zip) and the civmore mod (http://download.filefront.com/5053060;0f9679af12ef6af490ef39ff5db215bee10c530604 6efb1599a19702e641378bf8e8059120a3cb82). Could somebody please explain in detail what I need to do to merge these?
Officer Reene May 13, 2006, 01:40 AM ...Do any mods work in multiplayer? I'm thinking the game might automatically ignore customizations as an anti-cheating measure. Of course, I don't think an alert about city growth is actually cheating, but the game doesn't know that. I just sees a custom Python module...
In my limited experience, mods and MP dont go too well... unless it is a simple mod...
let me explain....
the biggest issues that I see is AI and python...
I find any mod that modifies python and/or AI actions doesnt work well in MP
it will work in MP for maybe like 20-40 turns then you will get Out Of Sync errors...
and then it becomes unplayable
(NOTE: MP will use the custom mods... but it doesnt last long)
the few times where mods work in MP is where the Python files are not altered... alot...
for example I am using the CivMore Mod:
http://forums.civfanatics.com/showthread.php?t=163596
Fitchn's CivMore Mod specfically does not mess with pythons extensively (however he does add more civics... that require changes in those python files) and therefore I have no MP issues...
he advises that OOS errors occur with Python modifications
and due to my limited search on the OOS problem... I happen to agree with him
however when I tried to merge some AI altering codes like:
Snaitf 's Allegiance Mod (allows for some enemy units to be converted to your /other civs by %)
Snaitf 's Contact Mod (allows for you to meet all civs that your first contact civ met)
I get OOS errors
yet I was able to merge
Snaitf 's Show Attitude Mod with CivMore Mod w/o any errors thus far...
I also used the Exavier Composite Mod but would get OOS errors (it uses alot of the "Snaitf" type python mods) However before the errors all the custom aspects of the mod seems to work
So I think when there are certain Python coding... it doesnt work...
**Also I am using the Snaitf's demolition mod (city razing whenever you want on your own cities/not only capture) but havent used it extensively in MP to see the effects (however thread information suggest it may cause OOS errors later on)
I am still using the 1.52 patch though.... dont know about the new patch
I am not a good coder/modder so I can not say that this for certain that is the reason mods
I can just tell you my experience... and since me and my bro like to play MP on LAN, but dont like the "vanilla" verson, it can be frustrating! :mad:
(also many people havent tested/or dont use mods in MP is a pain too)
I know that any XML additions (buildings/wonders/units) that I made works fine in MP as well as SP games... (as long as all my coding/moding is correct)
my conclusion
XML Modding in MP = good
PYTHON Modding in MP = bad
Note: I have had problems with the ALPHA Channel dds with MP...
I try to avoid using Alpha Channel (unless it is already used by the "vanilla" version) when customizing pics...
...however I made two custom/unique civilizations (for me and my bro) and you can not create a flag/banner without ALPHA Channel dds files
(it is too early to see if this causes problems in my MP games... but I can keep you posted if you wish...)
Another Note: I think this mod is a great idea... but for some reason I can not get it to work....in SP or MP ... so I will have to wait till some one can merge it with CivMore :blush:
well that's my thoughts ...hope it helps...
** Just tried to use the Demolition Mod in MP (1.52 patch) and it didnt work either :mad:
pholtz May 15, 2006, 02:28 AM I guess this is the place to post this message as the event handling was part of the alert package. Let me know if I should move it.
I have been looking at CvCustomEventManager in the latest HOF mod. My brain is a bit fried :twitch:, but I think I understand most of it. Here are some questions.
1. class CvCustomEventManager(CvEventManager.CvEventManager , object):
Does CvCustomEventmanager have two supers? If so, what does it inherit from "object"?
2. def __init__(self, *args, **kwargs):
args and kwargs look like a pointer and a handle.. but thats a different language. Sorry new to Python, could someone explain the * and the ** please?
3. def handleEvent(self, argsList):
"""Handles events by calling all installed handlers."""
self.origArgsList = argsList
flagsIndex = len(argsList) - 6
self.bDbg, self.bMultiPlayer, self.bAlt, self.bCtrl, self.bShift, self.bAllowCheats = argsList[flagsIndex:]
eventType = argsList[0]
return {
"kbdEvent": self._handleConsumableEvent,
"mouseEvent": self._handleConsumableEvent,
"OnSave": self._handleOnSaveEvent,
"OnLoad": self._handleOnLoadEvent
}.get(eventType, self._handleDefaultEvent)(eventType, argsList[1:])
I must have stared at this for hours. I finally figured out that you were handling a case where there is more than one function to handle each event. The value in the EventHandlerMap had been changed from a function to a list of functions. And sure enough up top in the comment area that is what you say, but that just didn't get into my skull when I read it. If I understand this right, then the following is true:
a. If you want to replace (override) all other handlers for an event then you use setEventHandler().
b. If you want to add your handling to an already installed event, then you use addEventHandler().
c. keyboard and mouse events are different in that if there are multiple handlers, after the first successfull handling of the event, the event gets dropped. The other handlers are not called.
d. no order is guarenteed to the handler calls.
Is my understanding correct?
4. I can't figure out what you are trying to do with Save and Load. They don't seem to complement each other.
5. Comparing your event handler with the standard it seems you are missing:
bDummy = false
I have no idea what bDummy does. Can you enlighten me at all?
By the way, :thanx: for this code, my brain just isn't quite up to speed yet.
Dr Elmer Jiggle May 15, 2006, 06:39 AM I basically learned Python for this mod, so a lot of this stuff is picked up, borrowed, stolen from various examples I found. As a result, my use of the techniques and more importantly my explanations may not be entirely right, but here's my best attempt.
Does CvCustomEventmanager have two supers? If so, what does it inherit from "object"?
Yes, it has two supers. Inheriting from object makes it a "new style" Python class, which enables the use of super as shown below.
super(CvCustomEventManager, self).__init__(*args, **kwargs)
Without inheriting from object, you need to do all kinds of other crazy stuff to call the superclass method. You'll see examples in some of the event managers in other mods. They do stuff like "self.parent = CvEventManager", which isn't going to work very well if someone tries to derive from their subclass (because then the subclass will reset parent to something else). Anyway, this seemed like a much safer way to deal with calling the superclass method.
2. def __init__(self, *args, **kwargs):
args and kwargs look like a pointer and a handle.. but thats a different language. Sorry new to Python, could someone explain the * and the ** please?
*args basically gets any extra arguments after the declared ones (like ... in C). **kwargs is for keyword arguments. I read something somewhere that said if you use super to call the superclass method, you should always include *args and **kwargs in your methods. They gave an example of why, but I can't remember what it was.
3. def handleEvent(self, argsList):
"""Handles events by calling all installed handlers."""
self.origArgsList = argsList
flagsIndex = len(argsList) - 6
self.bDbg, self.bMultiPlayer, self.bAlt, self.bCtrl, self.bShift, self.bAllowCheats = argsList[flagsIndex:]
eventType = argsList[0]
return {
"kbdEvent": self._handleConsumableEvent,
"mouseEvent": self._handleConsumableEvent,
"OnSave": self._handleOnSaveEvent,
"OnLoad": self._handleOnLoadEvent
}.get(eventType, self._handleDefaultEvent)(eventType, argsList[1:])
I must have stared at this for hours. I finally figured out that you were handling a case where there is more than one function to handle each event. The value in the EventHandlerMap had been changed from a function to a list of functions. And sure enough up top in the comment area that is what you say, but that just didn't get into my skull when I read it. If I understand this right, then the following is true:
It makes a little more sense if you break it down into several lines. Normally I would have done that myself, but this is supposedly a fairly standard Python idiom. It does this:
handlerFunctionMap = {
"kbdEvent": self._handleConsumableEvent,
"mouseEvent": self._handleConsumableEvent,
"OnSave": self._handleOnSaveEvent,
"OnLoad": self._handleOnLoadEvent
}
handlerFunction = handlerFunctionMap.get(eventType)
if (handlerFunction == null):
handlerFunction = self._handleDefaultEvent
return handlerFunction(eventType, argsList[1:])
It looks up the appropriate handler function from a dictionary / map. If nothing is found, it uses a default function. That function is then called with the eventType string and any additional arguments that are passed in by the game engine (like city where it occurred, player, etc.).
a. If you want to replace (override) all other handlers for an event then you use setEventHandler().
b. If you want to add your handling to an already installed event, then you use addEventHandler().
c. keyboard and mouse events are different in that if there are multiple handlers, after the first successfull handling of the event, the event gets dropped. The other handlers are not called.
d. no order is guarenteed to the handler calls.
Is my understanding correct?
Yes, all correct. There is actually an order guarantee in the current implementation, since new handlers are appended to an ordered list, but I didn't want to make that promise.
4. I can't figure out what you are trying to do with Save and Load. They don't seem to complement each other.
I can't figure it out either. If anyone can tell me what is supposed to happen when the save and load events are fired, I'll fix the handler functions. ;) Save returns a string. According to the comments in the game code, it's "The string to be saved." I don't know how the load event is supposed to do anything with that string, because it isn't passed as part of the event. Therefore, as you noticed, my load handler doesn't do anything with it.
5. Comparing your event handler with the standard it seems you are missing:
bDummy = false
I have no idea what bDummy does. Can you enlighten me at all?
bDummy is renamed in my code to bMultiPlayer. I forget where I got that from, but someone seems to have decided that's what it means, so I figured I'd use the more informative name. I'm not actually 100% certain that the new name is more correct. It might just be that I copied someone else's mistake.
fitchn May 15, 2006, 07:09 PM As I posted in the main Creation & customization forum, I wish to add this mod with the sdksixmapsizes mod (http://www.civfanatics.net/uploads11/sdksixmapsizes.zip) and the civmore mod (http://download.filefront.com/5053060;0f9679af12ef6af490ef39ff5db215bee10c530604 6efb1599a19702e641378bf8e8059120a3cb82). Could somebody please explain in detail what I need to do to merge these?
I was able to successfully merge this mod into CivMore! Civ4lerts will be included in my next release of CivMore!
@Dr Elmer Jiggle: I must say, I am quite impressed! Merging your mod was about as simple as they come! Move a couple files, check a few potential conflicts (of which all checked out), and it was up and running! Beautiful! Keep up the good work!
goodyhut May 15, 2006, 08:24 PM I was able to successfully merge this mod into CivMore! Civ4lerts will be included in my next release of CivMore!
@Dr Elmer Jiggle: I must say, I am quite impressed! Merging your mod was about as simple as they come! Move a couple files, check a few potential conflicts (of which all checked out), and it was up and running! Beautiful! Keep up the good work!
Awesome! You rock man!
pholtz May 17, 2006, 04:45 AM I am probably over analyzing this thing but I am looking at bDummy. In the original file it is a local variable. Seemingly used as a placeholder only. (at least as far as I can tell). For some reason they set it to false before using it.. as follows:
bDummy = false
self.bDbg, bDummy, self.bAlt, self.bCtrl, self.bShift, self.bAllowCheats = argsList[idx:]
Does anyone know if deleteing the bDummy = false line would have any negative effect on the code? The variable goes out of scope quickly and is never used again. The only thing I can think of is that since the argument list is variable it helps somehow to make bDummy a boolean explicitly.
Now in Alerts, you changed bDummy to self.bMultiPlayer. I think that makes it a data attribute, so now it is part of the class instance. Also it was not initialized to anything in __init__ as is the standard for data attributes.
So, since it doesn't seem to be used, I think it is best to leave it as a dummy and also not make it a data atribute. I am a python noob, probably making a mountain out of a molehill.
Dr Elmer Jiggle May 17, 2006, 07:13 AM So, since it doesn't seem to be used, I think it is best to leave it as a dummy and also not make it a data atribute. I am a python noob, probably making a mountain out of a molehill.
It isn't used directly by the event manager, but it can be used by event handlers (assuming someone actually knows what it means). I can't remember where I got the bMultiPlayer name, but I know I didn't make it up myself, so that means somebody somewhere is using it for something.
As far as initializing it, it obviously wouldn't hurt, but I don't think it's necessary. All of those variables only make sense in the context of handling an event, and since all events go through the handleEvent function first, the variables will be initialized before they're used.
Initializing them first in the constructor is probably good general practice, but it's really redundant in this case. I have no idea why they set bDummy to false. That just looks stupid. ;) I mean, it's essentially identical to:
x = 2
x = y * 3
HolyHandGrenade Jun 13, 2006, 11:48 PM I am currently playing HoF-Mod and I don't know if I am doing something wrong or if I just trapped somewhere but after one of my cities reached "legendary" status I got the message "<cities> cultural borders will expand next round" each turn. What must I do?
(... and thanks for the nice mod :))
Dr Elmer Jiggle Jun 14, 2006, 06:56 AM I am currently playing HoF-Mod and I don't know if I am doing something wrong or if I just trapped somewhere but after one of my cities reached "legendary" status I got the message "<cities> cultural borders will expand next round" each turn. What must I do?
The cultural border expansion warning is something they added in the HoF mod. I didn't write that code myself, so I'm not sure exactly what would cause it. I've noticed a similar problem with the city growth warnings when you have "stagnate growth" turned on, but I doubt that's related.
One simple workaround might be to just go to the options screen and turn off that warning for a while.
You should probably report this in the HoF mod thread. It does sound like a bug.
HolyHandGrenade Jun 15, 2006, 05:00 AM The cultural border expansion warning is something they added in the HoF mod. I didn't write that code myself, so I'm not sure exactly what would cause it. I've noticed a similar problem with the city growth warnings when you have "stagnate growth" turned on, but I doubt that's related.
I noticed this behaviour too.:(
One simple workaround might be to just go to the options screen and turn off that warning for a while.
Nice idea, but I normally don't play OCC - so switching off this message means switching it off for ALL citites - not only the one causing the problem.
You should probably report this in the HoF mod thread. It does sound like a bug.
Ok - I will do this - thx
Officer Reene Jul 10, 2006, 09:26 PM I just wanted to post further on the MP issues..
I got this to work in SP but of course in MP it doesnt work
when I tried to use it in MP in Fitchn's CivMore Mod version .40
http://forums.civfanatics.com/showthread.php?t=163596
Any non-host human player would get no interface
I also tried to merge this with Fitchn's earlier version .30
and got slightly better results (but still not working correctly)
Any non-host human player would not get the "Dawn of Man" pop up at the start of the game... and could not name/rename cities created..
dont know if your working on this anymore... but I figured I'd provide more info on it...
...and possibly get any suggestions to fix this problem? :mischief:
I really like this mod component... but since I play almost all my games in MP... I cant use it :sad:
NOTE: This mod works fine in SP.... :rolleyes:
Dr Elmer Jiggle Jul 10, 2006, 10:25 PM If someone comes up with a fix for multiplayer, I would merge that in with my source code, but since I only do single player myself, a) there's not much likelihood that I'll be able to figure it out on my own and b) it's not very high on my priority list. Theoretically, I'd like to get it working just for the personal satisfaction of being able to say that it works, but in practice it's not something that really affects me enough to do much about it.
FWIW, the Hall of Fame mod has an improved version of this mod, but I doubt any of the changes they made would have any impact on multiplayer use.
Jeckel Jul 11, 2006, 12:00 AM There is a good thread here (http://forums.civfanatics.com/showthread.php?t=174792) about causing and avoiding OOS errors when coding with python in Civ4.
Its a good read and it wouldn't hurt any python modder to read through it. :)
wotan321 Jul 20, 2006, 06:27 AM Okay, I am trying to add a half dozen componants to my mod, and I just can't get this one to work. I have checked and rechecked the additions of files, but since I am NOT a python programmer, I am not sure if some other mod is conflicting with this one to cancel it out.
What are some conflicts (as mentioned earlier) of lines that I should pay attention to?
Thanks for any feedback.
Jeckel Jul 22, 2006, 07:57 AM What sort of problems are you having? If you give a little specific info I'm sure someone can help you.
jonpfl Jul 27, 2006, 07:04 AM All,
Will this mod work with Warlords?
Has any tried this yet?
Thx
jonpfl
Dr Elmer Jiggle Jul 27, 2006, 07:19 AM I haven't tried it yet and won't until sometime after next week, but my gut feeling is that it will probably work, and if it doesn't, the changes should be simple. There were no changes necessary for the last patch.
jonpfl Jul 28, 2006, 03:50 PM So, anyone get this working with warlords yet?
Thx
jonpfl
TheLopez Jul 28, 2006, 04:27 PM So, anyone get this working with warlords yet?
Thx
jonpfl
It will work as long as you make the following change found in this posting:
http://forums.civfanatics.com/showpost.php?p=4330901&postcount=86
Officer Reene Jul 28, 2006, 05:56 PM It will work as long as you make the following change found in this posting:
http://forums.civfanatics.com/showpost.php?p=4330901&postcount=86
@TheLopez
Will that apply to all .py changes in any mod that changes some py files or only this particular py mod :confused:
TheLopez Jul 28, 2006, 09:27 PM @TheLopez
Will that apply to all .py changes in any mod that changes some py files or only this particular py mod :confused:
Only the ones that use Dr. Elmer's ini parsing code.
Officer Reene Jul 28, 2006, 09:39 PM Only the ones that use Dr. Elmer's ini parsing code.
ah ok...thx
mikezang Aug 03, 2006, 08:18 PM Here are the files I promised in my PM
Did you solve your problems?
Spocko Aug 05, 2006, 07:33 AM Did you solve your problems?
Actually I abandoned my efforts to incorporate Dr Jiggle's design for the event manager. I couldn't understand it well enough to know how to incorporate other mods into my fused mod.
Instead, I created a modcomp "ExecutiveBriefing" that is invoked in the event manager by "onCityDoTurn" (see code herein). It provides staggered messages about various aspects of your cities.
Good luck with your coding!
Spocko
## ExecutiveBriefing by Spocko
## Inspired by Dr Jiggle's Civ4Lerts mod
##
from CvPythonExtensions import *
import CvUtil
import PyHelpers
import Popup as PyPopup
import CvCameraControls
# globals
gc = CyGlobalContext()
class ExecutiveBriefing:
def onCityDoTurn(self, argsList):
pCity = argsList[0]
iPlayer = argsList[1]
iturn = gc.getGame().getGameTurn()
if ((not CyGame().isNetworkMultiPlayer()) and (pCity.getOwner() == CyGame().getActivePlayer()) and (not gc.getPlayer(iPlayer).isAnarchy())):
# City is about to grow and not because of it finishing producing a unit (settler or worker) using food
NoGrowthEmphasis = 5
if ((pCity.getFoodTurnsLeft() == 1) and not pCity.isFoodProduction() and (not pCity.AI_isEmphasize(NoGrowthEmphasis))):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,25,'%s will grow to size %s next turn...' %((pCity.getName()), (pCity.getPopulation() + 1)),'',1,'Art/Interface/Buttons/Units/Settler.dds',ColorTypes(8),pCity.getX(),pCity.getY (),True,True)
# City is about to grow and, by doing so, create one too many unhealthy people
if (pCity.goodHealth() <= pCity.badHealth(False)):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s will become unhealthy next turn...' %(pCity.getName()),'',1,'Art/Interface/Buttons/General/unhealthy_person.dds',ColorTypes(10),pCity.getX(), pCity.getY(),True,True)
# City is about to grow and, by doing so, create one too many unhappy people
if (pCity.happyLevel() <= pCity.unhappyLevel(0)):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s will become unhappy next turn...' %(pCity.getName()),'SND_CITY_REVOLT',1,'Art/Interface/Buttons/General/resistance.dds',ColorTypes(7),pCity.getX(),pCity.g etY(),True,True)
# Give a periodic status report on which cities are unhappy
if ((iturn % 4) == 0):
if (pCity.angryPopulation(0) > 0):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'The people of %s are angry!' %(pCity.getName()),'',1,'Art/Interface/Population Heads/angrycitizen.dds',ColorTypes(7),pCity.getX(),pCity .getY(),True,True)
# Give a periodic status report on which cities are unhealthy
if (((iturn + 1) % 4) == 0):
if (pCity.healthRate(False, 0) < 0):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'The people of %s are not in good health!' %(pCity.getName()),'',1,'Art/Interface/Buttons/General/unhealthy_person.dds',ColorTypes(10),pCity.getX(), pCity.getY(),True,True)
# Give a periodic status report on which cities have evenly split health/unhealthy (and the city is not about to grow - handled elsewhere)
if ((iturn % 5) == 0):
if ((pCity.getFoodTurnsLeft() != 1) and (pCity.goodHealth() == pCity.badHealth(0))):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s is half healthy, half unhealthy...' %(pCity.getName()),'',1,'Art/Interface/Buttons/General/unhealthy_person.dds',ColorTypes(13),pCity.getX(), pCity.getY(),True,True)
# Give a periodic status report on which cities have evenly split happy/unhappy (and the city is not about to grow - handled elsewhere)
if ((iturn +1 % 5) == 0):
if ((pCity.getFoodTurnsLeft() != 1) and (pCity.happyLevel() == pCity.unhappyLevel(0))):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s is poised between happiness and unhappiness...' %(pCity.getName()),'',1,'Art/Interface/Buttons/General/resistance.dds',ColorTypes(12),pCity.getX(),pCity. getY(),True,True)
# Give a periodic status report on which cities are either starving or close to it
if (((iturn - 1) % 3) == 0):
if (pCity.foodDifference(True) < 0):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s needs more food...' %(pCity.getName()),'',1,'Art/Interface/Symbols/Food/food05.dds',ColorTypes(7),pCity.getX(),pCity.getY( ),True,True)
# Give a periodic report on cities that have a long wait before finishing their current production
if ((iturn % 20) == 0):
if (pCity.getGeneralProductionTurnsLeft() > 30):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s needs %d turns to build a %s...' %(pCity.getName(),pCity.getGeneralProductionTurnsL eft(),pCity.getProductionName()),'',1,'Art/Interface/Symbols/Production/production05.dds',ColorTypes(78),pCity.getX(),pCit y.getY(),True,True)
# Give a periodic report on cities that are unproductive
if ((iturn % 16) == 0):
if ((pCity.getPopulation() > 3) and (pCity.getPopulation() > (pCity.getYieldRate(YieldTypes.YIELD_PRODUCTION)*1 .5))):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s is woefully unproductive ( %s )...' %(pCity.getName(),pCity.getProductionName()),'',1, 'Art/Interface/Symbols/Production/production05.dds',ColorTypes(11),pCity.getX(),pCit y.getY(),True,True)
# Give a periodic report on small cities that would benefit from Hurrying production
if (((iturn + 1) % 7) == 0):
civGovernment = gc.getPlayer(iPlayer).getCivics(0)
civLabor = gc.getPlayer(iPlayer).getCivics(2)
if (((civGovernment == gc.getInfoTypeForString('CIVIC_UNIVERSAL_SUFFRAGE' )) or (civLabor == gc.getInfoTypeForString('CIVIC_SLAVERY'))) and ((pCity.getPopulation() < 4) and (pCity.getGeneralProductionTurnsLeft() > 30))):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s could use some hurry-up production for its %s...' %(pCity.getName(),pCity.getProductionName()),'',1, 'Art/Interface/Symbols/Production/production05.dds',ColorTypes(11),pCity.getX(),pCit y.getY(),True,True)
# Give a periodic status report on which cities are set to emphasize NO GROWTH
if (((iturn - 2) % 7) == 0):
if (pCity.AI_isEmphasize(NoGrowthEmphasis)):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'The city governor of %s is emphasizing No Growth policies...' %(pCity.getName()),'',1,'Art/Interface/Buttons/Units/Settler.dds',ColorTypes(12),pCity.getX(),pCity.get Y(),True,True)
# Give a periodic report on cities that are not connected to the civ trade network
if ((iturn % 9) == 0):
if (not pCity.isConnectedToCapital(0)):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s is not connected to the capital city...' %(pCity.getName()),'',1,'Art/Interface/Buttons/Governor/commerce.dds',ColorTypes(13),pCity.getX(),pCity.ge tY(),True,True)
# Give a periodic report on cities that have a long wait before growing
if ((iturn % 15) == 0):
if ((pCity.getFoodTurnsLeft() > 30) and not pCity.isFoodProduction() and (not pCity.AI_isEmphasize(NoGrowthEmphasis)) and (pCity.getPopulation() > 3) and (pCity.getPopulation() < 9)):
CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s needs %d turns to grow to size %d...' %(pCity.getName(),pCity.getFoodTurnsLeft(),(pCity. getPopulation() + 1)),'',1,'Art/Interface/Buttons/Units/Settler.dds',ColorTypes(7),pCity.getX(),pCity.getY (),True,True)
# # Give a periodic report on small cities that would benefit from Hurrying production
# if (((iturn + 1) % 7) == 0):
# civGovernment = gc.getPlayer(iPlayer).getCivics(0)
# civLabor = gc.getPlayer(iPlayer).getCivics(2)
# if (((civGovernment == gc.getInfoTypeForString('CIVIC_POLICE_STATE')) or ( civGovernment == gc.getInfoTypeForString('CIVIC_UNIVERSAL_SUFFRAGE' )) or (civLabor == gc.getInfoTypeForString('CIVIC_SLAVERY'))) and ((pCity.getPopulation() < 4) and (pCity.getGeneralProductionTurnsLeft() > 30))):
# CyInterface().addMessage(CyGame().getActivePlayer( ),True,10,'%s could use some hurry-up production for its %s...' %(pCity.getName(),pCity.getProductionName()),'',1, 'Art/Interface/Symbols/Production/production05.dds',ColorTypes(11),pCity.getX(),pCit y.getY(),True,True)
Caesium Aug 05, 2006, 07:41 AM @spocko: May I use your code above for my mod?
Officer Reene Aug 05, 2006, 03:10 PM @Spocko
will that work in MP? :confused:
as I found out previously Civlerts will not :sad:
and I am still looking for something like Civlerts to add in my mod
also will it work with the vanilla version (not warlords expansion) of Civ4?
I still have not be able to upgrade my mod to warlords... so I could test it out in vanilla...(if compatable) and then when I upgrade to warlords I could do the same...... :mischief:
auldian Aug 06, 2006, 01:31 AM Hi,
I'm hoping to see this mod work on my games. I play single-player vanilla 1.61. I've seen zero alerts from this in hours of play. I've checked the location I unzipped the files & folders per the instructions:In the paragraphs that follow, <userdir> refers to the user's personal Civilization 4 directory, typically C:\Documents and Settings\User\My Documents\My Games\Sid Meier's Civilization 4.The civ4alert files seem present as well as their folders.
Is there a switch in the Civilizationiv.ini I need to enable as well, to permit this to run?
Thank you :)
[edit: Just as additional info, Civ is installed on my F: partition, not my system partition, if it matters.]
Spocko Aug 06, 2006, 07:08 AM @spocko: May I use your code above for my mod?
You certainly may. Keep in mind that some of the logic I borrowed from Dr Jiggle's code, so if you make this public, please give credit to Dr. Jiggle.
Spocko
Spocko Aug 06, 2006, 07:14 AM @Spocko
will that work in MP? :confused:
as I found out previously Civlerts will not :sad:
and I am still looking for something like Civlerts to add in my mod
also will it work with the vanilla version (not warlords expansion) of Civ4?
I still have not be able to upgrade my mod to warlords... so I could test it out in vanilla...(if compatable) and then when I upgrade to warlords I could do the same...... :mischief:
I've never played MP, so I don't know anything about the issues associated with modding for MP play. I can say that this class is referenced only once in the event manager, and that it does not alter gameplay (it only reports on existing conditions). And there's the code in the IF statement that reads "if ((not CyGame().isNetworkMultiPlayer())..." implying that this could be used in MP only if the IF statement was changed. It may be that the condition was placed there by Dr Jiggle because his code may not have been MP-ready and it may be that my statements are MP-ready, since they only check existing conditions and use no INI parsing.
This code, now in use with Warlords, is pretty much the same code I used for vanilla 1.61.
Good luck - I'll watch this thread.
Spocko
Officer Reene Aug 06, 2006, 07:51 AM I've never played MP, so I don't know anything about the issues associated with modding for MP play. I can say that this class is referenced only once in the event manager, and that it does not alter gameplay (it only reports on existing conditions). And there's the code in the IF statement that reads "if ((not CyGame().isNetworkMultiPlayer())..." implying that this could be used in MP only if the IF statement was changed. It may be that the condition was placed there by Dr Jiggle because his code may not have been MP-ready and it may be that my statements are MP-ready, since they only check existing conditions and use no INI parsing.
This code, now in use with Warlords, is pretty much the same code I used for vanilla 1.61.
Good luck - I'll watch this thread.
Spocko
Ok Ill test it... and tell you how it works.... :eek:
and if I use it in my mod.... I'll give you and the good doctor credit....
now where do place the code (specific file and line please :p )... and any specific instructions on installation.....? :mischief:
mikezang Aug 06, 2006, 08:40 AM Where can I find file Art/Interface/mainscreen/cityscreen/angry_citizen.dds?
Spocko Aug 06, 2006, 11:00 AM Ok Ill test it... and tell you how it works.... :eek:
now where do place the code (specific file and line please :p )... and any specific instructions on installation.....? :mischief:
I've attached a zip file with ExecutiveBriefing.py and my event manager. Place ExecutiveBriefing.py into your mod's Assets/Python/ folder, and edit your mod's eventmanager as follows:
At the top, where you declare your Imports, include (without the quotes):
"import ExecutiveBriefing"
... and then just below that where you see assignments that look like "gc = CyGlobalContext()", etc., include the statement (without the quotes):
"eb = ExecutiveBriefing.ExecutiveBriefing()"
These two lines should be within the first dozen or so lines of your mod's eventmanager.
Here's how the top of my eventmanager looks:
## Sid Meier's Civilization 4
## Copyright Firaxis Games 2005
##
## CvEventManager
## This class is passed an argsList from CvAppInterface.onEvent
## The argsList can contain anything from mouse location to key info
## The EVENTLIST that are being notified can be found
from CvPythonExtensions import *
import CvUtil
import CvEventManager
import CvAdvisorUtils
import CvCameraControls
import CvDebugTools
import CvScreensInterface
import CvTechChooser
import CvTopCivs
import CvWBPopups
import CvWorldBuilderScreen
import Popup as PyPopup
import PyHelpers
import random
import sys
#INSERT IMPORTS
import ExecutiveBriefing
eb = ExecutiveBriefing.ExecutiveBriefing()
gc = CyGlobalContext()
...
Then, add one more statement that is to be invoked whenever the game calls "onCityDoTurn", which is every turn for every city in the game. Search your mod's eventmanager for "onCityDoTurn" and insert the code "eb.onCityDoTurn(argsList)" at some point in the block of code such that "eb.onCity..." will be called each time. My block of code looks like this:
def onCityDoTurn(self, argsList):
'City Production'
self.parent.onCityDoTurn(self, argsList);
#INSERT MODS
eb.onCityDoTurn(argsList)
If these instructions are insufficient, let me know (you can pm me if you like). I'll help you as best I can. Much of this depends on how your mod's eventmanager file is structured...
I'm off now to continue my re-engineering of Religions and Civics. I'll check back either later this evening or sometime tomorrow evening. Good luck!
And be sure to back up your files before you dig in :)
Spocko
ps: As usual, I'm having tremendous difficulty using this forum to upload files, ZIPs are invalid, ACE's are invalid. So, you can copy the code I posted for ExecutiveBriefing http://forums.civfanatics.com/showpost.php?p=4365291&postcount=69 into a new file and name it ExecutiveBriefing.py. That code is the same as what I've tried to upload, and I've explained the significant points from my eventmanager. Sorry for this inconvenience - if you've been modding Civ4, these instructions should be workable; if you're new to modding, let me know and I'll work with you via PM or even direct email if you're willing (I can email you directly the two files I tried to upload). I will keep watching for your messages.
Jeckel Aug 06, 2006, 06:44 PM For uploading, I'm confused on how you are trying to upload your files. I go to the toolbar at the top of the pages and click on the 'Quick Links' tab and then pick the 'Upload File' option. This will allow you to upload zip, rar, ect file types.
You can also upload the file to the File Database, this also takes many different file extensions. :)
Officer Reene Aug 06, 2006, 06:55 PM @Spocko
ok... I think I understand you (sorry I cay code python as well as I can fly in the air on my own :crazyeye: )... but I'll try it :goodjob:
due to my own beta testing requirements... I wont be able to test this till the end of next week (hopefully) when I start a new testing cycle and add this code :eek:
I'll PM u if I have any problems ....
....and report my progress...
One question... does your events "pop up" like the DR in the events log?
(I just want to know where to look for the changes :p )
thanks for all your help and patience with this noob modder! ;)
Spocko Aug 06, 2006, 07:20 PM For uploading, I'm confused on how you are trying to upload your files. I go to the toolbar at the top of the pages and click on the 'Quick Links' tab and then pick the 'Upload File' option. This will allow you to upload zip, rar, ect file types.
You can also upload the file to the File Database, this also takes many different file extensions. :)
Thanks, Jeckel - I'll check this out during this week, if only to help Officer Reene (if he needs help that is...) :p
Spocko Aug 06, 2006, 07:24 PM @Spocko
I'll PM u if I have any problems ....
....and report my progress...
One question... does your events "pop up" like the DR in the events log?
(I just want to know where to look for the changes :p )
thanks for all your help and patience with this noob modder! ;)
Glad to help - I'm only an intermediate modder, so I can learn by helping.
I've never paid attention to the events log... but during gameplay the Icons popup along the edges of the camera view, centered over the city that pertains to the message.
I'll check into Jeckel's suggestions for uploading files so I will be better prepared to help out, if necessary. I was once able to upload files with no difficulty, but lately I've had no success using at least two different methods for creating a zip file on my drive that is acceptable to this Forum.
No problem, I'll figure out something. Good luck!
Spocko
Dr Elmer Jiggle Aug 07, 2006, 07:42 AM Where can I find file Art/Interface/mainscreen/cityscreen/angry_citizen.dds?
Those are part of the game, so they should be wherever you installed the game, typically something like C:\Program Files\Firaxis\Sid Meier's Civilization IV\Assets\...
Officer Reene Aug 07, 2006, 09:59 AM Glad to help - I'm only an intermediate modder, so I can learn by helping.
I've never paid attention to the events log... but during gameplay the Icons popup along the edges of the camera view, centered over the city that pertains to the message.
Spocko
No.. .thank you for your help! :D
I should be finished with my new modding my Thurs (hopefully:mischief: )
then I should be able to add it and test it by Fri
but now I know where to look :p
No problem, I'll figure out something. Good luck!
Spocko
thx for all your help again! I'll keep you posted ;)
jonpfl Aug 07, 2006, 11:20 AM Will this work in mplayer now?
Gaurav Aug 07, 2006, 01:21 PM Will this work in mplayer now?
One of the users of my mod had helped me identify a bug with team multiplayer for the HOF version of this mod. I have provided a choice of tentative patches for my mod in my thread. I would appreciate it if one of you would test them out, as I only have a single PC.
If anyone would like to separate out the component, that's fine with me.
jonpfl Aug 07, 2006, 01:42 PM One of the users of my mod had helped me identify a bug with team multiplayer for the HOF version of this mod. I have provided a choice of tentative patches for my mod in my thread. I would appreciate it if one of you would test them out, as I only have a single PC.
If anyone would like to separate out the component, that's fine with me.
When you get a finished product, please let us know
Thx
jonpfl
Dr Elmer Jiggle Aug 11, 2006, 09:43 AM Here's a quick and dirty version that appears to work in Warlords. Note that this will not work with Civ4 Classic. This is just a short term solution that always looks at the Warlords installation directory instead of the Classic installation directory. So far it doesn't seem like any other changes are required.
Um, what the heck? The forum's file manager won't let me attach a ZIP file. This always worked before. Anyone got any suggestions?
Civ4lerts Warlords Beta (http://forums.civfanatics.com/downloads.php?do=file&id=2291)
jonpfl Aug 11, 2006, 09:56 AM Here's a quick and dirty version that appears to work in Warlords. Note that this will not work with Civ4 Classic. This is just a short term solution that always looks at the Warlords installation directory instead of the Classic installation directory. So far it doesn't seem like any other changes are required.
Um, what the heck? The forum's file manager won't let me attach a ZIP file. This always worked before. Anyone got any suggestions?
So this works in multiplayer now?
Dr Elmer Jiggle Aug 11, 2006, 10:04 AM So this works in multiplayer now?
I doubt it. It works with Warlords. As far as multiplayer goes, I only play single player, so someone is going to need to tell me what's wrong and/or how to fix it. At this point all I know is that it supposedly doesn't work, but I have no idea what to do to fix it.
TheLopez Aug 11, 2006, 10:20 AM Here's a quick and dirty version that appears to work in Warlords. Note that this will not work with Civ4 Classic. This is just a short term solution that always looks at the Warlords installation directory instead of the Classic installation directory. So far it doesn't seem like any other changes are required.
Um, what the heck? The forum's file manager won't let me attach a ZIP file. This always worked before. Anyone got any suggestions?
You need to post the file through the new "File Database" and then post the link to the "File Database" upload.
Dr Elmer Jiggle Aug 11, 2006, 10:36 AM You need to post the file through the new "File Database" and then post the link to the "File Database" upload.
Thanks. Done.
Dr Elmer Jiggle Aug 11, 2006, 11:18 AM A more official update is now linked from the thread's first post. This one should work with both Warlords and Classic. Of course, you need to install them separately (since they reside in different directories), but the same mod files should work without change with either version of Civ4.
Multiplayer is still an oustanding issue.
Liquid Inferno Aug 11, 2006, 09:03 PM Hi,
I'm hoping to see this mod work on my games. I play single-player vanilla 1.61. I've seen zero alerts from this in hours of play. I've checked the location I unzipped the files & folders per the instructions:The civ4alert files seem present as well as their folders.
Is there a switch in the Civilizationiv.ini I need to enable as well, to permit this to run?
Thank you :)
[edit: Just as additional info, Civ is installed on my F: partition, not my system partition, if it matters.]
I too had this problem, couldn’t get alerts to work in either 1.61 or Warlords. They would work occasionally after I made a small change and tested with a quick game using the "Play Now" option. But when I loaded a "Custom Game" with my preferred settings it wouldn’t work anymore.
After days of frustration and playing around I finally made the connection, when playing a Custom Game I always had 'Lock Modified Assets' checked to remove the temptation to peek at the map. Unchecking this option fixed my problem and it works great now, even if it does require a little more willpower :)
Great mod, keep up the good work!
wotan321 Aug 16, 2006, 09:33 PM Should the line "load_module Civ4lerts" be in my PythonErr2.log file if it loaded correctly? It is not mentioned at all in that file. It doesn't ever show Alerts, and I don't know why.....
Any help is appreciated.
Dr Elmer Jiggle Aug 16, 2006, 09:51 PM Should the line "load_module Civ4lerts" be in my PythonErr2.log file if it loaded correctly?
Yes. The last several lines of my PythonErr2.log are
load_module Civ4lerts
load_module CvConfigParser
load_module ConfigParser
load_module CvPath
load_module _winreg
load_module CvModName
CvModName import failed
PY:OnInit
load_module CvAppInterface
Do you have any of those listed? Are there any actual errors listed in PythonErr2.log or PythonErr.log?
Note that "CvModName import failed" is expected. It's not a "real" error.
Are you using this with Warlords or Civ4 Classic? What is the full path to the folder where your Civ4lerts.py file is located (for example, mine is C:\Documents and Settings\Gill\My Documents\My Games\Warlords\CustomAssets\python)?
Zuul Aug 17, 2006, 02:09 AM # City will grow on the next turn
# City will become unhealthy on the next turn
# City will become angry on the next turn
Does it warn even if the city is set to not expand?
wotan321 Aug 17, 2006, 04:51 AM Thank you Dr. Jiggle for your help.
I am attempting to combine Paasky's WorldWar2:SF&B mod into your Civ4Alerts component, and though I have his events working, the Alerts are not. I am a python newbie, so I appreciate your patience.
To answer your question, no, none of that shows in my PythonErr2.log
Attached is the cobbled effort.... if you have time to look it over.
Again, thanks.
Dr Elmer Jiggle Aug 17, 2006, 06:39 AM Does it warn even if the city is set to not expand?
I think so. Obviously it shouldn't, but I think it does.
Keroberos Aug 19, 2006, 11:48 A |