Why I can't register a method which recieved a script class sucessfully?

Started by
5 comments, last by wdl7770016 10 years, 12 months ago

this is my c++ code:


class Base {
public:
    Base() {
        _refCount = 1;
        cout << "Base Create" << endl;
    }

    void addRef() {
        _refCount++;
    }

    void release() {
        _refCount--;
        if (_refCount == 0) {
            delete this;
        }
    }

    void reciever(asIScriptObject *obj) {
        cout << "???" << endl;
        man = obj;
    }

    void active() {
        cout << "??Active" << endl;
        cout << (man == 0) << endl;
        cout << "??Active" << endl;
    }

private:
    int _refCount;
    asIScriptObject *man;
};

Base *Base_Factory() {
    return new Base();
}
......
//---------------------------------------------------------
    scriptEngine->RegisterObjectType("Base", 0, asOBJ_REF);
    scriptEngine->RegisterObjectBehaviour("Base",asBEHAVE_FACTORY, "Base@ f()", asFUNCTION(Base_Factory), asCALL_CDECL);
    scriptEngine->RegisterObjectBehaviour("Base", asBEHAVE_ADDREF, "void f()", asMETHOD(Base, addRef), asCALL_THISCALL);
    scriptEngine->RegisterObjectBehaviour("Base", asBEHAVE_RELEASE, "void f()", asMETHOD(Base, release), asCALL_THISCALL);

    //---------------------------------------------------------
    CScriptBuilder builder;
    r = builder.StartNewModule(scriptEngine, "MyModule");

    int isOK = builder.AddSectionFromFile("init.as");
    asIObjectType *type = scriptEngine->GetObjectTypeByName("Human");
    cout << "type == " << (type == 0) << endl;

    //r = builder.AddSectionFromFile("test.as");

    r = builder.BuildModule();
  
    scriptEngine->RegisterObjectMethod("Base", "void reciever(Human @in)", asMETHOD(Base, reciever), asCALL_THISCALL);
    scriptEngine->RegisterObjectMethod("Base", "void active()", asMETHOD(Base, active), asCALL_THISCALL);
........

and in my init.as script code:


class Human {
	Human(){}
}

but it is still report a error:


Failed in call to function 'RegisterObjectMethod' with 'Base' and 'void reciever(Human @in)' (code: -10)

why ? may it must to reciever a interface nor a script class?

Advertisement
You need to register an interface name from the application first with asIScriptEngine::RegisterInterface(const char *name). Then you will be able to register the Base::receiver method that takes a handle to that interface. http://www.angelcode.com/angelscript/sdk/docs/manual/doc_use_script_class.html#doc_use_script_class_3

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

thanks

but there are something like this in the angelScript mannual:


Of course, since the class is declared in the script it isn't possible to know the type before the script is compiled.

but I can't work it successfully

is this because of angelScript does not support reciever a script class thich declared in the as script file?

It can receive it, but you cannot register functions that explicitly refer to the class, because the class type is not known at the time of registering the function. That's why the application should register an interface that the class will then implement. Like this:


void ReceiveClass(asIScriptObject *obj)
{
}
 
void ConfigureEngine(asIScriptEngine *engine)
{
   // Register an interface that the classes should inherit from
   engine->RegisterInterface("MyIntf");
 
   // Register the function that will receive the classes
   engine->RegisterGlobalFunction("void ReceiveClass(MyIntf @+)", asFUNCTION(ReceiveClass), asCALL_CDECL);
}

The script class is then implemented like this:

// AngelScript
class MyClass : MyIntf
{
}
 
void main()
{
   MyClass c;
 
   // Pass the object to the application
   ReceiveClass(c); 
}

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

well thanks

but is this means before we register the reciever function

we can add a new section from file A or memory(string)

so that engine can pass the script code and know the script class declared in file A

and when we register the reciever function the engine had know the script class type

I have try this but it not work

it's so strange>>>right?

Actually, it is not so strange. The types declared in the script modules are in a different scope than the engine registered functions and classes. That is why even though you have compiled a script the types from that script cannot be used when registering engine functions.

The reason for this is that multiple modules can declare the types with the same names without conflict. Modules can also be recompiled or removed dynamically. So if a registered function refer to any of those types, what would happen then?

AngelCode.com - game development and more - Reference DB - game developer references
AngelScript - free scripting library - BMFont - free bitmap font generator - Tower - free puzzle game

thanks

I have learned a lot

This topic is closed to new replies.

Advertisement