Skip to content
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

Resolving Changeset already inflight error when editing with 2 layers w/in map #1427

Open
wants to merge 36 commits into
base: hoot2x
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 6 commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
960b532
working on removing changeset error when editing w/ 2 layer in map
May 7, 2019
eb95c0b
can create new &/or edit existing features then save to selected layer
May 8, 2019
ce6f3cf
updated to account for deleting and adding new layers to map
May 8, 2019
8d9ab10
working on suppressing drawing for non-active layer
May 13, 2019
fac2925
comments...
maxgrossman May 13, 2019
14cf7f2
working on inflight error
May 17, 2019
70c4f1d
can now add or edit layers /w 2 in map when proper active layer selected
May 21, 2019
7e89286
working on synchronizing all draw behaviors with new activeLayer setup
May 31, 2019
bd72f67
can now successfully upload changes made to two separate map layers
May 31, 2019
7faae87
updated datum and activeLayer id checks in select.js class
Jun 3, 2019
ae33772
updating draw methods accounting for single layer editing w new activ…
Jun 3, 2019
16e099a
behaviors added to include activeLayer settings when only 1 layer in map
Jun 4, 2019
16b2fd8
updated behaviors to prevent unwanted hovering over non-active layers
Jun 5, 2019
7a390cb
fixed active node dragging, updated highlighting, now only active layer
Jun 6, 2019
5c988cb
conditional fix for way's finishDraw methods
Jun 6, 2019
875eac7
css switching update
Jun 7, 2019
d7182f4
added activeLayer check when removing layers, updated verticies svg c…
Jun 7, 2019
87d9353
added null check, revert to defaultFolder in domMetadata
Jun 10, 2019
a741581
Merge branch 'hoot2x' into 1425
Jun 10, 2019
fd82f8f
updating svg classes for proper activeLayer checking
Jun 10, 2019
ba9dda2
removed parsing of active layer id
Jun 10, 2019
1f0ec99
updating for failing jenkins tests
Jun 10, 2019
42af31c
fix behabior test
maxgrossman Jun 12, 2019
21d8219
fix history tests
maxgrossman Jun 12, 2019
76fabe0
fix entity tests
maxgrossman Jun 12, 2019
305efc5
fix some intersection/svglines test
maxgrossman Jun 12, 2019
2b2693b
don't comment out all the tests!
maxgrossman Jun 12, 2019
7e8a0de
keep using same intersection
maxgrossman Jun 12, 2019
2f78207
update intersection regexc
maxgrossman Jun 12, 2019
73f53a4
remove timeout
maxgrossman Jun 12, 2019
0ec1437
Merge branch 'hoot2x' into 1425
Jun 14, 2019
3207b64
Merge branch '1425' of github.com:ngageoint/hootenanny-ui into 1425
Jun 14, 2019
44371a1
merged hoot2x
Jun 14, 2019
3819c61
updated sidebar to prevent page from refreshing when switching active…
Jun 17, 2019
1e3bda4
updated layer keys in layerManager
Jun 19, 2019
e2179df
removed unused vars
Jun 20, 2019
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
55 changes: 55 additions & 0 deletions css/80_app.css
Original file line number Diff line number Diff line change
Expand Up @@ -334,6 +334,15 @@ button.disabled {
border-radius: 4px 0 0 4px;
}

.select-active-layer {
width: -webkit-fill-available;
font-weight: bold;
}


.button-active {
background: #e6e3e3;
}

