parent scenes change - helpers are now components - intersects are now per scene / camera and sorted to distance
parent
f9c18837e6
commit
d7a6185e46
|
@ -16,6 +16,7 @@ GameLib.Event.Subscriptions = {};
|
|||
*/
|
||||
GameLib.Event.WINDOW_RESIZE = 0x1;
|
||||
GameLib.Event.PARENT_SCENE_CHANGE = 0x2;
|
||||
GameLib.Event.PARENT_ENTITY_CHANGE = 0x3;
|
||||
|
||||
/**
|
||||
* Subscribe to some events
|
||||
|
|
|
@ -17,6 +17,11 @@ GameLib.D3.Helper = function(
|
|||
this.graphics = graphics;
|
||||
this.graphics.isNotThreeThrow();
|
||||
|
||||
GameLib.Component.call(
|
||||
this,
|
||||
GameLib.Component.COMPONENT_HELPER
|
||||
);
|
||||
|
||||
if (GameLib.Utils.UndefinedOrNull(id)) {
|
||||
id = GameLib.Utils.RandomId();
|
||||
}
|
||||
|
@ -67,6 +72,9 @@ GameLib.D3.Helper = function(
|
|||
this.instance = this.createInstance();
|
||||
};
|
||||
|
||||
GameLib.D3.Helper.prototype = Object.create(GameLib.Component.prototype);
|
||||
GameLib.D3.Helper.prototype.constructor = GameLib.D3.Helper;
|
||||
|
||||
/**
|
||||
* Helper types
|
||||
* @type {string}
|
||||
|
|
|
@ -191,12 +191,30 @@ GameLib.D3.Input.Editor.prototype.onMouseDown = function(entity, entityManager)
|
|||
|
||||
var cameras = entity.getComponents(GameLib.D3.Camera);
|
||||
|
||||
var scenes = entity.getComponents(GameLib.D3.Scene);
|
||||
|
||||
var meshes = entity.getComponents(GameLib.D3.Mesh);
|
||||
|
||||
var intersects = cameras.reduce(
|
||||
|
||||
function(result, camera){
|
||||
|
||||
var scene = scenes.reduce(
|
||||
function(result, scene) {
|
||||
|
||||
if (scene.activeCamera === camera) {
|
||||
result = scene;
|
||||
}
|
||||
|
||||
return result;
|
||||
},
|
||||
null
|
||||
);
|
||||
|
||||
if (scene) {
|
||||
meshes = scene.meshes;
|
||||
}
|
||||
|
||||
this.raycaster.instance.setFromCamera(
|
||||
this.mouse,
|
||||
camera.instance
|
||||
|
@ -206,14 +224,34 @@ GameLib.D3.Input.Editor.prototype.onMouseDown = function(entity, entityManager)
|
|||
|
||||
intersects.map(function(intersect){
|
||||
result.push(intersect);
|
||||
})
|
||||
});
|
||||
|
||||
return result;
|
||||
}.bind(this),
|
||||
[]
|
||||
);
|
||||
|
||||
if (intersects.length > 0) {
|
||||
intersects.sort(
|
||||
function(a, b) {
|
||||
if (a.distance < b.distance) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (a.distance > b.distance) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
);
|
||||
|
||||
meshes = intersects.map(function(intersect){
|
||||
return intersect.mesh;
|
||||
});
|
||||
|
||||
var mesh = meshes[0];
|
||||
|
||||
if (mesh) {
|
||||
|
||||
/**
|
||||
* Prevent default action (like context menu or whatever)
|
||||
|
@ -229,7 +267,7 @@ GameLib.D3.Input.Editor.prototype.onMouseDown = function(entity, entityManager)
|
|||
* Notify our component as being 'selected'
|
||||
* @type {boolean}
|
||||
*/
|
||||
intersects[0].selected = !intersects[0].selected;
|
||||
mesh.selected = !mesh.selected;
|
||||
|
||||
/**
|
||||
* Add a helper to the scene
|
||||
|
@ -237,53 +275,47 @@ GameLib.D3.Input.Editor.prototype.onMouseDown = function(entity, entityManager)
|
|||
*/
|
||||
var helper = null;
|
||||
|
||||
var scene = intersects[0].parentScene;
|
||||
var scene = mesh.parentScene;
|
||||
|
||||
if (!scene) {
|
||||
console.warn('the scene object for this mesh could not be located : ' + intersects[0].name);
|
||||
console.warn('the scene object for this mesh could not be located : ' + mesh.name);
|
||||
return;
|
||||
}
|
||||
|
||||
var gui = entity.getFirstComponent(GameLib.GUI);
|
||||
|
||||
if (intersects[0].selected) {
|
||||
if (mesh.selected) {
|
||||
|
||||
helper = new GameLib.D3.Helper(
|
||||
this.graphics,
|
||||
null,
|
||||
intersects[0].name + ' Helper',
|
||||
intersects[0],
|
||||
mesh.name + ' Helper',
|
||||
mesh,
|
||||
GameLib.D3.Helper.HELPER_TYPE_EDGES
|
||||
);
|
||||
|
||||
/**
|
||||
* Backup the polygonOffset value, then set it to 'true' - helps for clear nice outlines
|
||||
*/
|
||||
intersects[0].polygonOffset = intersects[0].instance.material.polygonOffset;
|
||||
mesh.polygonOffset = mesh.instance.material.polygonOffset;
|
||||
|
||||
intersects[0].instance.material.polygonOffset = true;
|
||||
mesh.instance.material.polygonOffset = true;
|
||||
|
||||
entity.addComponent(helper);
|
||||
|
||||
scene.instance.add(helper.instance);
|
||||
|
||||
scene.subscribe(GameLib.Event.PARENT_SCENE_CHANGE, function(data) {
|
||||
if (data.old === scene) {
|
||||
scene.instance.remove(helper.instance);
|
||||
}
|
||||
});
|
||||
|
||||
gui.addObject(intersects[0]);
|
||||
gui.addObject(mesh);
|
||||
|
||||
} else {
|
||||
|
||||
gui.removeObject(intersects[0]);
|
||||
gui.removeObject(mesh);
|
||||
|
||||
var components = entity.getComponents(GameLib.D3.Helper);
|
||||
|
||||
helper = components.reduce(
|
||||
function(result, component) {
|
||||
if (component.object === intersects[0]) {
|
||||
if (component.object === mesh) {
|
||||
result = component;
|
||||
}
|
||||
return result;
|
||||
|
@ -298,12 +330,12 @@ GameLib.D3.Input.Editor.prototype.onMouseDown = function(entity, entityManager)
|
|||
/**
|
||||
* Restore the polygonOffset value
|
||||
*/
|
||||
intersects[0].instance.material.polygonOffset = intersects[0].polygonOffset;
|
||||
mesh.instance.material.polygonOffset = mesh.polygonOffset;
|
||||
|
||||
entity.removeComponent(helper);
|
||||
|
||||
} else {
|
||||
console.warn('failed to locate helper object which should exist for ' + intersects[0].name);
|
||||
console.warn('failed to locate helper object which should exist for ' + mesh.name);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -163,7 +163,12 @@ GameLib.D3.Raycaster.prototype.getIntersectedObjects = function(meshes) {
|
|||
meshes.map(
|
||||
function(mesh){
|
||||
if (mesh.instance === intersect.object){
|
||||
result.push(mesh);
|
||||
result.push(
|
||||
{
|
||||
mesh : mesh,
|
||||
distance : intersect.distance
|
||||
}
|
||||
);
|
||||
}
|
||||
}
|
||||
);
|
||||
|
|
|
@ -64,6 +64,8 @@ GameLib.EntityManager = function(
|
|||
this.buildIdToObject();
|
||||
|
||||
this.instance = this.createInstance();
|
||||
|
||||
this.registerCallbacks();
|
||||
};
|
||||
|
||||
GameLib.EntityManager.prototype = Object.create(GameLib.API.EntityManager.prototype);
|
||||
|
@ -104,6 +106,54 @@ GameLib.EntityManager.prototype.createEntity = function(name) {
|
|||
return entity;
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns an entity by ID or null
|
||||
* @param id
|
||||
* @returns {*}
|
||||
*/
|
||||
GameLib.EntityManager.prototype.findEntityById = function(id) {
|
||||
|
||||
return this.entities.reduce(
|
||||
function(result, entity){
|
||||
|
||||
if (entity.id === id) {
|
||||
result = entity;
|
||||
}
|
||||
|
||||
return result;
|
||||
},
|
||||
null
|
||||
);
|
||||
};
|
||||
|
||||
GameLib.EntityManager.prototype.findHelperByObject = function(object) {
|
||||
|
||||
return this.entities.reduce(
|
||||
function(result, entity) {
|
||||
var helpers = entity.getComponents(GameLib.D3.Helper);
|
||||
var helper = helpers.reduce(
|
||||
function(helperResult, tmpHelper) {
|
||||
|
||||
if (tmpHelper.object === object) {
|
||||
helperResult = tmpHelper;
|
||||
}
|
||||
|
||||
return helperResult;
|
||||
},
|
||||
null
|
||||
);
|
||||
|
||||
if (helper) {
|
||||
result = helper;
|
||||
}
|
||||
|
||||
return result;
|
||||
},
|
||||
null
|
||||
);
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* Adds an entity to this manager
|
||||
* @param entity GameLib.Entity
|
||||
|
@ -258,6 +308,86 @@ GameLib.EntityManager.FromObjectEntityManager = function(graphics, objectEntityM
|
|||
return entityManager;
|
||||
};
|
||||
|
||||
GameLib.EntityManager.prototype.onParentSceneChange = function(data) {
|
||||
|
||||
if (data.object instanceof GameLib.D3.Mesh) {
|
||||
|
||||
/**
|
||||
* We remove the helper (if any) from the old scene and add it to the new scene
|
||||
*/
|
||||
var helper = this.findHelperByObject(data.object);
|
||||
if (helper) {
|
||||
data.originalScene.instance.remove(helper.instance);
|
||||
data.newScene.instance.add(helper.instance);
|
||||
}
|
||||
|
||||
/**
|
||||
* We remove the mesh from the old scene and add it to the new scene
|
||||
*/
|
||||
data.originalScene.removeMesh(data.object);
|
||||
data.newScene.addMesh(data.object);
|
||||
|
||||
/**
|
||||
* We inherit the parent entity of this new scene
|
||||
*/
|
||||
var originalEntity = null;
|
||||
var newEntity = null;
|
||||
|
||||
if (data.object.hasOwnProperty('parentEntity')) {
|
||||
originalEntity = data.object.parentEntity
|
||||
}
|
||||
|
||||
if (data.newScene.hasOwnProperty('parentEntity')) {
|
||||
newEntity = data.newScene.parentEntity;
|
||||
}
|
||||
|
||||
if (originalEntity && newEntity) {
|
||||
|
||||
/**
|
||||
* We also transfer the helper (as a component) to the new entity
|
||||
*/
|
||||
if (helper) {
|
||||
originalEntity.removeComponent(helper);
|
||||
newEntity.addComponent(helper);
|
||||
}
|
||||
|
||||
originalEntity.removeComponent(data.object);
|
||||
newEntity.addComponent(data.object);
|
||||
|
||||
/**
|
||||
* Now also remove the object from the GUI
|
||||
*/
|
||||
var gui = originalEntity.getFirstComponent(GameLib.GUI);
|
||||
if (gui) {
|
||||
gui.removeObject(data.object);
|
||||
gui.build(this);
|
||||
|
||||
gui = newEntity.getFirstComponent(GameLib.GUI);
|
||||
if (gui) {
|
||||
gui.addObject(data.object);
|
||||
gui.build(this);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (data.object instanceof GameLib.D3.Light) {
|
||||
console.log('implement remove light here');
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
GameLib.EntityManager.prototype.registerCallbacks = function() {
|
||||
|
||||
this.subscribe(
|
||||
GameLib.Event.PARENT_SCENE_CHANGE,
|
||||
this.onParentSceneChange
|
||||
)
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* Links object Ids to actual objects
|
||||
* @param idToObject
|
||||
|
|
|
@ -764,10 +764,10 @@ GameLib.GUI.prototype.buildSelectControl = function(folder, object, property, en
|
|||
GameLib.Event.Emit(
|
||||
GameLib.Event.PARENT_SCENE_CHANGE,
|
||||
{
|
||||
old: this.initialValue,
|
||||
current: object[property],
|
||||
originalScene: this.initialValue,
|
||||
newScene: object[property],
|
||||
object: object,
|
||||
property: property
|
||||
entityManager: entityManager
|
||||
}
|
||||
);
|
||||
} else {
|
||||
|
@ -841,13 +841,21 @@ GameLib.GUI.prototype.buildEntitySelectionControlFromArray = function(
|
|||
);
|
||||
|
||||
folder.add(object, property, options).name(property).listen().onChange(
|
||||
function(value) {
|
||||
function(entityManager) {
|
||||
return function(value) {
|
||||
|
||||
GameLib.Event.Emit(
|
||||
GameLib.Event.PARENT_ENTITY_CHANGE,
|
||||
{}
|
||||
);
|
||||
{
|
||||
originalEntity : this.initialValue,
|
||||
newEntity : entityManager.findEntityById(value),
|
||||
object : object
|
||||
}
|
||||
);
|
||||
|
||||
};
|
||||
}(entityManager)
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -884,10 +892,18 @@ GameLib.GUI.prototype.build = function(entityManager) {
|
|||
|
||||
var apiObject = object.toApiObject();
|
||||
|
||||
var folder = null;
|
||||
|
||||
try {
|
||||
var folder = this.instance.addFolder(apiObject.name);
|
||||
folder = this.instance.addFolder(apiObject.name);
|
||||
} catch (e) {
|
||||
//todo increase name count
|
||||
console.log(e.message);
|
||||
apiObject.name += GameLib.Utils.RandomId(3);
|
||||
folder = this.instance.addFolder(apiObject.name);
|
||||
}
|
||||
|
||||
if (!folder) {
|
||||
throw new Error('Could not create folder');
|
||||
}
|
||||
|
||||
var property;
|
||||
|
|
|
@ -204,8 +204,13 @@ GameLib.Utils.Raycast = function (
|
|||
* @returns {string}
|
||||
* @constructor
|
||||
*/
|
||||
GameLib.Utils.RandomId = function() {
|
||||
return Math.random().toString(36).substr(2, 10);
|
||||
GameLib.Utils.RandomId = function(length) {
|
||||
|
||||
if (GameLib.Utils.UndefinedOrNull(length)) {
|
||||
length = 10;
|
||||
}
|
||||
|
||||
return Math.random().toString(36).substr(2, length);
|
||||
};
|
||||
|
||||
GameLib.Utils.InvertWindingOrder = function(triangles) {
|
||||
|
|
Loading…
Reference in New Issue