agent def + windows fixes + 2d view + 3d view
This commit is contained in:
@@ -37,7 +37,7 @@ body[eicapp] {
|
||||
grid-template-columns: min-content auto;
|
||||
min-height: 100vh;
|
||||
box-sizing: border-box;
|
||||
background: repeating-linear-gradient( -45deg, #000, #555 10px, #000 10px, #555 20px );
|
||||
background: repeating-linear-gradient( -45deg, #000, #333 10px, #000 10px, #333 20px );
|
||||
}
|
||||
|
||||
[eicapp] [eicapptoolbar] {
|
||||
@@ -95,17 +95,20 @@ body[eicapp] {
|
||||
bottom: auto;
|
||||
overflow: hidden;
|
||||
z-index: 2;
|
||||
display: block;
|
||||
grid-template-rows: min-content 1fr;
|
||||
max-height: 90vh;
|
||||
max-width: 90vw;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
[eicapp] .app-workspace .window.active {
|
||||
z-index: 3;
|
||||
background: var(--app-color-primary);
|
||||
border-radius: .3rem;
|
||||
}
|
||||
[eicapp] .app-workspace .window > header { display: grid; }
|
||||
[eicapp] .app-workspace .window > header {
|
||||
flex: 0 0 auto;
|
||||
}
|
||||
[eicapp] .app-workspace .window > header h1 {
|
||||
padding: var(--eicui-base-spacing-xs);
|
||||
color: var(--app-color-white);
|
||||
@@ -125,12 +128,13 @@ body[eicapp] {
|
||||
[eicapp] .app-workspace .window > header .controls button.expand { display: inline-flex; }
|
||||
[eicapp] .app-workspace .window > header .controls button.shrink { display: none; }
|
||||
[eicapp] .app-workspace .window > section {
|
||||
padding: var(--eicui-base-spacing-xs) var(--eicui-base-spacing-s);
|
||||
/*background: var(--app-bg-color);*/
|
||||
padding: var(--eicui-base-spacing-2xs) var(--eicui-base-spacing-2xs);
|
||||
cursor: default;
|
||||
margin: 0;
|
||||
overflow: auto;
|
||||
transition: all 0.5s;
|
||||
flex: 1 1 auto;
|
||||
|
||||
}
|
||||
[eicapp] .app-workspace .window[device="tablet"] > section {
|
||||
padding: 0;
|
||||
@@ -142,8 +146,8 @@ body[eicapp] {
|
||||
box-shadow: none;
|
||||
width: 100%;
|
||||
max-width:none;
|
||||
padding: 0 var(--eicui-base-spacing-2xs) var(--eicui-base-spacing-3xl) var(--eicui-base-spacing-2xs);
|
||||
background: repeating-linear-gradient( -45deg, #000, #555 10px, #000 10px, #555 20px );
|
||||
padding: 0 var(--eicui-base-spacing-2xs) 0 var(--eicui-base-spacing-2xs);
|
||||
background: repeating-linear-gradient( -45deg, #000, #333 10px, #000 10px, #333 20px );
|
||||
cursor: default;
|
||||
margin: 0;
|
||||
overflow: visible;
|
||||
|
||||
@@ -17,12 +17,37 @@ class DashboardsController extends EICController {
|
||||
this.loadWindow(
|
||||
'dashboards/MainDashboardView',
|
||||
{
|
||||
title: 'Main dashboard',
|
||||
title: '3D view',
|
||||
static: true,
|
||||
expanded: true
|
||||
expanded: false,
|
||||
windowStyle:{
|
||||
width: '800px',
|
||||
height: '600px',
|
||||
left: '50px',
|
||||
top: '100px',
|
||||
}
|
||||
},
|
||||
{
|
||||
models: models
|
||||
models: models,
|
||||
camName: 'persp1'
|
||||
}
|
||||
)
|
||||
this.loadWindow(
|
||||
'dashboards/MainDashboardView',
|
||||
{
|
||||
title: '2D View',
|
||||
static: true,
|
||||
expanded: false,
|
||||
windowStyle:{
|
||||
width: '600px',
|
||||
height: '450px',
|
||||
right:'10px',
|
||||
top:'100px',
|
||||
}
|
||||
},
|
||||
{
|
||||
models: models,
|
||||
camName: 'cam2Dtop'
|
||||
}
|
||||
)
|
||||
}
|
||||
|
||||
@@ -103,6 +103,11 @@ class EICController extends Controller {
|
||||
<section></section>
|
||||
</div>`);
|
||||
if(options.expanded) content.setAttribute('expanded','');
|
||||
if(options.windowStyle){
|
||||
for(const k in options.windowStyle){
|
||||
content.style[k] = options.windowStyle[k]
|
||||
}
|
||||
}
|
||||
|
||||
let container = content.querySelector('section');
|
||||
container.innerHTML = Controller.processTemplate(options.name, html, data);
|
||||
@@ -291,7 +296,8 @@ class EICController extends Controller {
|
||||
}
|
||||
|
||||
attach(content) {
|
||||
ui.show(content.view.el,!content.expanded ? 'grid': 'block');
|
||||
//ui.show(content.view.el,!content.expanded ? 'grid': 'block');
|
||||
ui.show(content.view.el, 'flex');
|
||||
content.visible = true;
|
||||
}
|
||||
|
||||
|
||||
+85
-55
@@ -5,79 +5,109 @@ export class Threetobus{
|
||||
|
||||
constructor(canvasEl){
|
||||
this.canvasEl = canvasEl
|
||||
this.cameras = {}
|
||||
}
|
||||
|
||||
init(){
|
||||
initScene(){
|
||||
// Scene
|
||||
this.scene = new THREE.Scene()
|
||||
//scene.background = new THREE.Color(0x202080)
|
||||
this.scene = new THREE.Scene()
|
||||
|
||||
// Camera
|
||||
this.camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000)
|
||||
this.camera.position.set(3, 3, 5)
|
||||
// Cameras
|
||||
this.cameras.persp1 = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000)
|
||||
this.cameras.persp1.position.set(3, 3, 5)
|
||||
const aspect = window.innerWidth / window.innerHeight
|
||||
const frustumSize = 10
|
||||
this.cameras.cam2Dtop = new THREE.OrthographicCamera(
|
||||
-frustumSize * aspect / 2,
|
||||
frustumSize * aspect / 2,
|
||||
frustumSize / 2,
|
||||
-frustumSize / 2,
|
||||
0.1,
|
||||
1000
|
||||
)
|
||||
this.cameras.cam2Dtop.position.set(0, 100, 0)
|
||||
this.cameras.cam2Dtop.lookAt(0, 0, 0)
|
||||
//this.camera = this.cameras.persp1
|
||||
|
||||
// Renderer
|
||||
this.renderer = new THREE.WebGLRenderer({ antialias: true, canvas: this.canvasEl })
|
||||
// Lights
|
||||
const light = new THREE.DirectionalLight(0xffffff, 1)
|
||||
light.position.set(5, 5, 5)
|
||||
light.intensity = 2
|
||||
this.scene.add(light)
|
||||
this.scene.add(new THREE.AmbientLight(0xffffff, 0.4))
|
||||
|
||||
//renderer.setSize(window.innerWidth, window.innerHeight)
|
||||
// Renderer
|
||||
this.renderer = new THREE.WebGLRenderer({ antialias: true, canvas: this.canvasEl })
|
||||
|
||||
// Cube
|
||||
const geometry = new THREE.BoxGeometry()
|
||||
const material = new THREE.MeshStandardMaterial({ color: 'red' })
|
||||
this.cube = new THREE.Mesh(geometry, material)
|
||||
this.scene.add(this.cube)
|
||||
this.cube.position.x+=2
|
||||
}
|
||||
|
||||
startRendering(){
|
||||
//controls
|
||||
this.controls = new OrbitControls(this.camera, this.renderer.domElement)
|
||||
//this.renderer.render(this.scene, this.camera)
|
||||
|
||||
// Light
|
||||
const light = new THREE.DirectionalLight(0xffffff, 1)
|
||||
light.position.set(5, 5, 5)
|
||||
light.intensity = 2
|
||||
this.scene.add(light)
|
||||
this.scene.add(new THREE.AmbientLight(0xffffff, 0.4))
|
||||
window.addEventListener('resize', () => {
|
||||
this.camera.aspect = window.innerWidth / window.innerHeight
|
||||
this.camera.updateProjectionMatrix()
|
||||
renderer.setSize(window.innerWidth, window.innerHeight)
|
||||
})
|
||||
|
||||
this.controls = new OrbitControls(this.camera, this.renderer.domElement)
|
||||
this.renderer.render(this.scene, this.camera)
|
||||
this.render()
|
||||
}
|
||||
|
||||
window.addEventListener('resize', () => {
|
||||
this.camera.aspect = window.innerWidth / window.innerHeight
|
||||
this.camera.updateProjectionMatrix()
|
||||
renderer.setSize(window.innerWidth, window.innerHeight)
|
||||
changeCamera(camName){
|
||||
if(camName in this.cameras){
|
||||
this.camera = this.cameras[camName]
|
||||
}
|
||||
}
|
||||
|
||||
buildFromJSON(desc){
|
||||
let obj
|
||||
if(desc.type === 'Mesh') {
|
||||
const geom = new THREE[desc.geometry.type](...(desc.geometry.args || []))
|
||||
const mat = new THREE[desc.material.type]( desc.material.color ? { color: desc.material.color } : {} )
|
||||
obj = new THREE.Mesh(geom, mat)
|
||||
} else if(desc.type === 'Group') {
|
||||
obj = new THREE.Group()
|
||||
} else {
|
||||
throw new Error("Unknown type: " + desc.type)
|
||||
}
|
||||
|
||||
// Apply transforms
|
||||
if(desc.position) obj.position.set(...desc.position)
|
||||
if(desc.rotation) obj.rotation.set(...desc.rotation)
|
||||
if(desc.scale) obj.scale.set(...desc.scale)
|
||||
|
||||
// Recursively add children
|
||||
if(desc.children) {
|
||||
desc.children.forEach(childDesc => {
|
||||
obj.add(this.buildFromJSON(childDesc))
|
||||
})
|
||||
this.animate()
|
||||
|
||||
this._render()
|
||||
|
||||
}
|
||||
|
||||
_resizeRendererToDisplaySize() {
|
||||
const canvas = this.renderer.domElement
|
||||
const width = canvas.clientWidth
|
||||
const height = canvas.clientHeight
|
||||
if (canvas.width !== width || canvas.height !== height) {
|
||||
this.renderer.setSize(width, height, false)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
return obj
|
||||
}
|
||||
|
||||
_render() {
|
||||
if (this._resizeRendererToDisplaySize()) {
|
||||
this.camera.aspect = this.renderer.domElement.clientWidth / this.renderer.domElement.clientHeight
|
||||
this.camera.updateProjectionMatrix()
|
||||
}
|
||||
this.renderer.render(this.scene, this.camera)
|
||||
requestAnimationFrame(this._render.bind(this))
|
||||
_resizeRendererToDisplaySize() {
|
||||
const canvas = this.renderer.domElement
|
||||
const width = canvas.clientWidth
|
||||
const height = canvas.clientHeight
|
||||
if (canvas.width !== width || canvas.height !== height) {
|
||||
this.renderer.setSize(width, height, false)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
|
||||
animate() {
|
||||
requestAnimationFrame(this.animate.bind(this))
|
||||
this.cube.rotation.x += 0.01
|
||||
this.cube.rotation.y += 0.01
|
||||
this.controls.update()
|
||||
this.renderer.render(this.scene, this.camera)
|
||||
render() {
|
||||
if(this._resizeRendererToDisplaySize()) {
|
||||
this.camera.aspect = this.renderer.domElement.clientWidth / this.renderer.domElement.clientHeight
|
||||
this.camera.updateProjectionMatrix()
|
||||
}
|
||||
this.renderer.render(this.scene, this.camera)
|
||||
requestAnimationFrame(this.render.bind(this))
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -1,23 +1,33 @@
|
||||
class MainDashboardView extends EICDomContent {
|
||||
|
||||
|
||||
//TODO should come from the API, from some sprites lib. (allow switching representations)
|
||||
agentTypes = {
|
||||
molecule1:{
|
||||
type: 'circle',
|
||||
attrs: {
|
||||
r: 10,
|
||||
fill: '#BFB',
|
||||
stroke: "#0A0",
|
||||
strokeWidth: 2,
|
||||
}
|
||||
"type": "Mesh",
|
||||
"geometry": { "type": "BoxGeometry", "args": [1, 1, 1] },
|
||||
"material": { "type": "MeshStandardMaterial", "color": "orange" },
|
||||
"children": [
|
||||
{
|
||||
"type": "Mesh",
|
||||
"geometry": { "type": "SphereGeometry", "args": [0.3, 16, 16] },
|
||||
"material": { "type": "MeshStandardMaterial", "color": "blue" },
|
||||
"position": [0, 0.5, 0]
|
||||
}
|
||||
]
|
||||
},
|
||||
molecule2:{
|
||||
type: 'circle',
|
||||
attrs: {
|
||||
r: 10,
|
||||
fill: '#BBF',
|
||||
stroke: "#00A",
|
||||
strokeWidth: 2,
|
||||
}
|
||||
"type": "Mesh",
|
||||
"geometry": { "type": "SphereGeometry", "args": [1, 1, 1] },
|
||||
"material": { "type": "MeshStandardMaterial", "color": "green" },
|
||||
"children": [
|
||||
{
|
||||
"type": "Mesh",
|
||||
"geometry": { "type": "SphereGeometry", "args": [0.3, 16, 16] },
|
||||
"material": { "type": "MeshStandardMaterial", "color": "red" },
|
||||
"position": [0, 1, 0]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
}
|
||||
@@ -25,9 +35,18 @@ class MainDashboardView extends EICDomContent {
|
||||
constructor() {
|
||||
super()
|
||||
Object.assign(this, app.helpers.activeAttributes)
|
||||
//this.tileMarkup = app.Assets.Store.html['/app/assets/html/mailing/tile.html']
|
||||
}
|
||||
|
||||
DOMContentFocused(options) {
|
||||
// Avoid 2nd refesh on DomContentLoaded
|
||||
if(this.wasBlured){
|
||||
//this.refreshyoustuff()
|
||||
}
|
||||
this.wasBlured = false
|
||||
}
|
||||
|
||||
DOMContentBlured(options) { this.wasBlured = true }
|
||||
|
||||
DOMContentLoaded(options) {
|
||||
for(let model in options.models) this[model] = options.models[model]
|
||||
const components = ui.eicfy(this.el)
|
||||
@@ -35,30 +54,16 @@ class MainDashboardView extends EICDomContent {
|
||||
this.setupRefs(components)
|
||||
|
||||
this.ttb = new app.LoadedModules.Threetobus(this.outputs.paper43)
|
||||
this.ttb.init()
|
||||
this.ttb.initScene()
|
||||
this.ttb.changeCamera(options.camName)
|
||||
this.ttb.startRendering()
|
||||
|
||||
const m1 = this.ttb.buildFromJSON(this.agentTypes.molecule1)
|
||||
m1.name = 'toto'
|
||||
this.ttb.scene.add(m1)
|
||||
}
|
||||
|
||||
DOMContentFocused(options) {
|
||||
// Avoid 2nd refesh on DomContentLoaded
|
||||
if(this.wasBlured){
|
||||
//this.refreshSearch()
|
||||
}
|
||||
this.wasBlured = false
|
||||
}
|
||||
|
||||
DOMContentBlured(options) { this.wasBlured = true }
|
||||
|
||||
createAgent(agentType, id, x, y){
|
||||
if(!Object.keys(this.agentTypes).includes(agentType)) return
|
||||
this.agentTypes[agentType]
|
||||
const svgAgent = this.snaptobus.snap[this.agentTypes[agentType].type]().attr(this.agentTypes[agentType].attrs)
|
||||
svgAgent.attr({
|
||||
id: id,
|
||||
cx: x,
|
||||
cy:y,
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user