Skip to content

Implement scene.dragmode: false #1377

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Feb 15, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 9 additions & 3 deletions src/plots/gl3d/camera.js
Original file line number Diff line number Diff line change
Expand Up @@ -181,9 +181,13 @@ function createCamera(element, options) {

var lastX = 0, lastY = 0;
mouseChange(element, function(buttons, x, y, mods) {
var rotate = camera.keyBindingMode === 'rotate';
var pan = camera.keyBindingMode === 'pan';
var zoom = camera.keyBindingMode === 'zoom';
var keyBindingMode = camera.keyBindingMode;

if(keyBindingMode === false) return;

var rotate = keyBindingMode === 'rotate';
var pan = keyBindingMode === 'pan';
var zoom = keyBindingMode === 'zoom';

var ctrl = !!mods.control;
var alt = !!mods.alt;
Expand Down Expand Up @@ -226,6 +230,8 @@ function createCamera(element, options) {
});

mouseWheel(element, function(dx, dy) {
if(camera.keyBindingMode === false) return;

var flipX = camera.flipX ? 1 : -1;
var flipY = camera.flipY ? 1 : -1;
var t = now();
Expand Down
11 changes: 3 additions & 8 deletions src/plots/gl3d/layout/defaults.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@

'use strict';

var Lib = require('../../../lib');
var Color = require('../../../components/color');

var handleSubplotDefaults = require('../../subplot_defaults');
Expand All @@ -17,20 +18,14 @@ var supplyGl3dAxisLayoutDefaults = require('./axis_defaults');


module.exports = function supplyLayoutDefaults(layoutIn, layoutOut, fullData) {
var hasNon3D = (
layoutOut._has('cartesian') ||
layoutOut._has('geo') ||
layoutOut._has('gl2d') ||
layoutOut._has('pie') ||
layoutOut._has('ternary')
);
var hasNon3D = layoutOut._basePlotModules.length > 1;
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎉


// some layout-wide attribute are used in all scenes
// if 3D is the only visible plot type
function getDfltFromLayout(attr) {
if(hasNon3D) return;

var isValid = layoutAttributes[attr].values.indexOf(layoutIn[attr]) !== -1;
var isValid = Lib.validate(layoutIn[attr], layoutAttributes[attr]);
if(isValid) return layoutIn[attr];
}

Expand Down
2 changes: 1 addition & 1 deletion src/plots/gl3d/layout/layout_attributes.js
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,7 @@ module.exports = {
dragmode: {
valType: 'enumerated',
role: 'info',
values: ['orbit', 'turntable', 'zoom', 'pan'],
values: ['orbit', 'turntable', 'zoom', 'pan', false],
dflt: 'turntable',
description: [
'Determines the mode of drag interactions for this scene.'
Expand Down
2 changes: 2 additions & 0 deletions src/plots/gl3d/scene.js
Original file line number Diff line number Diff line change
Expand Up @@ -173,6 +173,8 @@ function initializeGLPlot(scene, fullLayout, canvas, gl) {
}

var relayoutCallback = function(scene) {
if(scene.fullSceneLayout.dragmode === false) return;

var update = {};
update[scene.id] = getLayoutCamera(scene.camera);
scene.saveCamera(scene.graphDiv.layout);
Expand Down
19 changes: 13 additions & 6 deletions test/jasmine/tests/gl3dlayout_test.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
var Gl3d = require('@src/plots/gl3d');
var Plots = require('@src/plots/plots');

var tinycolor = require('tinycolor2');
var Color = require('@src/components/color');
Expand All @@ -14,9 +13,7 @@ describe('Test Gl3d layout defaults', function() {
var supplyLayoutDefaults = Gl3d.supplyLayoutDefaults;

beforeEach(function() {
layoutOut = {
_has: Plots._hasPlotType
};
layoutOut = { _basePlotModules: ['gl3d'] };

// needs a scene-ref in a trace in order to be detected
fullData = [ { type: 'scatter3d', scene: 'scene' }];
Expand Down Expand Up @@ -174,8 +171,13 @@ describe('Test Gl3d layout defaults', function() {
expect(layoutOut.scene.dragmode)
.toBe('orbit', 'to user layout val if valid and 3d only');

layoutIn = { scene: {}, dragmode: 'invalid' };
supplyLayoutDefaults(layoutIn, layoutOut, fullData);
expect(layoutOut.scene.dragmode)
.toBe('turntable', 'to turntable if invalid and 3d only');

layoutIn = { scene: {}, dragmode: 'orbit' };
layoutOut._basePlotModules = [{ name: 'cartesian' }];
layoutOut._basePlotModules.push({ name: 'cartesian' });
supplyLayoutDefaults(layoutIn, layoutOut, fullData);
expect(layoutOut.scene.dragmode)
.toBe('turntable', 'to default if not 3d only');
Expand All @@ -202,8 +204,13 @@ describe('Test Gl3d layout defaults', function() {
expect(layoutOut.scene.hovermode)
.toBe(false, 'to user layout val if valid and 3d only');

layoutIn = { scene: {}, hovermode: 'invalid' };
supplyLayoutDefaults(layoutIn, layoutOut, fullData);
expect(layoutOut.scene.hovermode)
.toBe('closest', 'to closest if invalid and 3d only');

layoutIn = { scene: {}, hovermode: false };
layoutOut._basePlotModules = [{ name: 'cartesian' }];
layoutOut._basePlotModules.push({ name: 'cartesian' });
supplyLayoutDefaults(layoutIn, layoutOut, fullData);
expect(layoutOut.scene.hovermode)
.toBe('closest', 'to default if not 3d only');
Expand Down
89 changes: 66 additions & 23 deletions test/jasmine/tests/gl_plot_interact_test.js
Original file line number Diff line number Diff line change
Expand Up @@ -595,6 +595,23 @@ describe('Test gl plot interactions', function() {
});

describe('drag and wheel interactions', function() {

function scroll(target) {
return new Promise(function(resolve) {
target.dispatchEvent(new WheelEvent('wheel', {deltaY: 1}));
setTimeout(resolve, 0);
});
}

function drag(target) {
return new Promise(function(resolve) {
target.dispatchEvent(new MouseEvent('mousedown', {x: 0, y: 0}));
target.dispatchEvent(new MouseEvent('mousemove', { x: 100, y: 100}));
target.dispatchEvent(new MouseEvent('mouseup', { x: 100, y: 100}));
setTimeout(resolve, 0);
});
}

it('should update the scene camera', function(done) {
var sceneLayout = gd._fullLayout.scene,
sceneLayout2 = gd._fullLayout.scene2,
Expand All @@ -606,37 +623,63 @@ describe('Test gl plot interactions', function() {
expect(sceneLayout2.camera.eye)
.toEqual({x: 2.5, y: 2.5, z: 2.5});

// Wheel scene 1
sceneTarget.dispatchEvent(new WheelEvent('wheel', {deltaY: 1}));

// Wheel scene 2
sceneTarget2.dispatchEvent(new WheelEvent('wheel', {deltaY: 1}));

setTimeout(function() {

expect(relayoutCallback).toHaveBeenCalledTimes(2);

scroll(sceneTarget).then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

// Drag scene 1
sceneTarget.dispatchEvent(new MouseEvent('mousedown', {x: 0, y: 0}));
sceneTarget.dispatchEvent(new MouseEvent('mousemove', { x: 100, y: 100}));
sceneTarget.dispatchEvent(new MouseEvent('mouseup', { x: 100, y: 100}));
return scroll(sceneTarget2);
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

// Drag scene 2
sceneTarget2.dispatchEvent(new MouseEvent('mousedown', {x: 0, y: 0 }));
sceneTarget2.dispatchEvent(new MouseEvent('mousemove', {x: 100, y: 100}));
sceneTarget2.dispatchEvent(new MouseEvent('mouseup', {x: 100, y: 100}));
return drag(sceneTarget2);
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

setTimeout(function() {
return drag(sceneTarget);
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

expect(relayoutCallback).toHaveBeenCalledTimes(2);
return Plotly.relayout(gd, {
'scene.dragmode': false,
'scene2.dragmode': false
});
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

done();
return drag(sceneTarget);
})
.then(function() {
return drag(sceneTarget2);
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(0);

}, MODEBAR_DELAY);
return Plotly.relayout(gd, {
'scene.dragmode': 'orbit',
'scene2.dragmode': 'turntable'
});
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(1);
relayoutCallback.calls.reset();

}, MODEBAR_DELAY);
return drag(sceneTarget);
})
.then(function() {
return drag(sceneTarget2);
})
.then(function() {
expect(relayoutCallback).toHaveBeenCalledTimes(2);
})
.then(done);
});
});
});
Expand Down