Skip to content
This repository has been archived by the owner on Jun 3, 2024. It is now read-only.

Commit

Permalink
QMAPS-1883 refactor close buttons (#1051)
Browse files Browse the repository at this point in the history
  • Loading branch information
xem authored Apr 22, 2021
1 parent 6704b4f commit d37e7f8
Show file tree
Hide file tree
Showing 9 changed files with 130 additions and 64 deletions.
1 change: 1 addition & 0 deletions src/components/ui/Panel.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ class Panel extends React.Component {
isMapBottomUIDisplayed: PropTypes.bool,
floatingItems: PropTypes.arrayOf(PropTypes.object),
onTransitionEnd: PropTypes.func,
onClose: PropTypes.func,
};

static defaultProps = {
Expand Down
78 changes: 73 additions & 5 deletions src/panel/PanelManager.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import CategoryPanel from 'src/panel/category/CategoryPanel';
import DirectionPanel from 'src/panel/direction/DirectionPanel';
import Telemetry from 'src/libs/telemetry';
import CategoryService from 'src/adapters/category_service';
import { parseQueryString, getCurrentUrl } from 'src/libs/url_utils';
import { parseQueryString, getCurrentUrl, buildQueryString } from 'src/libs/url_utils';
import { fire, listen } from 'src/libs/customEvents';
import { isNullOrEmpty } from 'src/libs/object';
import { isMobileDevice } from 'src/libs/device';
Expand Down Expand Up @@ -77,18 +77,26 @@ export default class PanelManager extends React.Component {
const { ActivePanel, options } = this.state;

if (prevState.ActivePanel !== ActivePanel || prevState.options !== options) {
// poiFilters indicate we are in a "list of POI" context, where markers should be persistent
// Not in a "list of PoI" context (options.poiFilters is null)
if (isNullOrEmpty(options?.poiFilters)) {
// Markers are not persistent
fire('remove_category_markers');
}

// Handle search bar's style and text content
this.updateSearchBarContent(options);

// Handle top bar's return button
this.updateTopBarReturnButton(options);
}
}

updateSearchBarContent({ poiFilters = {}, query } = {}) {
updateSearchBarContent({ poiFilters = {}, poi = {}, query } = {}) {
const topBarHandle = document.querySelector('.top_bar');
if (poiFilters.category) {
if (poi.name) {
SearchInput.setInputValue(poi.name);
topBarHandle.classList.add('top_bar--search_filled');
} else if (poiFilters.category) {
const categoryLabel = CategoryService.getCategoryByName(poiFilters.category)?.getInputValue();
SearchInput.setInputValue(categoryLabel);
topBarHandle.classList.add('top_bar--search_filled');
Expand All @@ -104,6 +112,61 @@ export default class PanelManager extends React.Component {
}
}

updateTopBarReturnButton({ poiFilters = {}, isFromFavorite, poi = {} } = {}) {
const topBarReturnButton = document.querySelector('.search_form__return-to-list');
const backAction =
poiFilters.category || poiFilters.query
? this.backToList
: isFromFavorite
? this.backToFavorite
: () => {};
topBarReturnButton.onclick = e => {
backAction(e, poiFilters);
};

const topBarHandle = document.querySelector('.top_bar');

// Show return arrow (on mobile) if user comes from PoI / favorites list
if (poi.name && (poiFilters.category || poiFilters.query || isFromFavorite)) {
topBarHandle.classList.add('top_bar--poi-from-list');
}
// Hide return button when not on a POI anymore
else {
const topBarHandle = document.querySelector('.top_bar');
topBarHandle.classList.remove('top_bar--poi-from-list');
}
}

backToList(e, poiFilters) {
e.stopPropagation();
const queryObject = {};
const mappingParams = {
query: 'q',
category: 'type',
};

for (const name in poiFilters) {
if (!poiFilters[name]) {
continue;
}
const key = mappingParams[name];
queryObject[key || name] = poiFilters[name];
}

const params = buildQueryString(queryObject);
const uri = `/places/${params}`;

Telemetry.add(Telemetry.POI_BACKTOLIST);
fire('restore_location');
window.app.navigateTo(uri);
}

backToFavorite(e) {
e.stopPropagation();
Telemetry.add(Telemetry.POI_BACKTOFAVORITE);
window.app.navigateTo('/favs');
}

initRouter() {
const router = this.props.router;

Expand Down Expand Up @@ -134,7 +197,12 @@ export default class PanelManager extends React.Component {
const poiId = poiUrl.split('@')[0];
this.setState({
ActivePanel: PoiPanel,
options: { ...options, poiId },
options: {
...options,
poiId,
backToList: this.backToList,
backToFavorite: this.backToFavorite,
},
panelSize: 'default',
});
});
Expand Down
1 change: 0 additions & 1 deletion src/panel/direction/RouteResult.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ import React, { useCallback, useEffect } from 'react';
import PropTypes from 'prop-types';
import { listen, unListen } from 'src/libs/customEvents';
import Telemetry from 'src/libs/telemetry';

import RoutesList from './RoutesList';
import { SourceFooter } from 'src/components/ui';

Expand Down
54 changes: 14 additions & 40 deletions src/panel/poi/PoiPanel.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,15 @@ import PoiBlockContainer from './PoiBlockContainer';
import OsmContribution from 'src/components/OsmContribution';
import CategoryList from 'src/components/CategoryList';
import { isFromPagesJaunes, isFromOSM } from 'src/libs/pois';
import { buildQueryString, shouldShowBackToQwant } from 'src/libs/url_utils';
import { shouldShowBackToQwant } from 'src/libs/url_utils';
import IdunnPoi from 'src/adapters/poi/idunn_poi';
import Poi from 'src/adapters/poi/poi.js';
import { fire, listen, unListen } from 'src/libs/customEvents';
import { addToFavorites, removeFromFavorites, isInFavorites } from 'src/adapters/store';
import PoiItem from 'src/components/PoiItem';
import { isNullOrEmpty } from 'src/libs/object';
import { DeviceContext } from 'src/libs/device';
import { Flex, Panel, PanelNav, CloseButton, Divider, Button } from 'src/components/ui';
import { Flex, Panel, PanelNav, Divider, Button } from 'src/components/ui';
import { BackToQwantButton } from 'src/components/BackToQwantButton';

const covid19Enabled = (nconf.get().covid19 || {}).enabled;
Expand All @@ -28,6 +28,8 @@ export default class PoiPanel extends React.Component {
poi: PropTypes.object,
poiFilters: PropTypes.object,
centerMap: PropTypes.bool,
backToList: PropTypes.func,
backToFavorite: PropTypes.func,
};

static defaultProps = {
Expand Down Expand Up @@ -130,12 +132,6 @@ export default class PoiPanel extends React.Component {
});
}

backToFavorite = e => {
e.stopPropagation();
Telemetry.add(Telemetry.POI_BACKTOFAVORITE);
window.app.navigateTo('/favs');
};

getBestPoi() {
return this.state.fullPoi || this.props.poi;
}
Expand All @@ -156,31 +152,6 @@ export default class PoiPanel extends React.Component {
window.app.navigateTo('/');
};

backToList = e => {
e.stopPropagation();
const { poiFilters } = this.props;
const queryObject = {};
const mappingParams = {
query: 'q',
category: 'type',
};

for (const name in poiFilters) {
if (!poiFilters[name]) {
continue;
}
const key = mappingParams[name];
queryObject[key || name] = poiFilters[name];
}

const params = buildQueryString(queryObject);
const uri = `/places/${params}`;

Telemetry.add(Telemetry.POI_BACKTOLIST);
fire('restore_location');
window.app.navigateTo(uri);
};

onClickPhoneNumber = () => {
const poi = this.getBestPoi();
const source = poi.meta && poi.meta.source;
Expand Down Expand Up @@ -220,9 +191,9 @@ export default class PoiPanel extends React.Component {

const backAction =
poiFilters.category || poiFilters.query
? this.backToList
? this.props.backToList
: isFromFavorite
? this.backToFavorite
? this.props.backToFavorite
: this.closeAction;

const NavHeader = ({ isMobile }) => {
Expand All @@ -238,10 +209,17 @@ export default class PoiPanel extends React.Component {
);
}

// If source is a PoI list: show a button to return to the list
if (backAction !== this.closeAction) {
return (
<PanelNav>
<Button icon="arrow-left" variant="tertiary" onClick={backAction}>
<Button
icon="arrow-left"
variant="tertiary"
onClick={e => {
backAction(e, poiFilters);
}}
>
{_('Display all results')}
</Button>
</PanelNav>
Expand Down Expand Up @@ -276,10 +254,6 @@ export default class PoiPanel extends React.Component {
withOpeningHours
onClick={this.center}
/>
<CloseButton
onClick={isMobile ? backAction : this.closeAction}
position="topRight"
/>
</Flex>
<div className="u-mb-l">
<ActionButtons
Expand Down
24 changes: 13 additions & 11 deletions src/panel/poi/blocks/Covid19.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -85,17 +85,19 @@ const getContent = ({ status, opening_hours, note, contribute_url }) => {
const LocalizedWarning = ({ countryCode }) => {
const { frInformationUrl } = useConfig('covid19');

return <div>
<p>{_('Please comply with government travel restrictions.', 'covid19')}</p>
{countryCode === 'FR' && (
<p>
{_('More information at', 'covid19')}{' '}
<a rel="noopener noreferrer" href={frInformationUrl}>
gouvernement.fr/info-coronavirus
</a>
</p>
)}
</div>
return (
<div>
<p>{_('Please comply with government travel restrictions.', 'covid19')}</p>
{countryCode === 'FR' && (
<p>
{_('More information at', 'covid19')}{' '}
<a rel="noopener noreferrer" href={frInformationUrl}>
gouvernement.fr/info-coronavirus
</a>
</p>
)}
</div>
);
};

const LegalWarning = ({ countryCode }) => (
Expand Down
29 changes: 26 additions & 3 deletions src/scss/includes/search_form.scss
Original file line number Diff line number Diff line change
Expand Up @@ -86,8 +86,9 @@ input[type="search"] {
}
}

// Return arrow
.search_form__return {
// Return arrows
.search_form__return,
.search_form__return-to-list {
display: none;
}

Expand Down Expand Up @@ -191,7 +192,8 @@ input[type="search"] {
font-size: 14px;
}

.search_form__return {
.search_form__return,
.search_form__return-to-list {
display: none;
font-size: 20px;
text-align: center;
Expand Down Expand Up @@ -303,4 +305,25 @@ input[type="search"] {
display: none;
}
}

// When a PoI Panel is displayed
.top_bar--poi-from-list {

// Show the return arrow
.search_form__return-to-list {
display: block;
}

// If the search field is focused, hide it
&.top_bar--search_focus {
.search_form__return-to-list {
display: none;
}
}

// Make room for it on the left of the field
.search_form__wrapper {
padding-left: $spacing-xxl-3;
}
}
}
4 changes: 2 additions & 2 deletions tests/integration/tests/autocomplete.js
Original file line number Diff line number Diff line change
Expand Up @@ -249,8 +249,8 @@ test('Search Query', async () => {
await page.goto(`${APP_URL}/?q=${searchQuery}`);
const searchValue = await getInputValue(page, '#search');

// search input is filled with query
expect(searchValue).toEqual(searchQuery);
// search input is filled with PoI name (not the query)
expect(searchValue).toEqual('test result 1');

// app navigates to first result from autocomplete
expect(page.url()).toEqual(`${APP_URL}/place/osm:node:4872758213@test_result_1`);
Expand Down
2 changes: 0 additions & 2 deletions tests/integration/tests/poi.desktop.js
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,6 @@ test('add a poi as favorite and find it back in the favorite menu', async () =>
expect(await exists(page, '.poiTitle')).toBeTruthy();
expect(await exists(page, '.poi_panel')).toBeTruthy();
await page.click('.poi_panel__actions .poi_panel__action__favorite');
await page.click('.poi_panel .closeButton');
// we check that the first favorite item is our poi
await toggleFavoritePanel(page);
let fav = await getFavorites(page);
Expand All @@ -99,7 +98,6 @@ test('add a poi as favorite and find it back in the favorite menu', async () =>
expect(await exists(page, '.poi_panel')).toBeTruthy();

await page.click('.poi_panel__actions .poi_panel__action__favorite');
await page.click('.poi_panel .closeButton');
// it should disappear from the favorites
await toggleFavoritePanel(page);
fav = await getFavorites(page);
Expand Down
1 change: 1 addition & 0 deletions views/index.ejs
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@
></button>
<div class="search_form__wrapper empty">
<div class="search_form__return icon-arrow-left"></div>
<div class="search_form__return-to-list icon-arrow-left"></div>
<input id="search" type="search" class="search_form__input" spellcheck="false" required placeholder="<%= _('Search on Qwant Maps') %>" autocomplete="off">
<button id="clear_button_mobile" class="search_form__clear icon-x" type="button" onmousedown="clearSearch(event)" title="<%= _('Clear', 'search bar') %>"></button>
<input type="submit" value="" class="search_form__action" onclick="submitSearch()" title="<%= _('Search') %>">
Expand Down

0 comments on commit d37e7f8

Please sign in to comment.