6 Commits

12 changed files with 48 additions and 15 deletions

View File

@@ -2,6 +2,7 @@ import Component from '@glimmer/component';
import { fn } from '@ember/helper'; import { fn } from '@ember/helper';
import { on } from '@ember/modifier'; import { on } from '@ember/modifier';
import { humanizeOsmTag } from '../utils/format-text'; import { humanizeOsmTag } from '../utils/format-text';
import { getLocalizedName } from '../utils/osm';
import Icon from '../components/icon'; import Icon from '../components/icon';
import PlaceEditForm from './place-edit-form'; import PlaceEditForm from './place-edit-form';
@@ -22,8 +23,7 @@ export default class PlaceDetails extends Component {
get name() { get name() {
return ( return (
this.place.title || this.place.title ||
this.tags.name || getLocalizedName(this.tags) ||
this.tags['name:en'] ||
'Unnamed Place' 'Unnamed Place'
); );
} }

View File

@@ -7,6 +7,7 @@ import or from 'ember-truth-helpers/helpers/or';
import PlaceDetails from './place-details'; import PlaceDetails from './place-details';
import Icon from './icon'; import Icon from './icon';
import humanizeOsmTag from '../helpers/humanize-osm-tag'; import humanizeOsmTag from '../helpers/humanize-osm-tag';
import { getLocalizedName } from '../utils/osm';
export default class PlacesSidebar extends Component { export default class PlacesSidebar extends Component {
@service storage; @service storage;
@@ -85,8 +86,7 @@ export default class PlacesSidebar extends Component {
} else { } else {
// It's a fresh POI -> Save it // It's a fresh POI -> Save it
const placeData = { const placeData = {
title: title: getLocalizedName(place.osmTags, 'Untitled Place'),
place.osmTags.name || place.osmTags['name:en'] || 'Untitled Place',
lat: place.lat, lat: place.lat,
lon: place.lon, lon: place.lon,
tags: [], tags: [],

View File

@@ -46,7 +46,7 @@ export default class SettingsPane extends Component {
</option> </option>
<option <option
value="false" value="false"
selected={{if (not this.settings.mapKinetic) "selected"}} selected={{unless this.settings.mapKinetic "selected"}}
> >
Off Off
</option> </option>

View File

@@ -1,4 +1,5 @@
import Service, { service } from '@ember/service'; import Service, { service } from '@ember/service';
import { getLocalizedName } from '../utils/osm';
export default class OsmService extends Service { export default class OsmService extends Service {
@service settings; @service settings;
@@ -61,7 +62,7 @@ out center;
normalizePoi(poi) { normalizePoi(poi) {
return { return {
title: poi.tags?.name || poi.tags?.['name:en'] || 'Untitled Place', title: getLocalizedName(poi.tags),
lat: poi.lat || poi.center?.lat, lat: poi.lat || poi.center?.lat,
lon: poi.lon || poi.center?.lon, lon: poi.lon || poi.center?.lon,
url: poi.tags?.website, url: poi.tags?.website,

32
app/utils/osm.js Normal file
View File

@@ -0,0 +1,32 @@
export function getLocalizedName(tags, defaultName = 'Untitled Place') {
if (!tags) return defaultName;
// 1. Get user's preferred languages
const languages = navigator.languages || [navigator.language || 'en'];
// 2. Try to find a match for each preferred language
for (const lang of languages) {
if (!lang) continue;
// Handle "en-US", "de-DE", etc. -> look for "name:en", "name:de"
const shortLang = lang.split('-')[0];
const tagKey = `name:${shortLang}`;
if (tags[tagKey]) {
return tags[tagKey];
}
}
// 3. Fallback to standard "name"
if (tags.name) {
return tags.name;
}
// 4. Fallback to "name:en" (common in international places without local name)
if (tags['name:en']) {
return tags['name:en'];
}
// 5. Final fallback
return defaultName;
}

View File

@@ -1,6 +1,6 @@
{ {
"name": "marco", "name": "marco",
"version": "1.11.2", "version": "1.11.4",
"private": true, "private": true,
"description": "Unhosted maps app", "description": "Unhosted maps app",
"repository": { "repository": {

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -26,8 +26,8 @@
<meta name="msapplication-TileColor" content="#F6E9A6"> <meta name="msapplication-TileColor" content="#F6E9A6">
<meta name="msapplication-TileImage" content="/icons/icon-144.png"> <meta name="msapplication-TileImage" content="/icons/icon-144.png">
<script type="module" crossorigin src="/assets/main-CYFdUlXN.js"></script> <script type="module" crossorigin src="/assets/main-ji2SNMnp.js"></script>
<link rel="stylesheet" crossorigin href="/assets/main-D53xPL_H.css"> <link rel="stylesheet" crossorigin href="/assets/main-G8wPYi_P.css">
</head> </head>
<body> <body>
</body> </body>

View File

@@ -82,7 +82,7 @@ module('Acceptance | navigation', function (hooks) {
// Click the Close (X) button // Click the Close (X) button
await click('.close-btn'); await click('.close-btn');
await settled();
assert.strictEqual(currentURL(), '/', 'Returned to index'); assert.strictEqual(currentURL(), '/', 'Returned to index');
assert.false(mapUi.returnToSearch, 'Flag is reset after closing sidebar'); assert.false(mapUi.returnToSearch, 'Flag is reset after closing sidebar');
@@ -95,7 +95,7 @@ module('Acceptance | navigation', function (hooks) {
assert.ok(currentURL().includes('/place/'), 'Visited place directly'); assert.ok(currentURL().includes('/place/'), 'Visited place directly');
await click('.back-btn'); await click('.back-btn');
await settled();
assert.strictEqual(currentURL(), '/', 'Returned to index/map'); assert.strictEqual(currentURL(), '/', 'Returned to index/map');
assert.true(backStub.notCalled, 'window.history.back() was NOT called'); assert.true(backStub.notCalled, 'window.history.back() was NOT called');