Bridge Commander Central
		BC Forums => BC Scripting => Topic started by: Bat66wat6 on July 16, 2012, 08:51:04 PM
		
			
			- 
				Why is it that in Bridge Commander the python event handlers I set up fire multiple times for just one happening of the event ingame.
A perfect example of this could be say CTRL+SHIFT+K or CTRL+SHIFT+G but i've found all of the event handlers are guilty.
If I setup a handler and define it like so:
def GodModeOn(pObject, pEvent):
	print "God mode handler triggered"
        pObject.CallNextHandler(pEvent)
def init():
	App.g_kEventManager.AddBroadcastPythonFuncHandler(App.ET_INPUT_DEBUG_GOD_MODE, pMission, __name__ + ".GodModeOn")
I will see something like:
God mode handler triggered
God mode handler triggered
God mode handler triggered
God mode handler triggered
God mode handler triggered
in the log file for every single press of CTRL+SHIFT+G.
Why is it that this happens and how can I avoid it; have the handler triggered once per event?
			 
			
			- 
				god mode is just SHIFT+G, not CTRL+SHIFT+G
the only time CTRL+SHIFT is used is when using Q for 10 more quantum torps..
			 
			
			- 
				Well either way regardless of the keys handlers still fire lots of times for one occurance of an event.
Subsystem disabled = 
Log: 
Subsystem disabled
Subsystem disabled
Subsystem disabled
Subsystem disabled
Subsystem disabled
Subsystem disabled
 :hithead:
			 
			
			- 
				The longer you press the keys the more messages you get.
That way you can detect if a key is kept pressed, like it is used on primary fire.
			 
			
			- 
				
The longer you press the keys the more messages you get.
That way you can detect if a key is kept pressed, like it is used on primary fire.
That's interesting, but how would one go about only acting on the first call and ignoring all subsequent calls. I just tried hitting SHIFT+R once as fast as I could and predicatably obviously the handler fired at least four or five times. 
There has to be a better way than going out of my way to create elaborate functions such as the one below just so the handler fires once instead of a bagillion times. How'd Totally Games do it? I mean I can't find where the functions are that get called for events such as SHIFT+G or any of the other one-time user triggered keyboard events :doh: 
# check if ShipInstaRepair() has already ran
def InstaRepairAlreadyRan(pShip, opObjID=None):
	shipID = pShip.GetObjID()
	ShieldGenerators = GetAllShieldGenerators(pShip)
	# checking if both generators are operational
	if ShieldGenerators[0].IsDisabled() or ShieldGenerators[1].IsDisabled():
		return 0
	else:
		# are all shields at full strength
		lShields = GetPrimarySecondaryGenNames(pShip)
		pPrimaryGen = MissionLib.GetSubsystemByName(pShip, lShields[0])
		pSecondaryGen = MissionLib.GetSubsystemByName(pShip, lShields[1])
		pPrimaryGen = App.ShieldClass_Cast(pPrimaryGen)
		pSecondaryGen = App.ShieldClass_Cast(pSecondaryGen)
		i = 0
		while(i < 6):
			if not shipShieldVals[shipID][0][i] == pPrimaryGen.GetMaxShields(i):
				return 0
			if not shipShieldVals[shipID][1][i] == pSecondaryGen.GetMaxShields(i):
				return 0
			i = i + 1
	# bugfix: return 0 so SubsystemOperational() will redefine the generators even if the operational generator was  a CTRL+SHIFT+K victim
	if ctrlShiftKGenVictims.has_key(shipID):
		if opObjID==None:
			print "There is no opObjID"
			print "ctrlShiftKGenVictim ship key ", shipID, " removed from ctrlShiftKGenVictims"
			del ctrlShiftKGenVictims[shipID]
			return 0
		else:
			if opObjID in ctrlShiftKGenVictims[shipID]:
				# function was called by SubsystemOperational()
				print ">>>>>>>>>>>>>opObjID is ", opObjID
				print "ctrlShiftKGenVictim ship key ", shipID, " removed from ctrlShiftKGenVictims"
				del ctrlShiftKGenVictims[shipID]
				return 0
			else:
				print "Ship does NOT have a ctrlShiftKVictim generator"
	print "ctrlShiftKGenVictims contents: ", ctrlShiftKGenVictims
	return 1^ Seriously, I made all of that *just* so the handler wouldn't do the same thing five or six times for every one press of the key  :(
			 
			
			- 
				If you've ever developed a WinForms app or Web app you're probably familiar with KeyUp, KeyDown events...
This would be the BC equivalent for GodMode KeyUp for example (bear in mind this is just a code snippet):
1. Setup keyboard handler
	topWindow = App.TopWindow_GetTopWindow()
	topWindow.AddPythonFuncHandlerForInstance(App.ET_KEYBOARD, __name__ + ".HandleKeyboard")
2. Handle event
def HandleKeyboard(pObject, pEvent):
	charType = pEvent.GetUnicode()
	keyType = pEvent.GetKeyState()
	if charType == App.g_kKeyboardBinding.FindKey(App.ET_INPUT_DEBUG_GOD_MODE, App.KeyboardBinding.GET_EVENT, 0.0):		
		if (keyType == App.TGKeyboardEvent.KS_KEYUP and App.TopWindow_GetTopWindow().IsTacticalVisible()): # App.TopWindow_GetTopWindow().IsTacticalVisible() because we can only trigger god mode while in tactical view
			print 'key up'
        pObject.CallNextHandler(pEvent)
			 
			
			- 
				
If you've ever developed a WinForms app or Web app you're probably familiar with KeyUp, KeyDown events...
This would be the BC equivalent for GodMode KeyUp for example (bear in mind this is just a code snippet):
1. Setup keyboard handler
	topWindow = App.TopWindow_GetTopWindow()
	topWindow.AddPythonFuncHandlerForInstance(App.ET_KEYBOARD, __name__ + ".HandleKeyboard")
2. Handle event
def HandleKeyboard(pObject, pEvent):
	charType = pEvent.GetUnicode()
	keyType = pEvent.GetKeyState()
	if charType == App.g_kKeyboardBinding.FindKey(App.ET_INPUT_DEBUG_GOD_MODE, App.KeyboardBinding.GET_EVENT, 0.0):		
		if (keyType == App.TGKeyboardEvent.KS_KEYUP and App.TopWindow_GetTopWindow().IsTacticalVisible()): # App.TopWindow_GetTopWindow().IsTacticalVisible() because we can only trigger god mode while in tactical view
			print 'key up'
        pObject.CallNextHandler(pEvent)
I've got meager experience in messing around with JavaScript and VB in the past so i've come across KeyUp and KeyDown events. I could probably implement this new method of handling but the sad thing is i've spent so much time on the script and got it to run with the handlers/configurations it'd probably be more effort than it's worth to change things now that i've gone out of my way to make functions like InstaRepairAlreadyRan()  :(
I'll deffinitely remember about KeyUp/Down etc handlers in the future and hopefully avoid having to make functions just to check if a handler has already ran.
			 
			
			- 
				That is your right and choice :)
Though honestly I'd feel the same as you.