static void on_shell_signal (GDBusProxy *proxy, gchar *sender_name, gchar *signal_name, GVariant *parameters, gpointer user_data) { PluginObject *obj = user_data; if (strcmp (signal_name, "ExtensionStatusChanged") == 0) { gchar *uuid; gint32 status; gchar *error; NPVariant args[3]; NPVariant result; g_variant_get (parameters, "(sis)", &uuid, &status, &error); STRINGZ_TO_NPVARIANT (uuid, args[0]); INT32_TO_NPVARIANT (status, args[1]); STRINGZ_TO_NPVARIANT (error, args[2]); funcs.invokeDefault (obj->instance, obj->listener, args, 3, &result); funcs.releasevariantvalue (&result); g_free (uuid); g_free (error); } }
bool NPN_InvokeDefault(NPP id, NPObject* obj, const NPVariant* args, uint32_t count, NPVariant*result) { char msg[1024]; sprintf(msg, "NPN_InvokeDefault"); logger->logMessage(msg); bool rv = NPNFuncs.invokeDefault(id, obj, args, count, result); sprintf(msg, "--Return: %x", rv); logger->logMessage(msg); return rv; }
static void on_shell_appeared (GDBusConnection *connection, const gchar *name, const gchar *name_owner, gpointer user_data) { PluginObject *obj = (PluginObject*) user_data; if (obj->restart_listener) { NPVariant result = { NPVariantType_Void }; funcs.invokeDefault (obj->instance, obj->restart_listener, NULL, 0, &result); funcs.releasevariantvalue (&result); } }
bool NPN_InvokeDefault(NPP npp, NPObject* obj, const NPVariant *args, uint32_t argCount, NPVariant *result) { return NPNFuncs.invokeDefault(npp, obj, args, argCount, result); }
SEXP R_NPAPI_Invoke(SEXP plug, SEXP Robj, SEXP Rname, SEXP Rargs, SEXP RconvArgsEnum, SEXP RconvArgsFuns, SEXP RconvRet, SEXP RkeepRes ) { NPP inst = (NPP) R_ExternalPtrAddr(GET_SLOT( plug , Rf_install( "ref" ) ) ); NPNetscapeFuncs *funcs = (NPNetscapeFuncs *) R_ExternalPtrAddr(GET_SLOT( GET_SLOT(plug, Rf_install("funcs")), Rf_install("ref"))); NPVariant *obj = (NPVariant *) R_ExternalPtrAddr(GET_SLOT( Robj , Rf_install( "ref" ) ) ); if(!NPVARIANT_IS_OBJECT(*obj)) { //What should we return in this case? Rf_error("Robj is not an NPVariant containing an NPObject."); return R_NilValue; } //custom conversion functions are applied on R side for return value. convert_t convRet = (convert_t) INTEGER(RconvRet)[0]; convert_t curConvArg; int nargs = LENGTH(Rargs); NPVariant *args = (NPVariant *) funcs->memalloc(nargs*sizeof(NPVariant)); for(int i = 0; i < nargs; i++) { curConvArg = (convert_t) INTEGER(RconvArgsEnum)[i]; ConvertRToNP(VECTOR_ELT(Rargs, i), inst, funcs, &(args[i]), curConvArg); //If we have a custom converter we invoke it with here if(curConvArg == CONV_CUSTOM) { fprintf(stderr, "Custom argument converter detected. Attempting to call JS Conversion function.");fflush(stderr); funcs->invokeDefault(inst, ((NPVariant *) R_ExternalPtrAddr(GET_SLOT( VECTOR_ELT(RconvArgsFuns, i), Rf_install( "ref" ) ) ) ) -> value.objectValue, &args[i], 1, &args[i]) ; } } NPVariant *ret = (NPVariant *) funcs->memalloc(sizeof(NPVariant)); const char *ccname = CHAR(STRING_ELT(Rname, 0)); bool hasMethod = funcs->hasmethod(inst, obj->value.objectValue, funcs->getstringidentifier(ccname)); if(!hasMethod) { char msg[200]; sprintf(msg, "Object has no %s method.", ccname); Rf_error(msg); return R_NilValue; } bool success = funcs->invoke(inst, obj->value.objectValue, funcs->getstringidentifier(ccname), args, nargs, ret); if(!success) { fprintf(stderr, "\nInvocation of JS method %s failed.", ccname);fflush(stderr); } for(int j=0; j<nargs; j++) { if (NPVARIANT_IS_OBJECT(args[j])) funcs->releaseobject(args[j].value.objectValue); //funcs->releasevariantvalue(&args[j]); } funcs->memfree(args); if(!success) { char msg2[200]; sprintf(msg2, "Invoke failed for %s method.", ccname); Rf_error(msg2); return R_NilValue; } SEXP ans; //PROTECT(ans = R_NilValue); PROTECT(ans = NEW_INTEGER(1)); bool canfree = ConvertNPToR(ret, inst, funcs, convRet, &ans); bool keepRes = LOGICAL(RkeepRes)[0]; if(canfree || !keepRes) funcs->releasevariantvalue(ret); UNPROTECT(1); if(keepRes) return ans ; else return R_NilValue; }