Skip to content

Commit b010a1c

Browse files
committed
orthographic view
adjust ortho camera dist in module and added orthographic mocks adjust camera structure in jasmine test & corrected baselines
1 parent c5bdee9 commit b010a1c

14 files changed

+2968
-306
lines changed

package-lock.json

Lines changed: 13 additions & 16 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@
5757
]
5858
},
5959
"dependencies": {
60-
"3d-view": "^2.0.0",
60+
"3d-view-controls": "git://github.com/archmoj/3d-view-controls.git#fe3c77b807618c0d51f4c50a691e2af0486bfda9",
6161
"alpha-shape": "^1.0.0",
6262
"array-range": "^1.0.1",
6363
"canvas-fit": "^1.5.0",
@@ -81,7 +81,7 @@
8181
"gl-mat4": "^1.2.0",
8282
"gl-mesh3d": "^2.0.7",
8383
"gl-plot2d": "^1.4.2",
84-
"gl-plot3d": "^1.6.3",
84+
"gl-plot3d": "git://github.com/gl-vis/gl-plot3d.git#33d5169a62d9b903a8f3a4607f4dae726c4bb57b",
8585
"gl-pointcloud2d": "^1.0.2",
8686
"gl-scatter3d": "^1.1.6",
8787
"gl-select-box": "^1.0.3",

src/plots/gl3d/camera.js

Lines changed: 0 additions & 270 deletions
Original file line numberDiff line numberDiff line change
@@ -5,273 +5,3 @@
55
* This source code is licensed under the MIT license found in the
66
* LICENSE file in the root directory of this source tree.
77
*/
8-
9-
'use strict';
10-
11-
module.exports = createCamera;
12-
13-
var now = require('right-now');
14-
var createView = require('3d-view');
15-
var mouseChange = require('mouse-change');
16-
var mouseWheel = require('mouse-wheel');
17-
var mouseOffset = require('mouse-event-offset');
18-
var supportsPassive = require('has-passive-events');
19-
20-
function createCamera(element, options) {
21-
element = element || document.body;
22-
options = options || {};
23-
24-
var limits = [ 0.01, Infinity ];
25-
if('distanceLimits' in options) {
26-
limits[0] = options.distanceLimits[0];
27-
limits[1] = options.distanceLimits[1];
28-
}
29-
if('zoomMin' in options) {
30-
limits[0] = options.zoomMin;
31-
}
32-
if('zoomMax' in options) {
33-
limits[1] = options.zoomMax;
34-
}
35-
36-
var view = createView({
37-
center: options.center || [0, 0, 0],
38-
up: options.up || [0, 1, 0],
39-
eye: options.eye || [0, 0, 10],
40-
mode: options.mode || 'orbit',
41-
distanceLimits: limits
42-
});
43-
44-
var pmatrix = [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0];
45-
var distance = 0.0;
46-
var width = element.clientWidth;
47-
var height = element.clientHeight;
48-
49-
var camera = {
50-
keyBindingMode: 'rotate',
51-
enableWheel: true,
52-
view: view,
53-
element: element,
54-
delay: options.delay || 16,
55-
rotateSpeed: options.rotateSpeed || 1,
56-
zoomSpeed: options.zoomSpeed || 1,
57-
translateSpeed: options.translateSpeed || 1,
58-
flipX: !!options.flipX,
59-
flipY: !!options.flipY,
60-
modes: view.modes,
61-
tick: function() {
62-
var t = now();
63-
var delay = this.delay;
64-
var ctime = t - 2 * delay;
65-
view.idle(t - delay);
66-
view.recalcMatrix(ctime);
67-
view.flush(t - (100 + delay * 2));
68-
var allEqual = true;
69-
var matrix = view.computedMatrix;
70-
for(var i = 0; i < 16; ++i) {
71-
allEqual = allEqual && (pmatrix[i] === matrix[i]);
72-
pmatrix[i] = matrix[i];
73-
}
74-
var sizeChanged =
75-
element.clientWidth === width &&
76-
element.clientHeight === height;
77-
width = element.clientWidth;
78-
height = element.clientHeight;
79-
if(allEqual) return !sizeChanged;
80-
distance = Math.exp(view.computedRadius[0]);
81-
return true;
82-
},
83-
lookAt: function(center, eye, up) {
84-
view.lookAt(view.lastT(), center, eye, up);
85-
},
86-
rotate: function(pitch, yaw, roll) {
87-
view.rotate(view.lastT(), pitch, yaw, roll);
88-
},
89-
pan: function(dx, dy, dz) {
90-
view.pan(view.lastT(), dx, dy, dz);
91-
},
92-
translate: function(dx, dy, dz) {
93-
view.translate(view.lastT(), dx, dy, dz);
94-
}
95-
};
96-
97-
Object.defineProperties(camera, {
98-
matrix: {
99-
get: function() {
100-
return view.computedMatrix;
101-
},
102-
set: function(mat) {
103-
view.setMatrix(view.lastT(), mat);
104-
return view.computedMatrix;
105-
},
106-
enumerable: true
107-
},
108-
mode: {
109-
get: function() {
110-
return view.getMode();
111-
},
112-
set: function(mode) {
113-
var curUp = view.computedUp.slice();
114-
var curEye = view.computedEye.slice();
115-
var curCenter = view.computedCenter.slice();
116-
view.setMode(mode);
117-
if(mode === 'turntable') {
118-
// Hacky time warping stuff to generate smooth animation
119-
var t0 = now();
120-
view._active.lookAt(t0, curEye, curCenter, curUp);
121-
view._active.lookAt(t0 + 500, curEye, curCenter, [0, 0, 1]);
122-
view._active.flush(t0);
123-
}
124-
return view.getMode();
125-
},
126-
enumerable: true
127-
},
128-
center: {
129-
get: function() {
130-
return view.computedCenter;
131-
},
132-
set: function(ncenter) {
133-
view.lookAt(view.lastT(), null, ncenter);
134-
return view.computedCenter;
135-
},
136-
enumerable: true
137-
},
138-
eye: {
139-
get: function() {
140-
return view.computedEye;
141-
},
142-
set: function(neye) {
143-
view.lookAt(view.lastT(), neye);
144-
return view.computedEye;
145-
},
146-
enumerable: true
147-
},
148-
up: {
149-
get: function() {
150-
return view.computedUp;
151-
},
152-
set: function(nup) {
153-
view.lookAt(view.lastT(), null, null, nup);
154-
return view.computedUp;
155-
},
156-
enumerable: true
157-
},
158-
distance: {
159-
get: function() {
160-
return distance;
161-
},
162-
set: function(d) {
163-
view.setDistance(view.lastT(), d);
164-
return d;
165-
},
166-
enumerable: true
167-
},
168-
distanceLimits: {
169-
get: function() {
170-
return view.getDistanceLimits(limits);
171-
},
172-
set: function(v) {
173-
view.setDistanceLimits(v);
174-
return v;
175-
},
176-
enumerable: true
177-
}
178-
});
179-
180-
element.addEventListener('contextmenu', function(ev) {
181-
ev.preventDefault();
182-
return false;
183-
});
184-
185-
var lastX = 0;
186-
var lastY = 0;
187-
var lastMods = {shift: false, control: false, alt: false, meta: false};
188-
camera.mouseListener = mouseChange(element, handleInteraction);
189-
190-
// enable simple touch interactions
191-
element.addEventListener('touchstart', function(ev) {
192-
var xy = mouseOffset(ev.changedTouches[0], element);
193-
handleInteraction(0, xy[0], xy[1], lastMods);
194-
handleInteraction(1, xy[0], xy[1], lastMods);
195-
196-
ev.preventDefault();
197-
}, supportsPassive ? {passive: false} : false);
198-
element.addEventListener('touchmove', function(ev) {
199-
var xy = mouseOffset(ev.changedTouches[0], element);
200-
handleInteraction(1, xy[0], xy[1], lastMods);
201-
202-
ev.preventDefault();
203-
}, supportsPassive ? {passive: false} : false);
204-
element.addEventListener('touchend', function(ev) {
205-
handleInteraction(0, lastX, lastY, lastMods);
206-
207-
ev.preventDefault();
208-
}, supportsPassive ? {passive: false} : false);
209-
210-
function handleInteraction(buttons, x, y, mods) {
211-
var keyBindingMode = camera.keyBindingMode;
212-
213-
if(keyBindingMode === false) return;
214-
215-
var rotate = keyBindingMode === 'rotate';
216-
var pan = keyBindingMode === 'pan';
217-
var zoom = keyBindingMode === 'zoom';
218-
219-
var ctrl = !!mods.control;
220-
var alt = !!mods.alt;
221-
var shift = !!mods.shift;
222-
var left = !!(buttons & 1);
223-
var right = !!(buttons & 2);
224-
var middle = !!(buttons & 4);
225-
226-
var scale = 1.0 / element.clientHeight;
227-
var dx = scale * (x - lastX);
228-
var dy = scale * (y - lastY);
229-
230-
var flipX = camera.flipX ? 1 : -1;
231-
var flipY = camera.flipY ? 1 : -1;
232-
233-
var t = now();
234-
235-
var drot = Math.PI * camera.rotateSpeed;
236-
237-
if((rotate && left && !ctrl && !alt && !shift) || (left && !ctrl && !alt && shift)) {
238-
// Rotate
239-
view.rotate(t, flipX * drot * dx, -flipY * drot * dy, 0);
240-
}
241-
242-
if((pan && left && !ctrl && !alt && !shift) || right || (left && ctrl && !alt && !shift)) {
243-
// Pan
244-
view.pan(t, -camera.translateSpeed * dx * distance, camera.translateSpeed * dy * distance, 0);
245-
}
246-
247-
if((zoom && left && !ctrl && !alt && !shift) || middle || (left && !ctrl && alt && !shift)) {
248-
// Zoom
249-
var kzoom = -camera.zoomSpeed * dy / window.innerHeight * (t - view.lastT()) * 100;
250-
view.pan(t, 0, 0, distance * (Math.exp(kzoom) - 1));
251-
}
252-
253-
lastX = x;
254-
lastY = y;
255-
lastMods = mods;
256-
257-
return true;
258-
}
259-
260-
camera.wheelListener = mouseWheel(element, function(dx, dy) {
261-
// TODO remove now that we can disable scroll via scrollZoom?
262-
if(camera.keyBindingMode === false) return;
263-
if(!camera.enableWheel) return;
264-
265-
var flipX = camera.flipX ? 1 : -1;
266-
var flipY = camera.flipY ? 1 : -1;
267-
var t = now();
268-
if(Math.abs(dx) > Math.abs(dy)) {
269-
view.rotate(t, 0, 0, -dx * flipX * Math.PI * camera.rotateSpeed / window.innerWidth);
270-
} else {
271-
var kzoom = -camera.zoomSpeed * flipY * dy / window.innerHeight * (t - view.lastT()) / 20.0;
272-
view.pan(t, 0, 0, distance * (Math.exp(kzoom) - 1));
273-
}
274-
}, true);
275-
276-
return camera;
277-
}

src/plots/gl3d/index.js

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,7 @@ exports.plot = function plotGl3d(gd) {
4848
var sceneId = sceneIds[i];
4949
var fullSceneData = getSubplotData(fullData, GL3D, sceneId);
5050
var sceneLayout = fullLayout[sceneId];
51+
var camera = sceneLayout.camera;
5152
var scene = sceneLayout._scene;
5253

5354
if(!scene) {
@@ -56,7 +57,8 @@ exports.plot = function plotGl3d(gd) {
5657
graphDiv: gd,
5758
container: gd.querySelector('.gl-container'),
5859
staticPlot: gd._context.staticPlot,
59-
plotGlPixelRatio: gd._context.plotGlPixelRatio
60+
plotGlPixelRatio: gd._context.plotGlPixelRatio,
61+
camera: camera
6062
},
6163
fullLayout
6264
);

src/plots/gl3d/layout/defaults.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ function handleGl3dDefaults(sceneLayoutIn, sceneLayoutOut, coerce, opts) {
6868
coerce('camera.' + cameraKeys[j] + '.y');
6969
coerce('camera.' + cameraKeys[j] + '.z');
7070
}
71+
coerce('camera.ortho');
7172

7273
/*
7374
* coerce to positive number (min 0) but also do not accept 0 (>0 not >=0)

src/plots/gl3d/layout/layout_attributes.js

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,16 @@ module.exports = {
7272
'of this scene.'
7373
].join(' ')
7474
}),
75+
ortho: extendFlat({
76+
valType: 'boolean',
77+
role: 'info',
78+
dflt: false,
79+
editType: 'camera',
80+
description: [
81+
'Enable/disable orthographic camera.',
82+
'Default is perspective.'
83+
].join(' ')
84+
}),
7585
editType: 'camera'
7686
},
7787
domain: domainAttrs({name: 'scene', editType: 'plot'}),

0 commit comments

Comments
 (0)