/* Action buttons */
button.action {
Expand All @@ -359,6 +368,52 @@ button[disabled].action:hover {
cursor: not-allowed;
}

.disable-non-active,
.disable-non-active:hover {
cursor: not-allowed;
}

.active-pulse {
border-radius: 50%;
background: #cccccc;
cursor: pointer;
box-shadow: 0 0 0 rgba(136,136,136, 0.4);
animation: active-pulse 2.5s infinite;
}
.active-pulse:hover {
animation: none;
}

@-webkit-keyframes active-pulse {
0% {
-webkit-box-shadow: 0 0 0 0 rgba(136,136,136, 0.4);
}
70% {
-webkit-box-shadow: 0 0 0 10px rgba(136,136,136, 0);
}
100% {
-webkit-box-shadow: 0 0 0 0 rgba(136,136,136, 0);
}
}
@keyframes active-pulse {
0% {
-moz-box-shadow: 0 0 0 0 rgba(136,136,136, 0.4);
box-shadow: 0 0 0 0 rgba(136,136,136, 0.4);
}
70% {
-moz-box-shadow: 0 0 0 10px rgba(136,136,136, 0);
box-shadow: 0 0 0 10px rgba(136,136,136, 0);
}
100% {
-moz-box-shadow: 0 0 0 0 rgba(136,136,136, 0);
box-shadow: 0 0 0 0 rgba(136,136,136, 0);
}
}

.no-click {
pointer-events: none;
}


/* Icons
------------------------------------------------------- */
Expand Down
26 changes: 26 additions & 0 deletions modules/Hoot/managers/api.js
Original file line number Diff line number Diff line change
Expand Up @@ -327,6 +327,32 @@ export default class API {
} );
}


/**
* Get all id's necessary to create new map features
*
* @param {Promise|array} mapId + changesetId, nodeId, wayId, relationId
Copy link
Contributor

Choose a reason for hiding this comment

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

Just a reminder, let's update this comment!

*/
getAllIds( mapId ) {
const params = {
path: `/osm/api/0.6/map/${ mapId }/startingIndex`,
method: 'GET'
};

return this.request( params )
.then( resp => {

let activeIds = {};
Copy link
Contributor

Choose a reason for hiding this comment

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

I think just return resp.data!

activeIds = resp.data;
return activeIds;
} )
.catch( err => {
const message = this.internalError( err ) || 'Unable to retrieve all map ids';

return Promise.reject( message );
} );
}

