proximity and propagator demo
This commit is contained in:
parent
d9df421dde
commit
62d8da10bf
|
|
@ -0,0 +1,147 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Proximity And Propagators</title>
|
||||
<style>
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
html {
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
body {
|
||||
min-height: 100%;
|
||||
position: relative;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
folk-map,
|
||||
geo-wiki {
|
||||
display: block;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
geo-wiki {
|
||||
display: block;
|
||||
background: white;
|
||||
border: solid 2px black;
|
||||
border-radius: 5px;
|
||||
ul {
|
||||
height: 100%;
|
||||
overflow: auto;
|
||||
margin: 0;
|
||||
scroll-padding-block-end: 1rem;
|
||||
}
|
||||
}
|
||||
|
||||
folk-cluster {
|
||||
display: block;
|
||||
position: absolute;
|
||||
inset: 0 0 0 0;
|
||||
pointer-events: none;
|
||||
background-color: #b4d8f63b;
|
||||
}
|
||||
|
||||
folk-weather {
|
||||
display: block;
|
||||
background: white;
|
||||
border: solid 2px black;
|
||||
border-radius: 5px;
|
||||
padding: 1rem;
|
||||
}
|
||||
|
||||
folk-event-propagator {
|
||||
display: block;
|
||||
position: absolute;
|
||||
inset: 0 0 0 0;
|
||||
pointer-events: none;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<folk-shape x="25" y="500">
|
||||
<label>Lat: <input type="range" min="40.5" max="41" step="0.001" value="40.76845173617708" /></label>
|
||||
</folk-shape>
|
||||
|
||||
<folk-proximity>
|
||||
<folk-shape id="g1" x="25" y="100" width="400" height="200">
|
||||
<folk-map coordinates="40.76845173617708, -73.97983074188234" zoom="15"></folk-map>
|
||||
</folk-shape>
|
||||
|
||||
<folk-shape id="g3" x="400" y="300" width="500" height="300">
|
||||
<geo-wiki></geo-wiki>
|
||||
</folk-shape>
|
||||
|
||||
<folk-shape id="g4" x="450" y="100">
|
||||
<folk-weather></folk-weather>
|
||||
</folk-shape>
|
||||
</folk-proximity>
|
||||
|
||||
<folk-event-propagator
|
||||
source="input[type='range']"
|
||||
target="folk-map"
|
||||
triggers="input"
|
||||
expression="lat: from.value"
|
||||
></folk-event-propagator>
|
||||
|
||||
<script type="module">
|
||||
import { FolkShape } from '../src/folk-shape.ts';
|
||||
import { FolkEventPropagator } from '../src/folk-event-propagator.ts';
|
||||
import { FolkMap } from '../src/folk-map.ts';
|
||||
import { FolkWeather } from '../src/folk-weather.ts';
|
||||
import { FolkCluster, FolkProximity } from '../src/folk-proximity.ts';
|
||||
import { GeoWiki } from './src/geo-wiki.ts';
|
||||
|
||||
FolkCluster.registerElement({
|
||||
constructor: FolkMap,
|
||||
events: {
|
||||
recenter: (e) => ({
|
||||
lat: e.target.coordinates.lat,
|
||||
lng: e.target.coordinates.lng,
|
||||
}),
|
||||
},
|
||||
onAdd: (element) => ({
|
||||
lat: element.coordinates.lat,
|
||||
lng: element.coordinates.lng,
|
||||
}),
|
||||
});
|
||||
|
||||
FolkCluster.registerElement({
|
||||
constructor: FolkWeather,
|
||||
onUpdate(element, data, changes) {
|
||||
const lat = data.get('lat');
|
||||
const lng = data.get('lng');
|
||||
|
||||
if (lat && lng) {
|
||||
element.coordinates = [lat, lng];
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
FolkCluster.registerElement({
|
||||
constructor: GeoWiki,
|
||||
onUpdate(element, data, changes) {
|
||||
const lat = data.get('lat');
|
||||
const lng = data.get('lng');
|
||||
|
||||
if (lat && lng) {
|
||||
element.coordinates = [lat, lng];
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
FolkShape.define();
|
||||
FolkMap.define();
|
||||
FolkCluster.define();
|
||||
FolkProximity.define();
|
||||
FolkWeather.define();
|
||||
GeoWiki.define();
|
||||
FolkEventPropagator.define();
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
@ -80,69 +80,7 @@
|
|||
import { FolkMap } from '../src/folk-map.ts';
|
||||
import { FolkWeather } from '../src/folk-weather.ts';
|
||||
import { FolkCluster, FolkProximity } from '../src/folk-proximity.ts';
|
||||
|
||||
class GeoWiki extends HTMLElement {
|
||||
static tagName = 'geo-wiki';
|
||||
|
||||
static define() {
|
||||
customElements.define(this.tagName, this);
|
||||
}
|
||||
|
||||
static observedAttributes = ['coordinates'];
|
||||
|
||||
#coordinates = [0, 0];
|
||||
#results = [];
|
||||
|
||||
get coordinates() {
|
||||
return this.#coordinates;
|
||||
}
|
||||
|
||||
set coordinates(coordinates) {
|
||||
this.setAttribute('coordinates', coordinates.join(', '));
|
||||
}
|
||||
|
||||
attributeChangedCallback(name, oldValue, newValue) {
|
||||
if (name === 'coordinates') {
|
||||
this.#coordinates = newValue.split(',').map((str) => Number(str)) || [0, 0];
|
||||
this.searchWiki(this.#coordinates);
|
||||
}
|
||||
}
|
||||
|
||||
async searchWiki([lat, long]) {
|
||||
const params = new URLSearchParams({
|
||||
action: 'query',
|
||||
format: 'json',
|
||||
list: 'geosearch',
|
||||
gscoord: `${lat}|${long}`,
|
||||
gsradius: '1000',
|
||||
gslimit: '50',
|
||||
origin: '*',
|
||||
});
|
||||
// https://www.mediawiki.org/wiki/API:Geosearch
|
||||
this.#results = await fetch(`https://en.wikipedia.org/w/api.php?${params}`)
|
||||
.then((response) => response.json())
|
||||
.then((data) => data?.query?.geosearch ?? []);
|
||||
|
||||
this.#renderResults();
|
||||
}
|
||||
|
||||
#renderResults() {
|
||||
this.firstElementChild?.remove();
|
||||
|
||||
const list = document.createElement('ul');
|
||||
|
||||
for (const result of this.#results) {
|
||||
const li = document.createElement('li');
|
||||
const a = document.createElement('a');
|
||||
a.href = `https://en.wikipedia.org/wiki/${result.title}`;
|
||||
a.textContent = result.title;
|
||||
li.appendChild(a);
|
||||
list.appendChild(li);
|
||||
}
|
||||
|
||||
this.appendChild(list);
|
||||
}
|
||||
}
|
||||
import { GeoWiki } from './src/geo-wiki.ts';
|
||||
|
||||
FolkCluster.registerElement({
|
||||
constructor: FolkMap,
|
||||
|
|
@ -160,7 +98,6 @@
|
|||
|
||||
FolkCluster.registerElement({
|
||||
constructor: FolkWeather,
|
||||
onAdd: console.log,
|
||||
onUpdate(element, data, changes) {
|
||||
const lat = data.get('lat');
|
||||
const lng = data.get('lng');
|
||||
|
|
|
|||
|
|
@ -0,0 +1,64 @@
|
|||
type LatLng = [number, number];
|
||||
|
||||
export class GeoWiki extends HTMLElement {
|
||||
static tagName = 'geo-wiki';
|
||||
|
||||
static define() {
|
||||
customElements.define(this.tagName, this);
|
||||
}
|
||||
|
||||
static observedAttributes = ['coordinates'];
|
||||
|
||||
#coordinates: LatLng = [0, 0];
|
||||
#results: any[] = [];
|
||||
|
||||
get coordinates() {
|
||||
return this.#coordinates;
|
||||
}
|
||||
|
||||
set coordinates(coordinates) {
|
||||
this.setAttribute('coordinates', coordinates.join(', '));
|
||||
}
|
||||
|
||||
attributeChangedCallback(name: string, oldValue: string | null, newValue: string | null) {
|
||||
if (name === 'coordinates') {
|
||||
this.#coordinates = ((newValue || '').split(',').map((str) => Number(str)) || [0, 0]) as LatLng;
|
||||
this.searchWiki(this.#coordinates);
|
||||
}
|
||||
}
|
||||
|
||||
async searchWiki([lat, long]: LatLng) {
|
||||
const params = new URLSearchParams({
|
||||
action: 'query',
|
||||
format: 'json',
|
||||
list: 'geosearch',
|
||||
gscoord: `${lat}|${long}`,
|
||||
gsradius: '1000',
|
||||
gslimit: '50',
|
||||
origin: '*',
|
||||
});
|
||||
// https://www.mediawiki.org/wiki/API:Geosearch
|
||||
this.#results = await fetch(`https://en.wikipedia.org/w/api.php?${params}`)
|
||||
.then((response) => response.json())
|
||||
.then((data) => data?.query?.geosearch ?? []);
|
||||
|
||||
this.#renderResults();
|
||||
}
|
||||
|
||||
#renderResults() {
|
||||
this.firstElementChild?.remove();
|
||||
|
||||
const list = document.createElement('ul');
|
||||
|
||||
for (const result of this.#results) {
|
||||
const li = document.createElement('li');
|
||||
const a = document.createElement('a');
|
||||
a.href = `https://en.wikipedia.org/wiki/${result.title}`;
|
||||
a.textContent = result.title;
|
||||
li.appendChild(a);
|
||||
list.appendChild(li);
|
||||
}
|
||||
|
||||
this.appendChild(list);
|
||||
}
|
||||
}
|
||||
|
|
@ -288,8 +288,6 @@ export class RecordPlayer extends HTMLElement {
|
|||
this.#audio.pause();
|
||||
this.#audio.currentTime = 0;
|
||||
this.dispatchEvent(new Event('stopped', { bubbles: true }));
|
||||
|
||||
// console.log(a);
|
||||
}
|
||||
|
||||
handleEvent(event: Event) {
|
||||
|
|
|
|||
|
|
@ -34,17 +34,29 @@ export class FolkMap extends HTMLElement {
|
|||
constructor() {
|
||||
super();
|
||||
|
||||
this.handleEvent = this.handleEvent.bind(this);
|
||||
|
||||
const shadow = this.attachShadow({ mode: 'open' });
|
||||
shadow.adoptedStyleSheets.push(styles);
|
||||
shadow.appendChild(this.#container);
|
||||
}
|
||||
|
||||
get coordinates() {
|
||||
get lat() {
|
||||
return this.coordinates.lat;
|
||||
}
|
||||
set lat(lat) {
|
||||
this.coordinates = [lat, this.lng];
|
||||
}
|
||||
|
||||
get lng() {
|
||||
return this.coordinates.lng;
|
||||
}
|
||||
set lng(lng) {
|
||||
this.coordinates = [this.lat, lng];
|
||||
}
|
||||
|
||||
get coordinates(): LatLng {
|
||||
return this.#map.getCenter();
|
||||
}
|
||||
set coordinates(coordinates) {
|
||||
set coordinates(coordinates: LatLngExpression) {
|
||||
this.#map.setView(coordinates);
|
||||
}
|
||||
|
||||
|
|
@ -64,7 +76,7 @@ export class FolkMap extends HTMLElement {
|
|||
})
|
||||
);
|
||||
|
||||
this.#map.on('zoom', this.handleEvent);
|
||||
// Move end includes changes to zoom
|
||||
this.#map.on('moveend', this.handleEvent);
|
||||
|
||||
this.#map.setView(
|
||||
|
|
@ -73,13 +85,12 @@ export class FolkMap extends HTMLElement {
|
|||
);
|
||||
}
|
||||
|
||||
handleEvent(event: LeafletEvent) {
|
||||
handleEvent = (event: LeafletEvent) => {
|
||||
switch (event.type) {
|
||||
case 'zoom':
|
||||
case 'moveend': {
|
||||
this.dispatchEvent(new RecenterEvent());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ export interface ElementConfig<E extends Element = Element> {
|
|||
}
|
||||
|
||||
// TODO don't hard code this
|
||||
const PROXIMITY = 50;
|
||||
const PROXIMITY = 100;
|
||||
|
||||
declare global {
|
||||
interface HTMLElementTagNameMap {
|
||||
|
|
|
|||
Loading…
Reference in New Issue