summaryrefslogtreecommitdiff
path: root/javascript
diff options
context:
space:
mode:
authorVincent Sanders <vince@netsurf-browser.org>2012-10-26 12:36:14 +0100
committerVincent Sanders <vince@netsurf-browser.org>2012-10-26 12:36:14 +0100
commit99c54f1d9d198fc6ea9477ff58aafb76e5c1f20a (patch)
tree90b76990e079f19ad7e2a04f1236827b16979f46 /javascript
parent3ed0b09beb55dfd1247c57a87a13b96d3324f64b (diff)
downloadnetsurf-99c54f1d9d198fc6ea9477ff58aafb76e5c1f20a.tar.gz
netsurf-99c54f1d9d198fc6ea9477ff58aafb76e5c1f20a.tar.bz2
split class prototype initialisation from instantiation
Diffstat (limited to 'javascript')
-rw-r--r--javascript/jsapi.c53
-rw-r--r--javascript/jsapi.h44
-rw-r--r--javascript/jsapi/binding.h82
-rw-r--r--javascript/jsapi/console.c2
-rw-r--r--javascript/jsapi/window.c297
5 files changed, 238 insertions, 240 deletions
diff --git a/javascript/jsapi.c b/javascript/jsapi.c
index f7ac3eda1..4e980b5fd 100644
--- a/javascript/jsapi.c
+++ b/javascript/jsapi.c
@@ -17,6 +17,7 @@
*/
#include "javascript/jsapi.h"
+#include "javascript/jsapi/binding.h"
#include "content/content.h"
#include "javascript/content.h"
@@ -90,46 +91,32 @@ void js_destroycontext(jscontext *ctx)
}
-
+/** Create new compartment to run scripts within
+ *
+ * This performs the following actions
+ * 1. constructs a new global object by initialising a window class
+ * 2. Instantiate the global a window object
+ */
jsobject *js_newcompartment(jscontext *ctx, void *win_priv, void *doc_priv)
{
JSContext *cx = (JSContext *)ctx;
- JSObject *window_obj = NULL;
- JSObject *document_obj;
- JSObject *navigator_obj;
- JSObject *console_obj;
- struct html_content *htmlc = doc_priv;
-
- if (cx == NULL)
- goto js_newcompartment_fail;
-
- /* create the window object as the global */
- window_obj = jsapi_new_window(cx, NULL, win_priv);
- if (window_obj == NULL)
- goto js_newcompartment_fail;
-
- /* attach the subclasses off the window global */
- document_obj = jsapi_new_Document(cx, window_obj, htmlc->document, htmlc);
- if (document_obj == NULL)
- goto js_newcompartment_fail;
-
- navigator_obj = jsapi_new_navigator(cx, window_obj);
- if (navigator_obj == NULL)
- goto js_newcompartment_fail;
+ JSObject *window_proto;
+ JSObject *window;
- /* @todo forms, history, location */
-
- console_obj = jsapi_new_console(cx, window_obj);
- if (console_obj == NULL)
- goto js_newcompartment_fail;
-
- return (jsobject *)window_obj;
+ if (cx == NULL) {
+ return NULL;
+ }
-js_newcompartment_fail:
+ window_proto = jsapi_InitClass_Window(cx, NULL);
+ if (window_proto == NULL) {
+ LOG(("Unable to initialise window class"));
+ return NULL;
+ }
- LOG(("New compartment creation failed"));
+ window = jsapi_new_Window(cx, window_proto, NULL, win_priv, doc_priv);
+
+ return (jsobject *)window;
- return NULL;
}
bool js_exec(jscontext *ctx, const char *txt, size_t txtlen)
diff --git a/javascript/jsapi.h b/javascript/jsapi.h
index 91d9184b4..93c0effdd 100644
--- a/javascript/jsapi.h
+++ b/javascript/jsapi.h
@@ -17,7 +17,7 @@
*/
/** \file
- * spidermonkey jsapi bindings and compatability glue.
+ * spidermonkey jsapi compatability glue.
*/
#ifndef _NETSURF_JAVASCRIPT_JSAPI_H_
@@ -149,47 +149,5 @@ JS_NewCompartmentAndGlobalObject(JSContext *cx,
#endif
-/** Create a new javascript window object
- *
- * @param cx The javascript context.
- * @param parent The parent object or NULL for new global
- * @param win_priv The private context to set on the object
- * @return new javascript object or NULL on error
- */
-JSObject *jsapi_new_window(JSContext *cx, JSObject *parent, void *win_priv);
-
-/** Create a new javascript document object
- *
- * @param cx The javascript context.
- * @param parent The parent object, usually a global window object
- * @param doc_priv The private context to set on the object
- * @return new javascript object or NULL on error
- */
-JSObject *jsapi_new_Document(JSContext *cx, JSObject *parent, dom_document *node, struct html_content *htmlc);
-
-/** Create a new javascript console object
- *
- * @param cx The javascript context.
- * @param parent The parent object, usually a global window object
- * @return new javascript object or NULL on error
- */
-JSObject *jsapi_new_console(JSContext *cx, JSObject *parent);
-
-/** Create a new javascript navigator object
- *
- * @param cx The javascript context.
- * @param parent The parent object, usually a global window object
- * @return new javascript object or NULL on error
- */
-JSObject *jsapi_new_navigator(JSContext *cx, JSObject *parent);
-
-/** Create a new javascript element object
- *
- * @param cx The javascript context.
- * @param parent The parent object, usually a global window object
- * @param doc_priv The private context to set on the object
- * @return new javascript object or NULL on error
- */
-JSObject *jsapi_new_element(JSContext *cx, JSObject *parent, struct html_content *htmlc, struct dom_element *domelement);
#endif
diff --git a/javascript/jsapi/binding.h b/javascript/jsapi/binding.h
new file mode 100644
index 000000000..b565136af
--- /dev/null
+++ b/javascript/jsapi/binding.h
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2012 Vincent Sanders <vince@netsurf-browser.org>
+ *
+ * This file is part of NetSurf, http://www.netsurf-browser.org/
+ *
+ * NetSurf is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; version 2 of the License.
+ *
+ * NetSurf is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+/** \file
+ * spidermonkey jsapi class bindings
+ */
+
+#ifndef _NETSURF_JAVASCRIPT_JSAPI_BINDING_H_
+#define _NETSURF_JAVASCRIPT_JSAPI_BINDING_H_
+
+JSObject *jsapi_InitClass_Window(JSContext *cx, JSObject *parent);
+
+/** Create a new javascript window object
+ *
+ * @param cx The javascript context.
+ * @param parent The parent object or NULL for new global
+ * @param win_priv The private context to set on the object
+ * @return new javascript object or NULL on error
+ */
+JSObject *jsapi_new_Window(JSContext *cx,
+ JSObject *window,
+ JSObject *parent,
+ struct browser_window *bw,
+ html_content *htmlc);
+
+
+JSObject *jsapi_InitClass_Document(JSContext *cx, JSObject *parent);
+
+/** Create a new javascript document object
+ *
+ * @param cx The javascript context.
+ * @param parent The parent object, usually a global window object
+ * @param doc_priv The private context to set on the object
+ * @return new javascript object or NULL on error
+ */
+JSObject *jsapi_new_Document(JSContext *cx,
+ JSObject *proto,
+ JSObject *parent,
+ dom_document *node,
+ struct html_content *htmlc);
+
+/** Create a new javascript console object
+ *
+ * @param cx The javascript context.
+ * @param parent The parent object, usually a global window object
+ * @return new javascript object or NULL on error
+ */
+JSObject *jsapi_new_Console(JSContext *cx, JSObject *parent);
+
+/** Create a new javascript navigator object
+ *
+ * @param cx The javascript context.
+ * @param parent The parent object, usually a global window object
+ * @return new javascript object or NULL on error
+ */
+JSObject *jsapi_new_Navigator(JSContext *cx, JSObject *parent);
+
+/** Create a new javascript element object
+ *
+ * @param cx The javascript context.
+ * @param parent The parent object, usually a global window object
+ * @param doc_priv The private context to set on the object
+ * @return new javascript object or NULL on error
+ */
+JSObject *jsapi_new_element(JSContext *cx, JSObject *parent, struct html_content *htmlc, struct dom_element *domelement);
+
+#endif
diff --git a/javascript/jsapi/console.c b/javascript/jsapi/console.c
index 6a6d7d3c3..3cd51883d 100644
--- a/javascript/jsapi/console.c
+++ b/javascript/jsapi/console.c
@@ -137,7 +137,7 @@ static JSClass jsclass_console =
};
-JSObject *jsapi_new_console(JSContext *cx, JSObject *parent)
+JSObject *jsapi_new_Console(JSContext *cx, JSObject *parent)
{
return JS_InitClass(cx,
parent,
diff --git a/javascript/jsapi/window.c b/javascript/jsapi/window.c
index 72d3837d9..476a38324 100644
--- a/javascript/jsapi/window.c
+++ b/javascript/jsapi/window.c
@@ -19,131 +19,33 @@
#include "utils/log.h"
#include "javascript/jsapi.h"
+#include "javascript/jsapi/binding.h"
-/* IDL
-
-[NamedPropertiesObject]
-interface Window : EventTarget {
- // the current browsing context
- [Unforgeable] readonly attribute WindowProxy window;
- [Replaceable] readonly attribute WindowProxy self;
- [Unforgeable] readonly attribute Document document;
- attribute DOMString name;
- [PutForwards=href, Unforgeable] readonly attribute Location location;
- readonly attribute History history;
-
- boolean find(optional DOMString aString, optional boolean aCaseSensitive, optional boolean aBackwards, optional boolean aWrapAround, optional boolean aWholeWord, optional boolean aSearchInFrames, optional boolean aShowDialog);
-
- [Replaceable] readonly attribute BarProp locationbar;
- [Replaceable] readonly attribute BarProp menubar;
- [Replaceable] readonly attribute BarProp personalbar;
- [Replaceable] readonly attribute BarProp scrollbars;
- [Replaceable] readonly attribute BarProp statusbar;
- [Replaceable] readonly attribute BarProp toolbar;
- attribute DOMString status;
- void close();
- void stop();
- void focus();
- void blur();
-
- // other browsing contexts
- [Replaceable] readonly attribute WindowProxy frames;
- [Replaceable] readonly attribute unsigned long length;
- [Unforgeable] readonly attribute WindowProxy top;
- attribute WindowProxy? opener;
- readonly attribute WindowProxy parent;
- readonly attribute Element? frameElement;
- WindowProxy open(optional DOMString url, optional DOMString target, optional DOMString features, optional boolean replace);
- getter WindowProxy (unsigned long index);
- getter object (DOMString name);
-
- // the user agent
- readonly attribute Navigator navigator;
- readonly attribute External external;
- readonly attribute ApplicationCache applicationCache;
-
- // user prompts
- void alert(DOMString message);
- boolean confirm(DOMString message);
- DOMString? prompt(DOMString message, optional DOMString default);
- void print();
- any showModalDialog(DOMString url, optional any argument);
-
- // cross-document messaging
- void postMessage(any message, DOMString targetOrigin, optional sequence<Transferable> transfer);
-
- // event handler IDL attributes
- [TreatNonCallableAsNull] attribute Function? onabort;
- [TreatNonCallableAsNull] attribute Function? onafterprint;
- [TreatNonCallableAsNull] attribute Function? onbeforeprint;
- [TreatNonCallableAsNull] attribute Function? onbeforeunload;
- [TreatNonCallableAsNull] attribute Function? onblur;
- [TreatNonCallableAsNull] attribute Function? oncancel;
- [TreatNonCallableAsNull] attribute Function? oncanplay;
- [TreatNonCallableAsNull] attribute Function? oncanplaythrough;
- [TreatNonCallableAsNull] attribute Function? onchange;
- [TreatNonCallableAsNull] attribute Function? onclick;
- [TreatNonCallableAsNull] attribute Function? onclose;
- [TreatNonCallableAsNull] attribute Function? oncontextmenu;
- [TreatNonCallableAsNull] attribute Function? oncuechange;
- [TreatNonCallableAsNull] attribute Function? ondblclick;
- [TreatNonCallableAsNull] attribute Function? ondrag;
- [TreatNonCallableAsNull] attribute Function? ondragend;
- [TreatNonCallableAsNull] attribute Function? ondragenter;
- [TreatNonCallableAsNull] attribute Function? ondragleave;
- [TreatNonCallableAsNull] attribute Function? ondragover;
- [TreatNonCallableAsNull] attribute Function? ondragstart;
- [TreatNonCallableAsNull] attribute Function? ondrop;
- [TreatNonCallableAsNull] attribute Function? ondurationchange;
- [TreatNonCallableAsNull] attribute Function? onemptied;
- [TreatNonCallableAsNull] attribute Function? onended;
- [TreatNonCallableAsNull] attribute Function? onerror;
- [TreatNonCallableAsNull] attribute Function? onfocus;
- [TreatNonCallableAsNull] attribute Function? onhashchange;
- [TreatNonCallableAsNull] attribute Function? oninput;
- [TreatNonCallableAsNull] attribute Function? oninvalid;
- [TreatNonCallableAsNull] attribute Function? onkeydown;
- [TreatNonCallableAsNull] attribute Function? onkeypress;
- [TreatNonCallableAsNull] attribute Function? onkeyup;
- [TreatNonCallableAsNull] attribute Function? onload;
- [TreatNonCallableAsNull] attribute Function? onloadeddata;
- [TreatNonCallableAsNull] attribute Function? onloadedmetadata;
- [TreatNonCallableAsNull] attribute Function? onloadstart;
- [TreatNonCallableAsNull] attribute Function? onmessage;
- [TreatNonCallableAsNull] attribute Function? onmousedown;
- [TreatNonCallableAsNull] attribute Function? onmousemove;
- [TreatNonCallableAsNull] attribute Function? onmouseout;
- [TreatNonCallableAsNull] attribute Function? onmouseover;
- [TreatNonCallableAsNull] attribute Function? onmouseup;
- [TreatNonCallableAsNull] attribute Function? onmousewheel;
- [TreatNonCallableAsNull] attribute Function? onoffline;
- [TreatNonCallableAsNull] attribute Function? ononline;
- [TreatNonCallableAsNull] attribute Function? onpause;
- [TreatNonCallableAsNull] attribute Function? onplay;
- [TreatNonCallableAsNull] attribute Function? onplaying;
- [TreatNonCallableAsNull] attribute Function? onpagehide;
- [TreatNonCallableAsNull] attribute Function? onpageshow;
- [TreatNonCallableAsNull] attribute Function? onpopstate;
- [TreatNonCallableAsNull] attribute Function? onprogress;
- [TreatNonCallableAsNull] attribute Function? onratechange;
- [TreatNonCallableAsNull] attribute Function? onreset;
- [TreatNonCallableAsNull] attribute Function? onresize;
- [TreatNonCallableAsNull] attribute Function? onscroll;
- [TreatNonCallableAsNull] attribute Function? onseeked;
- [TreatNonCallableAsNull] attribute Function? onseeking;
- [TreatNonCallableAsNull] attribute Function? onselect;
- [TreatNonCallableAsNull] attribute Function? onshow;
- [TreatNonCallableAsNull] attribute Function? onstalled;
- [TreatNonCallableAsNull] attribute Function? onstorage;
- [TreatNonCallableAsNull] attribute Function? onsubmit;
- [TreatNonCallableAsNull] attribute Function? onsuspend;
- [TreatNonCallableAsNull] attribute Function? ontimeupdate;
- [TreatNonCallableAsNull] attribute Function? onunload;
- [TreatNonCallableAsNull] attribute Function? onvolumechange;
- [TreatNonCallableAsNull] attribute Function? onwaiting;
+
+struct jsclass_private {
+ struct browser_window *bw;
+ struct html_content *htmlc;
+ JSObject *document_obj;
+ JSObject *navigator_obj;
+ JSObject *console_obj;
};
-*/
+static void jsclass_finalize(JSContext *cx, JSObject *obj);
+static JSBool jsclass_resolve(JSContext *cx, JSObject *obj, jsval id, uintN flags, JSObject **objp);
+
+JSClass JSClass_Window = {
+ "Window",
+ JSCLASS_NEW_RESOLVE | JSCLASS_HAS_PRIVATE | JSCLASS_GLOBAL_FLAGS,
+ JS_PropertyStub,
+ JS_PropertyStub,
+ JS_PropertyStub,
+ JS_StrictPropertyStub,
+ JS_EnumerateStub,
+ (JSResolveOp)jsclass_resolve,
+ JS_ConvertStub,
+ jsclass_finalize,
+ JSCLASS_NO_OPTIONAL_MEMBERS
+};
static JSBool JSAPI_NATIVE(alert, JSContext *cx, uintN argc, jsval *vp)
@@ -254,62 +156,130 @@ static JSBool JSAPI_PROPERTYGET(self, JSContext *cx, JSObject *obj, jsval *vp)
return JS_TRUE;
}
+static JSBool JSAPI_PROPERTYGET(document, JSContext *cx, JSObject *obj, jsval *vp)
+{
+ struct jsclass_private *private;
+
+ private = JS_GetInstancePrivate(cx,
+ obj,
+ &JSClass_Window,
+ NULL);
+ if (private == NULL)
+ return JS_FALSE;
+
+ JS_SET_RVAL(cx, vp, OBJECT_TO_JSVAL(private->document_obj));
+ return JS_TRUE;
+}
+
static JSPropertySpec jsproperties_window[] =
{
+ JSAPI_PS_RO(document, 0, JSPROP_ENUMERATE | JSPROP_SHARED),
JSAPI_PS_RO(window, 0, JSPROP_ENUMERATE | JSPROP_SHARED),
JSAPI_PS_RO(self, 0, JSPROP_ENUMERATE | JSPROP_SHARED),
JSAPI_PS_END
};
-/* The class of the global object. */
-static JSClass jsclass_window = {
- "window",
- JSCLASS_HAS_PRIVATE | JSCLASS_GLOBAL_FLAGS,
- JS_PropertyStub,
- JS_PropertyStub,
- JS_PropertyStub,
- JS_StrictPropertyStub,
- JS_EnumerateStub,
- JS_ResolveStub,
- JS_ConvertStub,
- JS_FinalizeStub,
- JSCLASS_NO_OPTIONAL_MEMBERS
-};
+static JSBool jsclass_resolve(JSContext *cx, JSObject *obj, jsval id, uintN flags, JSObject **objp)
+{
+ *objp = NULL;
+ return JS_TRUE;
+}
+static void jsclass_finalize(JSContext *cx, JSObject *obj)
+{ struct jsclass_private *private;
-JSObject * jsapi_new_window(JSContext *cx, JSObject *parent, void *win_priv)
+ private = JS_GetInstancePrivate(cx, obj, &JSClass_Window, NULL);
+ if (private != NULL) {
+ free(private);
+ }
+}
+
+JSObject *jsapi_InitClass_Window(JSContext *cx, JSObject *parent)
{
JSObject *window = NULL;
+ JSObject *proto;
+
+ window = JS_NewCompartmentAndGlobalObject(cx, &JSClass_Window, NULL);
+ if (window == NULL) {
+ return NULL;
+ }
+
+ /** @todo reconsider global object handling. future
+ * editions of spidermonkey appear to be removing the
+ * idea of a global so we probably need to handle
+ * global object references internally
+ */
+
+ /* set the contexts global */
+ JS_SetGlobalObject(cx, window);
+
+ /* Populate the global object with the standard globals, like
+ * Object and Array.
+ */
+ if (!JS_InitStandardClasses(cx, window)) {
+ return NULL;
+ }
+
+ /* Initialises all the user javascript classes to make their
+ * prototypes available.
+ */
+ /** @todo should we be managing these prototype objects ourselves */
+ proto = jsapi_InitClass_Document(cx, window);
+ if (proto == NULL) {
+ return NULL;
+ }
+
+ return window;
+}
- if (parent == NULL) {
- window = JS_NewCompartmentAndGlobalObject(cx, &jsclass_window, NULL);
- if (window == NULL) {
- return NULL;
- }
-
- /** @todo reconsider global object handling. future
- * editions of spidermonkey appear to be removing the
- * idea of a global so we probably need to handle
- * global object references internally
- */
-
- /* set the contexts global */
- JS_SetGlobalObject(cx, window);
-
- /* Populate the global object with the standard globals, like
- * Object and Array.
- */
- if (!JS_InitStandardClasses(cx, window)) {
- return NULL;
- }
-
- } else {
- /* @todo sort out windows that are not globals */
- assert(false);
+JSObject *jsapi_new_Window(JSContext *cx,
+ JSObject *window,
+ JSObject *parent,
+ struct browser_window *bw,
+ html_content *htmlc)
+{
+ struct jsclass_private *private;
+
+ /* @todo sort out windows that are not globals */
+ assert(parent == NULL);
+
+ /* create private data */
+ private = malloc(sizeof(struct jsclass_private));
+ if (private == NULL) {
+ return NULL;
+ }
+ private->bw = bw;
+ private->htmlc = htmlc;
+
+
+ /* instantiate the subclasses off the window global */
+ private->document_obj = jsapi_new_Document(cx,
+ NULL,
+ window,
+ htmlc->document,
+ htmlc);
+ if (private->document_obj == NULL) {
+ free(private);
+ return NULL;
+ }
+
+/*
+ private->navigator_obj = jsapi_new_Navigator(cx, window);
+ if (private->navigator_obj == NULL) {
+ free(private);
+ return NULL;
+ }
+*/
+ /** @todo forms, history, location */
+
+ private->console_obj = jsapi_new_Console(cx, window);
+ if (private->console_obj == NULL) {
+ free(private);
+ return NULL;
}
/* private pointer to browsing context */
- if (!JS_SetPrivate(cx, window, win_priv))
+ if (!JS_SetPrivate(cx, window, private))
return NULL;
/* functions */
@@ -321,6 +291,7 @@ JSObject * jsapi_new_window(JSContext *cx, JSObject *parent, void *win_priv)
if (!JS_DefineProperties(cx, window, jsproperties_window))
return NULL;
+
LOG(("Created new window object %p", window));
return window;