diff --git a/src/r3-a-2-event-0.js b/src/r3-a-2-event-0.js
index 442ac47..d8784a2 100644
--- a/src/r3-a-2-event-0.js
+++ b/src/r3-a-2-event-0.js
@@ -10,7 +10,6 @@ R3.Event = function() {
* @type {{}}
*/
R3.Event.Subscriptions = {};
-R3.Event.OnceSubscriptions = {};
/**
* Subscribe to some events
@@ -24,46 +23,6 @@ R3.Event.prototype.subscribe = function(
return R3.Event.Subscribe(eventName, callback.bind(this));
};
-
-// /**
-// * Stop listening for this event after the callback returns true
-// * @param eventName
-// * @param callback
-// * @returns {{fn, remove: remove}}
-// */
-// R3.Event.prototype.subscribeOnce = function(
-// eventName,
-// callback
-// ) {
-// throw new Error('implement first properly');
-// // var fn = callback.bind(this);
-// //
-// // if (R3.Event.OnceSubscriptions.hasOwnProperty(eventName)) {
-// // R3.Event.OnceSubscriptions[eventName].push(fn);
-// // } else {
-// // R3.Event.OnceSubscriptions[eventName] = [];
-// // R3.Event.OnceSubscriptions[eventName].push(fn);
-// // }
-// //
-// // /**
-// // * Return a handle to the caller to allow us to unsubscribe to this event
-// // */
-// // return {
-// // fn : fn,
-// // remove : function() {
-// // R3.Event.Subscriptions[eventName].splice(
-// // R3.Event.Subscriptions[eventName].indexOf(fn),
-// // 1
-// // );
-// // }
-// // }
-// };
-
-/**
- *
- * @param eventName
- * @param data
- */
/**
* Publish some event happened with some data
* @param eventName
@@ -87,8 +46,8 @@ R3.Event.prototype.emit = function(
};
/**
- * Static method call
- * @param eventName
+ * Static Synchrnonous Event - Calls clientCallback directly after the event result is obtained
+ * @param eventId
* @param data
* @param clientCallback is executed ideally when the event completed
* @param clientErrorCallback
@@ -96,111 +55,41 @@ R3.Event.prototype.emit = function(
* @constructor
*/
R3.Event.Emit = function(
- eventName,
+ eventId,
data,
clientCallback,
clientErrorCallback
) {
- var count = 0;
+ if (R3.Event.Subscriptions.hasOwnProperty(eventId)) {
- if (R3.Event.Subscriptions.hasOwnProperty(eventName)) {
+ var subscriptionIds = Object.keys(R3.Event.Subscriptions[eventId]);
- if (R3.Event.Subscriptions[eventName].length === 0) {
-
- if (clientCallback) {
- /**
- * We execute the client callback immediately since there are no subscriptions to this event
- */
- clientCallback();
- }
-
- if (clientErrorCallback) {
- clientErrorCallback({
- message : 'No subscriptions for event ' + eventName
- })
- }
- }
-
- /**
- * We need to execute all the callbacks, but not execute them twice, but also keep in mind they can remove
- * themselves during execution
- */
- // var length = R3.Event.Subscriptions[eventName].length;
- //
- // for (var i = 0; i < length; i++) {
- //
- // var object = R3.Event.Subscriptions[eventName][i];
- //
- // if (object.fn && object.executed === false) {
- // object.fn(data, clientCallback, clientErrorCallback);
- // object.executed = true;
- // }
- //
- // if (length !== R3.Event.Subscriptions[eventName].length) {
- // /**
- // * this callback removed a subscription - reset i and reset the length
- // */
- // i = 0;
- // length = R3.Event.Subscriptions[eventName].length;
- // }
- // }
- //
- // R3.Event.Subscriptions[eventName].map(
- // function(object){
- // object.executed = false;
- // }
- // )
-
- R3.Event.Subscriptions[eventName].map(
- function(subscription) {
- if (subscription) {
-
- try {
- var result = subscription(data, clientCallback, clientErrorCallback);
- } catch (error) {
-
- if (clientErrorCallback) {
- try {
- clientErrorCallback(error);
- } catch (error2) {
- console.error('failed to execute client callback error:', error2);
- }
- }
-
- return;
- }
+ subscriptionIds.map(
+ function(subscriptionId) {
+ try {
+ var result = R3.Event.Subscriptions[eventId][subscriptionId](data);
if (clientCallback) {
clientCallback(result);
}
- count++;
+ } catch (error) {
+ if (clientErrorCallback) {
+ clientErrorCallback(error);
+ } else {
+ console.error(error);
+ }
}
}
)
- } else {
- if (clientCallback) {
- /**
- * We execute the client callback immediately since there are no subscriptions to this event
- */
- clientCallback();
- }
-
- if (clientErrorCallback) {
- clientErrorCallback({
- message : 'No subscriptions for event ' + eventName
- })
- }
}
-
- return count;
};
/**
* Execute the functions which subscribe to this event, but don't process the client callback - the subscription function
* should execute the client callback
- * @param eventName
+ * @param eventId
* @param data
* @param clientCallback
* @param clientErrorCallback
@@ -208,76 +97,78 @@ R3.Event.Emit = function(
* @constructor
*/
R3.Event.Async = function(
- eventName,
+ eventId,
data,
clientCallback,
clientErrorCallback
) {
+ if (R3.Event.Subscriptions.hasOwnProperty(eventId)) {
- var count = 0;
+ var subscriptionIds = Object.keys(R3.Event.Subscriptions[eventId]);
- if (R3.Event.Subscriptions.hasOwnProperty(eventName)) {
- R3.Event.Subscriptions[eventName].map(
- function(subscription) {
- if (subscription) {
- subscription(data, clientCallback, clientErrorCallback);
- count++;
+ subscriptionIds.map(
+ function(subscriptionId) {
+ try {
+ R3.Event.Subscriptions[eventId][subscriptionId](data, clientCallback, clientErrorCallback);
+ } catch (error) {
+ if (clientErrorCallback) {
+ clientErrorCallback(error);
+ } else {
+ console.error(error);
+ }
}
}
)
}
-
- return count;
};
R3.Event.Subscribe = function(
eventName,
- fn
+ fn,
) {
+ /**
+ * Todo - maybe eventually store a boolean which indicates if the function has been executed
+ */
+ var subscriptionId = R3.Utils.RandomId(10);
if (R3.Event.Subscriptions.hasOwnProperty(eventName)) {
- R3.Event.Subscriptions[eventName].push(fn);
- // {
- // fn : fn,
- // executed : false
- // }
- // );
+
+ if (R3.Event.Subscriptions[eventName][subscriptionId]) {
+ throw new Error('A component can only subscribe to a particular event ID once');
+ }
+
+ R3.Event.Subscriptions[eventName][subscriptionId] = fn;
} else {
- R3.Event.Subscriptions[eventName] = [];
- R3.Event.Subscriptions[eventName].push(fn);
- // {
- // fn : fn,
- // executed : false
- // }
- // );
+ R3.Event.Subscriptions[eventName] = {};
+ R3.Event.Subscriptions[eventName][subscriptionId] = fn;
}
/**
* Return a handle to the caller to allow us to unsubscribe to this event
*/
return {
- fn : fn,
- remove : function() {
+ fn: fn,
+ remove: function (eventId, subscriptionId) {
- var index = R3.Event.Subscriptions[eventName].indexOf(fn);
- // reduce(
- // function(result, object, index) {
- // if (object.fn === fn) {
- // result = index;
- // }
- // return result;
- // },
- // -1
- // );
+ return function () {
- if (index === -1) {
- throw new Error('could not remove subscription');
+ /**
+ * Stop listening for this event from this component
+ */
+ delete R3.Event.Subscriptions[eventId][subscriptionId];
+
+ /**
+ * If the length of listeners is 0, stop referencing this event
+ * @type {string[]}
+ */
+ var listeners = Object.keys(R3.Event.Subscriptions[eventId]);
+ if (listeners.length === 0) {
+ delete R3.Event.Subscriptions[eventId];
+ }
}
- R3.Event.Subscriptions[eventName].splice(
- index,
- 1
- );
- }
- }
+ }(eventName, subscriptionId),
+ subscriptionId : subscriptionId
+ };
+
};
\ No newline at end of file
diff --git a/src/r3-a-2-event-1.js b/src/r3-a-2-event-1.js
index b1b77c7..f575341 100644
--- a/src/r3-a-2-event-1.js
+++ b/src/r3-a-2-event-1.js
@@ -84,37 +84,40 @@ R3.Event.PAUSE = 0x53;
R3.Event.PAUSE_ALL_AUDIO = 0x54;
R3.Event.PLAY_AUDIO = 0x55;
R3.Event.PROJECT_LOADED = 0x56;
-R3.Event.QUERY_PARSED = 0x57;
-R3.Event.RECEIVE_DESTINATION_CHANGED = 0x58;
-R3.Event.REGISTER_DEPENDENCIES = 0x59;
-R3.Event.REGISTER_UPDATE = 0x5a;
-R3.Event.REMOVE_COMPONENT = 0x5b;
-R3.Event.REMOVE_MESH = 0x5c;
-R3.Event.REMOVE_PARTICLE_ENGINE = 0x5d;
-R3.Event.RENDERER_SIZE_CHANGE = 0x5e;
-R3.Event.REPLACE_COMPONENT = 0x5f;
-R3.Event.RESOLVE_DEPENDENCIES = 0x60;
-R3.Event.RESTART = 0x61;
-R3.Event.SAVE_COMPONENT = 0x62;
-R3.Event.SAVE_COMPONENT_ERROR = 0x63;
-R3.Event.SAVING = 0x64;
-R3.Event.SELECTION_MODE_CHANGE = 0x65;
-R3.Event.SIGN_IN = 0x66;
-R3.Event.SIGN_OUT = 0x67;
-R3.Event.START = 0x68;
-R3.Event.STOP_ALL_AUDIO = 0x69;
-R3.Event.STOP_AUDIO = 0x6a;
-R3.Event.STOP_VISUALIZE = 0x6b;
-R3.Event.TEXTURE_ANIMATED_CHANGE = 0x6c;
-R3.Event.TEXTURE_INSTANCE_UPDATED = 0x6d;
-R3.Event.TOUCH_CANCEL = 0x6e;
-R3.Event.TOUCH_END = 0x6f;
-R3.Event.TOUCH_MOVE = 0x70;
-R3.Event.TOUCH_START = 0x71;
-R3.Event.UNRESOLVED_DEPENDENCIES_UPDATE = 0x72;
-R3.Event.VISUALIZE = 0x73;
-R3.Event.WINDOW_RESIZE = 0x74;
-R3.Event.MAX_EVENTS = 0x75;
+R3.Event.QUERY = 0x57;
+R3.Event.QUERY_INTERVAL_CHANGE = 0x58;
+R3.Event.QUERY_PARSED = 0x59;
+R3.Event.RECEIVE_DESTINATION_CHANGED = 0x5a;
+R3.Event.REGISTER_COMPONENT = 0x5b;
+R3.Event.REGISTER_DEPENDENCIES = 0x5c;
+R3.Event.REGISTER_UPDATE = 0x5d;
+R3.Event.REMOVE_COMPONENT = 0x5e;
+R3.Event.REMOVE_MESH = 0x5f;
+R3.Event.REMOVE_PARTICLE_ENGINE = 0x60;
+R3.Event.RENDERER_SIZE_CHANGE = 0x61;
+R3.Event.REPLACE_COMPONENT = 0x62;
+R3.Event.RESOLVE_DEPENDENCIES = 0x63;
+R3.Event.RESTART = 0x64;
+R3.Event.SAVE_COMPONENT = 0x65;
+R3.Event.SAVE_COMPONENT_ERROR = 0x66;
+R3.Event.SAVING = 0x67;
+R3.Event.SELECTION_MODE_CHANGE = 0x68;
+R3.Event.SIGN_IN = 0x69;
+R3.Event.SIGN_OUT = 0x6a;
+R3.Event.START = 0x6b;
+R3.Event.STOP_ALL_AUDIO = 0x6c;
+R3.Event.STOP_AUDIO = 0x6d;
+R3.Event.STOP_VISUALIZE = 0x6e;
+R3.Event.TEXTURE_ANIMATED_CHANGE = 0x6f;
+R3.Event.TEXTURE_INSTANCE_UPDATED = 0x70;
+R3.Event.TOUCH_CANCEL = 0x71;
+R3.Event.TOUCH_END = 0x72;
+R3.Event.TOUCH_MOVE = 0x73;
+R3.Event.TOUCH_START = 0x74;
+R3.Event.UNRESOLVED_DEPENDENCIES_UPDATE = 0x75;
+R3.Event.VISUALIZE = 0x76;
+R3.Event.WINDOW_RESIZE = 0x77;
+R3.Event.MAX_EVENTS = 0x78;
/**
* R3.Event.GetEventName
@@ -211,36 +214,39 @@ R3.Event.GetEventName = function(eventId) {
case 0x54 : return 'pause_all_audio';
case 0x55 : return 'play_audio';
case 0x56 : return 'project_loaded';
- case 0x57 : return 'query_parsed';
- case 0x58 : return 'receive_destination_changed';
- case 0x59 : return 'register_dependencies';
- case 0x5a : return 'register_update';
- case 0x5b : return 'remove_component';
- case 0x5c : return 'remove_mesh';
- case 0x5d : return 'remove_particle_engine';
- case 0x5e : return 'renderer_size_change';
- case 0x5f : return 'replace_component';
- case 0x60 : return 'resolve_dependencies';
- case 0x61 : return 'restart';
- case 0x62 : return 'save_component';
- case 0x63 : return 'save_component_error';
- case 0x64 : return 'saving';
- case 0x65 : return 'selection_mode_change';
- case 0x66 : return 'sign_in';
- case 0x67 : return 'sign_out';
- case 0x68 : return 'start';
- case 0x69 : return 'stop_all_audio';
- case 0x6a : return 'stop_audio';
- case 0x6b : return 'stop_visualize';
- case 0x6c : return 'texture_animated_change';
- case 0x6d : return 'texture_instance_updated';
- case 0x6e : return 'touch_cancel';
- case 0x6f : return 'touch_end';
- case 0x70 : return 'touch_move';
- case 0x71 : return 'touch_start';
- case 0x72 : return 'unresolved_dependencies_update';
- case 0x73 : return 'visualize';
- case 0x74 : return 'window_resize';
+ case 0x57 : return 'query';
+ case 0x58 : return 'query_interval_change';
+ case 0x59 : return 'query_parsed';
+ case 0x5a : return 'receive_destination_changed';
+ case 0x5b : return 'register_component';
+ case 0x5c : return 'register_dependencies';
+ case 0x5d : return 'register_update';
+ case 0x5e : return 'remove_component';
+ case 0x5f : return 'remove_mesh';
+ case 0x60 : return 'remove_particle_engine';
+ case 0x61 : return 'renderer_size_change';
+ case 0x62 : return 'replace_component';
+ case 0x63 : return 'resolve_dependencies';
+ case 0x64 : return 'restart';
+ case 0x65 : return 'save_component';
+ case 0x66 : return 'save_component_error';
+ case 0x67 : return 'saving';
+ case 0x68 : return 'selection_mode_change';
+ case 0x69 : return 'sign_in';
+ case 0x6a : return 'sign_out';
+ case 0x6b : return 'start';
+ case 0x6c : return 'stop_all_audio';
+ case 0x6d : return 'stop_audio';
+ case 0x6e : return 'stop_visualize';
+ case 0x6f : return 'texture_animated_change';
+ case 0x70 : return 'texture_instance_updated';
+ case 0x71 : return 'touch_cancel';
+ case 0x72 : return 'touch_end';
+ case 0x73 : return 'touch_move';
+ case 0x74 : return 'touch_start';
+ case 0x75 : return 'unresolved_dependencies_update';
+ case 0x76 : return 'visualize';
+ case 0x77 : return 'window_resize';
default :
throw new Error('Event type not defined : ' + eventId);
}
diff --git a/src/r3-a-3-api-component.js b/src/r3-a-3-api-component.js
index 8358b99..9421d7f 100644
--- a/src/r3-a-3-api-component.js
+++ b/src/r3-a-3-api-component.js
@@ -5,6 +5,7 @@
* @param name
* @param register
* @param selected
+ * @param isPublic
* @constructor
*/
R3.API.Component = function(
diff --git a/src/r3-a-3-utils.js b/src/r3-a-3-utils.js
index 398eb18..25859f6 100644
--- a/src/r3-a-3-utils.js
+++ b/src/r3-a-3-utils.js
@@ -25,6 +25,28 @@ R3.Utils.GetFirstParent = function(object, constructor) {
};
+R3.Utils.SyntaxHighlight = function(json) {
+ if (typeof json != 'string') {
+ json = JSON.stringify(json, undefined, 2);
+ }
+ json = json.replace(/&/g, '&').replace(//g, '>');
+ return json.replace(/("(\\u[a-zA-Z0-9]{4}|\\[^u]|[^\\"])*"(\s*:)?|\b(true|false|null)\b|-?\d+(?:\.\d*)?(?:[eE][+\-]?\d+)?)/g, function (match) {
+ var cls = 'number';
+ if (/^"/.test(match)) {
+ if (/:$/.test(match)) {
+ cls = 'key';
+ } else {
+ cls = 'string';
+ }
+ } else if (/true|false/.test(match)) {
+ cls = 'boolean';
+ } else if (/null/.test(match)) {
+ cls = 'null';
+ }
+ return '' + match + '';
+ });
+};
+
R3.Utils.GetParentProject = function(component) {
if (R3.Utils.UndefinedOrNull(component.parent)) {
diff --git a/src/r3-a-4-component.js b/src/r3-a-4-component.js
index 32bf9ea..6df92c3 100644
--- a/src/r3-a-4-component.js
+++ b/src/r3-a-4-component.js
@@ -30,6 +30,17 @@ R3.Component = function() {
this.instanceCreated.bind(this)
);
+ /**
+ * This component, no doubt - is a parent to some other components.
+ * We register this component with the EntityManager, so it can link the parent property of all
+ * this component's child components to this
+ */
+
+ R3.Event.Emit(
+ R3.Event.REGISTER_COMPONENT,
+ this
+ );
+
this.buildVectoredComponents();
this.buildLinkedComponents();
@@ -198,7 +209,7 @@ R3.Component.prototype.instanceCreated = function(data) {
/**
* Ignore components with no parent
*/
- if (data.component.parent === null) {
+ if (R3.Utils.UndefinedOrNull(data.component.parent)) {
return;
}
@@ -361,6 +372,7 @@ R3.Component.prototype.buildLinkedComponents = function() {
*/
this[property] = this[property].reduce(
+
function (component, _property) {
return function (result, item, index) {
@@ -379,7 +391,7 @@ R3.Component.prototype.buildLinkedComponents = function() {
componentId: item,
},
function (__component, __property, __index, __id, __dependencyString) {
- return function (data) {
+ return function (rawComponent) {
if (R3.Utils.UndefinedOrNull(__component[__property])) {
throw new Error('The component took too long to load and the component property was damaged: ' + R3.GetComponentName(__component) + '.' + __property);
@@ -393,7 +405,9 @@ R3.Component.prototype.buildLinkedComponents = function() {
throw new Error('The component loaded however it no longer exists as an id: ' + R3.GetComponentName(__component) + '.' + __property + '[' + __index + '] !==' + __id);
}
- __component[__property][__index] = data.component;
+ var Constructor = R3.GetConstructorFromComponentType(rawComponent.componentType);
+
+ __component[__property][__index] = new Constructor(rawComponent);
var deleteIndex = __component.dependencies.indexOf(__dependencyString);
@@ -410,12 +424,12 @@ R3.Component.prototype.buildLinkedComponents = function() {
}
}
- }(this, _property, index, item, dependencyString),
- function (component, __property) {
- return function (error) {
- console.error('Failed to load ' + R3.GetComponentName(component) + '.' + __property + ' because of ' + error);
+ }(component, _property, index, item, dependencyString),
+ function (__component, __property) {
+ return function (__error) {
+ console.error('Failed to load ' + R3.GetComponentName(__component) + '.' + __property + ' because of ' + __error);
};
- }(this, _property)
+ }(component, _property)
);
result.push(item);
@@ -474,6 +488,7 @@ R3.Component.prototype.buildLinkedComponents = function() {
throw new Error('Unhandled situation - could not process : ' + R3.GetComponentName(component) + '.' + _property + '[' + index + ']');
};
+
}(this, property),
[]
);
@@ -489,7 +504,7 @@ R3.Component.prototype.buildLinkedComponents = function() {
/**
* This object is not loaded yet - we should notify (a storage system perhaps) that it should be loaded and add it as a dependency
*/
- var dependencyString = R3.GetComponentName(component) + '.' + _property + '(' + this[property] + ')';
+ var dependencyString = R3.GetComponentName(this) + '.' + property + '(' + this[property] + ')';
R3.Utils.PushUnique(this.dependencies, dependencyString);
R3.Event.Async(
@@ -497,36 +512,40 @@ R3.Component.prototype.buildLinkedComponents = function() {
{
componentId: this[property],
},
- function (component, _property, _id, _dependencyString) {
- return function (data) {
+ function (__component, __property, __id, __dependencyString) {
- if (R3.Utils.UndefinedOrNull(component[_property])) {
- throw new Error('The component took too long to load and the component property was damaged: ' + R3.GetComponentName(component) + '.' + _property);
+ return function (rawComponent) {
+
+ if (R3.Utils.UndefinedOrNull(__component[__property])) {
+ throw new Error('The component took too long to load and the component property was damaged: ' + R3.GetComponentName(__component) + '.' + __property);
}
- if (component[_property] !== _id) {
- throw new Error('The component loaded however it no longer exists as an id: ' + R3.GetComponentName(component) + '.' + _property + ' !==' + _id);
+ if (__component[__property] !== __id) {
+ throw new Error('The component loaded however it no longer exists as an id: ' + R3.GetComponentName(__component) + '.' + __property + ' !==' + __id);
}
- component[_property] = data.component;
+ var Constructor = R3.GetConstructorFromComponentType(rawComponent.componentType);
- var deleteIndex = component.dependencies.indexOf(_dependencyString);
+ __component[__property] = new Constructor(rawComponent);
+
+ var deleteIndex = __component.dependencies.indexOf(__dependencyString);
if (deleteIndex === -1) {
- throw new Error('The dependency ' + _dependencyString + ' was removed during the time that the component was loading');
+ throw new Error('The dependency ' + __dependencyString + ' was removed during the time that the component was loading');
}
- component.dependencies = component.dependencies.splice(deleteIndex, 1);
+ __component.dependencies = __component.dependencies.splice(deleteIndex, 1);
- if (component.dependencies.length === 0) {
- component.performInstanceCreation();
+ if (__component.dependencies.length === 0) {
+ __component.performInstanceCreation();
}
}
+
}(this, property, this[property], dependencyString),
- function (component, _property) {
- return function (error) {
- console.error('Failed to load ' + R3.GetComponentName(component) + '.' + _property + ' because of ' + error);
+ function (__component, __property) {
+ return function (__error) {
+ console.error('Failed to load ' + R3.GetComponentName(__component) + '.' + __property + ' because of ' + __error);
};
}(this, property)
);
@@ -623,17 +642,6 @@ R3.Component.prototype.createInstance = function() {
this.loaded = true;
- /**
- * Use this event to know that the object has now loaded and all 'INSTANCE_CREATED' events have been handled.
- * The idToObject property of this component can now be trusted.
- */
- R3.Event.Emit(
- R3.Event.INSTANCE_LOADED,
- {
- component: this
- }
- );
-
if (this instanceof R3.Project) {
R3.Event.Emit(
R3.Event.PROJECT_LOADED,
@@ -652,6 +660,16 @@ R3.Component.prototype.createInstance = function() {
)
}
+ /**
+ * Use this event to know that the object has now loaded and all 'INSTANCE_CREATED' events have been handled.
+ * The idToObject property of this component can now be trusted.
+ */
+ R3.Event.Emit(
+ R3.Event.INSTANCE_LOADED,
+ {
+ component: this
+ }
+ );
};
R3.Component.prototype.updateInstance = function(property) {
diff --git a/src/r3-api-graph-table.js b/src/r3-api-graph-table.js
index a0094ed..54b528f 100644
--- a/src/r3-api-graph-table.js
+++ b/src/r3-api-graph-table.js
@@ -27,6 +27,11 @@ R3.API.Graph.Table = function(
}
this.rows = apiComponent.rows;
+ if (R3.Utils.UndefinedOrNull(apiComponent.pageSize)) {
+ apiComponent.pageSize = 10;
+ }
+ this.pageSize = apiComponent.pageSize;
+
};
R3.API.Graph.Table.prototype = Object.create(R3.API.Graph.prototype);
diff --git a/src/r3-api-query-0.js b/src/r3-api-query-0.js
index 97eb32a..092c2de 100644
--- a/src/r3-api-query-0.js
+++ b/src/r3-api-query-0.js
@@ -52,6 +52,10 @@ R3.API.Query = function(
}
this.httpMethod = apiComponent.httpMethod;
+ if (R3.Utils.UndefinedOrNull(apiComponent.tooltips)) {
+ apiComponent.tooltips = [];
+ }
+ this.tooltips = apiComponent.tooltips;
};
R3.API.Query.prototype = Object.create(R3.API.Component.prototype);
@@ -61,6 +65,7 @@ R3.API.Query.QUERY_SIZE = 'QUERY_SIZE';
R3.API.Query.QUERY_START = 'QUERY_START';
R3.API.Query.QUERY_END = 'QUERY_END';
R3.API.Query.QUERY_TIMEZONE = 'QUERY_TIMEZONE';
+R3.API.Query.QUERY_TIME_INTERVAL = 'QUERY_TIME_INTERVAL';
R3.API.Query.QUERY_BUCKET_FIELD = 'QUERY_BUCKET_FIELD';
R3.API.Query.QUERY_LOGIN_TYPE = 'QUERY_LOGIN_TYPE';
R3.API.Query.QUERY_ACKNOWLEDGED = 'QUERY_ACKNOWLEDGED';
diff --git a/src/r3-api-query-alerts-firstTimeLogin-0.js b/src/r3-api-query-alerts-firstTimeLogin-0.js
index 9d5b997..6e1854c 100644
--- a/src/r3-api-query-alerts-firstTimeLogin-0.js
+++ b/src/r3-api-query-alerts-firstTimeLogin-0.js
@@ -47,7 +47,7 @@ R3.API.Query.Alerts.FirstTimeLogin = function(
' "term" : { "alert_type.keyword": "First Time Login" }\n' +
' },\n' +
' {\n' +
- ' "regexp" : { "login.login_type.keyword": "' + R3.API.Query.QUERY_LOGIN_TYPE + '" }\n' +
+ ' "regexp" : { "login.type.keyword": "' + R3.API.Query.QUERY_LOGIN_TYPE + '" }\n' +
' }\n' +
' ]\n' +
' }\n' +
diff --git a/src/r3-api-query-alerts-timeseries.js b/src/r3-api-query-alerts-timeseries.js
index 2ca752a..f2d311c 100644
--- a/src/r3-api-query-alerts-timeseries.js
+++ b/src/r3-api-query-alerts-timeseries.js
@@ -28,7 +28,7 @@ R3.API.Query.Alerts.Timeseries = function(
' "mins": {\n' +
' "date_histogram": {\n' +
' "field": "timestamp",\n' +
- ' "calendar_interval": "1d",\n' +
+ ' "calendar_interval": "' + R3.API.Query.QUERY_TIME_INTERVAL + '",\n' +
' "time_zone": "' + R3.API.Query.QUERY_TIMEZONE + '",\n' +
' "min_doc_count": 0,\n' +
' "format" : "yyyy-MM-dd"\n' +
@@ -63,6 +63,11 @@ R3.API.Query.Alerts.Timeseries = function(
}
this.text = apiComponent.text;
+ if (R3.Utils.UndefinedOrNull(apiComponent.timeInterval)) {
+ apiComponent.timeInterval = '1d';
+ }
+ this.timeInterval = apiComponent.timeInterval;
+
R3.API.Query.Alerts.call(
this,
apiComponent
diff --git a/src/r3-api-query-logins-0.js b/src/r3-api-query-logins-0.js
index cf80175..2817804 100644
--- a/src/r3-api-query-logins-0.js
+++ b/src/r3-api-query-logins-0.js
@@ -46,7 +46,7 @@ R3.API.Query.Logins = function(
' }\n' +
' },\n' +
' {\n' +
- ' "regexp" : { "login_type.keyword": "(' + R3.API.Query.QUERY_LOGIN_TYPE + ')" }\n' +
+ ' "regexp" : { "type.keyword": "(' + R3.API.Query.QUERY_LOGIN_TYPE + ')" }\n' +
' }\n' +
' ]\n' +
' }\n' +
diff --git a/src/r3-d3-raycaster.js b/src/r3-d3-raycaster.js
index f49e953..ae4f010 100644
--- a/src/r3-d3-raycaster.js
+++ b/src/r3-d3-raycaster.js
@@ -9,6 +9,9 @@ R3.D3.Raycaster = function(
__RUNTIME_COMPONENT__;
+ this.linkedComponents.position = R3.Vector3;
+ this.linkedComponents.direction = R3.Vector3;
+
__UPGRADE_TO_RUNTIME__;
};
diff --git a/src/r3-d3-viewport-fixedAspect-0.js b/src/r3-d3-viewport-fixedAspect-0.js
index a514ab0..f531e6a 100644
--- a/src/r3-d3-viewport-fixedAspect-0.js
+++ b/src/r3-d3-viewport-fixedAspect-0.js
@@ -28,6 +28,30 @@ R3.D3.Viewport.FixedAspect.prototype.constructor = R3.D3.Viewport.FixedAspect;
R3.D3.Viewport.FixedAspect.prototype.createInstance = function() {
+ /**
+ * We have a dependency on our parent which could still need to call 'createInstance'
+ */
+
+ // if (typeof this.parent === 'string') {
+ //
+ // if (R3.Utils.UndefinedOrNull(this.instanceLoaded)) {
+ //
+ // this.instanceLoaded = R3.Event.Subscribe(
+ // R3.Event.INSTANCE_LOADED,
+ // function (data) {
+ // if (data.component.id === this.parent) {
+ // this.parent = data.component;
+ // this.createInstance();
+ // this.instanceLoaded.remove();
+ // }
+ // }.bind(this)
+ // );
+ //
+ // }
+ //
+ // return;
+ // }
+
this.calculateDimensions();
this.instance = this.graphics.Vector4(
diff --git a/src/r3-entityManager.js b/src/r3-entityManager.js
index 94ee58e..4d67201 100644
--- a/src/r3-entityManager.js
+++ b/src/r3-entityManager.js
@@ -19,11 +19,6 @@ R3.EntityManager = function(
this.instanceDisposal = [];
- R3.Event.Subscribe(
- R3.Event.INSTANCE_CREATED,
- this.instanceCreated.bind(this)
- );
-
R3.Event.Subscribe(
R3.Event.REMOVE_COMPONENT,
this.removeComponent.bind(this)
@@ -32,6 +27,11 @@ R3.EntityManager = function(
R3.Event.Subscribe(
R3.Event.INSTANCE_DISPOSAL,
this.removeInstances.bind(this)
+ );
+
+ R3.Event.Subscribe(
+ R3.Event.REGISTER_COMPONENT,
+ this.registerComponent.bind(this)
)
// R3.Event.Subscribe(
@@ -42,24 +42,35 @@ R3.EntityManager = function(
};
-R3.EntityManager.prototype.instanceCreated = function(data) {
+R3.EntityManager.prototype.registerComponent = function(component) {
/**
- * Register this component in componentType to Component register
+ * Register this component in the componentType to component register
*/
- if (R3.Utils.UndefinedOrNull(this.register[data.component.componentType])) {
- this.register[data.component.componentType] = {};
+ if (R3.Utils.UndefinedOrNull(this.register[component.componentType])) {
+ this.register[component.componentType] = {};
}
- if (R3.Utils.UndefinedOrNull(this.register[data.component.componentType][data.component.id])) {
- this.register[data.component.componentType][data.component.id] = data.component;
+ this.register[component.componentType][component.id] = component;
+
+ /**
+ * Register this component in the id to component register
+ */
+ if (R3.Utils.UndefinedOrNull(this.idRegister[component.id])) {
+ this.idRegister[component.id] = component;
}
/**
- * Register this component in the Component.id to Component register
+ * If this component has a parent - link it right away
*/
- if (R3.Utils.UndefinedOrNull(this.idRegister[data.component.id])) {
- this.idRegister[data.component.id] = data.component;
+ if (typeof component.parent === 'string') {
+
+ if (R3.Utils.UndefinedOrNull(this.idRegister[component.parent])) {
+ throw new Error('A component links to a parent which has not been registered yet');
+ }
+
+ component.parent = this.idRegister[component.parent];
+
}
};
diff --git a/src/r3-graph-barchart-stacked.js b/src/r3-graph-barchart-stacked.js
index b83a657..989ef76 100644
--- a/src/r3-graph-barchart-stacked.js
+++ b/src/r3-graph-barchart-stacked.js
@@ -39,6 +39,7 @@ R3.Graph.Barchart.Stacked.prototype.createInstance = function() {
R3.Graph.Barchart.Stacked.prototype.updateInstance = function(property) {
if (property === 'query') {
+ this.chart.destroy();
this.instance = this.graphics.BarchartStacked(this);
}
diff --git a/src/r3-query-0.js b/src/r3-query-0.js
index e8f2627..64ed8b7 100644
--- a/src/r3-query-0.js
+++ b/src/r3-query-0.js
@@ -46,9 +46,23 @@ R3.Query.prototype.updateInstance = function(property) {
return;
}
+ if (property === 'tooltips') {
+ console.warn('todo: update query tooltips');
+ return;
+ }
+
__UPDATE_INSTANCE__;
};
-R3.Query.prototype.parse = function() {
- console.warn('override R3.Query.prototype.parse() in child function');
+R3.Query.prototype.parse = function(data) {
+ console.warn(data);
+
+ if (data.hits && data.hits.hits) {
+ data.hits.hits.map(
+ function(hit) {
+ this.tooltips.push(hit._source);
+ }.bind(this)
+ )
+ }
+
};
\ No newline at end of file
diff --git a/src/r3-query-alerts-0.js b/src/r3-query-alerts-0.js
index 7394127..b08cab7 100644
--- a/src/r3-query-alerts-0.js
+++ b/src/r3-query-alerts-0.js
@@ -27,3 +27,9 @@ R3.Query.Alerts.prototype.updateInstance = function(property) {
R3.Query.prototype.updateInstance.call(this, property);
};
+
+R3.Query.Alerts.prototype.parse = function(data) {
+
+ R3.Query.prototype.parse.call(this, data);
+
+};
\ No newline at end of file
diff --git a/src/r3-query-alerts-buckets.js b/src/r3-query-alerts-buckets.js
index 33bc2c3..ea03cd3 100644
--- a/src/r3-query-alerts-buckets.js
+++ b/src/r3-query-alerts-buckets.js
@@ -124,10 +124,14 @@ R3.Query.Alerts.Buckets.prototype.parse = function(data) {
]
);
+ this.tooltips.push(bucket);
+
result.push(key.concat(priorities));
return result;
- },
+ }.bind(this),
[]
);
+ //R3.Query.Alerts.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-firstTimeLogin-0.js b/src/r3-query-alerts-firstTimeLogin-0.js
index ca0aff5..960f70e 100644
--- a/src/r3-query-alerts-firstTimeLogin-0.js
+++ b/src/r3-query-alerts-firstTimeLogin-0.js
@@ -42,5 +42,9 @@ R3.Query.Alerts.FirstTimeLogin.prototype.updateInstance = function(property) {
};
R3.Query.Alerts.FirstTimeLogin.prototype.parse = function(data) {
+
console.warn('not yet implemented');
+
+ R3.Query.Alerts.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-firstTimeLogin-applications.js b/src/r3-query-alerts-firstTimeLogin-applications.js
index 5e47b83..fe64542 100644
--- a/src/r3-query-alerts-firstTimeLogin-applications.js
+++ b/src/r3-query-alerts-firstTimeLogin-applications.js
@@ -58,14 +58,7 @@ R3.Query.Alerts.FirstTimeLogin.Applications.prototype.parse = function(data) {
];
if (data.hits.hits.length === 0) {
- this.rows = [
- [
- 'no data',
- null,
- null,
- null
- ]
- ]
+ this.rows = [null];
} else {
this.rows = data.hits.hits.reduce(
function (result, hit) {
@@ -81,4 +74,6 @@ R3.Query.Alerts.FirstTimeLogin.Applications.prototype.parse = function(data) {
);
}
+ R3.Query.Alerts.FirstTimeLogin.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-firstTimeLogin-devices.js b/src/r3-query-alerts-firstTimeLogin-devices.js
index 36fc85a..5d47edc 100644
--- a/src/r3-query-alerts-firstTimeLogin-devices.js
+++ b/src/r3-query-alerts-firstTimeLogin-devices.js
@@ -65,16 +65,7 @@ R3.Query.Alerts.FirstTimeLogin.Devices.prototype.parse = function(data) {
},
];
- if (data.hits.hits.length === 0) {
- this.rows = [
- [
- 'no data',
- null,
- null,
- null
- ]
- ]
- } else {
+ if (data.hits && data.hits.hits) {
this.rows = data.hits.hits.reduce(
function (result, hit) {
var row = [
@@ -90,4 +81,6 @@ R3.Query.Alerts.FirstTimeLogin.Devices.prototype.parse = function(data) {
[]
);
}
+
+ R3.Query.Alerts.FirstTimeLogin.prototype.parse.call(this, data);
};
diff --git a/src/r3-query-alerts-firstTimeLogin-vpn.js b/src/r3-query-alerts-firstTimeLogin-vpn.js
index f82aa5e..e017931 100644
--- a/src/r3-query-alerts-firstTimeLogin-vpn.js
+++ b/src/r3-query-alerts-firstTimeLogin-vpn.js
@@ -86,4 +86,6 @@ R3.Query.Alerts.FirstTimeLogin.VPN.prototype.parse = function(data) {
[]
);
+ R3.Query.Alerts.FirstTimeLogin.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-list.js b/src/r3-query-alerts-list.js
index fd7b193..cf1de8d 100644
--- a/src/r3-query-alerts-list.js
+++ b/src/r3-query-alerts-list.js
@@ -42,10 +42,6 @@ R3.Query.Alerts.List.prototype.updateInstance = function(property) {
R3.Query.Alerts.List.prototype.parse = function(data) {
this.columns = [
- {
- type : 'datetime',
- name : 'Time'
- },
{
type : 'number',
name : 'Priority'
@@ -55,28 +51,60 @@ R3.Query.Alerts.List.prototype.parse = function(data) {
name : 'Alert Type'
},
{
- type : 'boolean',
+ type : 'string',
+ name : 'Hostname'
+ },
+ {
+ type : 'string',
+ name : 'Device'
+ },
+ {
+ type : 'string',
+ name : 'MAC Address'
+ },
+ {
+ type : 'string',
name : 'Acknowledged'
+ },
+ {
+ type : 'datetime',
+ name : 'Time'
}
];
+
+
this.rows = data.hits.hits.reduce(
function(result, hit) {
var row = [];
- row.push(new Date(hit._source.timestamp));
+
row.push(hit._source.priority);
row.push(hit._source.alert_type);
- row.push(hit._source.acknowledged);
- // if (hit._source.acknowledged) {
- // row.push({v:'ButtonName', f:''});
- // } else {
- // row.push({v:'ButtonName', f:''});
- // }
+
+ var hostname = 'unknown';
+ if (hit._source.login && hit._source.login.destination_hostname) {
+ hostname = hit._source.login.destination_hostname;
+ }
+ row.push(hostname);
+
+ var device = 'unknown';
+ if (hit._source.device && hit._source.device.ip_v4) {
+ device = hit._source.device.ip_v4;
+ }
+ row.push(device);
+
+ row.push(hit._source.mac);
+
+ row.push({v:'ButtonName', f:hit._source.acknowledged?'Yes':'No'});
+ row.push(new Date(hit._source.timestamp));
result.push(row);
+
return result;
- },
+ }.bind(this),
[]
);
+ R3.Query.Alerts.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-summary.js b/src/r3-query-alerts-summary.js
index 99f173e..8a77586 100644
--- a/src/r3-query-alerts-summary.js
+++ b/src/r3-query-alerts-summary.js
@@ -44,9 +44,12 @@ R3.Query.Alerts.Summary.prototype.parse = function(data) {
this.priorities = data.aggregations.priorities.buckets.reduce(
function(result, bucket) {
result.push(bucket.doc_count);
+ this.tooltips.push(bucket);
return result;
- },
+ }.bind(this),
[]
);
+ // R3.Query.Alerts.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-alerts-timeseries.js b/src/r3-query-alerts-timeseries.js
index 5f02a37..b2fc473 100644
--- a/src/r3-query-alerts-timeseries.js
+++ b/src/r3-query-alerts-timeseries.js
@@ -59,20 +59,72 @@ R3.Query.Alerts.Timeseries.prototype.parse = function(data) {
return day + '-' + monthNames[monthIndex] + '-' + year;
}
- result.push(formatDate(new Date(bucket.key)));
+ function formatHour(date) {
+
+ var day = date.getDate();
+ var hour = date.getHours();
+ var monthIndex = date.getMonth();
+
+ var monthNames = [
+ "Jan", "Feb", "Mar",
+ "Apr", "May", "Jun", "Jul",
+ "Aug", "Sep", "Oct",
+ "Nov", "Dec"
+ ];
+ return monthIndex+1 + '/' + day + ' ' + date.toLocaleTimeString();
+ return monthNames[monthIndex] + ' ' + day + '-' + hour + ':00';
+ }
+
+ function formatMinute(date) {
+
+ var hour = date.getHours();
+ var minute = date.getMinutes();
+
+ return date.toLocaleTimeString();
+ return hour + ':' + minute;
+ }
+
+ if (this.timeInterval === '1d') {
+ result.push(formatDate(new Date(bucket.key)));
+ } else if (this.timeInterval === '1h') {
+ result.push(formatHour(new Date(bucket.key)));
+ } else if (this.timeInterval === '1m') {
+ result.push(formatMinute(new Date(bucket.key)));
+ } else {
+ console.warn('invalid time format');
+ }
+
return result;
- },
+ }.bind(this),
[]
);
this.datasets = data.aggregations.mins.buckets.reduce(
function(result, bucket) {
- console.log('todo here');
- bucket.priorities.buckets.map(
- function(prio) {
- result[prio.key - 1].data.push(prio.doc_count);
+
+ var count = bucket.priorities.buckets.reduce(
+ function(struct, prio) {
+ struct[prio.key - 1] = prio.doc_count;
+ return struct;
+ },
+ [
+ 0,
+ 0,
+ 0,
+ 0
+ ]
+ );
+
+ if (R3.Utils.UndefinedOrNull(count)) {
+ count = [0, 0, 0, 0];
+ }
+
+ count.map(
+ function(data, index) {
+ result[index].data.push(data);
}
- )
+ );
+
return result;
},
[
@@ -138,4 +190,6 @@ R3.Query.Alerts.Timeseries.prototype.parse = function(data) {
// []
// );
+ R3.Query.Alerts.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-devices-0.js b/src/r3-query-devices-0.js
index ce42c54..cb3e54d 100644
--- a/src/r3-query-devices-0.js
+++ b/src/r3-query-devices-0.js
@@ -78,4 +78,5 @@ R3.Query.Devices.prototype.parse = function(data) {
);
}
+ R3.Query.prototype.parse.call(this, data);
};
diff --git a/src/r3-query-devices-known.js b/src/r3-query-devices-known.js
index 85f930e..02f78ca 100644
--- a/src/r3-query-devices-known.js
+++ b/src/r3-query-devices-known.js
@@ -81,4 +81,5 @@ R3.Query.Devices.Known.prototype.parse = function(data) {
);
}
+ R3.Query.Devices.prototype.parse.call(this, data);
};
diff --git a/src/r3-query-devices-sql.js b/src/r3-query-devices-sql.js
index aad5541..c8112de 100644
--- a/src/r3-query-devices-sql.js
+++ b/src/r3-query-devices-sql.js
@@ -45,20 +45,28 @@ R3.Query.Devices.SQL.prototype.parse = function(data) {
this.columns = [
{
type: 'string',
- name: 'Hostname'
+ name: 'IP'
},
{
type: 'string',
- name: 'IP'
+ name: 'Hostname'
},
{
type: 'string',
name: 'MAC Address'
},
{
- type: 'datetime',
- name: 'Created'
+ type: 'string',
+ name: 'Agent ID'
},
+ {
+ type: 'string',
+ name: 'Acknowledged'
+ },
+ {
+ type: 'datetime',
+ name: 'First Seen'
+ }
];
if (data.error) {
@@ -69,14 +77,17 @@ R3.Query.Devices.SQL.prototype.parse = function(data) {
this.rows = data.devices.reduce(
function (result, device) {
var row = [
- device.hostname,
device.ip_v4,
+ device.hostname,
device.mac,
+ device.agent_id,
+ {v:'ButtonName', f:device.acknowledged?'Yes':'No'},
new Date(device.created)
];
result.push(row);
+ this.tooltips.push(device);
return result;
- },
+ }.bind(this),
[]
);
}
diff --git a/src/r3-query-devices-unknown.js b/src/r3-query-devices-unknown.js
index cf34af9..eb792e7 100644
--- a/src/r3-query-devices-unknown.js
+++ b/src/r3-query-devices-unknown.js
@@ -82,4 +82,5 @@ R3.Query.Devices.Unknown.prototype.parse = function(data) {
);
}
+ R3.Query.Devices.prototype.parse.call(this, data);
};
diff --git a/src/r3-query-logins-0.js b/src/r3-query-logins-0.js
index 4f16580..b8ed72e 100644
--- a/src/r3-query-logins-0.js
+++ b/src/r3-query-logins-0.js
@@ -29,3 +29,9 @@ R3.Query.Logins.prototype.updateInstance = function(property) {
R3.Query.prototype.updateInstance.call(this, property);
};
+
+R3.Query.Logins.prototype.parse = function(data) {
+
+ R3.Query.prototype.parse.call(this, data);
+
+};
\ No newline at end of file
diff --git a/src/r3-query-logins-applications.js b/src/r3-query-logins-applications.js
index e6430ba..730804e 100644
--- a/src/r3-query-logins-applications.js
+++ b/src/r3-query-logins-applications.js
@@ -51,6 +51,10 @@ R3.Query.Logins.Applications.prototype.parse = function(data) {
type: 'string',
name: 'Application'
},
+ {
+ type: 'string',
+ name: 'Login Result'
+ },
{
type: 'datetime',
name: 'Time'
@@ -62,6 +66,7 @@ R3.Query.Logins.Applications.prototype.parse = function(data) {
var row = [
hit._source.username,
hit._source.application,
+ hit._source.success?'Login Success':'Login Failure',
new Date(hit._source.timestamp)
];
result.push(row);
@@ -70,4 +75,6 @@ R3.Query.Logins.Applications.prototype.parse = function(data) {
[]
);
+ R3.Query.Logins.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-logins-devices.js b/src/r3-query-logins-devices.js
index e3e4188..36a5a56 100644
--- a/src/r3-query-logins-devices.js
+++ b/src/r3-query-logins-devices.js
@@ -51,6 +51,10 @@ R3.Query.Logins.Devices.prototype.parse = function(data) {
type : 'string',
name : 'Device'
},
+ {
+ type : 'string',
+ name : 'Login Result'
+ },
{
type : 'string',
name : 'Type'
@@ -65,15 +69,14 @@ R3.Query.Logins.Devices.prototype.parse = function(data) {
},
];
-
this.rows = data.hits.hits.reduce(
function(result, hit) {
- console.log('device login : ', hit);
var row = [
hit._source.username,
hit._source.destination_hostname,
- hit._source.login_type,
- hit._source.login_protocol,
+ hit._source.success?'Login Success':'Login Failure',
+ hit._source.type,
+ hit._source.application,
new Date(hit._source.timestamp)
];
result.push(row);
@@ -82,4 +85,6 @@ R3.Query.Logins.Devices.prototype.parse = function(data) {
[]
);
+ R3.Query.Logins.prototype.parse.call(this, data);
+
};
diff --git a/src/r3-query-logins-vpn.js b/src/r3-query-logins-vpn.js
index 642d678..ac8c843 100644
--- a/src/r3-query-logins-vpn.js
+++ b/src/r3-query-logins-vpn.js
@@ -76,4 +76,5 @@ R3.Query.Logins.VPN.prototype.parse = function(data) {
[]
);
+ R3.Query.Logins.prototype.parse.call(this, data);
};
diff --git a/src/r3-query-userDevices-0.js b/src/r3-query-userDevices-0.js
index 4f2ddab..db54e36 100644
--- a/src/r3-query-userDevices-0.js
+++ b/src/r3-query-userDevices-0.js
@@ -75,6 +75,7 @@ R3.Query.UserDevices.prototype.parse = function(data) {
return result;
},
[]
- )
+ );
+ R3.Query.prototype.parse.call(this, data);
};
\ No newline at end of file
diff --git a/src/r3-query-users.js b/src/r3-query-users.js
index 05a5666..d27b8f5 100644
--- a/src/r3-query-users.js
+++ b/src/r3-query-users.js
@@ -44,19 +44,15 @@ R3.Query.Users.prototype.parse = function(data) {
this.columns = [
{
type: 'string',
- name: 'Email'
+ name: 'User'
},
{
type: 'datetime',
- name: 'Created'
+ name: 'First Seen'
},
];
- if (data.error) {
- this.rows = [
- ['error', null, null, null]
- ]
- } else {
+ if (!data.error) {
this.rows = data.users.reduce(
function (result, user) {
var row = [
@@ -64,10 +60,14 @@ R3.Query.Users.prototype.parse = function(data) {
new Date(user.created)
];
result.push(row);
+
+ this.tooltips.push(user);
+
return result;
- },
+ }.bind(this),
[]
);
}
+
};
diff --git a/src/r3-renderer-d3-0.js b/src/r3-renderer-d3-0.js
index c0a95a3..0a10679 100644
--- a/src/r3-renderer-d3-0.js
+++ b/src/r3-renderer-d3-0.js
@@ -7,10 +7,10 @@ R3.Renderer.D3 = function(
inherited
) {
- __INHERIT_ONLY__
+ __INHERIT_ONLY__;
this.linkedComponents.viewports = [R3.D3.Viewport];
- this.linkedComponents.scenes = [R3.D3.Scenes];
+ this.linkedComponents.scenes = [R3.D3.Scene];
R3.Renderer.call(
this,
diff --git a/src/r3-renderer-d3-canvas-0.js b/src/r3-renderer-d3-canvas-0.js
index 5583b23..ec5e1be 100644
--- a/src/r3-renderer-d3-canvas-0.js
+++ b/src/r3-renderer-d3-canvas-0.js
@@ -9,7 +9,7 @@ R3.Renderer.D3.Canvas = function(
inherited
) {
- __INHERIT_AND_INSTANTIATE__
+ __INHERIT_AND_INSTANTIATE__;
this.linkedComponents.canvas = R3.Canvas;
diff --git a/src/r3-runtime-graphics-chart.js b/src/r3-runtime-graphics-chart.js
index 4ddd940..e9e285a 100644
--- a/src/r3-runtime-graphics-chart.js
+++ b/src/r3-runtime-graphics-chart.js
@@ -29,7 +29,17 @@ R3.Runtime.Graphics.Chart.prototype.createInstance = function() {
*/
R3.Runtime.Graphics.Chart.prototype.BarchartStacked = function(runtimeObject) {
- var ctx = document.getElementById(runtimeObject.domElement.domElementId).getContext('2d');
+ var domElement = document.getElementById(runtimeObject.domElement.domElementId);
+ //
+ // var divs = domElement.parentElement.getElementsByTagName('div');
+ //
+ // for (var div of divs) {
+ // domElement.parentElement.removeChild(div);
+ // }
+
+ var ctx = domElement.getContext('2d');
+
+
var barChartData = {
labels: runtimeObject.query.labels,
diff --git a/src/r3-runtime-graphics-google.js b/src/r3-runtime-graphics-google.js
index 3ac721a..564cf47 100644
--- a/src/r3-runtime-graphics-google.js
+++ b/src/r3-runtime-graphics-google.js
@@ -22,15 +22,169 @@ R3.Runtime.Graphics.Google.prototype.createInstance = function() {
this.instance = google.charts;
};
+R3.Runtime.Graphics.Google.Tooltip = function(domTable, table, graph) {
+
+ var tooltip = document.createElement('div');
+ tooltip.setAttribute('class', 'google-visualization-tooltip tooltip-minimized');
+
+ var header = document.createElement('div');
+ header.setAttribute('class', 'tooltip-header');
+
+ var headerTitle = document.createElement('div');
+ headerTitle.innerText = 'Click for more info...';
+
+ var button = document.createElement('button');
+ button.setAttribute('class', 'btn btn-info btn-white close-button');
+ button.innerText = 'X';
+
+ header.appendChild(headerTitle);
+ header.appendChild(button);
+
+ var tooltipContent = document.createElement('pre');
+
+ tooltip.appendChild(header);
+ tooltip.appendChild(tooltipContent);
+
+ if (graph.tooltip) {
+ document.body.removeChild(graph.tooltip);
+ }
+
+ graph.tooltip = tooltip;
+
+ document.body.appendChild(tooltip);
+
+ if (graph.mouseover) {
+ domTable.removeEventListener('mouseover', graph.mouseover);
+ }
+
+ if (graph.mouseout) {
+ domTable.removeEventListener('mouseout', graph.mouseout);
+ }
+
+ if (graph.mousemove) {
+ domTable.removeEventListener('mousemove', graph.mousemove);
+ }
+
+ graph.mouseover = function(tooltip) {
+ return function(event) {
+ tooltip.style.display = 'flex';
+ tooltip.style.left = (event.pageX + 10) + "px";
+ tooltip.style.top = (event.pageY + 10) + "px";
+ };
+ }(tooltip);
+
+ graph.mouseout = function(tooltip) {
+ return function(event) {
+ tooltip.style.display = 'none';
+ };
+ }(tooltip);
+
+ graph.mousemove = function(tooltip) {
+ return function(event) {
+ tooltip.style.left = (event.pageX + 10) + "px";
+ tooltip.style.top = (event.pageY + 10) + "px";
+ };
+ }(tooltip);
+
+ button.addEventListener('click', function(graph, tooltip, button, domTable) {
+ return function(event) {
+ domTable.addEventListener('mouseover', graph.mouseover);
+ domTable.addEventListener('mouseout', graph.mouseout);
+ domTable.addEventListener('mousemove', graph.mousemove);
+ tooltip.style.left = (event.pageX + 10) + "px";
+ tooltip.style.top = (event.pageY + 10) + "px";
+ tooltip.style.display = 'none';
+ tooltip.setAttribute('class', 'google-visualization-tooltip tooltip-minimized');
+ button.style.display = 'none';
+ }
+ }(graph, tooltip, button, domTable));
+
+ google.visualization.events.addListener(
+ table,
+ 'ready',
+ function(domTable, graph) {
+ return function() {
+ domTable.addEventListener('mouseover', graph.mouseover);
+ domTable.addEventListener('mouseout', graph.mouseout);
+ domTable.addEventListener('mousemove', graph.mousemove);
+ };
+ }(domTable, graph)
+ );
+
+ google.visualization.events.addListener(
+ table,
+ 'select',
+ function(domTable, graph, tooltipContent) {
+ return function() {
+ domTable.removeEventListener('mouseover', graph.mouseover);
+ domTable.removeEventListener('mouseout', graph.mouseout);
+ domTable.removeEventListener('mousemove', graph.mousemove);
+ tooltip.setAttribute('class', 'google-visualization-tooltip tooltip-maximized');
+ button.style.display = 'block';
+
+ var selection = table.getSelection();
+
+ var row = 0;
+
+ if (selection && selection[0]) {
+ row = selection[0].row
+ }
+
+ tooltipContent.innerHTML = R3.Utils.SyntaxHighlight(JSON.stringify(graph.query.tooltips[row], null, 2));
+ }
+ }(domTable, graph, tooltipContent)
+ );
+
+ return {
+ main : tooltip,
+ closeButton : button,
+ header : header,
+ title : headerTitle,
+ content : tooltipContent
+ };
+};
+
R3.Runtime.Graphics.Google.prototype.Table = function(runtimeObject) {
google.charts.load('current', {'packages':['table']});
google.charts.setOnLoadCallback(
function(graph) {
+
return function() {
+
var dataTable = new google.visualization.DataTable();
+ // var makeTooltipActive = function(object, moveEventListener, overOutEventListener, table) {
+ // return function(event) {
+ // var selection = table.getSelection();
+ //
+ // object.domElement.instance.removeEventListener('mousemove', moveTooltip);
+ //
+ // var closeButton = document.getElementById('button-close-tooltip');
+ // closeButton.style.display = 'block';
+ // var tooltip = document.getElementById('div-tooltip');
+ // tooltip.setAttribute('class', 'google-visualization-tooltip tooltip-maximized');
+ // var tooltipContent = document.getElementById('pre-tooltip-content');
+ // tooltipContent.style.display = 'block';
+ //
+ //
+ // var row = selection[0].row;
+ // var tooltip = document.getElementById('div-tooltip');
+ // var tooltipContent = document.getElementById('pre-tooltip-content');
+ // var tooltipHeader = document.getElementById('div-tooltip-header');
+ // tooltipContent.innerHTML = R3.Utils.SyntaxHighlight(JSON.stringify(object.query.tooltips[row], null, 2));
+ // tooltip.style.display = 'flex';
+ // moveTooltip(event);
+ //
+ // }
+ // };
+ //
+ // var closeButtonClick = ;
+ //
+ // var closeButton = document.getElementById('button-close-tooltip');
+ // closeButton.addEventListener('click', closeButtonClick);
+
graph.columns.map(
function(column) {
dataTable.addColumn(column.type, column.name);
@@ -39,9 +193,38 @@ R3.Runtime.Graphics.Google.prototype.Table = function(runtimeObject) {
dataTable.addRows(graph.rows);
- var table = new google.visualization.Table(document.getElementById(graph.domElement.domElementId));
+ var domTable = document.getElementById(graph.domElement.domElementId);
- table.draw(dataTable, {showRowNumber: false, width: '100%', height: '100%'});
+ var table = new google.visualization.Table(domTable);
+
+ var tooltip = R3.Runtime.Graphics.Google.Tooltip(
+ domTable,
+ table,
+ graph
+ );
+
+ table.draw(
+ dataTable,
+ {
+ showRowNumber: false,
+ allowHtml : true,
+ cssClassNames: {
+ tableCell: 'fixed-row-height',
+ hoverTableRow : 'hover-row'
+ },
+ width: '100%',
+ height: '100%',
+ page: 'enable',
+ pageSize: graph.pageSize,
+ sortColumn: graph.columns.length - 1,
+ sortAscending : false,
+ pagingSymbols: {
+ prev: 'prev',
+ next: 'next'
+ },
+ pagingButtonsConfiguration: 'auto'
+ }
+ );
}
}(runtimeObject)
diff --git a/src/r3-system-input.js b/src/r3-system-input.js
index b3c4b17..cd0fbdf 100644
--- a/src/r3-system-input.js
+++ b/src/r3-system-input.js
@@ -14,6 +14,7 @@ R3.System.Input = function() {
R3.Event.Emit(
R3.Event.GET_APPLICATION_MODE,
+ null,
function(applicationMode) {
this.applicationMode = applicationMode;
}.bind(this)
diff --git a/src/r3-system-query.js b/src/r3-system-query.js
index a5c02e5..0bd5c29 100644
--- a/src/r3-system-query.js
+++ b/src/r3-system-query.js
@@ -21,10 +21,38 @@ R3.System.Query.prototype.start = function() {
this.query
);
+ this.querySubscription = R3.Event.Subscribe(
+ R3.Event.QUERY,
+ this.query
+ );
+
+ this.intervalChangeSubscription = R3.Event.Subscribe(
+ R3.Event.QUERY_INTERVAL_CHANGE,
+ this.intervalChange.bind(this)
+ );
+
R3.System.prototype.start.call(this);
};
+R3.System.Query.prototype.intervalChange = function(data) {
+
+ var graphs = R3.EntityManager.Instance.findComponentsByConstructor(R3.Graph);
+
+ graphs.map(
+ function(graph) {
+ graph.query.start = 'now-' + data.interval;
+ graph.query.timeInterval = data.timeInterval;
+ R3.Event.Emit(
+ R3.Event.QUERY,
+ {
+ component : graph.query
+ }
+ )
+ }
+ );
+
+};
/**
* Check for query instances - then run them
@@ -81,6 +109,10 @@ R3.System.Query.prototype.query = function(data) {
queryText = queryText.replace(new RegExp(R3.API.Query.QUERY_ACKNOWLEDGED, "g"), query.acknowledged);
}
+ if (R3.Utils.Defined(query.timeInterval)) {
+ queryText = queryText.replace(new RegExp(R3.API.Query.QUERY_TIME_INTERVAL, "g"), query.timeInterval);
+ }
+
if (typeof XMLHttpRequest === 'undefined') {
console.log('Implement server side query here');
return;
@@ -123,6 +155,8 @@ R3.System.Query.prototype.stop = function() {
this.querySubscription.remove();
+ this.intervalChangeSubscription.remove();
+
R3.System.prototype.stop.call(this);
};
diff --git a/src/r3-system-storage.js b/src/r3-system-storage.js
index b843bad..c66d478 100644
--- a/src/r3-system-storage.js
+++ b/src/r3-system-storage.js
@@ -642,7 +642,19 @@ R3.System.Storage.prototype.createRuntimeObject = function(responseText, clientE
return runtimeComponent;
};
-R3.System.Storage.prototype.loadComponent = function(apiUrl, toProcess, includeDependencies, clientCallback, clientErrorCallback) {
+/**
+ * Loads a component and its dependencies if specified
+ * @param urlData
+ * @param componentData
+ * @param clientCallback
+ * @param clientErrorCallback
+ */
+R3.System.Storage.prototype.loadComponent = function(
+ urlData,
+ componentData,
+ clientCallback,
+ clientErrorCallback
+) {
/**
* TODO: ensure parents of this component are loaded first
@@ -655,7 +667,8 @@ R3.System.Storage.prototype.loadComponent = function(apiUrl, toProcess, includeD
* We don't override runtime versions of the dependencies of the loading components - since they could be later.
* But we do override runtime versions of the loading component since the user actually selected them and clicked 'load'
*/
- toProcess.map(
+ componentData.ids.map(
+
function(id) {
R3.Utils.PushUnique(this.loading, id);
@@ -665,15 +678,27 @@ R3.System.Storage.prototype.loadComponent = function(apiUrl, toProcess, includeD
if (component) {
component.remove();
}
+
}.bind(this)
+
);
- toProcess.map(
+ componentData.ids.map(
function(id) {
var xhr = new XMLHttpRequest();
+ xhr.open(
+ 'GET',
+ urlData.apiUrl + '/component/load/' + id
+ );
+
+ xhr.setRequestHeader("Accept", "application/json");
+ xhr.setRequestHeader("Content-Type", "application/json");
+ xhr.setRequestHeader("x-api-authorization", urlData.apiAuthorization);
+ xhr.setRequestHeader('x-api-user-token', urlData.apiUserToken);
+
xhr.onload = function(__system) {
return function() {
@@ -844,12 +869,6 @@ R3.System.Storage.prototype.loadComponent = function(apiUrl, toProcess, includeD
}.bind(this);
}(id);
- xhr.open(
- 'GET',
- apiUrl + '/component/load/' + id
- );
-
-
xhr.send();
}.bind(this)
@@ -862,34 +881,36 @@ R3.System.Storage.prototype.loadComponent = function(apiUrl, toProcess, includeD
/**
* 'Loads' data from a url
*/
-R3.System.Storage.prototype.load = function(data, clientCallback, clientErrorCallback) {
+R3.System.Storage.prototype.load = function(componentData, clientCallback, clientErrorCallback) {
- this.emit(
- R3.Event.GET_API_URL,
+
+ if (typeof XMLHttpRequest === 'undefined') {
+ throw new Error('Implement server side save here');
+ }
+
+ if (R3.Utils.UndefinedOrNull(componentData.ids) || componentData.ids.length < 1) {
+ throw new Error('No components defined for loading');
+ }
+
+ var event = R3.Event.GET_API_URL;
+
+ if (componentData.remote) {
+ event = R3.Event.GET_REMOTE_API_URL
+ }
+
+ R3.Event.Emit(
+ event,
null,
function(urlData) {
- if (typeof XMLHttpRequest === 'undefined') {
- console.log('Implement server side load here');
- return;
- }
-
- if (data.ids && data.ids.length > 0) {
- this.loadComponent(
- urlData.apiUrl,
- data.ids,
- data.includeDependencies,
- clientCallback,
- clientErrorCallback
- );
- } else {
- console.log('No components selected');
- }
+ this.loadComponent(
+ urlData,
+ componentData,
+ clientCallback,
+ clientErrorCallback
+ );
}.bind(this),
- function(error) {
- console.error(error.message);
- throw new Error(error.message);
- }
- );
+ console.error
+ )
};
diff --git a/src/r3-vector3.js b/src/r3-vector3.js
index bc8a7ab..61340d5 100644
--- a/src/r3-vector3.js
+++ b/src/r3-vector3.js
@@ -27,6 +27,30 @@ R3.Vector3.prototype.constructor = R3.Vector3;
*/
R3.Vector3.prototype.createInstance = function() {
+ /**
+ * We have a dependency on our parent which could still need to call 'createInstance'
+ */
+
+ // if (typeof this.parent === 'string') {
+ //
+ // if (R3.Utils.UndefinedOrNull(this.instanceLoaded)) {
+ //
+ // this.instanceLoaded = R3.Event.Subscribe(
+ // R3.Event.INSTANCE_LOADED,
+ // function (data) {
+ // if (data.component.id === this.parent) {
+ // this.parent = data.component;
+ // this.createInstance();
+ // this.instanceLoaded.remove();
+ // }
+ // }.bind(this)
+ // );
+ //
+ // }
+ //
+ // return;
+ // }
+
var runtime = R3.Component.GetComponentRuntime(this.parent);
switch (runtime) {