/**
* Get all layer links from the database
*
Expand Down
10 changes: 7 additions & 3 deletions modules/Hoot/managers/layerManager.js
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ export default class Layers {
this.allLayers = [];
this.loadedLayers = {};
this.hashLayers = {};
this.allIds = {};
this.recentlyUsedLayers = null;
this.mergedLayer = null;
this.mergedConflicts = null;
Expand Down Expand Up @@ -136,13 +137,16 @@ export default class Layers {

async loadLayer( params ) {
try {
let mapId = params.id,
tags = await this.hoot.api.getMapTags( mapId ),
layerExtent = await this.layerExtent( mapId );
let mapId = params.id,
tags = await this.hoot.api.getMapTags( mapId ),
layerExtent = await this.layerExtent( mapId ),
activeIds = await Hoot.api.getAllIds( mapId );

let layer = {
name: params.name,
id: params.id,
activeLayer: params.activeLayer,
activeIds: activeIds,
refType: params.refType,
color: params.color,
merged: params.merged || false,
Expand Down
7 changes: 6 additions & 1 deletion modules/Hoot/ui/sidebar/layerAdd.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

import _map from 'lodash-es/map';
import _reject from 'lodash-es/reject';
import _find from 'lodash-es/find';

import FolderTree from '../../tools/folderTree';
import SidebarForm from './sidebarForm';
Expand All @@ -18,7 +19,9 @@ export default class LayerAdd extends SidebarForm {

this.selectedLayer = {
name: null,
id: null
id: null,
activeLayer: null,
activeIds: null
};
}

Expand Down Expand Up @@ -201,6 +204,8 @@ export default class LayerAdd extends SidebarForm {
name: d ? d.name : this.selectedLayer.name,
id: d ? d.id : this.selectedLayer.id,
refType: this.formMeta.refType,
activeLayer: d ? d.activeLayer : this.selectedLayer.activeLayer,
activeIds: d ? d.activeIds : this.selectedLayer.activeIds,
color
};

Expand Down
119 changes: 118 additions & 1 deletion modules/Hoot/ui/sidebar/sidebar.js
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import {
utilQsString,
utilStringQs
} from '../../../util';
import { diff3MergeIndices } from 'node-diff3';
Copy link
Contributor

Choose a reason for hiding this comment

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

think we can remove this import!


/**
* Create the sidebar
Expand Down Expand Up @@ -126,7 +127,7 @@ export default class Sidebar {

form.controller.update();
form.loadingLayerName = null;

this.saveChanges();
this.conflateCheck();
}
} );
Expand Down Expand Up @@ -168,6 +169,122 @@ export default class Sidebar {
this.adjustSize();
}

saveChanges() {
let loadedLayers = Object.values(Hoot.layers.loadedLayers);
let selectReference = d3.selectAll('#reference');
let selectSecondary = d3.selectAll('#secondary');
if (loadedLayers.length === 2) {
let referenceActive = loadedLayers[0];
let secondaryActive = loadedLayers[1];
let changeActive = new LayerAdd();
let referenceState;
let secondaryState;


if (d3.select('#reference button.select-active-layer').empty()) {
Copy link
Contributor

Choose a reason for hiding this comment

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

wonder if the on click callback can be generalized in a single function? seems like when we click one fo the active layer buttons, we make the one we click's classes all set to active, and the other one's set to false. so a function could have 2 params, one we want to set to active, one we want to disable and just use those accordingly.

so naively, something like

function update(active, inactive) {
   //...update active button class
   //...update inactive button
}

selectReference
.append('button')
.classed('select-active-layer', true)
.text('Set as active layer')
.on('click', function () {

d3.event.preventDefault();

d3.select('#reference')
.classed('active-pulse', true);

d3.select('#secondary')
.classed('active-pulse', false);

d3.select('#reference button.select-active-layer')
.text('Active Layer')
.classed('button-active', true);

d3.select('#secondary button.select-active-layer')
.text('Set as active layer')
.classed('button-active', false);

d3.selectAll('#secondary div.controller')
.classed('disable-non-active', true);

d3.selectAll('#reference div.controller')
.classed('disable-non-active', false);

d3.selectAll('#secondary button.delete-button')
.classed('disable-non-active', true)
.classed('no-click', true);

d3.selectAll('#reference button.delete-button')
.classed('disable-non-active', false)
.classed('no-click', false);


referenceState = referenceActive;

if (secondaryState) {
secondaryState.activeLayer = false;
referenceState.activeLayer = true;
}
else {
referenceState.activeLayer = true;
}
changeActive.selectedLayer = referenceState;
});
}

if (d3.select('#secondary button.select-active-layer').empty()) {
selectSecondary
.append('button')
.classed('select-active-layer', true)
.text('Set as active layer')
.on('click', function () {

d3.event.preventDefault();
d3.select('#secondary')
.classed('active-pulse', true);

d3.select('#reference')
.classed('active-pulse', false);

d3.select('#secondary button.select-active-layer')
.text('Active Layer')
.classed('button-active', true);

d3.select('#reference button.select-active-layer')
.text('Set as active layer')
.classed('button-active', false);

d3.selectAll('#reference div.controller')
.classed('disable-non-active', true);

d3.selectAll('#secondary div.controller')
.classed('disable-non-active', false);

d3.selectAll('#reference button.delete-button')
.classed('disable-non-active', true)
.classed('no-click', true);

d3.selectAll('#secondary button.delete-button')
.classed('disable-non-active', false)
.classed('no-click', false);

secondaryState = secondaryActive;

if (referenceState) {
referenceState.activeLayer = false;
secondaryState.activeLayer = true;
}
else {
secondaryState.activeLayer = true;
}

changeActive.selectedLayer = secondaryState;

});
}
}
}

conflateCheck() {
let loadedLayers = Object.values( Hoot.layers.loadedLayers ),
addControllers = d3.selectAll( '.add-controller' );
Expand Down
33 changes: 20 additions & 13 deletions modules/behavior/draw.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,13 @@ import { behaviorHover } from './hover';
import { behaviorTail } from './tail';
import { geoChooseEdge, geoVecLength } from '../geo';
import { utilKeybinding, utilRebind } from '../util';
import _find from 'lodash-es/find';


var _usedTails = {};
var _disableSpace = false;
var _lastSpace = null;


export function behaviorDraw(context) {
var dispatch = d3_dispatch(
'move', 'click', 'clickWay', 'clickNode', 'undo', 'cancel', 'finish'
Expand Down Expand Up @@ -124,20 +124,27 @@ export function behaviorDraw(context) {
function click() {
var d = datum();
var target = d && d.properties && d.properties.entity;
var _activeLayer = _find( Hoot.layers.loadedLayers, function(a, b) { return a.activeLayer; });

// for each if/elseif statment add boolean (is _activeLayer===target.mapId)...

if (target && target.type === 'node') { // Snap to a node
dispatch.call('clickNode', this, target, d);
return;

} else if (target && target.type === 'way') { // Snap to a way
var choice = geoChooseEdge(
context.childNodes(target), context.mouse(), context.projection, context.activeID()
);
if (choice) {
var edge = [target.nodes[choice.index - 1], target.nodes[choice.index]];
dispatch.call('clickWay', this, choice.loc, edge, d);
if (target && target.type === 'node' && _activeLayer.id === Number(target.mapId)) { // Snap to a node
console.log(target.name + ' (' + target.id + ')' + ' is an active layer' );
dispatch.call('clickNode', this, target, d);
return;
}
// dispatch.call('clickNode', this, target, d);
// return;

} else if (target && target.type === 'way' && _activeLayer.id === Number(target.mapId)) { // Snap to a way
console.log(target.id + ' is an active layer' );
var choice = geoChooseEdge(
context.childNodes(target), context.mouse(), context.projection, context.activeID()
);
if (choice) {
var edge = [target.nodes[choice.index - 1], target.nodes[choice.index]];
dispatch.call('clickWay', this, choice.loc, edge, d);
return;
}
}
dispatch.call('click', this, context.map().mouseCoordinates(), d);
}
Expand Down
3 changes: 3 additions & 0 deletions modules/behavior/draw_way.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import { geoChooseEdge, geoHasSelfIntersections } from '../geo';
import { modeBrowse, modeSelect } from '../modes';
import { osmNode } from '../osm';
import { utilKeybinding } from '../util';
import _find from 'lodash-es/find';


export function behaviorDrawWay(context, wayId, index, mode, startGraph) {
Expand Down Expand Up @@ -73,6 +74,8 @@ export function behaviorDrawWay(context, wayId, index, mode, startGraph) {
function move(datum) {
context.surface().classed('nope-disabled', d3_event.altKey);

// add one more boolean at end, is activeLayer===mapId
var _activeLayer = _find( Hoot.layers.loadedLayers, function(a, b) { return a.activeLayer; });
Copy link
Contributor

@maxgrossman maxgrossman May 17, 2019

Choose a reason for hiding this comment

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

I think we need to make use of this here, making sure to only apply a target loc if active ids match.

here in iD a question is asked (is this target loc one that allows vertex).

Our question needs to be does the datum's mapId equal the _activeLayer mapId

var targetLoc = datum && datum.properties && datum.properties.entity && datum.properties.entity.loc;
Copy link
Contributor

Choose a reason for hiding this comment

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

I think we need to implement the commented out piece here, using the same split stuff we do in the draw.js file.

var targetNodes = datum && datum.properties && datum.properties.nodes;
var loc = context.map().mouseCoordinates();
Expand Down
1 change: 1 addition & 0 deletions modules/behavior/hover.js
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,7 @@ export function behaviorHover(context) {
return;
}

// again, boolean, is entity.mapId === activeLayerId...
var suppressed = _altDisables && d3_event && d3_event.altKey;
Copy link
Contributor

@maxgrossman maxgrossman May 23, 2019

Choose a reason for hiding this comment

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

need to do same is this the active layer check here too

_selection.selectAll(selector)
.classed(suppressed ? 'hover-suppressed' : 'hover', true);
Expand Down
Loading