1

我有这个 getValue 方法 + NPclass 方法:

static bool hasmethod(NPObject *npobj, NPIdentifier name)
{
    return true;
}
static NPObject* allocate (NPP npp, NPClass *aClass)
{
    return  browser-> createobject(npp, aClass);
}
static bool hasProperty(NPObject *npobj, NPIdentifier name)
{
     return true;
}
static bool getProperty (NPObject *npobj, NPIdentifier name, NPVariant *result)
{
   if (!result) 
       return false;
   INT32_TO_NPVARIANT(50, *result);
   return true;
}
static void deallocate (NPObject *npobj)
{
   browser -> memfree(npobj);
}
static bool enumerate(NPObject *npobj, NPIdentifier **value, uint32_t *count)
{
    return false;
}
static bool defaultInvoke(NPObject* obj, const NPVariant *args, uint32_t argCount,     NPVariant *result)
{
    if (!result) 
    return false;
    INT32_TO_NPVARIANT(42, *result);
    return true;
}
static bool setProperty (NPObject *npobj, NPIdentifier name, const NPVariant *value)
{
    return false;
}  
static void invalidate(NPObject *npobj)
{
}
static bool removeProperty (NPObject *npobj,NPIdentifier name)
{
    return false;
}
NPError NPP_GetValue(NPP instance, NPPVariable variable, void *value)
{
    if (! instance)
    {
        return NPERR_INVALID_INSTANCE_ERROR;
    }
struct NPClass class;
class.structVersion = NP_CLASS_STRUCT_VERSION;
class.construct = NULL;
class.deallocate = deallocate;
class.hasMethod = hasmethod;
class.getProperty= getProperty;
class.enumerate= enumerate;
class.removeProperty= removeProperty;
class.hasProperty = hasProperty;
class.invoke = pinvoke;
class.invokeDefault = defaultInvoke;
class.invalidate = invalidate;
class.setProperty = setProperty;
class.allocate = allocate;
if (variable == NPPVpluginScriptableNPObject)
{
    void **v = (void **)value;
    struct NPObject *object = NPN_CreateObject(instance, &class);
    NPN_RetainObject(object);
    *v = object;
    return NPERR_NO_ERROR;
}
return NPERR_GENERIC_ERROR;
}

以下是该类指向的另外两个方法:

 bool hasmethod(NPObject *npobj, NPIdentifier name)
 {
     return true;
 }

static bool pinvoke(NPObject* obj, NPIdentifier methodName, const NPVariant *args, uint32_t argCount, NPVariant *result)
{
    if (!result) 
    return false;
    INT32_TO_NPVARIANT(32, *result);
    return true;
}

基本上,我希望对象在调用任何内容时返回 32 以进行测试。

这是我的创建和保留方法:

NPObject *NPN_CreateObject(NPP npp, NPClass *aClass)
{
    return browser->createobject(npp, aClass);
}

NPObject *NPN_RetainObject(NPObject *npobj)
{
    return browser->retainobject(npobj);
}

在我的 Javascript 中:

        <embed type="application/x-my-extension" id="pluginId">
            <script>
            var plugin = document.getElementById("pluginId");
            console.log(plugin.something);

窗口在页面上绘制,但控制台输出未定义。帮助将不胜感激。谢谢!

更新:Georg 建议浏览器由于我的 allocate 方法的无限递归而崩溃。这是新的:

 void* NPN_MemAlloc(uint32_t size)
 {
     return browser->memalloc(size);
 }
 static NPObject* allocate (NPP npp, NPClass *aClass)
 {
   NPObject* object = (NPObject*)NPN_MemAlloc(sizeof(NPObject));
   if (!object)
   {
    return NULL;
   }
   memset(object, 0, sizeof(NPObject));
   return object;
 }

该插件仍然崩溃。

更新 2:我使对象实例特定

typedef struct PluginInstance {
  NPP npp;
  NPWindow window;
  NPObject *object;
}PluginInstance;

在我的 NPP_New 方法中,我有

 PluginInstance *newInstance = (PluginInstance*)malloc(sizeof(PluginInstance));
 bzero(newInstance, sizeof(PluginInstance));
 newInstance -> object = NPN_CreateObject(instance, &class);
 newInstance->npp = instance;
 instance->pdata = newInstance;

在我的 getValue 方法中:

    NPObject* obj = ((PluginInstance *) (instance->pdata)) -> object;
    void **v = (void **)value;
    NPN_RetainObject(obj);
    *v = obj;

还是一样的问题

4

1 回答 1

1

您不应该只填写部分NPClass功能,最值得注意的是您缺少hasProperty& getProperty。浏览器可能会处理其他缺失的功能,但据我所知,它们不是必需的。

另请注意,您NPP_GetValue()应该只返回variable == NPPVpluginScriptableNPObject.
然后,您应该为每个插件实例创建可编写脚本的对象(请记住,您的插件的多个实例可以同时运行)并且NPN_Release()当您的插件消失时不要忘记可编写脚本的对象。
pinvoke()可以改进为:

static bool pinvoke(NPObject* obj, NPIdentifier methodName, const NPVariant *args, 
                    uint32_t argCount, NPVariant *result)
{
    if (!result) 
        return false;
    INT32_TO_NPVARIANT(32, *result);
    return true;
}
于 2012-07-26T09:19:09.540 回答