Skip to content

Commit

Permalink
Move the edit menu logic to uiInit
Browse files Browse the repository at this point in the history
Make context the first argument of operation objects
Add Paste operation to edit menu when opening the context menu on a blank area of the map (close #2508)
  • Loading branch information
quincylvania committed May 14, 2020
1 parent c939924 commit db9eed2
Show file tree
Hide file tree
Showing 32 changed files with 256 additions and 148 deletions.
9 changes: 9 additions & 0 deletions data/core.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,15 @@ en:
annotation:
single: Copied a feature.
multiple: "Copied {n} features."
paste:
title: Paste
description:
single: "Add a duplicate {feature} here."
multiple: "Add {n} duplicate features here."
annotation:
single: Pasted a feature.
multiple: "Pasted {n} features."
nothing_copied: No features have been copied.
circularize:
title: Circularize
description:
Expand Down
12 changes: 12 additions & 0 deletions dist/locales/en.json
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,18 @@
"multiple": "Copied {n} features."
}
},
"paste": {
"title": "Paste",
"description": {
"single": "Add a duplicate {feature} here.",
"multiple": "Add {n} duplicate features here."
},
"annotation": {
"single": "Pasted a feature.",
"multiple": "Pasted {n} features."
},
"nothing_copied": "No features have been copied."
},
"circularize": {
"title": "Circularize",
"description": {
Expand Down
8 changes: 4 additions & 4 deletions modules/behavior/paste.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import { geoExtent, geoPointInPolygon, geoVecSubtract } from '../geo';
import { modeMove } from '../modes/move';
import { uiCmd } from '../ui/cmd';


// see also `operationPaste`
export function behaviorPaste(context) {

function doPaste() {
Expand All @@ -22,13 +22,13 @@ export function behaviorPaste(context) {

if (!geoPointInPolygon(mouse, viewport)) return;

var extent = geoExtent();
var oldIDs = context.copyIDs();
if (!oldIDs.length) return;

var extent = geoExtent();
var oldGraph = context.copyGraph();
var newIDs = [];

if (!oldIDs.length) return;

var action = actionCopyEntities(oldIDs, oldGraph);
context.perform(action);

Expand Down
27 changes: 9 additions & 18 deletions modules/behavior/select.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import { event as d3_event, select as d3_select } from 'd3-selection';

import { geoVecLength } from '../geo';
import { prefs } from '../core/preferences';
import { modeBrowse } from '../modes/browse';
import { modeSelect } from '../modes/select';
import { modeSelectData } from '../modes/select_data';
Expand All @@ -12,8 +11,6 @@ import { utilFastMouse } from '../util/util';


export function behaviorSelect(context) {
// legacy option to show menu on every click
var _alwaysShowMenu = +prefs('edit-menu-show-always') === 1;
var _tolerancePx = 4;
var _lastPointerEvent = null;
var _showMenu = false;
Expand All @@ -35,7 +32,7 @@ export function behaviorSelect(context) {
function keydown() {

if (d3_event.keyCode === 32) {
// don't react to spacebar events during text input
// don't react to spacebar events during text input
var activeNode = document.activeElement;
if (activeNode && new Set(['INPUT', 'TEXTAREA']).has(activeNode.nodeName)) return;
}
Expand Down Expand Up @@ -80,7 +77,6 @@ export function behaviorSelect(context) {
} else if (d3_event.keyCode === 32) { // spacebar
d3_event.preventDefault();
_lastInteractionType = 'spacebar';
_showMenu = _alwaysShowMenu;
click();
}
}
Expand All @@ -98,8 +94,6 @@ export function behaviorSelect(context) {

d3_select(window)
.on(_pointerPrefix + 'up.select', pointerup, true);

_showMenu = _alwaysShowMenu;
}


Expand Down Expand Up @@ -176,6 +170,7 @@ export function behaviorSelect(context) {
if (entity) datum = entity;

if (datum && datum.type === 'midpoint') {
// treat targeting midpoints as if targeting the parent way
datum = datum.parents[0];
}

Expand All @@ -187,36 +182,27 @@ export function behaviorSelect(context) {
context.selectedErrorID(null);

if (!isMultiselect) {
if (selectedIDs.length > 1 && (_showMenu && !_alwaysShowMenu)) {
// multiple things already selected, just show the menu...
mode.reselect().showMenu(point, _lastInteractionType);
} else {
if (selectedIDs.length <= 1 || !_showMenu) {
// always enter modeSelect even if the entity is already
// selected since listeners may expect `context.enter` events,
// e.g. in the walkthrough
newMode = modeSelect(context, [datum.id]);
context.enter(newMode);
if (_showMenu) newMode.showMenu(point, _lastInteractionType);
}

} else {
if (selectedIDs.indexOf(datum.id) !== -1) {
// clicked entity is already in the selectedIDs list..
if (_showMenu && !_alwaysShowMenu) {
// don't deselect clicked entity, just show the menu.
mode.reselect().showMenu(point, _lastInteractionType);
} else {
if (!_showMenu) {
// deselect clicked entity, then reenter select mode or return to browse mode..
selectedIDs = selectedIDs.filter(function(id) { return id !== datum.id; });
context.enter(selectedIDs.length ? modeSelect(context, selectedIDs) : modeBrowse(context));
}
} else {

// clicked entity is not in the selected list, add it..
selectedIDs = selectedIDs.concat([datum.id]);
newMode = modeSelect(context, selectedIDs);
context.enter(newMode);
if (_showMenu) newMode.showMenu(point, _lastInteractionType);
}
}

Expand All @@ -243,6 +229,11 @@ export function behaviorSelect(context) {
}
}

context.ui().closeEditMenu();

// always request to show the edit menu in case the mode needs it
if (_showMenu) context.ui().showEditMenu(point, _lastInteractionType);

resetProperties();
}

Expand Down
6 changes: 6 additions & 0 deletions modules/modes/browse.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import { behaviorSelect } from '../behavior/select';
import { modeDragNode } from './drag_node';
import { modeDragNote } from './drag_note';

import { operationPaste } from '../operations/paste';

export function modeBrowse(context) {
var mode = {
Expand Down Expand Up @@ -60,5 +61,10 @@ export function modeBrowse(context) {
};


mode.operations = function() {
return [operationPaste(context)];
};


return mode;
}
12 changes: 6 additions & 6 deletions modules/modes/move.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,12 @@ export function modeMove(context, entityIDs, baseGraph) {
var keybinding = utilKeybinding('move');
var behaviors = [
behaviorEdit(context),
operationCircularize(entityIDs, context).behavior,
operationDelete(entityIDs, context).behavior,
operationOrthogonalize(entityIDs, context).behavior,
operationReflectLong(entityIDs, context).behavior,
operationReflectShort(entityIDs, context).behavior,
operationRotate(entityIDs, context).behavior
operationCircularize(context, entityIDs).behavior,
operationDelete(context, entityIDs).behavior,
operationOrthogonalize(context, entityIDs).behavior,
operationReflectLong(context, entityIDs).behavior,
operationReflectShort(context, entityIDs).behavior,
operationRotate(context, entityIDs).behavior
];
var annotation = entityIDs.length === 1 ?
t('operations.move.annotation.' + context.graph().geometry(entityIDs[0])) :
Expand Down
12 changes: 6 additions & 6 deletions modules/modes/rotate.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,12 +34,12 @@ export function modeRotate(context, entityIDs) {
var keybinding = utilKeybinding('rotate');
var behaviors = [
behaviorEdit(context),
operationCircularize(entityIDs, context).behavior,
operationDelete(entityIDs, context).behavior,
operationMove(entityIDs, context).behavior,
operationOrthogonalize(entityIDs, context).behavior,
operationReflectLong(entityIDs, context).behavior,
operationReflectShort(entityIDs, context).behavior
operationCircularize(context, entityIDs).behavior,
operationDelete(context, entityIDs).behavior,
operationMove(context, entityIDs).behavior,
operationOrthogonalize(context, entityIDs).behavior,
operationReflectLong(context, entityIDs).behavior,
operationReflectShort(context, entityIDs).behavior
];
var annotation = entityIDs.length === 1 ?
t('operations.rotate.annotation.' + context.graph().geometry(entityIDs[0])) :
Expand Down
71 changes: 11 additions & 60 deletions modules/modes/select.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ import { modeDragNode } from './drag_node';
import { modeDragNote } from './drag_note';
import { osmNode, osmWay } from '../osm';
import * as Operations from '../operations/index';
import { uiEditMenu } from '../ui/edit_menu';
import { uiCmd } from '../ui/cmd';
import {
utilArrayIntersection, utilDeepMemberSelector, utilEntityOrDeepMemberSelector,
Expand Down Expand Up @@ -46,7 +45,6 @@ export function modeSelect(context, selectedIDs) {
modeDragNote(context).behavior
];
var inspector; // unused?
var _editMenu; // uiEditMenu
var _newFeature = false;
var _follow = false;

Expand Down Expand Up @@ -141,44 +139,6 @@ export function modeSelect(context, selectedIDs) {
}


function closeMenu() {
// remove any existing menu no matter how it was added
context.map().supersurface
.select('.edit-menu').remove();
}

mode.showMenu = function(anchorPoint, triggerType) {

// remove any displayed menu
closeMenu();

// disable menu if in wide selection, for example
if (!context.map().editableDataEnabled()) return;

// don't show the menu for relations alone
if (selectedIDs.every(function(id) {
return context.graph().geometry(id) === 'relation';
})) return;

var surfaceNode = context.surface().node();
if (surfaceNode.focus) { // FF doesn't support it
// focus the surface or else clicking off the menu may not trigger modeBrowse
surfaceNode.focus();
}

// don't load the menu until it's needed
if (!_editMenu) _editMenu = uiEditMenu(context);

_editMenu
.anchorLoc(anchorPoint)
.triggerType(triggerType)
.operations(operations);

// render the menu
context.map().supersurface.call(_editMenu);
};


mode.selectedIDs = function() {
return selectedIDs;
};
Expand All @@ -189,12 +149,6 @@ export function modeSelect(context, selectedIDs) {
};


mode.reselect = function() {
if (!checkSelectedIDs()) return;
return mode;
};


mode.newFeature = function(val) {
if (!arguments.length) return _newFeature;
_newFeature = val;
Expand All @@ -219,12 +173,12 @@ export function modeSelect(context, selectedIDs) {
});

operations = Object.values(Operations)
.map(function(o) { return o(selectedIDs, context); })
.map(function(o) { return o(context, selectedIDs); })
.filter(function(o) { return o.available() && o.id !== 'delete' && o.id !== 'downgrade'; });

var downgradeOperation = Operations.operationDowngrade(selectedIDs, context);
var downgradeOperation = Operations.operationDowngrade(context, selectedIDs);
// don't allow delete if downgrade is available
var lastOperation = !context.inIntro() && downgradeOperation.available() ? downgradeOperation : Operations.operationDelete(selectedIDs, context);
var lastOperation = !context.inIntro() && downgradeOperation.available() ? downgradeOperation : Operations.operationDelete(context, selectedIDs);

operations.push(lastOperation);

Expand All @@ -235,9 +189,13 @@ export function modeSelect(context, selectedIDs) {
});

// remove any displayed menu
closeMenu();
context.ui().closeEditMenu();
}

mode.operations = function() {
return operations;
};


mode.enter = function() {
if (!checkSelectedIDs()) return;
Expand Down Expand Up @@ -269,11 +227,10 @@ export function modeSelect(context, selectedIDs) {
// reselect after change in case relation members were removed or added
selectElements();
})
.on('undone.select', update)
.on('redone.select', update);
.on('undone.select', checkSelectedIDs)
.on('redone.select', checkSelectedIDs);

context.map()
.on('move.select', closeMenu)
.on('drawn.select', selectElements)
.on('crossEditableZoom.select', function() {
selectElements();
Expand Down Expand Up @@ -301,12 +258,6 @@ export function modeSelect(context, selectedIDs) {
}


function update() {
closeMenu();
checkSelectedIDs();
}


function didDoubleUp(loc) {
if (!context.map().withinEditableZoom()) return;

Expand Down Expand Up @@ -500,7 +451,7 @@ export function modeSelect(context, selectedIDs) {
d3_select(document)
.call(keybinding.unbind);

closeMenu();
context.ui().closeEditMenu();

context.history()
.on('change.select', null)
Expand Down
2 changes: 1 addition & 1 deletion modules/operations/circularize.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { behaviorOperation } from '../behavior/operation';
import { utilGetAllNodes } from '../util';


export function operationCircularize(selectedIDs, context) {
export function operationCircularize(context, selectedIDs) {
var _extent;
var _actions = selectedIDs.map(getAction).filter(Boolean);
var _amount = _actions.length === 1 ? 'single' : 'multiple';
Expand Down
2 changes: 1 addition & 1 deletion modules/operations/continue.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { behaviorOperation } from '../behavior/operation';
import { utilArrayGroupBy } from '../util';


export function operationContinue(selectedIDs, context) {
export function operationContinue(context, selectedIDs) {
var graph = context.graph();
var entities = selectedIDs.map(function(id) { return graph.entity(id); });
var geometries = Object.assign(
Expand Down
4 changes: 2 additions & 2 deletions modules/operations/copy.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { behaviorOperation } from '../behavior/operation';
import { uiCmd } from '../ui/cmd';
import { utilArrayGroupBy } from '../util';

export function operationCopy(selectedIDs, context) {
export function operationCopy(context, selectedIDs) {

function getFilteredIdsToCopy() {
return selectedIDs.filter(function(selectedID) {
Expand Down Expand Up @@ -112,7 +112,7 @@ export function operationCopy(selectedIDs, context) {
operation.annotation = function() {
return selectedIDs.length === 1 ?
t('operations.copy.annotation.single') :
t('operations.copy.annotation.multiple', { n: selectedIDs.length });
t('operations.copy.annotation.multiple', { n: selectedIDs.length.toString() });
};


Expand Down
Loading

0 comments on commit db9eed2

Please sign in to comment.