mirror of
https://gitlab.com/openstapps/openstapps.git
synced 2026-01-21 17:12:43 +00:00
@@ -12,7 +12,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License along with
|
* You should have received a copy of the GNU General Public License along with
|
||||||
* this program. If not, see <https://www.gnu.org/licenses/>.
|
* this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
import {Component, Input} from '@angular/core';
|
import {Component, Input, OnInit} from '@angular/core';
|
||||||
import {
|
import {
|
||||||
SCBuilding,
|
SCBuilding,
|
||||||
SCFloor,
|
SCFloor,
|
||||||
@@ -21,6 +21,7 @@ import {
|
|||||||
SCThings,
|
SCThings,
|
||||||
} from '@openstapps/core';
|
} from '@openstapps/core';
|
||||||
import {DataProvider} from '../../data.provider';
|
import {DataProvider} from '../../data.provider';
|
||||||
|
import {hasValidLocation, isSCFloor} from './place-types';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TODO
|
* TODO
|
||||||
@@ -31,12 +32,17 @@ import {DataProvider} from '../../data.provider';
|
|||||||
selector: 'stapps-place-detail-content',
|
selector: 'stapps-place-detail-content',
|
||||||
templateUrl: 'place-detail-content.html',
|
templateUrl: 'place-detail-content.html',
|
||||||
})
|
})
|
||||||
export class PlaceDetailContentComponent {
|
export class PlaceDetailContentComponent implements OnInit {
|
||||||
/**
|
/**
|
||||||
* TODO
|
* TODO
|
||||||
*/
|
*/
|
||||||
@Input() item: SCBuilding | SCRoom | SCPointOfInterest | SCFloor;
|
@Input() item: SCBuilding | SCRoom | SCPointOfInterest | SCFloor;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Does it have valid location or not (for showing in in a map widget)
|
||||||
|
*/
|
||||||
|
hasValidLocation = false;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TODO
|
* TODO
|
||||||
*
|
*
|
||||||
@@ -60,4 +66,9 @@ export class PlaceDetailContentComponent {
|
|||||||
(item.categories as string[]).includes('restaurant'))
|
(item.categories as string[]).includes('restaurant'))
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ngOnInit() {
|
||||||
|
this.hasValidLocation =
|
||||||
|
!isSCFloor(this.item) && hasValidLocation(this.item);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -26,8 +26,8 @@
|
|||||||
</ion-card-content>
|
</ion-card-content>
|
||||||
</ion-card>
|
</ion-card>
|
||||||
</ng-container>
|
</ng-container>
|
||||||
<ng-container *ngIf="item.type !== 'floor'">
|
<ng-container *ngIf="hasValidLocation">
|
||||||
<ion-card *ngIf="item.geo" class="map-widget">
|
<ion-card class="map-widget">
|
||||||
<stapps-map-widget [place]="item" expandable="true"></stapps-map-widget>
|
<stapps-map-widget [place]="item" expandable="true"></stapps-map-widget>
|
||||||
</ion-card>
|
</ion-card>
|
||||||
</ng-container>
|
</ng-container>
|
||||||
|
|||||||
@@ -13,22 +13,14 @@
|
|||||||
* this program. If not, see <https://www.gnu.org/licenses/>.
|
* this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
import {Component, Input} from '@angular/core';
|
import {Component, Input} from '@angular/core';
|
||||||
import {SCBuilding, SCFloor, SCPointOfInterest, SCRoom} from '@openstapps/core';
|
|
||||||
import {PositionService} from '../../../map/position.service';
|
import {PositionService} from '../../../map/position.service';
|
||||||
import {Subscription, interval} from 'rxjs';
|
import {Subscription, interval} from 'rxjs';
|
||||||
|
import {
|
||||||
type placeTypes = (SCBuilding | SCRoom | SCPointOfInterest | SCFloor) & {
|
hasValidLocation,
|
||||||
distance?: number;
|
isSCFloor,
|
||||||
};
|
PlaceTypes,
|
||||||
|
PlaceTypesWithDistance,
|
||||||
/**
|
} from './place-types';
|
||||||
* Provide information if a place is a floor
|
|
||||||
*
|
|
||||||
* @param place A place to check
|
|
||||||
*/
|
|
||||||
function isSCFloor(place: placeTypes): place is SCFloor {
|
|
||||||
return place.type === 'floor';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Shows a place as a list item
|
* Shows a place as a list item
|
||||||
@@ -41,16 +33,16 @@ export class PlaceListItemComponent {
|
|||||||
/**
|
/**
|
||||||
* Item getter
|
* Item getter
|
||||||
*/
|
*/
|
||||||
get item(): placeTypes {
|
get item(): PlaceTypesWithDistance {
|
||||||
return this._item;
|
return this._item;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An item to show (setter is used as there were issues assigning the distance to the right place in a list)
|
* An item to show (setter is used as there were issues assigning the distance to the right place in a list)
|
||||||
*/
|
*/
|
||||||
@Input() set item(item: placeTypes) {
|
@Input() set item(item: PlaceTypes) {
|
||||||
this._item = item;
|
this._item = item;
|
||||||
if (!isSCFloor(item)) {
|
if (!isSCFloor(item) && hasValidLocation(item)) {
|
||||||
this.distance = this.positionService.getDistance(item.geo.point);
|
this.distance = this.positionService.getDistance(item.geo.point);
|
||||||
this.distanceSubscription = interval(10_000).subscribe(_ => {
|
this.distanceSubscription = interval(10_000).subscribe(_ => {
|
||||||
this.distance = this.positionService.getDistance(item.geo.point);
|
this.distance = this.positionService.getDistance(item.geo.point);
|
||||||
@@ -61,7 +53,7 @@ export class PlaceListItemComponent {
|
|||||||
/**
|
/**
|
||||||
* An item to show
|
* An item to show
|
||||||
*/
|
*/
|
||||||
private _item: placeTypes;
|
private _item: PlaceTypesWithDistance;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Distance in meters
|
* Distance in meters
|
||||||
|
|||||||
45
src/app/modules/data/types/place/place-types.ts
Normal file
45
src/app/modules/data/types/place/place-types.ts
Normal file
@@ -0,0 +1,45 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2021 StApps
|
||||||
|
* This program is free software: you can redistribute it and/or modify it
|
||||||
|
* under the terms of the GNU General Public License as published by the Free
|
||||||
|
* Software Foundation, version 3.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||||
|
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||||
|
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||||
|
* more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License along with
|
||||||
|
* this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
import {SCBuilding, SCFloor, SCPointOfInterest, SCRoom} from '@openstapps/core';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Possible place types
|
||||||
|
*/
|
||||||
|
export type PlaceTypes = SCBuilding | SCRoom | SCPointOfInterest | SCFloor;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Place types with their dynamic distance (from the position of the device)
|
||||||
|
*/
|
||||||
|
export type PlaceTypesWithDistance = PlaceTypes & {
|
||||||
|
distance?: number;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Detects "null island" places, which means places with point coordinates [0, 0]
|
||||||
|
*
|
||||||
|
* @param place A place to check
|
||||||
|
*/
|
||||||
|
export function hasValidLocation(place: Exclude<PlaceTypes, SCFloor>) {
|
||||||
|
return place.geo.point.coordinates.some(coordinate => coordinate !== 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Provide information if a place is a floor
|
||||||
|
*
|
||||||
|
* @param place A place to check
|
||||||
|
*/
|
||||||
|
export function isSCFloor(place: PlaceTypes): place is SCFloor {
|
||||||
|
return place.type === 'floor';
|
||||||
|
}
|
||||||
@@ -14,6 +14,7 @@
|
|||||||
*/
|
*/
|
||||||
import {ElementRef, Injectable} from '@angular/core';
|
import {ElementRef, Injectable} from '@angular/core';
|
||||||
import {
|
import {
|
||||||
|
SCBuilding,
|
||||||
SCSearchFilter,
|
SCSearchFilter,
|
||||||
SCSearchQuery,
|
SCSearchQuery,
|
||||||
SCSearchResponse,
|
SCSearchResponse,
|
||||||
@@ -24,6 +25,7 @@ import {Point, Polygon} from 'geojson';
|
|||||||
import {divIcon, geoJSON, icon, LatLng, Map, marker, Marker} from 'leaflet';
|
import {divIcon, geoJSON, icon, LatLng, Map, marker, Marker} from 'leaflet';
|
||||||
import {DataProvider} from '../data/data.provider';
|
import {DataProvider} from '../data/data.provider';
|
||||||
import {MapPosition, PositionService} from './position.service';
|
import {MapPosition, PositionService} from './position.service';
|
||||||
|
import {hasValidLocation} from '../data/types/place/place-types';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Provides methods for presenting the map
|
* Provides methods for presenting the map
|
||||||
@@ -125,7 +127,8 @@ export class MapProvider {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Provide places (buildings and canteens)
|
* Provide places (buildings and canteens) const result = await this.dataProvider.search(query);
|
||||||
|
|
||||||
*
|
*
|
||||||
* @param contextFilter Additional contextual filter (e.g. from the context menu)
|
* @param contextFilter Additional contextual filter (e.g. from the context menu)
|
||||||
* @param queryText Query (text) of the search query
|
* @param queryText Query (text) of the search query
|
||||||
@@ -224,6 +227,12 @@ export class MapProvider {
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.dataProvider.search(query);
|
const result = await this.dataProvider.search(query);
|
||||||
|
|
||||||
|
result.data = result.data.filter(place =>
|
||||||
|
hasValidLocation(place as SCBuilding),
|
||||||
|
);
|
||||||
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -448,12 +448,15 @@ export class MapPageComponent {
|
|||||||
* Show a single place
|
* Show a single place
|
||||||
*/
|
*/
|
||||||
async showItemModal(item: SCPlace) {
|
async showItemModal(item: SCPlace) {
|
||||||
const placeWithoutGeo = {...item, geo: undefined};
|
const placeWithNullLocation = {
|
||||||
|
...item,
|
||||||
|
geo: {point: {coordinates: [0, 0]}},
|
||||||
|
};
|
||||||
this.modal = await this.modalController.create({
|
this.modal = await this.modalController.create({
|
||||||
component: MapSingleModalComponent,
|
component: MapSingleModalComponent,
|
||||||
swipeToClose: true,
|
swipeToClose: true,
|
||||||
componentProps: {
|
componentProps: {
|
||||||
item: placeWithoutGeo,
|
item: placeWithNullLocation,
|
||||||
dismissAction: () => {
|
dismissAction: () => {
|
||||||
this.modal.dismiss();
|
this.modal.dismiss();
|
||||||
},
|
},
|
||||||
|
|||||||
Reference in New Issue
Block a user