Skip to content

Commit

Permalink
Merge pull request #988 from geoadmin/fix-PB-729-recent-earthquake-to…
Browse files Browse the repository at this point in the history
…oltip

PB-729 : fix recent earthquake tooltip - #patch
  • Loading branch information
pakb authored Jul 5, 2024
2 parents 297f9b5 + a2a3331 commit 81b3127
Show file tree
Hide file tree
Showing 7 changed files with 66 additions and 34 deletions.
45 changes: 35 additions & 10 deletions src/api/features/features.api.js
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,7 @@ export async function identifyOnGeomAdminLayer({
geometryType: `esriGeometry${coordinate.length === 2 ? 'Point' : 'Envelope'}`,
limit: featureCount,
tolerance: DEFAULT_FEATURE_IDENTIFICATION_TOLERANCE,
returnGeometry: true,
returnGeometry: layer.isHighlightable,
timeInstant: getApi3TimeInstantParam(layer),
lang: lang,
offset,
Expand All @@ -171,10 +171,12 @@ export async function identifyOnGeomAdminLayer({
screenWidth,
screenHeight,
mapExtent,
coordinate,
})
features.push(
parseGeomAdminFeature(layer, feature, featureData, projection, {
lang,
coordinate,
})
)
}
Expand Down Expand Up @@ -575,9 +577,16 @@ function generateFeatureUrl(layer, featureId) {
* @param {Number} [options.screenWidth] Current screen width in pixels
* @param {Number} [options.screenHeight] Current screen height in pixels
* @param {[Number, Number, Number, Number]} [options.mapExtent]
* @param {[Number, Number]} [options.coordinate]
*/
function generateFeatureParams(options = {}) {
const { lang = 'en', screenWidth = null, screenHeight = null, mapExtent = null } = options
const {
lang = 'en',
screenWidth = null,
screenHeight = null,
mapExtent = null,
coordinate = null,
} = options
let imageDisplay = null
if (screenWidth && screenHeight) {
imageDisplay = `${screenWidth},${screenHeight},96`
Expand All @@ -587,6 +596,7 @@ function generateFeatureParams(options = {}) {
lang,
imageDisplay,
mapExtent: mapExtent?.join(',') ?? null,
coord: coordinate?.join(',') ?? null,
}
}

Expand All @@ -600,6 +610,8 @@ function generateFeatureParams(options = {}) {
* @param {String} [options.lang] The lang the title of the feature should be look up. Some features
* do provide a title per lang, instead of an all-purpose title. In this case we need the lang ISO
* code to be able to decide which title the feature will have. Default is `en`
* @param {[Number, Number]} [options.coordinate] Where the identify took place, will be used if no
* geometry was requested (if the layer isn't highlightable) to place the anchor of the tooltip
* @returns {LayerFeature}
*/
function parseGeomAdminFeature(
Expand All @@ -609,11 +621,10 @@ function parseGeomAdminFeature(
outputProjection,
options = {}
) {
const { lang = 'en' } = options
const featureGeoJSONGeometry = featureMetadata.geometry
let featureExtent = []
const { lang = 'en', coordinate = null } = options
let featureExtent = null
if (featureMetadata.bbox) {
featureExtent.push(...featureMetadata.bbox)
featureExtent = [...featureMetadata.bbox]
}
let featureName = featureMetadata.id
if (featureMetadata.properties) {
Expand All @@ -630,18 +641,30 @@ function parseGeomAdminFeature(
}
}

if (outputProjection.epsg !== LV95.epsg) {
if (featureExtent.length === 4) {
featureExtent = projExtent(LV95, outputProjection, featureExtent)
if (outputProjection.epsg !== LV95.epsg && featureExtent?.length === 4) {
featureExtent = projExtent(LV95, outputProjection, featureExtent)
}

let featureGeoJSONGeometry = null
if (layer.isHighlightable) {
featureGeoJSONGeometry = featureMetadata.geometry
} else if (coordinate) {
featureGeoJSONGeometry = {
type: 'MultiPoint',
coordinates: [coordinate],
}
}
let coordinates = null
if (featureGeoJSONGeometry) {
coordinates = getGeoJsonFeatureCoordinates(featureGeoJSONGeometry, LV95, outputProjection)
}

return new LayerFeature({
layer,
id: featureMetadata.id,
name: featureName,
data: featureHtmlPopup,
coordinates: getGeoJsonFeatureCoordinates(featureGeoJSONGeometry, LV95, outputProjection),
coordinates,
extent: featureExtent,
geometry: featureGeoJSONGeometry,
})
Expand Down Expand Up @@ -724,6 +747,8 @@ const getFeature = (layer, featureId, outputProjection, options = {}) => {
* @param {Number} [options.screenHeight] Height of the screen in pixels
* @param {[Number, Number, Number, Number]} [options.mapExtent] Current extent of the map,
* described in LV95.
* @param {[Number, Number]} [options.coordinate] Coordinate of the click/identify, will be used by
* some layer to gather more information in the HTML popup
* @returns {Promise<String>}
*/
export function getFeatureHtmlPopup(layer, featureId, options) {
Expand Down
4 changes: 4 additions & 0 deletions src/modules/infobox/components/FeatureDetail.vue
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,10 @@ function getIframeHosts(value) {
:global(.htmlpopup-content) {
padding: 7px;
}
// fix for layer HTML containing table, such as ch.bafu.gefahren-aktuelle_erdbeben
:global(.t_list) {
width: 100%;
}
td {
vertical-align: top;
}
Expand Down
4 changes: 2 additions & 2 deletions src/modules/infobox/components/FeatureListCategoryItem.vue
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ const dispatcher = { dispatcher: 'FeatureListCategoryItem.vue' }
const props = defineProps({
name: {
type: String,
type: [String, Number],
required: true,
},
item: {
Expand Down Expand Up @@ -91,7 +91,7 @@ function showContentAndScrollIntoView(event) {
@mouseleave.passive="clearHighlightedFeature"
>
<FontAwesomeIcon :icon="`caret-${showContent ? 'down' : 'right'}`" class="mx-2" />
<TextTruncate :text="name" class="flex-grow-1">
<TextTruncate :text="`${name}`" class="flex-grow-1">
<strong>{{ name }}</strong>
</TextTruncate>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,7 @@ const popoverCoordinate = computed(() => {
// If no editable feature is selected while drawing, we place the popover depending on the geometry of all
// selected features. We will find the most southern coordinate present in all features and use it as anchor.
const mostSouthernFeature = selectedFeatures.value
.filter((feature) => feature.geometry !== null)
.map((feature) => feature.geometry)
.map((geometry) => transformIntoTurfEquivalent(geometry, projection.value))
.map((turfGeom) => explode(turfGeom))
Expand Down
15 changes: 9 additions & 6 deletions src/modules/map/components/openlayers/OpenLayersPopover.vue
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import MapPopover, { MapPopoverMode } from '@/modules/map/components/MapPopover.
const props = defineProps({
coordinates: {
type: Array,
required: true,
default: null,
},
authorizePrint: {
type: Boolean,
Expand All @@ -38,17 +38,20 @@ const popoverAnchor = ref(null)
const olMap = inject('olMap')
watch(coordinates, getPixelForCoordinateFromMap)
watch(coordinates, calculateAnchorPosition)
onMounted(() => {
getPixelForCoordinateFromMap()
olMap.on('postrender', getPixelForCoordinateFromMap)
calculateAnchorPosition()
olMap.on('postrender', calculateAnchorPosition)
})
onUnmounted(() => {
olMap.un('postrender', getPixelForCoordinateFromMap)
olMap.un('postrender', calculateAnchorPosition)
})
function getPixelForCoordinateFromMap() {
function calculateAnchorPosition() {
if (!coordinates.value) {
return
}
const computedPixel = olMap.getPixelFromCoordinate(coordinates.value)
// when switching back from Cesium (or any other map framework), there can be a very small
// period where the map isn't yet able to process a pixel, this if is there to defend against that
Expand Down
21 changes: 9 additions & 12 deletions src/router/storeSync/LayerParamConfig.class.js
Original file line number Diff line number Diff line change
Expand Up @@ -122,23 +122,20 @@ export function createLayerObject(parsedLayer, currentLayer, store, featuresRequ
layer.updateDelay = updateDelay
}

if (features !== undefined) {
// only highlightable feature will output something, for the others a click coordinate is required
// (and we don't have it if we are here, as we are dealing with pre-selected feature in the URL at app startup)
if (layer.isHighlightable && features !== undefined) {
features
.toString()
.split(':')
.forEach((featureId) => {
featuresRequests.push(
getFeature(
store.getters.getLayerConfigById(parsedLayer.id),
featureId,
store.state.position.projection,
{
lang: store.state.i18n.lang,
screenWidth: store.state.ui.width,
screenHeight: store.state.ui.height,
mapExtent: flattenExtent(store.getters.extent),
}
)
getFeature(layer, featureId, store.state.position.projection, {
lang: store.state.i18n.lang,
screenWidth: store.state.ui.width,
screenHeight: store.state.ui.height,
mapExtent: flattenExtent(store.getters.extent),
})
)
})
}
Expand Down
10 changes: 6 additions & 4 deletions src/store/modules/features.store.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,11 @@ import log from '@/utils/logging'
/** @param {SelectableFeature} feature */
export function canFeatureShowProfile(feature) {
return (
(feature?.geometry?.type && ['LineString', 'Polygon'].includes(feature.geometry.type)) ||
// if MultiLineString or MultiPolygon but only contains one "feature", that's fine too (mislabeled as "multi")
(['MultiLineString', 'MultiPolygon'].includes(feature.geometry.type) &&
feature.geometry.coordinates.length === 1)
feature?.geometry?.type &&
(['LineString', 'Polygon'].includes(feature.geometry.type) ||
// if MultiLineString or MultiPolygon but only contains one "feature", that's fine too (mislabeled as "multi")
(['MultiLineString', 'MultiPolygon'].includes(feature.geometry.type) &&
feature.geometry.coordinates.length === 1))
)
}

Expand Down Expand Up @@ -653,6 +654,7 @@ export default {
screenWidth: rootState.ui.width,
screenHeight: rootState.ui.height,
mapExtent: flattenExtent(rootState.getters.mapExtent),
coordinate: rootState.map.clickInfo?.coordinate,
})
)
}
Expand Down

0 comments on commit 81b3127

Please sign in to comment.