ScriptEventListener( const String &s, int uniqueId, Element *target ) : script( s ), loaded( false ), released( false ), uniqueId( uniqueId ), target( target ) { asmodule = UI_Main::Get()->getAS(); if( target ) { target->AddReference(); } }
virtual void ProcessEvent( Event &event ) { if( !target ) { return; } if( released ) { // the function pointer has been released, but // we're hanging around, waiting for shutdown or GC return; } Element *elem = event.GetTargetElement(); if( elem->GetOwnerDocument() != target->GetOwnerDocument() ) { // make sure the event originated from the same document as the original target return; } UI_ScriptDocument *document = dynamic_cast<UI_ScriptDocument *>(elem->GetOwnerDocument()); if( !document || document->IsLoading() ) { return; } fetchFunctionPtr( document->GetModule() ); // push elem and event as parameters to the internal function // and call it if( UI_Main::Get()->debugOn() ) { Com_Printf( "ScriptEventListener: Event %s, target %s, script %s\n", event.GetType().CString(), event.GetTargetElement()->GetTagName().CString(), script.CString() ); } if( funcPtr.isValid() ) { target->AddReference(); event.AddReference(); try { asIScriptContext *context = asmodule->getContext(); // the context may actually be NULL after AS shutdown if( context ) { funcPtr.setContext( context ); funcPtr( target, &event ); } } catch( ASBind::Exception & ) { Com_Printf( S_COLOR_RED "ScriptEventListener: Failed to call function %s %s\n", funcName.CString(), script.CString() ); } } else { Com_Printf( S_COLOR_RED "ScriptEventListener: Not gonna call invalid function %s %s\n", funcName.CString(), script.CString() ); } }