27 #include "kjs/object.h"
28 #include "kjs/JSVariableObject.h"
29 #include "kjs/context.h"
30 #include "kjs/interpreter.h"
36 class KJSCustomProperty
41 : getter(g), setter(s)
45 JSValue* read(ExecState* exec,
void*
object);
46 void write(ExecState* exec,
void*
object, JSValue* value);
53 class CustomObjectInfo {
55 CustomObjectInfo(
void* v): iv(v) {}
56 virtual ~CustomObjectInfo() {}
57 void* internalValue() {
return iv; }
63 class CustomObject :
public Base,
public CustomObjectInfo {
65 CustomObject(JSValue* proto,
void* v)
71 void put(ExecState* exec,
const Identifier&
id,
72 JSValue *value,
int attr = None);
76 static const ClassInfo info;
77 const ClassInfo* classInfo()
const {
return &info; }
81 const ClassInfo CustomObject<JSObject>::info = {
"CustomObject", 0, 0, 0 };
84 const ClassInfo CustomObject<JSGlobalObject>::info = {
"CustomGlobalObject", 0, 0, 0 };
86 class KJSCustomFunction :
public JSObject {
91 setPrototype(exec->lexicalInterpreter()->builtinObjectPrototype());
94 JSValue* callAsFunction(ExecState* exec, JSObject* thisObj,
96 bool implementsCall()
const {
return true; }
102 JSValue* KJSCustomFunction::callAsFunction(ExecState* exec, JSObject* thisObj,
106 CustomObjectInfo* inf =
dynamic_cast<CustomObjectInfo*
>(thisObj);
109 const char* errMsg =
"Attempt at calling a function with an invalid receiver";
110 KJS::JSObject *err = KJS::Error::create(exec, KJS::TypeError, errMsg);
111 exec->setException(err);
115 void* thisValue = inf->internalValue();
119 KJSObject res = (*callback)(&ctx, thisValue, a);
123 JSValue* KJSCustomProperty::read(ExecState* exec,
void*
object)
132 void KJSCustomProperty::write(ExecState* exec,
void*
object, JSValue* value)
138 (*setter)(&ctx, object, vo);
140 JSObject *e = Error::create(exec, GeneralError,
141 "Property is read-only");
142 exec->setException(e);
147 const Identifier&,
const PropertySlot& sl)
149 CustomObjectInfo* inf =
dynamic_cast<CustomObjectInfo*
>(originalObject);
151 return jsUndefined();
153 KJSCustomProperty* p =
154 reinterpret_cast<KJSCustomProperty*
>(sl.customValue());
156 return p->read(exec, inf->internalValue());
163 class CustomPrototype :
public JSObject {
170 qDeleteAll(properties);
173 using KJS::JSObject::getOwnPropertySlot;
174 bool getOwnPropertySlot(ExecState *exec,
const Identifier&
id,
177 CustomPropertyMap::iterator it = properties.find(
id.ustring());
178 if (it == properties.end())
179 return JSObject::getOwnPropertySlot(exec,
id, sl);
186 void registerProperty(
const QString& name,
190 properties.insert(
toUString(name),
new KJSCustomProperty(g, s));
193 void registerFunction(ExecState* exec,
196 putDirect(
toIdentifier(name),
new KJSCustomFunction(exec, f));
199 template<
typename Base>
200 bool setProperty(ExecState* exec, CustomObject<Base>* obj,
201 const Identifier&
id, JSValue* value)
203 CustomPropertyMap::iterator it = properties.find(
id.ustring());
204 if (it == properties.end())
207 (*it)->write(exec, obj->internalValue(), value);
217 void CustomObject<Base>::put(ExecState* exec,
const Identifier&
id,
218 JSValue* value,
int attr)
220 CustomPrototype* p =
static_cast<CustomPrototype*
>(this->prototype());
222 if (!p->setProperty(exec,
this,
id, value))
223 Base::put(exec,
id, value, attr);
228 CustomPrototype* p =
new CustomPrototype;
244 DontEnum|DontDelete|ReadOnly);
252 DontEnum|DontDelete|ReadOnly);
260 DontEnum|DontDelete|ReadOnly);
267 if (ctx && !p->prototype()) {
269 KJS::Interpreter* i = exec->lexicalInterpreter();
270 JSObject* objectProto = i->builtinObjectPrototype();
271 p->setPrototype(objectProto);
274 CustomObject<JSObject>* newObj =
new CustomObject<JSObject>(p, internalValue);
282 CustomObject<JSGlobalObject>* newObj =
new CustomObject<JSGlobalObject>(p, internalValue);
288 PropertyGetter getter,
289 PropertySetter setter)
296 p->registerProperty(name, getter, setter);
300 const QString& name, FunctionCall callback)
307 p->registerFunction(exec, name, callback);
KJSObject(* PropertyGetter)(KJSContext *context, void *object)
Function signature for a property getter function.
void defineProperty(KJSContext *ctx, const QString &name, PropertyGetter getter, PropertySetter setter=0)
Defines a property of this prototype with C++ callback functions for getting and setting the property...
KJSGlobalObject constructGlobalObject(void *internalValue=0)
Similar to constructObject() but specialized on the construction of global objects.
~KJSPrototype()
Destructs this prototype object.
static KJS::UString toUString(const QString &s)
A class representing a global object of an execution environment.
void(* PropertySetter)(KJSContext *context, void *object, KJSObject value)
Function signature for a property setter function.
A class representing a JavaScript execution context.
void defineFunction(KJSContext *ctx, const QString &name, FunctionCall callback)
Define a function.
#define EXECSTATE_HANDLE(c)
A class representing a list of JavaScript arguments.
void defineConstant(const QString &name, double value)
Add a read-only numerical property to this object.
static KJS::Identifier toIdentifier(const QString &s)
A class representing a JavaScript value.
KJSPrototype()
Constructs a prototype object with its own prototype property set to the Object prototype.
QMap< UString, KJSCustomProperty * > CustomPropertyMap
static JSValue * getPropertyValue(ExecState *exec, JSObject *originalObject, const Identifier &, const PropertySlot &sl)
#define PROTOTYPE_HANDLE(p)
#define JSVALUE_HANDLE(v)
KJSObject(* FunctionCall)(KJSContext *context, void *object, const KJSArguments &arguments)
Signature for function call callback function.
KJSObject constructObject(KJSContext *ctx, void *internalValue=0)
Construct an object with this prototype and the specified internal value.