This repository has been archived by the owner on Aug 19, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 5
/
ASExtendAdapter.cpp
132 lines (94 loc) · 3.11 KB
/
ASExtendAdapter.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
#include <cassert>
#include <sstream>
#include "Angelscript/wrapper/ASCallable.h"
#include "IASExtendAdapter.h"
#include "ASExtendAdapter.h"
namespace as
{
std::string CreateExtendBaseclassDeclaration(
const char* const pszClassName, const char* const pszBaseClassName,
const char* const pszCPPClassName, const char* const pszCPPBaseClassName,
const char* const pszClassContents )
{
assert( pszClassName );
assert( pszBaseClassName );
assert( pszCPPClassName );
std::stringstream stream;
stream << "class " << pszClassName << " : " << pszBaseClassName << std::endl
<< '{' << std::endl;
//Provide the self member.
stream << "\tprivate " << pszCPPClassName << "@ m_pSelf;" << std::endl;
stream << "\tprivate void SetSelf( " << pszCPPClassName << "@ self )" << std::endl
<< "\t{" << std::endl
<< "\t\t@this.m_pSelf = self;" << std::endl
<< "\t}" << std::endl
<< "\t" << pszCPPClassName << "@ get_self() const { return m_pSelf; }" << std::endl;
//If the user has provided a baseclass type, provide the BaseClass member.
if( pszCPPBaseClassName )
{
stream << "\tprivate " << pszCPPBaseClassName << "@ m_pBaseClass;" << std::endl;
stream << "\tprivate void SetBaseClass( " << pszCPPBaseClassName << "@ BaseClass )" << std::endl
<< "\t{" << std::endl
<< "\t\t@this.m_pBaseClass = BaseClass;" << std::endl
<< "\t}" << std::endl
<< "\t" << pszCPPBaseClassName << "@ get_BaseClass() const { return m_pBaseClass; }" << std::endl;
}
if( pszClassContents )
{
//Output it so it's aligned with the rest of the class contents.
std::stringstream contents( pszClassContents );
std::string szLine;
while( std::getline( contents, szLine ) )
{
stream << '\t' << szLine << std::endl;
}
}
stream << '}' << std::endl;
return stream.str();
}
bool InitializeExtendClass( IASExtendAdapter& adapter, void* const pThis, const char* const pszCPPClassName, const char* const pszCPPBaseClassName )
{
assert( pThis );
assert( pszCPPClassName );
auto obj = adapter.GetObject();
assert( obj );
if( !obj )
return false;
const auto& typeInfo = obj.GetTypeInfo();
assert( typeInfo );
std::stringstream stream;
stream << "void SetSelf( " << pszCPPClassName << "@ )";
std::string szFunction = stream.str();
bool bSuccess = false;
//Initialize the self member.
if( auto pFunction = typeInfo->GetMethodByDecl( szFunction.c_str() ) )
{
CASOwningContext ctx( *pFunction->GetEngine() );
CASMethod method( *pFunction, ctx, *obj );
assert( method.IsValid() );
if( method.Call( CallFlag::NONE, pThis ) )
{
bSuccess = true;
}
}
//If the user has provided a baseclass type, initialize the BaseClass member.
if( bSuccess && pszCPPBaseClassName )
{
bSuccess = false;
stream.str( "" );
stream << "void SetBaseClass( " << pszCPPBaseClassName << "@ )";
szFunction = stream.str();
if( auto pFunction = typeInfo->GetMethodByDecl( szFunction.c_str() ) )
{
CASOwningContext ctx( *pFunction->GetEngine() );
CASMethod method( *pFunction, ctx, *obj );
assert( method.IsValid() );
if( method.Call( CallFlag::NONE, pThis ) )
{
bSuccess = true;
}
}
}
return bSuccess;
}
}