1、函数回调,C++主动调用JS
前端:
<embed id="objinput" type="application/safeinput" width="300" height="50">
function enter(){
alert("enter");
}
embed1=document.getElementById('objinput');
embed1.OnEnter=enter;
后端验证
bool ScriptablePluginObject::HasProperty(NPIdentifier name)
{
return (name ==s_idOnEnter);//通过属性传递过来的回调函数,
}
//在获得这个属性时,一定要调用NPN_RetainObject保存起来。这里的属性就是JS的函数指针
bool ScriptablePluginObject::SetProperty(NPIdentifier name, const NPVariant *value)
{
if(name == s_idOnEnter){
if(!m_pJsCallBackObj)
{
m_pJsCallBackObj=NPN_RetainObject(NPVARIANT_TO_OBJECT(*value));
} //NPN_ReleaseObject(m_pJsCallBackObj);
}
return true;
}
保存完成后就可以在需要时调用这个JS了
if(!m_pJsCallBackObj)
MessageBox(NULL,"回调函数不正确!","title",0);
NPVariant result;
NPN_InvokeDefault(mNpp,m_pJsCallBackObj,NULL,0,&result);
NPN_ReleaseVariantValue(&result);
最后还有一个重要的一点:就是一定要在ScriptablePluginObjectBase::_Deallocate(NPObject *npobj)方法中释放回调接口,否则刷新页面时就会崩溃
if(m_pJsCallBackObj)
{
NPN_ReleaseObject(m_pJsCallBackObj);
m_pJsCallBackObj=NULL;
}
关于ScriptablePluginObjectBase::_Deallocate,实际上就是NPClass的一个成员回调函数:
#define DECLARE_NPOBJECT_CLASS_WITH_BASE(_class, ctor) \
static NPClass s##_class##_NPClass = { \
NP_CLASS_STRUCT_VERSION_CTOR, \
ctor, \
ScriptablePluginObjectBase::_Deallocate, \
ScriptablePluginObjectBase::_Invalidate, \
ScriptablePluginObjectBase::_HasMethod, \
ScriptablePluginObjectBase::_Invoke, \
ScriptablePluginObjectBase::_InvokeDefault, \
ScriptablePluginObjectBase::_HasProperty, \
ScriptablePluginObjectBase::_GetProperty, \
ScriptablePluginObjectBase::_SetProperty, \
ScriptablePluginObjectBase::_RemoveProperty, \
ScriptablePluginObjectBase::_Enumerate, \
ScriptablePluginObjectBase::_Construct \
};