--- /dev/null
+elgg.ElggPriorityList = function() {
+ this.length = 0;
+ this.priorities_ = [];
+};
+
+elgg.ElggPriorityList.prototype.insert = function(obj, opt_priority) {
+ if (opt_priority == undefined) {
+ opt_priority = 500;
+ }
+
+ opt_priority = parseInt(opt_priority);
+ if (opt_priority < 0) {
+ opt_priority = 0;
+ }
+
+ if (this.priorities_[opt_priority] == undefined) {
+ this.priorities_[opt_priority] = [];
+ }
+
+ this.priorities_[opt_priority].push(obj);
+ this.length++;
+};
+
+elgg.ElggPriorityList.prototype.forEach = function(callback) {
+ elgg.assertTypeOf('function', callback);
+
+ var index = 0;
+ for (var p in this.priorities_) {
+ var elems = this.priorities_[p];
+ for (var i in elems) {
+ callback(elems[i], index);
+ index++;
+ }
+ }
+};
+
+elgg.ElggPriorityList.prototype.every = function(callback) {
+ elgg.assertTypeOf('function', callback);
+
+ var index = 0;
+ for (var p in this.priorities_) {
+ var elems = this.priorities_[p];
+ for (var i in elems) {
+ if (!callback(elems[i], index)) {
+ return false;
+ };
+ }
+ }
+
+ return true;
+};
+
+elgg.ElggPriorityList.prototype.remove = function(obj) {
+ this.priorities_.forEach(function(elems, priority) {
+ var index;
+ while ((index = elems.indexOf(obj)) != -1) {
+ elems.splice(index, 1);
+ }
+ });
+};
\ No newline at end of file
*/\r
var elgg = elgg || {};\r
\r
-elgg.init = function() {\r
- //if the user clicks a system message, make it disappear\r
- $('.elgg_system_message').live('click', function() {\r
- $(this).stop().fadeOut('fast');\r
- });\r
+elgg.assertTypeOf = function(type, param) {\r
+ if (typeof param !== type) {\r
+ throw new TypeError("Expecting param to be a " + type + ". Was a " + typeof param + ".");\r
+ }\r
};\r
\r
/**\r
*/\r
elgg.forward = function(url) {\r
location.href = elgg.extendUrl(url);\r
-};\r
-\r
-/**\r
- * Initialise Elgg\r
- * @todo How should plugins, etc. initialize themselves?\r
- */\r
-$(function() {\r
- elgg.init();\r
-});\r
+};
\ No newline at end of file
--- /dev/null
+elgg.provide('elgg.config.events');
+elgg.provide('elgg.config.events.all');
+elgg.provide('elgg.config.events.all.all');
+
+elgg.register_event_handler = function(event, type, callback, priority) {
+ elgg.assertTypeOf('string', event);
+ elgg.assertTypeOf('string', event);
+ elgg.assertTypeOf('function', callback);
+
+ if (!event || !type) {
+ return false;
+ }
+
+ elgg.provide('elgg.config.events.' + event + '.' + type);
+
+ var events = elgg.config.events;
+
+ if (!(events[event][type] instanceof elgg.ElggPriorityList)) {
+ events[event][type] = new elgg.ElggPriorityList();
+ }
+
+ return events[event][type].insert(callback, priority);
+};
+
+elgg.trigger_event = function(event, type, object) {
+ elgg.assertTypeOf('string', event);
+ elgg.assertTypeOf('string', event);
+
+ elgg.provide('elgg.config.events.' + event + '.' + type);
+ elgg.provide('elgg.config.events.all.' + type);
+ elgg.provide('elgg.config.events.' + event + '.all');
+ elgg.provide('elgg.config.events.all.all');
+
+ var events = elgg.config.events;
+
+ var callEventHandler = function(handler) {
+ return handler(event, type, object) !== false;
+ };
+
+ if (events[event][type] instanceof elgg.ElggPriorityList) {
+ if (!events[event][type].every(callEventHandler)) {
+ return false;
+ }
+ }
+
+ if (events['all'][type] instanceof elgg.ElggPriorityList) {
+ if (!events['all'][type].every(callEventHandler)) {
+ return false;
+ }
+ }
+
+ if (events[event]['all'] instanceof elgg.ElggPriorityList) {
+ if (!events[event]['all'].every(callEventHandler)) {
+ return false;
+ }
+ }
+
+ if (events['all']['all'] instanceof elgg.ElggPriorityList) {
+ if (!events['all']['all'].every(callEventHandler)) {
+ return false;
+ }
+ }
+
+ return true;
+};
\ No newline at end of file
\r
elgg.config.language = 'en';\r
\r
-elgg.config.translations.init = function() {\r
- elgg.reload_all_translations();\r
-};\r
-\r
elgg.add_translation = function(lang, translations) {\r
elgg.provide('elgg.config.translations.' + lang);\r
\r
});\r
};\r
\r
-/**\r
- * @deprecated Use elgg.reload_all_translations\r
- */\r
-elgg.config.translations.load = elgg.reload_all_translations;\r
-\r
/**\r
* Get the current language\r
* @return {String}\r
return undefined;\r
};\r
\r
-$(function() {\r
- elgg.config.translations.init();\r
-});
\ No newline at end of file
+elgg.config.translations.init = function() {\r
+ elgg.reload_all_translations();\r
+};\r
+\r
+elgg.register_event_handler('boot', 'system', elgg.config.translations.init);
\ No newline at end of file
\r
elgg.security.token = {};\r
\r
-elgg.security.init = function() {\r
- //refresh security token every 5 minutes\r
- setInterval(elgg.security.refreshToken, elgg.security.interval);\r
-};\r
-\r
elgg.security.setToken = function(json) {\r
//update the convenience object\r
elgg.security.token = json;\r
throw new TypeError("elgg.security.addToken not implemented for " + (typeof data) + "s");\r
};\r
\r
-$(function() {\r
- elgg.security.init();\r
-});
\ No newline at end of file
+elgg.security.init = function() {\r
+ //refresh security token every 5 minutes\r
+ setInterval(elgg.security.refreshToken, elgg.security.interval);\r
+};\r
+\r
+elgg.register_event_handler('boot', 'system', elgg.security.init);
\ No newline at end of file
elgg.provide('elgg.ui');\r
\r
elgg.ui.init = function () {\r
+ //if the user clicks a system message, make it disappear\r
+ $('.elgg_system_message').live('click', function() {\r
+ $(this).stop().fadeOut('fast');\r
+ });\r
+ \r
$('a.collapsibleboxlink').click(elgg.ui.toggleCollapsibleBox);\r
\r
// set-up hover class for dragged widgets\r
};\r
})(jQuery);\r
\r
-$(function() {\r
- elgg.ui.init();\r
-});
\ No newline at end of file
+elgg.register_event_handler('init', 'system', elgg.ui.init);
\ No newline at end of file
widget_state = elgg.ui.widgets.state,\r
outputWidgetList = elgg.ui.widgets.outputList;\r
\r
-$(function() {\r
- elgg.ui.widgets.init();\r
-});\r
+elgg.register_event_handler('init', 'system', elgg.ui.widgets.init);
\ No newline at end of file
--- /dev/null
+ElggEventsTest = TestCase("ElggEventsTest");
+
+ElggEventsTest.prototype.setUp = function() {
+ elgg.config.events = {};
+ elgg.provide('elgg.config.events.all.all');
+};
+
+ElggEventsTest.prototype.testEventHandlersMustBeFunctions = function() {
+ assertException(function() { elgg.register_event_handler('str', 'str', 'oops'); });
+};
+
+ElggEventsTest.prototype.testReturnValueDefaultsToTrue = function() {
+ assertTrue(elgg.trigger_event('fee', 'fum'));
+
+ elgg.register_event_handler('fee', 'fum', function() {});
+ assertTrue(elgg.trigger_event('fee', 'fum'));
+};
+
+ElggEventsTest.prototype.testCanGlomEventsWithAll = function() {
+ elgg.register_event_handler('all', 'bar', function() { throw new Error(); });
+ assertException("all,bar", function() { elgg.trigger_event('foo', 'bar'); });
+
+ elgg.register_event_handler('foo', 'all', function() { throw new Error(); });
+ assertException("foo,all", function() { elgg.trigger_event('foo', 'baz'); });
+
+ elgg.register_event_handler('all', 'all', function() { throw new Error(); });
+ assertException("all,all", function() { elgg.trigger_event('pinky', 'winky'); });
+};
\ No newline at end of file
assertTrue(window === elgg.global);\r
};\r
\r
+ElggLibTest.prototype.testAssertTypeOf = function() {\r
+ var noexceptions = [\r
+ ['string', ''],\r
+ ['object', {}],\r
+ ['boolean', true], \r
+ ['boolean', false], \r
+ ['undefined', undefined], \r
+ ['number', 0], \r
+ ['function', function() {}],\r
+ ];\r
+ \r
+ for (var i in noexceptions) {\r
+ assertNoException(function() { \r
+ elgg.assertTypeOf.apply(elgg, noexceptions[i]); \r
+ });\r
+ }\r
+ \r
+ var exceptions = [\r
+ ['function', {}],\r
+ ['object', function() {}],\r
+ ];\r
+ \r
+ for (var i in exceptions) {\r
+ assertException(function() {\r
+ elgg.assertTypeOf.apply(elgg, exceptions[i]);\r
+ });\r
+ }\r
+};\r
+\r
ElggLibTest.prototype.testProvide = function() {\r
elgg.provide('foo.bar.baz');\r
\r
\r
elgg.inherit(Child, Base);\r
\r
- \r
assertInstanceOf(Base, new Child());\r
assertEquals(Child, Child.prototype.constructor);\r
};\r
\r
url = 'pg/test';\r
assertEquals('http://www.elgg.org/pg/test', elgg.extendUrl(url));\r
-};\r
-\r
-\r
-\r
-\r
-\r
-\r
-\r
+};
\ No newline at end of file
--- /dev/null
+ElggPriorityListTest = TestCase("ElggPriorityListTest");
+
+ElggPriorityListTest.prototype.setUp = function() {
+ this.list = new elgg.ElggPriorityList();
+};
+
+ElggPriorityListTest.prototype.tearDown = function() {
+ this.list = null;
+};
+
+ElggPriorityListTest.prototype.testInsert = function() {
+ this.list.insert('foo');
+
+ assertEquals('foo', this.list.priorities_[500][0]);
+
+ this.list.insert('bar', 501);
+
+ assertEquals('foo', this.list.priorities_[501][0]);
+};
+
+ElggPriorityListTest.prototype.testInsertRespectsPriority = function() {
+ var values = [5, 4, 3, 2, 1, 0];
+
+ for (var i in values) {
+ this.list.insert(values[i], values[i]);
+ }
+
+ this.list.forEach(function(elem, idx)) {
+ assertEquals(elem, idx);
+ }
+};
+
+ElggPriorityListTest.prototype.testInsertHandlesDuplicatePriorities = function() {
+ values = [0, 1, 2, 3, 4, 5, 6, 7, 8 , 9];
+
+ for (var i in values) {
+ this.list.insert(values[i], values[i]/3);
+ }
+
+ this.list.forEach(function(elem, idx) {
+ assertEquals(elem, idx);
+ });
+};
+
+ElggPriorityListTest.prototype.testEveryDefaultsToTrue = function() {
+ assertTrue(this.list.every(function() {}));
+};
\ No newline at end of file
*/
global $CONFIG;
-//Include library files
-$lib_files = array(
- //core
- 'elgglib',
+include("{$CONFIG->path}engine/js/lib/elgglib.js");
+//No such thing as autoloading classes in javascript
+$model_files = array(
+ 'ElggEntity',
+ 'ElggUser',
+ 'ElggPriorityList',
+);
+
+foreach($model_files as $file) {
+ include("{$CONFIG->path}engine/js/classes/$file.js");
+}
+
+//Include library files
+$libs = array(
//libraries
+ 'events',
'security',
'languages',
'ajax',
'ui.widgets',
);
-foreach($lib_files as $file) {
+foreach($libs as $file) {
include("{$CONFIG->path}engine/js/lib/$file.js");
}
-//Include classes
-$model_files = array(
- 'ElggEntity',
-
- 'ElggUser',
-);
-
-foreach($model_files as $file) {
- include("{$CONFIG->path}engine/js/classes/$file.js");
-}
-
/**
- * Finally, set some values that are cacheable
+ * Set some values that are cacheable
*/
?>
elgg.config.wwwroot = '<?php echo elgg_get_site_url(); ?>';
elgg.security.interval = 5 * 60 * 1000; <?php //TODO make this configurable ?>
+//Mimic PHP engine boot process
+
+//Before the DOM is ready -- note that plugins aren't loaded yet
+elgg.trigger_event('boot', 'system');
+
+//After the DOM is ready
+$(function() {
+ elgg.trigger_event('init', 'system');
+});
+
$(document).ready(function () {
// COLLAPSABLE WIDGETS (on Dashboard? & Profile pages)