From aff86979a6b80d035bbbb001d9c12941d0d4a864 Mon Sep 17 00:00:00 2001 From: Quincy Morgan Date: Wed, 20 Feb 2019 13:47:11 -0500 Subject: [PATCH] Better pane display at narrow window widths (close #5890) --- css/80_app.css | 47 ++++++++-------- modules/ui/background.js | 117 +++++++++++++++++++------------------- modules/ui/help.js | 116 +++++++++++++++++++------------------- modules/ui/init.js | 18 ++++-- modules/ui/issues.js | 109 +++++++++++++++++------------------ modules/ui/map_data.js | 119 +++++++++++++++++++-------------------- 6 files changed, 264 insertions(+), 262 deletions(-) diff --git a/css/80_app.css b/css/80_app.css index 3615417f9..265b21f9d 100644 --- a/css/80_app.css +++ b/css/80_app.css @@ -2955,39 +2955,39 @@ div.full-screen > button:hover { text-overflow: ellipsis; } -.map-data-control .layer-list button, -.background-control .layer-list button { +.map-data-pane .layer-list button, +.background-pane .layer-list button { float: right; height: 100%; width: 10%; border-left: 1px solid #ccc; border-radius: 0; } -[dir='rtl'] .map-data-control .layer-list button, -[dir='rtl'] .background-control .layer-list button { +[dir='rtl'] .map-data-pane .layer-list button, +[dir='rtl'] .background-pane .layer-list button { float: left; border-left: none; border-right: 1px solid #ccc; } -.map-data-control .layer-list button .icon, -.background-control .layer-list button .icon { +.map-data-pane .layer-list button .icon, +.background-pane .layer-list button .icon { opacity: 0.5; } -.map-data-control .layer-list button:first-of-type, -.background-control .layer-list button:first-of-type { +.map-data-pane .layer-list button:first-of-type, +.background-pane .layer-list button:first-of-type { border-radius: 0 3px 3px 0; } -[dir='rtl'] .map-data-control .layer-list button:first-of-type, -[dir='rtl'] .background-control .layer-list button:first-of-type { +[dir='rtl'] .map-data-pane .layer-list button:first-of-type, +[dir='rtl'] .background-pane .layer-list button:first-of-type { border-radius: 3px 0 0 3px; } -.map-data-control .vectortile-container .vectortile-header { +.map-data-pane .vectortile-container .vectortile-header { padding-bottom: 5px; } -.map-data-control .vectortile-container .vectortile-footer { +.map-data-pane .vectortile-container .vectortile-footer { padding-bottom: 10px; } @@ -3186,7 +3186,7 @@ ul.issue-fix-list button { /* Background - Adjust Alignment ------------------------------------------------------- */ -.background-control .nudge-container { +.background-pane .nudge-container { border: 1px solid #ccc; border-radius: 4px; padding: 10px; @@ -3287,25 +3287,25 @@ ul.issue-fix-list button { cursor: move; } -.background-control .nudge.right::after { +.background-pane .nudge.right::after { border-top: 5px solid transparent; border-bottom: 5px solid transparent; border-left: 5px solid #222; } -.background-control .nudge.left::after { +.background-pane .nudge.left::after { border-top: 5px solid transparent; border-bottom: 5px solid transparent; border-right: 5px solid #222; } -.background-control .nudge.top::after { +.background-pane .nudge.top::after { border-right: 5px solid transparent; border-left: 5px solid transparent; border-bottom: 5px solid #222; } -.background-control .nudge.bottom::after { +.background-pane .nudge.bottom::after { border-right: 5px solid transparent; border-left: 5px solid transparent; border-top: 5px solid #222; @@ -3315,15 +3315,16 @@ ul.issue-fix-list button { /* Side Panes - Background / Map Data / Help ------------------------------------------------------- */ .map-pane { - position: fixed; + position: absolute; top: 60px; bottom: 30px; right: 0; - width: 33.3333%; + width: 100%; max-width: 400px; + min-width: 180px; padding-bottom: 50px; overflow: hidden; - z-index: -1; + z-index: 10; } [dir='rtl'] .map-pane { left: 0; @@ -3331,7 +3332,6 @@ ul.issue-fix-list button { } .map-pane.help-wrap { - width: 50.0000%; max-width: 600px; } @@ -3340,15 +3340,16 @@ ul.issue-fix-list button { flex-flow: row nowrap; justify-content: space-between; border-bottom: 1px solid #ccc; + height: 60px; } .pane-heading h2 { - margin: 15px 20px; + margin: 14px 20px; } .pane-heading button { width: 40px; - height: 61px; + height: 100%; border-radius: 0; } diff --git a/modules/ui/background.js b/modules/ui/background.js index 0f1f784be..8d793f226 100644 --- a/modules/ui/background.js +++ b/modules/ui/background.js @@ -29,7 +29,7 @@ import { tooltip } from '../util/tooltip'; export function uiBackground(context) { var key = t('background.key'); - var pane = d3_select(null); + var _pane = d3_select(null), _toggleButton = d3_select(null); var _customSource = context.background().findSource('custom'); var _previousBackground = context.background().findSource(context.storage('background-last-used-toggle')); @@ -284,11 +284,11 @@ export function uiBackground(context) { function update() { - if (!pane.select('.disclosure-wrap-background_list').classed('hide')) { + if (!_pane.select('.disclosure-wrap-background_list').classed('hide')) { updateBackgroundList(); } - if (!pane.select('.disclosure-wrap-overlay_list').classed('hide')) { + if (!_pane.select('.disclosure-wrap-overlay_list').classed('hide')) { updateOverlayList(); } @@ -310,70 +310,71 @@ export function uiBackground(context) { } } + var paneTooltip = tooltip() + .placement((textDirection === 'rtl') ? 'right' : 'left') + .html(true) + .title(uiTooltipHtml(t('background.description'), key)); - function background(selection) { + uiBackground.togglePane = function() { + if (d3_event) d3_event.preventDefault(); + paneTooltip.hide(_toggleButton); + uiBackground.setVisible(!_toggleButton.classed('active')); + }; - function hidePane() { - setVisible(false); - } + uiBackground.hidePane = function() { + uiBackground.setVisible(false); + }; - function togglePane() { - if (d3_event) d3_event.preventDefault(); - paneTooltip.hide(button); - setVisible(!button.classed('active')); - } + uiBackground.setVisible = function(show) { + if (show !== _shown) { + _toggleButton.classed('active', show); + _shown = show; - function setVisible(show) { - if (show !== _shown) { - button.classed('active', show); - _shown = show; + if (show) { + uiHelp.hidePane(); + uiIssues.hidePane(); + uiMapData.hidePane(); + update(); - if (show) { - uiHelp.hidePane(); - uiIssues.hidePane(); - uiMapData.hidePane(); - update(); + _pane + .style('display', 'block') + .style('right', '-300px') + .transition() + .duration(200) + .style('right', '0px'); - pane - .style('display', 'block') - .style('right', '-300px') - .transition() - .duration(200) - .style('right', '0px'); - - } else { - pane - .style('display', 'block') - .style('right', '0px') - .transition() - .duration(200) - .style('right', '-300px') - .on('end', function() { - d3_select(this).style('display', 'none'); - }); - } + } else { + _pane + .style('display', 'block') + .style('right', '0px') + .transition() + .duration(200) + .style('right', '-300px') + .on('end', function() { + d3_select(this).style('display', 'none'); + }); } } + }; + uiBackground.renderToggleButton = function(selection) { - pane = selection - .append('div') - .attr('class', 'fillL map-pane hide'); - - var paneTooltip = tooltip() - .placement((textDirection === 'rtl') ? 'right' : 'left') - .html(true) - .title(uiTooltipHtml(t('background.description'), key)); - - var button = selection + _toggleButton = selection .append('button') .attr('tabindex', -1) - .on('click', togglePane) + .on('click', uiBackground.togglePane) .call(svgIcon('#iD-icon-layers', 'light')) .call(paneTooltip); + }; + + uiBackground.renderPane = function(selection) { + + _pane = selection + .append('div') + .attr('class', 'fillL map-pane background-pane hide'); - var heading = pane + var heading = _pane .append('div') .attr('class', 'pane-heading'); @@ -383,11 +384,11 @@ export function uiBackground(context) { heading .append('button') - .on('click', function() { uiBackground.hidePane(); }) + .on('click', uiBackground.hidePane) .call(svgIcon('#iD-icon-close')); - var content = pane + var content = _pane .append('div') .attr('class', 'pane-content'); @@ -431,13 +432,9 @@ export function uiBackground(context) { update(); context.keybinding() - .on(key, togglePane) + .on(key, uiBackground.togglePane) .on(uiCmd('⌘' + key), quickSwitch); + }; - uiBackground.hidePane = hidePane; - uiBackground.togglePane = togglePane; - uiBackground.setVisible = setVisible; - } - - return background; + return uiBackground; } diff --git a/modules/ui/help.js b/modules/ui/help.js index 973ed96cc..371522a50 100644 --- a/modules/ui/help.js +++ b/modules/ui/help.js @@ -20,6 +20,10 @@ import { icon } from './intro/helper'; export function uiHelp(context) { var key = t('help.key'); + var _pane = d3_select(null), _toggleButton = d3_select(null); + + var _shown = false; + var docKeys = [ ['help', [ 'welcome', @@ -282,49 +286,60 @@ export function uiHelp(context) { }; }); + var paneTooltip = tooltip() + .placement((textDirection === 'rtl') ? 'right' : 'left') + .html(true) + .title(uiTooltipHtml(t('help.title'), key)); - function help(selection) { + uiHelp.hidePane = function() { + uiHelp.setVisible(false); + }; - function hidePane() { - setVisible(false); - } + uiHelp.togglePane = function() { + if (d3_event) d3_event.preventDefault(); + paneTooltip.hide(_toggleButton); + uiHelp.setVisible(!_toggleButton.classed('active')); + }; + uiHelp.setVisible = function(show) { + if (show !== _shown) { + _toggleButton.classed('active', show); + _shown = show; - function togglePane() { - if (d3_event) d3_event.preventDefault(); - tooltipBehavior.hide(button); - setVisible(!button.classed('active')); - } + if (show) { + uiBackground.hidePane(); + uiIssues.hidePane(); + uiMapData.hidePane(); + _pane.style('display', 'block') + .style('right', '-500px') + .transition() + .duration(200) + .style('right', '0px'); - function setVisible(show) { - if (show !== shown) { - button.classed('active', show); - shown = show; - - if (show) { - uiBackground.hidePane(); - uiIssues.hidePane(); - uiMapData.hidePane(); - - pane.style('display', 'block') - .style('right', '-500px') - .transition() - .duration(200) - .style('right', '0px'); - - } else { - pane.style('right', '0px') - .transition() - .duration(200) - .style('right', '-500px') - .on('end', function() { - d3_select(this).style('display', 'none'); - }); - } + } else { + _pane.style('right', '0px') + .transition() + .duration(200) + .style('right', '-500px') + .on('end', function() { + d3_select(this).style('display', 'none'); + }); } } + }; + uiHelp.renderToggleButton = function(selection) { + + _toggleButton = selection.append('button') + .attr('tabindex', -1) + .on('click', uiHelp.togglePane) + .call(svgIcon('#iD-icon-help', 'light')) + .call(paneTooltip); + }; + + + uiHelp.renderPane = function(selection) { function clickHelp(d, i) { var rtl = (textDirection === 'rtl'); @@ -384,7 +399,7 @@ export function uiHelp(context) { function clickWalkthrough() { if (context.inIntro()) return; context.container().call(uiIntro(context)); - setVisible(false); + uiHelp.setVisible(false); } @@ -393,24 +408,10 @@ export function uiHelp(context) { } - var pane = selection.append('div') + _pane = selection.append('div') .attr('class', 'help-wrap map-pane fillL hide'); - var tooltipBehavior = tooltip() - .placement((textDirection === 'rtl') ? 'right' : 'left') - .html(true) - .title(uiTooltipHtml(t('help.title'), key)); - - var button = selection.append('button') - .attr('tabindex', -1) - .on('click', togglePane) - .call(svgIcon('#iD-icon-help', 'light')) - .call(tooltipBehavior); - - var shown = false; - - - var heading = pane + var heading = _pane .append('div') .attr('class', 'pane-heading'); @@ -420,11 +421,11 @@ export function uiHelp(context) { heading .append('button') - .on('click', function() { uiHelp.hidePane(); }) + .on('click', uiHelp.hidePane) .call(svgIcon('#iD-icon-close')); - var content = pane + var content = _pane .append('div') .attr('class', 'pane-content'); @@ -487,12 +488,9 @@ export function uiHelp(context) { clickHelp(docs[0], 0); context.keybinding() - .on(key, togglePane); + .on(key, uiHelp.togglePane); - uiHelp.hidePane = hidePane; - uiHelp.togglePane = togglePane; - uiHelp.setVisible = setVisible; - } + }; - return help; + return uiHelp; } diff --git a/modules/ui/init.js b/modules/ui/init.js index 366530afc..d1d962658 100644 --- a/modules/ui/init.js +++ b/modules/ui/init.js @@ -142,7 +142,7 @@ export function uiInit(context) { // Map controls (appended to #bar, but absolutely positioned) - var controls = bar + var controls = content .append('div') .attr('class', 'map-controls'); @@ -156,25 +156,33 @@ export function uiInit(context) { .attr('class', 'map-control geolocate-control') .call(uiGeolocate(context)); + var background = uiBackground(context); controls .append('div') .attr('class', 'map-control background-control') - .call(uiBackground(context)); + .call(background.renderToggleButton); + content.call(background.renderPane); + var mapData = uiMapData(context); controls .append('div') .attr('class', 'map-control map-data-control') - .call(uiMapData(context)); + .call(mapData.renderToggleButton); + content.call(mapData.renderPane); + var issues = uiIssues(context); controls .append('div') .attr('class', 'map-control map-issues-control') - .call(uiIssues(context)); + .call(issues.renderToggleButton); + content.call(issues.renderPane); + var help = uiHelp(context); controls .append('div') .attr('class', 'map-control help-control') - .call(uiHelp(context)); + .call(help.renderToggleButton); + content.call(help.renderPane); // Add attribution and footer diff --git a/modules/ui/issues.js b/modules/ui/issues.js index 0bc430f9a..f323e76f0 100644 --- a/modules/ui/issues.js +++ b/modules/ui/issues.js @@ -21,7 +21,7 @@ export function uiIssues(context) { var _errorsList = d3_select(null); var _warningsList = d3_select(null); var _pane = d3_select(null); - var _button = d3_select(null); + var _toggleButton = d3_select(null); var _shown = false; context.validator().on('reload.issues_pane', update); @@ -226,7 +226,7 @@ export function uiIssues(context) { var errors = context.validator().getErrors(); var warnings = context.validator().getWarnings(); - _button.selectAll('.icon-badge') + _toggleButton.selectAll('.icon-badge') .classed('error', (errors.length > 0)) .classed('warning', (errors.length === 0 && warnings.length > 0)) .classed('hide', (errors.length === 0 && warnings.length === 0)); @@ -261,66 +261,71 @@ export function uiIssues(context) { //} } - function issues(selection) { + var paneTooltip = tooltip() + .placement((textDirection === 'rtl') ? 'right' : 'left') + .html(true) + .title(uiTooltipHtml(t('issues.title'), key)); - function hidePane() { - setVisible(false); - } + uiIssues.hidePane = function() { + uiIssues.setVisible(false); + }; - function togglePane() { - if (d3_event) d3_event.preventDefault(); - setVisible(!_button.classed('active')); - } + uiIssues.togglePane = function() { + if (d3_event) d3_event.preventDefault(); + paneTooltip.hide(_toggleButton); + uiIssues.setVisible(!_toggleButton.classed('active')); + }; - function setVisible(show) { - if (show !== _shown) { - _button.classed('active', show); - _shown = show; + uiIssues.setVisible = function(show) { + if (show !== _shown) { + _toggleButton.classed('active', show); + _shown = show; - if (show) { - uiBackground.hidePane(); - uiHelp.hidePane(); - uiMapData.hidePane(); - update(); + if (show) { + uiBackground.hidePane(); + uiHelp.hidePane(); + uiMapData.hidePane(); + update(); - _pane - .style('display', 'block') - .style('right', '-300px') - .transition() - .duration(200) - .style('right', '0px'); + _pane + .style('display', 'block') + .style('right', '-300px') + .transition() + .duration(200) + .style('right', '0px'); - } else { - _pane - .style('display', 'block') - .style('right', '0px') - .transition() - .duration(200) - .style('right', '-300px') - .on('end', function() { - d3_select(this).style('display', 'none'); - }); - } + } else { + _pane + .style('display', 'block') + .style('right', '0px') + .transition() + .duration(200) + .style('right', '-300px') + .on('end', function() { + d3_select(this).style('display', 'none'); + }); } } + }; - _pane = selection - .append('div') - .attr('class', 'fillL map-pane hide'); + uiIssues.renderToggleButton = function(selection) { - var paneTooltip = tooltip() - .placement((textDirection === 'rtl') ? 'right' : 'left') - .html(true) - .title(uiTooltipHtml(t('issues.title'), key)); - - _button = selection + _toggleButton = selection .append('button') .attr('tabindex', -1) - .on('click', togglePane) + .on('click', uiIssues.togglePane) .call(svgIcon('#iD-icon-alert', 'light')) .call(addIconBadge) .call(paneTooltip); + }; + + uiIssues.renderPane = function(selection) { + + _pane = selection + .append('div') + .attr('class', 'fillL map-pane issues-pane hide'); + var heading = _pane .append('div') .attr('class', 'pane-heading'); @@ -331,7 +336,7 @@ export function uiIssues(context) { heading .append('button') - .on('click', function() { uiIssues.hidePane(); }) + .on('click', uiIssues.hidePane) .call(svgIcon('#iD-icon-close')); var content = _pane @@ -383,12 +388,8 @@ export function uiIssues(context) { update(); context.keybinding() - .on(key, togglePane); + .on(key, uiIssues.togglePane); + }; - uiIssues.hidePane = hidePane; - uiIssues.togglePane = togglePane; - uiIssues.setVisible = setVisible; - } - - return issues; + return uiIssues; } diff --git a/modules/ui/map_data.js b/modules/ui/map_data.js index 99236e246..fe7fcf28e 100644 --- a/modules/ui/map_data.js +++ b/modules/ui/map_data.js @@ -25,7 +25,7 @@ export function uiMapData(context) { var settingsCustomData = uiSettingsCustomData(context) .on('change', customChanged); - var pane = d3_select(null); + var _pane = d3_select(null), _toggleButton = d3_select(null); var _fillSelected = context.storage('area-fill') || 'partial'; var _shown = false; @@ -595,13 +595,13 @@ export function uiMapData(context) { function update() { - if (!pane.select('.disclosure-wrap-data_layers').classed('hide')) { + if (!_pane.select('.disclosure-wrap-data_layers').classed('hide')) { updateDataLayers(); } - if (!pane.select('.disclosure-wrap-fill_area').classed('hide')) { + if (!_pane.select('.disclosure-wrap-fill_area').classed('hide')) { updateFillList(); } - if (!pane.select('.disclosure-wrap-map_features').classed('hide')) { + if (!_pane.select('.disclosure-wrap-map_features').classed('hide')) { updateFeatureList(); } @@ -626,70 +626,71 @@ export function uiMapData(context) { context.map().pan([0,0]); // trigger a redraw } + var paneTooltip = tooltip() + .placement((textDirection === 'rtl') ? 'right' : 'left') + .html(true) + .title(uiTooltipHtml(t('map_data.description'), key)); - function mapData(selection) { + uiMapData.hidePane = function() { + uiMapData.setVisible(false); + }; - function hidePane() { - setVisible(false); - } + uiMapData.togglePane = function() { + if (d3_event) d3_event.preventDefault(); + paneTooltip.hide(_toggleButton); + uiMapData.setVisible(!_toggleButton.classed('active')); + }; - function togglePane() { - if (d3_event) d3_event.preventDefault(); - paneTooltip.hide(button); - setVisible(!button.classed('active')); - } + uiMapData.setVisible = function(show) { + if (show !== _shown) { + _toggleButton.classed('active', show); + _shown = show; - function setVisible(show) { - if (show !== _shown) { - button.classed('active', show); - _shown = show; + if (show) { + uiBackground.hidePane(); + uiHelp.hidePane(); + uiIssues.hidePane(); + update(); - if (show) { - uiBackground.hidePane(); - uiHelp.hidePane(); - uiIssues.hidePane(); - update(); + _pane + .style('display', 'block') + .style('right', '-300px') + .transition() + .duration(200) + .style('right', '0px'); - pane - .style('display', 'block') - .style('right', '-300px') - .transition() - .duration(200) - .style('right', '0px'); - - } else { - pane - .style('display', 'block') - .style('right', '0px') - .transition() - .duration(200) - .style('right', '-300px') - .on('end', function() { - d3_select(this).style('display', 'none'); - }); - } + } else { + _pane + .style('display', 'block') + .style('right', '0px') + .transition() + .duration(200) + .style('right', '-300px') + .on('end', function() { + d3_select(this).style('display', 'none'); + }); } } + }; + uiMapData.renderToggleButton = function(selection) { - pane = selection - .append('div') - .attr('class', 'fillL map-pane hide'); - - var paneTooltip = tooltip() - .placement((textDirection === 'rtl') ? 'right' : 'left') - .html(true) - .title(uiTooltipHtml(t('map_data.description'), key)); - - var button = selection + _toggleButton = selection .append('button') .attr('tabindex', -1) - .on('click', togglePane) + .on('click', uiMapData.togglePane) .call(svgIcon('#iD-icon-data', 'light')) .call(paneTooltip); + }; - var heading = pane + uiMapData.renderPane = function(selection) { + + _pane = selection + .append('div') + .attr('class', 'fillL map-pane map-data-pane hide'); + + var heading = _pane .append('div') .attr('class', 'pane-heading'); @@ -699,11 +700,11 @@ export function uiMapData(context) { heading .append('button') - .on('click', function() { uiMapData.hidePane(); }) + .on('click', uiMapData.hidePane) .call(svgIcon('#iD-icon-close')); - var content = pane + var content = _pane .append('div') .attr('class', 'pane-content'); @@ -744,13 +745,9 @@ export function uiMapData(context) { setFill(_fillSelected); context.keybinding() - .on(key, togglePane) + .on(key, uiMapData.togglePane) .on(t('area_fill.wireframe.key'), toggleWireframe); + }; - uiMapData.hidePane = hidePane; - uiMapData.togglePane = togglePane; - uiMapData.setVisible = setVisible; - } - - return mapData; + return uiMapData; }