Exemple #1
0
	virtual void ProcessEvent( Event &event ) {
		Element *elem = event.GetTargetElement();

		UI_ScriptDocument *document = dynamic_cast<UI_ScriptDocument *>( elem->GetOwnerDocument() );
		if( !document || document->IsLoading() ) {
			return;
		}

		if( UI_Main::Get()->debugOn() ) {
			Com_Printf( "ScriptEventCaller: Event %s, target %s, func %s\n",
						event.GetType().CString(),
						event.GetTargetElement()->GetTagName().CString(),
						funcPtr.getName() );
		}

		if( funcPtr.isValid() ) {
			event.AddReference();
			try {
				asIScriptContext *context = as->getContext();

				// the context may actually be NULL after AS shutdown
				if( context ) {
					funcPtr.setContext( context );
					funcPtr( NULL, &event );
				}
			} catch( ASBind::Exception & ) {
				Com_Printf( S_COLOR_RED "ScriptEventListener: Failed to call function %s\n", funcPtr.getName() );
			}
		} else {
			Com_Printf( S_COLOR_RED "ScriptEventListener: Not gonna call invalid function %s\n", funcPtr.getName() );
		}
	}
Exemple #2
0
	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() );
		}
	}
	virtual void ProcessEvent( Event &event )
	{
		if( released ) {
			// the function pointer has been released, but
			// we're hanging around, waiting for shutdown or GC
			return;
		}

		// onloads cant be called within building process
		if( /* event.GetType() == "load" && */ asmodule->isBuilding() )
		{
			// TODO: we should eliminate chain to DocumentLoader like this, so move
			// event postponing somewhere else
			UI_Main::Get()->getDocumentLoader()->postponeOnload( this, event );
			return;
		}

		Element *elem = event.GetTargetElement();

		fetchFunctionPtr( elem->GetOwnerDocument()->GetSourceURL() );

		// 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() ) {
			elem->AddReference();
			event.AddReference();
			try {
				asIScriptContext *context = asmodule->getContext();

				// the context may actually be NULL after AS shutdown
				if( context ) {
					funcPtr.setContext( context );
					funcPtr( elem, &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() );
		}
	}
Exemple #4
0
	ScriptEventCaller( ASInterface *as, asIScriptFunction *func ) : as( as ) {
		funcPtr = ASBind::CreateFunctionPtr( func, funcPtr );
		if( !funcPtr.isValid() ) {
			Com_Printf( S_COLOR_YELLOW "WARNING: ScriptEventCaller::CreateFunctionPtr failed with %s\n", func ? func->GetDeclaration() : "NULL" );
			return;
		}
	}
	void fetchFunctionPtr( const String &document_name )
	{
		if( loaded ) {
			return;
		}

		loaded = true;

		asIScriptModule *module = asmodule->getModule( document_name.CString() );

		assert( module != NULL );
		if( module == NULL ) {
			Com_Printf( S_COLOR_YELLOW "WARNING: ScriptEventListener unable to find module %s\n", 
				document_name.CString() );
		}

		// check direct function-name
		if( script[0] == '$' )
			funcName = script.Substring( 1 );
		else
		{
			// compile inline code
			funcName = createFunctionName( uniqueId );
			String funcCode = createFunctionCode( uniqueId, script );
			script = funcCode;
			asIScriptFunction *scriptFunc = NULL;

			if( !asmodule->addFunction( module, funcName.CString(), funcCode.CString(), &scriptFunc ) ) {
				Com_Printf( S_COLOR_YELLOW "WARNING: ScriptEventListener addFunction failed with %s %s\n", 
					funcName.CString(), funcCode.CString() );
			} else if( scriptFunc ) {
				// I think we only hit this scenario when we do smth like
				// elem.setInnerRML( '<button onclick="window.close();" />' );
				funcPtr = ASBind::CreateFunctionPtr( scriptFunc, funcPtr );
				funcPtr.addref();
				scriptFunc->Release();
			}
			return;
		}

		funcPtr = ASBind::CreateFunctionPtr( funcName.CString(), module, funcPtr );
		if( !funcPtr.isValid() ) {
			Com_Printf( S_COLOR_YELLOW "WARNING: ScriptEventListener::fetchFunctionPtr failed with %s\n", funcName.CString() );
			return;
		}
		funcPtr.addref();
	}
Exemple #6
0
	void releaseFunctionPtr() {
		if( released ) {
			return;
		}

		released = true;
		funcPtr.release();

		if( target ) {
			target->RemoveReference();
			target = NULL;
		}
	}
	virtual void ProcessEvent( Event &event )
	{
		// onloads cant be called within building process
		if( /* event.GetType() == "load" && */ asmodule->isBuilding() )
		{
			UI_Main::Get()->getDocumentLoader()->postponeOnload( this, event );
			return;
		}

		Element *elem = event.GetTargetElement();

		if( UI_Main::Get()->debugOn() ) {
			Com_Printf( "ScriptEventCaller: Event %s, target %s, func %s\n",
				event.GetType().CString(),
				event.GetTargetElement()->GetTagName().CString(),
				funcPtr.getName() );
		}

		if( funcPtr.isValid() ) {
			elem->AddReference();
			event.AddReference();
			try {
				asIScriptContext *context = asmodule->getContext();

				// the context may actually be NULL after AS shutdown
				if( context ) {
					funcPtr.setContext( context );
					funcPtr( elem, &event );
				}
			} catch( ASBind::Exception & ) {
				Com_Printf( S_COLOR_RED "ScriptEventListener: Failed to call function %s\n", funcPtr.getName() );
			}
		}
		else {
			Com_Printf( S_COLOR_RED "ScriptEventListener: Not gonna call invalid function %s\n", funcPtr.getName() );
		}
	}
Exemple #8
0
	virtual ~ScriptEventCaller() {
		funcPtr.release();
	}
	void releaseFunctionPtr()
	{
		released = true;
		funcPtr.release();
	}