@unabridged/midwest 0.24.3 → 0.24.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (26) hide show
  1. package/app/assets/javascript/midwest/index.ts +8 -0
  2. package/app/assets/javascript/midwest/map_providers.ts +61 -0
  3. package/app/assets/javascript/midwest.js +972 -6
  4. package/app/assets/javascript/midwest.js.map +1 -1
  5. package/app/assets/stylesheets/midwest.css +1 -1
  6. package/app/assets/stylesheets/midwest.tailwind.css +6 -1
  7. package/dist/css/midwest.css +1 -1
  8. package/dist/javascript/collection/app/assets/javascript/midwest/index.js +8 -0
  9. package/dist/javascript/collection/app/assets/javascript/midwest/index.js.map +1 -1
  10. package/dist/javascript/collection/app/assets/javascript/midwest/map_providers.js +56 -0
  11. package/dist/javascript/collection/app/assets/javascript/midwest/map_providers.js.map +1 -0
  12. package/dist/javascript/collection/app/components/midwest/form/address_component/address_component_controller.js +441 -0
  13. package/dist/javascript/collection/app/components/midwest/form/address_component/address_component_controller.js.map +1 -0
  14. package/dist/javascript/collection/app/components/midwest/form/live_summary_component/live_summary_component_controller.js +55 -1
  15. package/dist/javascript/collection/app/components/midwest/form/live_summary_component/live_summary_component_controller.js.map +1 -1
  16. package/dist/javascript/collection/app/components/midwest/map_component/map_component_controller.js +297 -0
  17. package/dist/javascript/collection/app/components/midwest/map_component/map_component_controller.js.map +1 -0
  18. package/dist/javascript/collection/app/components/midwest/onboarding_component/onboarding_component_controller.js +34 -5
  19. package/dist/javascript/collection/app/components/midwest/onboarding_component/onboarding_component_controller.js.map +1 -1
  20. package/dist/javascript/collection/app/components/midwest/page_transition_component/page_transition_component_controller.js +38 -0
  21. package/dist/javascript/collection/app/components/midwest/page_transition_component/page_transition_component_controller.js.map +1 -0
  22. package/dist/javascript/collection/app/components/midwest/popover_component/popover_component_controller.js +67 -0
  23. package/dist/javascript/collection/app/components/midwest/popover_component/popover_component_controller.js.map +1 -0
  24. package/dist/javascript/midwest.js +972 -6
  25. package/dist/javascript/midwest.js.map +1 -1
  26. package/package.json +1 -1
@@ -0,0 +1 @@
1
+ {"version":3,"file":"map_component_controller.js","sources":["../../../../../../../app/components/midwest/map_component/map_component_controller.ts"],"sourcesContent":["import { Controller } from '@hotwired/stimulus'\nimport { loadMapKitScript, loadGoogleMapsScript, loadLeafletScript } from '../../../assets/javascript/midwest/map_providers'\n\n// Leaflet tile layers keyed by Midwest map type (MapKit-style strings) and a\n// special 'Dark' entry for dark color schemes. CartoDB and ESRI tiles are free\n// for open-source / low-traffic use; no API key required.\nconst LEAFLET_TILES: Record<string, { url: string; attribution: string; maxZoom?: number }> = {\n MutedStandard: {\n url: 'https://{s}.basemaps.cartocdn.com/light_all/{z}/{x}/{y}{r}.png',\n attribution: '&copy; <a href=\"https://www.openstreetmap.org/copyright\">OpenStreetMap</a> contributors &copy; <a href=\"https://carto.com/attributions\">CARTO</a>'\n },\n Standard: {\n url: 'https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png',\n attribution: '&copy; <a href=\"https://www.openstreetmap.org/copyright\">OpenStreetMap</a> contributors',\n maxZoom: 19\n },\n Hybrid: {\n url: 'https://{s}.basemaps.cartocdn.com/rastertiles/voyager/{z}/{x}/{y}{r}.png',\n attribution: '&copy; <a href=\"https://www.openstreetmap.org/copyright\">OpenStreetMap</a> contributors &copy; <a href=\"https://carto.com/attributions\">CARTO</a>'\n },\n Satellite: {\n url: 'https://server.arcgisonline.com/ArcGIS/rest/services/World_Imagery/MapServer/tile/{z}/{y}/{x}',\n attribution: 'Tiles &copy; Esri &mdash; Source: Esri, i-cubed, USDA, USGS, AEX, GeoEye, Getmapping, Aerogrid, IGN, IGP, UPR-EGP, and the GIS User Community',\n maxZoom: 18\n },\n Dark: {\n url: 'https://{s}.basemaps.cartocdn.com/dark_all/{z}/{x}/{y}{r}.png',\n attribution: '&copy; <a href=\"https://www.openstreetmap.org/copyright\">OpenStreetMap</a> contributors &copy; <a href=\"https://carto.com/attributions\">CARTO</a>'\n }\n}\n\n// Muted (light) style for Google Maps — mirrors MapKit's MutedStandard.\nconst GOOGLE_MUTED_STYLES = [\n { elementType: 'geometry', stylers: [{ color: '#f5f5f5' }] },\n { elementType: 'labels.icon', stylers: [{ visibility: 'off' }] },\n { elementType: 'labels.text.fill', stylers: [{ color: '#616161' }] },\n { elementType: 'labels.text.stroke', stylers: [{ color: '#f5f5f5' }] },\n { featureType: 'administrative.land_parcel', elementType: 'labels', stylers: [{ visibility: 'off' }] },\n { featureType: 'poi', elementType: 'geometry', stylers: [{ color: '#eeeeee' }] },\n { featureType: 'poi.park', elementType: 'geometry', stylers: [{ color: '#e5e5e5' }] },\n { featureType: 'road', elementType: 'geometry', stylers: [{ color: '#ffffff' }] },\n { featureType: 'road.highway', elementType: 'geometry', stylers: [{ color: '#dadada' }] },\n { featureType: 'water', elementType: 'geometry', stylers: [{ color: '#c9c9c9' }] }\n]\n\n// Google's standard dark theme.\nconst GOOGLE_DARK_STYLES = [\n { elementType: 'geometry', stylers: [{ color: '#242f3e' }] },\n { elementType: 'labels.text.stroke', stylers: [{ color: '#242f3e' }] },\n { elementType: 'labels.text.fill', stylers: [{ color: '#746855' }] },\n { featureType: 'administrative.locality', elementType: 'labels.text.fill', stylers: [{ color: '#d59563' }] },\n { featureType: 'poi', elementType: 'labels.text.fill', stylers: [{ color: '#d59563' }] },\n { featureType: 'poi.park', elementType: 'geometry', stylers: [{ color: '#263c3f' }] },\n { featureType: 'poi.park', elementType: 'labels.text.fill', stylers: [{ color: '#6b9a76' }] },\n { featureType: 'road', elementType: 'geometry', stylers: [{ color: '#38414e' }] },\n { featureType: 'road', elementType: 'geometry.stroke', stylers: [{ color: '#212a37' }] },\n { featureType: 'road', elementType: 'labels.text.fill', stylers: [{ color: '#9ca5b3' }] },\n { featureType: 'road.highway', elementType: 'geometry', stylers: [{ color: '#746855' }] },\n { featureType: 'road.highway', elementType: 'geometry.stroke', stylers: [{ color: '#1f2835' }] },\n { featureType: 'road.highway', elementType: 'labels.text.fill', stylers: [{ color: '#f3d19c' }] },\n { featureType: 'transit', elementType: 'geometry', stylers: [{ color: '#2f3948' }] },\n { featureType: 'transit.station', elementType: 'labels.text.fill', stylers: [{ color: '#d59563' }] },\n { featureType: 'water', elementType: 'geometry', stylers: [{ color: '#17263c' }] },\n { featureType: 'water', elementType: 'labels.text.fill', stylers: [{ color: '#515c6d' }] },\n { featureType: 'water', elementType: 'labels.text.stroke', stylers: [{ color: '#17263c' }] }\n]\n\n\nexport default class Map extends Controller<HTMLElement> {\n static values = {\n latitude: { type: Number, default: 37.334886 },\n longitude: { type: Number, default: -122.008988 },\n span: { type: Number, default: 0.1 },\n mapType: { type: String, default: 'MutedStandard' },\n colorScheme: { type: String, default: 'Auto' },\n provider: { type: String, default: '' },\n token: { type: String, default: '' },\n tokenUrl: { type: String, default: '' },\n apiKey: { type: String, default: '' },\n zoom: { type: Number, default: -1 },\n markers: { type: Array, default: [] },\n showsUserLocation: { type: Boolean, default: false },\n showsMapTypeControl: { type: Boolean, default: false },\n showsZoomControl: { type: Boolean, default: true },\n showsCompass: { type: String, default: 'Adaptive' },\n rotation: { type: Number, default: 0 }\n }\n\n declare latitudeValue: number\n declare longitudeValue: number\n declare spanValue: number\n declare mapTypeValue: string\n declare colorSchemeValue: string\n declare providerValue: string\n declare tokenValue: string\n declare tokenUrlValue: string\n declare apiKeyValue: string\n declare zoomValue: number\n declare markersValue: {\n latitude: number\n longitude: number\n title?: string\n subtitle?: string\n color?: string\n glyphText?: string\n /** When true, the callout / info window is shown on first load. */\n open?: boolean\n }[]\n\n declare showsUserLocationValue: boolean\n declare showsMapTypeControlValue: boolean\n declare showsZoomControlValue: boolean\n declare showsCompassValue: string\n declare rotationValue: number\n\n private mapInstance: any = null\n\n async connect (): Promise<void> {\n const provider = this.providerValue\n if (!provider) return\n\n try {\n if (provider === 'mapkit') {\n await loadMapKitScript()\n this.initMapKit()\n this.initMapKitMap()\n } else if (provider === 'google') {\n await loadGoogleMapsScript(this.apiKeyValue)\n this.initGoogleMap()\n } else if (provider === 'leaflet') {\n await loadLeafletScript()\n this.initLeafletMap()\n }\n } catch (err) {\n console.error(`[midwest-map] Failed to initialise ${provider} map:`, err)\n }\n }\n\n disconnect (): void {\n if (this.mapInstance) {\n if (this.providerValue === 'mapkit') this.mapInstance.destroy()\n if (this.providerValue === 'leaflet') this.mapInstance.remove()\n this.mapInstance = null\n }\n }\n\n tokenValueChanged (): void {\n if (this.mapInstance && this.providerValue === 'mapkit') this.initMapKit()\n }\n\n // --- MapKit ---\n\n private initMapKit (): void {\n const mk = (window as any).mapkit\n const token = this.tokenValue\n const tokenUrl = this.tokenUrlValue\n\n mk.init({\n authorizationCallback: (done: (t: string) => void) => {\n if (token) {\n done(token)\n } else if (tokenUrl) {\n fetch(tokenUrl)\n .then(r => r.text())\n .then(done)\n .catch(err => console.error('[midwest-map] Token fetch failed:', err))\n }\n },\n language: document.documentElement.lang || 'en'\n })\n }\n\n private initMapKitMap (): void {\n const mk = (window as any).mapkit\n\n const region = new mk.CoordinateRegion(\n new mk.Coordinate(this.latitudeValue, this.longitudeValue),\n new mk.CoordinateSpan(this.spanValue, this.spanValue)\n )\n\n const colorScheme = this.colorSchemeValue === 'Auto'\n ? (window.matchMedia('(prefers-color-scheme: dark)').matches\n ? mk.Map.ColorSchemes.Dark\n : mk.Map.ColorSchemes.Light)\n : mk.Map.ColorSchemes[this.colorSchemeValue]\n\n this.mapInstance = new mk.Map(this.element, {\n region,\n mapType: mk.Map.MapTypes[this.mapTypeValue],\n colorScheme,\n showsUserLocation: this.showsUserLocationValue,\n showsMapTypeControl: this.showsMapTypeControlValue,\n showsZoomControl: this.showsZoomControlValue,\n showsCompass: mk.FeatureVisibility[this.showsCompassValue],\n rotation: this.rotationValue\n })\n\n this.addMapKitMarkers()\n this.element.dataset.mapLoaded = 'true'\n }\n\n private addMapKitMarkers (): void {\n const mk = (window as any).mapkit\n if (!this.markersValue.length) return\n\n const annotations = this.markersValue.map(m => {\n const opts: Record<string, any> = {}\n if (m.title) opts.title = m.title\n if (m.subtitle) opts.subtitle = m.subtitle\n if (m.color) opts.color = m.color\n if (m.glyphText) opts.glyphText = m.glyphText\n\n return new mk.MarkerAnnotation(\n new mk.Coordinate(m.latitude, m.longitude),\n opts\n )\n })\n\n this.mapInstance.addAnnotations(annotations)\n\n // Select the first marker flagged as open so its callout shows on load.\n const openIndex = this.markersValue.findIndex(m => m.open)\n if (openIndex >= 0) {\n this.mapInstance.selectedAnnotation = annotations[openIndex]\n }\n }\n\n // --- Google Maps ---\n\n private initGoogleMap (): void {\n const g = (window as any).google\n const zoom = this.zoomValue > 0 ? this.zoomValue : this.spanToZoom(this.spanValue)\n\n const isDark = this.colorSchemeValue === 'Dark' ||\n (this.colorSchemeValue === 'Auto' && window.matchMedia('(prefers-color-scheme: dark)').matches)\n\n const mapTypeId = this.googleMapTypeId()\n\n const opts: Record<string, any> = {\n center: { lat: this.latitudeValue, lng: this.longitudeValue },\n zoom,\n mapTypeId,\n disableDefaultUI: true,\n zoomControl: this.showsZoomControlValue,\n mapTypeControl: this.showsMapTypeControlValue,\n fullscreenControl: false,\n streetViewControl: false\n }\n\n const styles = this.googleMapStyles(isDark, mapTypeId)\n if (styles) opts.styles = styles\n\n this.mapInstance = new g.maps.Map(this.element, opts)\n this.addGoogleMarkers()\n this.element.dataset.mapLoaded = 'true'\n }\n\n private googleMapTypeId (): string {\n const types: Record<string, string> = {\n Standard: 'roadmap',\n Hybrid: 'hybrid',\n Satellite: 'satellite',\n MutedStandard: 'roadmap'\n }\n return types[this.mapTypeValue] ?? 'roadmap'\n }\n\n private googleMapStyles (isDark: boolean, mapTypeId: string): object[] | null {\n if (mapTypeId !== 'roadmap') return null\n if (isDark) return GOOGLE_DARK_STYLES\n if (this.mapTypeValue === 'MutedStandard') return GOOGLE_MUTED_STYLES\n return null\n }\n\n private addGoogleMarkers (): void {\n const g = (window as any).google\n if (!this.markersValue.length) return\n\n this.markersValue.forEach(m => {\n const marker = new g.maps.Marker({\n map: this.mapInstance,\n position: { lat: m.latitude, lng: m.longitude },\n title: m.title ?? ''\n })\n\n if (m.open && m.title) {\n const content = m.subtitle\n ? `<strong>${m.title}</strong><br><span style=\"color:#777\">${m.subtitle}</span>`\n : `<strong>${m.title}</strong>`\n const infoWindow = new g.maps.InfoWindow({ content })\n infoWindow.open(this.mapInstance, marker)\n }\n })\n }\n\n // --- Leaflet ---\n\n private initLeafletMap (): void {\n const L = (window as any).L\n const zoom = this.zoomValue > 0 ? this.zoomValue : this.spanToZoom(this.spanValue)\n\n const isDark = this.colorSchemeValue === 'Dark' ||\n (this.colorSchemeValue === 'Auto' && window.matchMedia('(prefers-color-scheme: dark)').matches)\n\n const tileKey = isDark ? 'Dark' : this.mapTypeValue\n const tile = LEAFLET_TILES[tileKey] ?? LEAFLET_TILES.MutedStandard\n\n this.mapInstance = L.map(this.element, {\n center: [this.latitudeValue, this.longitudeValue],\n zoom,\n zoomControl: this.showsZoomControlValue,\n attributionControl: true\n })\n\n L.tileLayer(tile.url, {\n attribution: tile.attribution,\n maxZoom: tile.maxZoom ?? 19\n }).addTo(this.mapInstance)\n\n this.addLeafletMarkers()\n this.element.dataset.mapLoaded = 'true'\n }\n\n private addLeafletMarkers (): void {\n const L = (window as any).L\n if (!this.markersValue.length) return\n\n this.markersValue.forEach(m => {\n const icon = this.leafletMarkerIcon(m.color, m.glyphText)\n const marker = L.marker([m.latitude, m.longitude], { icon })\n .addTo(this.mapInstance)\n\n if (m.title) {\n const content = m.subtitle\n ? `<strong>${m.title}</strong><br><span style=\"color:#777\">${m.subtitle}</span>`\n : `<strong>${m.title}</strong>`\n marker.bindPopup(content)\n if (m.open) marker.openPopup()\n }\n })\n }\n\n // Returns a Leaflet icon — default blue when no color/glyph, otherwise a\n // custom SVG pin rendered via divIcon.\n private leafletMarkerIcon (color?: string, glyphText?: string): any {\n const L = (window as any).L\n if (!color && !glyphText) return new L.Icon.Default()\n\n const fill = color ?? '#2563eb'\n const inner = glyphText\n ? `<text x=\"12\" y=\"16\" text-anchor=\"middle\" font-size=\"9\" font-family=\"system-ui,sans-serif\" fill=\"white\">${glyphText}</text>`\n : `<circle cx=\"12\" cy=\"12\" r=\"4\" fill=\"rgba(255,255,255,0.9)\"/>`\n\n const svg = [\n '<svg xmlns=\"http://www.w3.org/2000/svg\" viewBox=\"0 0 24 36\" width=\"24\" height=\"36\">',\n ` <path d=\"M12 0C5.373 0 0 5.373 0 12c0 9 12 24 12 24s12-15 12-24C24 5.373 18.627 0 12 0z\" fill=\"${fill}\"/>`,\n ` ${inner}`,\n '</svg>'\n ].join('')\n\n return L.divIcon({\n html: svg,\n className: '',\n iconSize: [24, 36] as [number, number],\n iconAnchor: [12, 36] as [number, number],\n popupAnchor: [0, -36] as [number, number]\n })\n }\n\n // Approximate MapKit coordinate span to a Web Mercator zoom level.\n // CoordinateSpan 360° = zoom 0; halving span adds 1 zoom level.\n private spanToZoom (span: number): number {\n return Math.round(Math.log2(360 / span))\n }\n}\n"],"names":[],"mappings":"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"}
@@ -10,14 +10,14 @@ const FOCUSABLE = [
10
10
  ].join(", ");
11
11
  const GAP = 12;
12
12
  class Onboarding extends Controller {
13
- static targets = ["step", "overlay", "card", "title", "body", "back", "next", "done", "arrow"];
13
+ static targets = ["step", "overlay", "card", "title", "body", "back", "next", "done", "arrow", "motion"];
14
14
  static values = {
15
- autoOpen: { type: Boolean, default: false },
16
- confirm: { type: String, default: "" }
15
+ autoOpen: { type: Boolean, default: false }
17
16
  };
18
17
  steps = [];
19
18
  index = 0;
20
19
  active = false;
20
+ justOpened = false;
21
21
  previousFocus = null;
22
22
  highlighted = null;
23
23
  connect() {
@@ -47,6 +47,7 @@ class Onboarding extends Controller {
47
47
  this.previousFocus = document.activeElement;
48
48
  this.overlayTarget.hidden = false;
49
49
  this.cardTarget.hidden = false;
50
+ this.justOpened = true;
50
51
  document.addEventListener("keydown", this.handleKeydown, true);
51
52
  window.addEventListener("resize", this.reposition);
52
53
  window.addEventListener("scroll", this.reposition, true);
@@ -81,14 +82,14 @@ class Onboarding extends Controller {
81
82
  cancel() {
82
83
  if (!this.active)
83
84
  return;
84
- if (this.confirmValue && !window.confirm(this.confirmValue))
85
- return;
86
85
  this.teardown();
87
86
  this.dispatch("cancel", { bubbles: true });
88
87
  }
89
88
  render(index) {
90
89
  this.index = index;
91
90
  const step = this.steps[index];
91
+ const replay = !this.justOpened;
92
+ this.justOpened = false;
92
93
  this.clearHighlight();
93
94
  this.titleTarget.textContent = step.title;
94
95
  this.renderBody(step);
@@ -100,6 +101,9 @@ class Onboarding extends Controller {
100
101
  } else {
101
102
  this.center();
102
103
  }
104
+ if (replay && this.hasMotionTarget) {
105
+ this.replayMotion(this.cardTarget.dataset.placement ?? "center");
106
+ }
103
107
  this.dispatch("show", { detail: { index, name: step.name }, bubbles: true });
104
108
  this.focusCard();
105
109
  }
@@ -201,9 +205,34 @@ class Onboarding extends Controller {
201
205
  this.cardTarget.focus();
202
206
  });
203
207
  }
208
+ // Re-triggers the midwest_motion @starting-style entry on step transitions.
209
+ // The initial show is handled by @starting-style firing when the card's
210
+ // `hidden` is removed; subsequent steps need an explicit re-trigger since the
211
+ // card stays in the DOM. Toggling `hidden` on the motion element triggers
212
+ // @starting-style again; the rAF ensures both DOM writes land in the same
213
+ // paint so there is no blank-card flash.
214
+ replayMotion(placement) {
215
+ const el = this.motionTarget;
216
+ const dir = { bottom: "up", top: "down", right: "left", left: "right" };
217
+ el.classList.remove("from-up", "from-down", "from-left", "from-right");
218
+ const from = dir[placement];
219
+ if (from)
220
+ el.classList.add(`from-${from}`);
221
+ el.hidden = true;
222
+ requestAnimationFrame(() => {
223
+ if (this.active)
224
+ el.hidden = false;
225
+ });
226
+ }
204
227
  teardown() {
205
228
  this.active = false;
206
229
  this.clearHighlight();
230
+ this.element.querySelectorAll("[popover]").forEach((el) => {
231
+ try {
232
+ el.hidePopover();
233
+ } catch {
234
+ }
235
+ });
207
236
  this.overlayTarget.hidden = true;
208
237
  this.cardTarget.hidden = true;
209
238
  document.removeEventListener("keydown", this.handleKeydown, true);
@@ -1 +1 @@
1
- {"version":3,"file":"onboarding_component_controller.js","sources":["../../../../../../../app/components/midwest/onboarding_component/onboarding_component_controller.ts"],"sourcesContent":["import { Controller } from '@hotwired/stimulus'\n\nconst FOCUSABLE = [\n 'a[href]',\n 'button:not([disabled])',\n 'textarea:not([disabled])',\n 'input:not([disabled])',\n 'select:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"])'\n].join(', ')\n\nconst GAP = 12 // px between the target and the card\n\ninterface StepConfig {\n el: HTMLElement\n name: string\n selector: string\n position: string\n title: string\n nextText: string\n backText: string\n completeText: string\n canClickTarget: boolean\n}\n\n// Native, dependency-free guided-tour engine. Reads the nested step config\n// carriers, then walks the user through them with a dimmed overlay, a card\n// positioned against each step's target element, and Back/Next/Done buttons.\nexport default class Onboarding extends Controller<HTMLElement> {\n static targets = ['step', 'overlay', 'card', 'title', 'body', 'back', 'next', 'done', 'arrow']\n\n static values = {\n autoOpen: { type: Boolean, default: false },\n confirm: { type: String, default: '' }\n }\n\n declare readonly stepTargets: HTMLElement[]\n declare readonly overlayTarget: HTMLElement\n declare readonly cardTarget: HTMLElement\n declare readonly titleTarget: HTMLElement\n declare readonly bodyTarget: HTMLElement\n declare readonly backTarget: HTMLButtonElement\n declare readonly nextTarget: HTMLButtonElement\n declare readonly doneTarget: HTMLButtonElement\n declare readonly arrowTarget: HTMLElement\n declare autoOpenValue: boolean\n declare confirmValue: string\n\n private steps: StepConfig[] = []\n private index = 0\n private active = false\n private previousFocus: HTMLElement | null = null\n private highlighted: HTMLElement | null = null\n\n connect () {\n this.steps = this.stepTargets.map((el) => ({\n el,\n name: el.dataset.name ?? '',\n selector: el.dataset.selector ?? '',\n position: el.dataset.position ?? 'auto',\n title: el.dataset.title ?? '',\n nextText: el.dataset.nextText ?? 'Next',\n backText: el.dataset.backText ?? 'Back',\n completeText: el.dataset.completeText ?? 'Done',\n canClickTarget: el.dataset.canClickTarget === 'true'\n }))\n\n window.addEventListener('midwest-onboarding:open', this.handleOpen)\n\n if (this.autoOpenValue) this.start()\n }\n\n disconnect () {\n window.removeEventListener('midwest-onboarding:open', this.handleOpen)\n this.teardown()\n }\n\n start () {\n if (this.active || this.steps.length === 0) return\n this.active = true\n this.previousFocus = document.activeElement as HTMLElement | null\n this.overlayTarget.hidden = false\n this.cardTarget.hidden = false\n document.addEventListener('keydown', this.handleKeydown, true)\n window.addEventListener('resize', this.reposition)\n window.addEventListener('scroll', this.reposition, true)\n this.dispatch('start', { bubbles: true })\n this.render(0)\n }\n\n next () {\n if (this.index < this.steps.length - 1) this.render(this.index + 1)\n else this.complete()\n }\n\n back () {\n if (this.index > 0) this.render(this.index - 1)\n }\n\n // Jump to a step by its `name`.\n show (name: string) {\n const target = this.steps.findIndex((step) => step.name === name)\n if (target >= 0) {\n if (!this.active) this.start()\n this.render(target)\n }\n }\n\n complete () {\n if (!this.active) return\n this.teardown()\n this.dispatch('complete', { bubbles: true })\n }\n\n cancel () {\n if (!this.active) return\n if (this.confirmValue && !window.confirm(this.confirmValue)) return\n this.teardown()\n this.dispatch('cancel', { bubbles: true })\n }\n\n private render (index: number) {\n this.index = index\n const step = this.steps[index]\n\n this.clearHighlight()\n\n this.titleTarget.textContent = step.title\n this.renderBody(step)\n this.renderButtons(step, index)\n\n const target = step.selector\n ? document.querySelector<HTMLElement>(step.selector)\n : null\n\n if (target) {\n this.highlight(target, step.canClickTarget)\n this.position(target, step.position)\n } else {\n this.center()\n }\n\n this.dispatch('show', { detail: { index, name: step.name }, bubbles: true })\n this.focusCard()\n }\n\n private renderBody (step: StepConfig) {\n this.bodyTarget.replaceChildren()\n const template = step.el.querySelector('template')\n if (template) this.bodyTarget.appendChild(template.content.cloneNode(true))\n }\n\n private renderButtons (step: StepConfig, index: number) {\n const isFirst = index === 0\n const isLast = index === this.steps.length - 1\n\n // Back keeps its layout box (visibility) so the forward button never shifts;\n // Next and Done are mutually exclusive, so exactly one fills the right slot.\n this.backTarget.textContent = step.backText\n this.backTarget.style.visibility = isFirst ? 'hidden' : ''\n\n // Inline display beats the button's own `display: inline-flex` rule.\n this.nextTarget.textContent = step.nextText\n this.nextTarget.style.display = isLast ? 'none' : ''\n\n this.doneTarget.textContent = step.completeText\n this.doneTarget.style.display = isLast ? '' : 'none'\n }\n\n private highlight (target: HTMLElement, canClickTarget: boolean) {\n target.classList.add('midwest-onboarding-highlight')\n target.classList.toggle('is-locked', !canClickTarget)\n this.highlighted = target\n target.scrollIntoView({ behavior: 'smooth', block: 'center' })\n }\n\n private clearHighlight () {\n this.highlighted?.classList.remove('midwest-onboarding-highlight', 'is-locked')\n this.highlighted = null\n }\n\n // Places the card against the target, choosing a side when `position` is auto.\n private position (target: HTMLElement, position: string) {\n const rect = target.getBoundingClientRect()\n const card = this.cardTarget.getBoundingClientRect()\n const vw = window.innerWidth\n const vh = window.innerHeight\n\n let placement = position\n if (placement === 'auto') {\n if (rect.bottom + card.height + GAP <= vh) placement = 'bottom'\n else if (rect.top - card.height - GAP >= 0) placement = 'top'\n else if (rect.right + card.width + GAP <= vw) placement = 'right'\n else placement = 'left'\n }\n\n let top: number\n let left: number\n\n switch (placement) {\n case 'top':\n top = rect.top - card.height - GAP\n left = rect.left + rect.width / 2 - card.width / 2\n break\n case 'left':\n top = rect.top + rect.height / 2 - card.height / 2\n left = rect.left - card.width - GAP\n break\n case 'right':\n top = rect.top + rect.height / 2 - card.height / 2\n left = rect.right + GAP\n break\n default: // bottom\n top = rect.bottom + GAP\n left = rect.left + rect.width / 2 - card.width / 2\n break\n }\n\n // Keep the card fully on screen.\n left = Math.max(8, Math.min(left, vw - card.width - 8))\n top = Math.max(8, Math.min(top, vh - card.height - 8))\n\n this.cardTarget.style.top = `${top}px`\n this.cardTarget.style.left = `${left}px`\n this.cardTarget.dataset.placement = placement\n\n this.positionArrow(placement, rect, top, left)\n }\n\n // Nudges the arrow so it points at the target's center, not the card's.\n private positionArrow (placement: string, rect: DOMRect, top: number, left: number) {\n const card = this.cardTarget.getBoundingClientRect()\n const arrow = this.arrowTarget.style\n\n if (placement === 'top' || placement === 'bottom') {\n const targetCenter = rect.left + rect.width / 2\n const offset = Math.max(12, Math.min(targetCenter - left, card.width - 12))\n arrow.left = `${offset}px`\n arrow.top = ''\n } else {\n const targetCenter = rect.top + rect.height / 2\n const offset = Math.max(12, Math.min(targetCenter - top, card.height - 12))\n arrow.top = `${offset}px`\n arrow.left = ''\n }\n }\n\n private center () {\n const card = this.cardTarget.getBoundingClientRect()\n this.cardTarget.style.top = `${Math.max(8, window.innerHeight / 2 - card.height / 2)}px`\n this.cardTarget.style.left = `${Math.max(8, window.innerWidth / 2 - card.width / 2)}px`\n this.cardTarget.dataset.placement = 'center'\n }\n\n private focusCard () {\n requestAnimationFrame(() => {\n if (this.active) this.cardTarget.focus()\n })\n }\n\n private teardown () {\n this.active = false\n this.clearHighlight()\n this.overlayTarget.hidden = true\n this.cardTarget.hidden = true\n document.removeEventListener('keydown', this.handleKeydown, true)\n window.removeEventListener('resize', this.reposition)\n window.removeEventListener('scroll', this.reposition, true)\n this.previousFocus?.focus()\n this.previousFocus = null\n }\n\n private handleOpen = (event: Event) => {\n const detail = (event as CustomEvent).detail ?? {}\n const id = String(detail.id ?? '').replace('#', '')\n if (id === this.element.id) this.start()\n }\n\n private reposition = () => {\n if (!this.active) return\n const step = this.steps[this.index]\n const target = step.selector ? document.querySelector<HTMLElement>(step.selector) : null\n if (target) this.position(target, step.position)\n else this.center()\n }\n\n private handleKeydown = (event: KeyboardEvent) => {\n if (!this.active) return\n\n switch (event.key) {\n case 'Escape':\n event.preventDefault()\n this.cancel()\n break\n case 'ArrowRight':\n event.preventDefault()\n this.next()\n break\n case 'ArrowLeft':\n event.preventDefault()\n this.back()\n break\n case 'Tab':\n this.trapTab(event)\n break\n }\n }\n\n // Keep Tab focus within the card while the tour is active.\n private trapTab (event: KeyboardEvent) {\n const focusable = Array.from(this.cardTarget.querySelectorAll<HTMLElement>(FOCUSABLE))\n .filter((el) => !el.hidden && el.offsetParent !== null && getComputedStyle(el).visibility !== 'hidden')\n if (focusable.length === 0) return\n\n const first = focusable[0]\n const last = focusable[focusable.length - 1]\n const active = document.activeElement\n\n if (event.shiftKey) {\n if (active === first || active === this.cardTarget || !this.cardTarget.contains(active)) {\n event.preventDefault()\n last.focus()\n }\n } else if (active === last || !this.cardTarget.contains(active)) {\n event.preventDefault()\n first.focus()\n }\n }\n}\n"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"onboarding_component_controller.js","sources":["../../../../../../../app/components/midwest/onboarding_component/onboarding_component_controller.ts"],"sourcesContent":["import { Controller } from '@hotwired/stimulus'\n\nconst FOCUSABLE = [\n 'a[href]',\n 'button:not([disabled])',\n 'textarea:not([disabled])',\n 'input:not([disabled])',\n 'select:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"])'\n].join(', ')\n\nconst GAP = 12 // px between the target and the card\n\ninterface StepConfig {\n el: HTMLElement\n name: string\n selector: string\n position: string\n title: string\n nextText: string\n backText: string\n completeText: string\n canClickTarget: boolean\n}\n\n// Native, dependency-free guided-tour engine. Reads the nested step config\n// carriers, then walks the user through them with a dimmed overlay, a card\n// positioned against each step's target element, and Back/Next/Done buttons.\nexport default class Onboarding extends Controller<HTMLElement> {\n static targets = ['step', 'overlay', 'card', 'title', 'body', 'back', 'next', 'done', 'arrow', 'motion']\n\n static values = {\n autoOpen: { type: Boolean, default: false }\n }\n\n declare readonly stepTargets: HTMLElement[]\n declare readonly overlayTarget: HTMLElement\n declare readonly cardTarget: HTMLElement\n declare readonly titleTarget: HTMLElement\n declare readonly bodyTarget: HTMLElement\n declare readonly backTarget: HTMLButtonElement\n declare readonly nextTarget: HTMLButtonElement\n declare readonly doneTarget: HTMLButtonElement\n declare readonly arrowTarget: HTMLElement\n declare readonly motionTarget: HTMLElement\n declare readonly hasMotionTarget: boolean\n declare autoOpenValue: boolean\n\n private steps: StepConfig[] = []\n private index = 0\n private active = false\n private justOpened = false\n private previousFocus: HTMLElement | null = null\n private highlighted: HTMLElement | null = null\n\n connect () {\n this.steps = this.stepTargets.map((el) => ({\n el,\n name: el.dataset.name ?? '',\n selector: el.dataset.selector ?? '',\n position: el.dataset.position ?? 'auto',\n title: el.dataset.title ?? '',\n nextText: el.dataset.nextText ?? 'Next',\n backText: el.dataset.backText ?? 'Back',\n completeText: el.dataset.completeText ?? 'Done',\n canClickTarget: el.dataset.canClickTarget === 'true'\n }))\n\n window.addEventListener('midwest-onboarding:open', this.handleOpen)\n\n if (this.autoOpenValue) this.start()\n }\n\n disconnect () {\n window.removeEventListener('midwest-onboarding:open', this.handleOpen)\n this.teardown()\n }\n\n start () {\n if (this.active || this.steps.length === 0) return\n this.active = true\n this.previousFocus = document.activeElement as HTMLElement | null\n this.overlayTarget.hidden = false\n this.cardTarget.hidden = false\n this.justOpened = true\n document.addEventListener('keydown', this.handleKeydown, true)\n window.addEventListener('resize', this.reposition)\n window.addEventListener('scroll', this.reposition, true)\n this.dispatch('start', { bubbles: true })\n this.render(0)\n }\n\n next () {\n if (this.index < this.steps.length - 1) this.render(this.index + 1)\n else this.complete()\n }\n\n back () {\n if (this.index > 0) this.render(this.index - 1)\n }\n\n // Jump to a step by its `name`.\n show (name: string) {\n const target = this.steps.findIndex((step) => step.name === name)\n if (target >= 0) {\n if (!this.active) this.start()\n this.render(target)\n }\n }\n\n complete () {\n if (!this.active) return\n this.teardown()\n this.dispatch('complete', { bubbles: true })\n }\n\n cancel () {\n if (!this.active) return\n this.teardown()\n this.dispatch('cancel', { bubbles: true })\n }\n\n private render (index: number) {\n this.index = index\n const step = this.steps[index]\n const replay = !this.justOpened\n this.justOpened = false\n\n this.clearHighlight()\n\n this.titleTarget.textContent = step.title\n this.renderBody(step)\n this.renderButtons(step, index)\n\n const target = step.selector\n ? document.querySelector<HTMLElement>(step.selector)\n : null\n\n if (target) {\n this.highlight(target, step.canClickTarget)\n this.position(target, step.position)\n } else {\n this.center()\n }\n\n if (replay && this.hasMotionTarget) {\n this.replayMotion(this.cardTarget.dataset.placement ?? 'center')\n }\n\n this.dispatch('show', { detail: { index, name: step.name }, bubbles: true })\n this.focusCard()\n }\n\n private renderBody (step: StepConfig) {\n this.bodyTarget.replaceChildren()\n const template = step.el.querySelector('template')\n if (template) this.bodyTarget.appendChild(template.content.cloneNode(true))\n }\n\n private renderButtons (step: StepConfig, index: number) {\n const isFirst = index === 0\n const isLast = index === this.steps.length - 1\n\n // Back keeps its layout box (visibility) so the forward button never shifts;\n // Next and Done are mutually exclusive, so exactly one fills the right slot.\n this.backTarget.textContent = step.backText\n this.backTarget.style.visibility = isFirst ? 'hidden' : ''\n\n // Inline display beats the button's own `display: inline-flex` rule.\n this.nextTarget.textContent = step.nextText\n this.nextTarget.style.display = isLast ? 'none' : ''\n\n this.doneTarget.textContent = step.completeText\n this.doneTarget.style.display = isLast ? '' : 'none'\n }\n\n private highlight (target: HTMLElement, canClickTarget: boolean) {\n target.classList.add('midwest-onboarding-highlight')\n target.classList.toggle('is-locked', !canClickTarget)\n this.highlighted = target\n target.scrollIntoView({ behavior: 'smooth', block: 'center' })\n }\n\n private clearHighlight () {\n this.highlighted?.classList.remove('midwest-onboarding-highlight', 'is-locked')\n this.highlighted = null\n }\n\n // Places the card against the target, choosing a side when `position` is auto.\n private position (target: HTMLElement, position: string) {\n const rect = target.getBoundingClientRect()\n const card = this.cardTarget.getBoundingClientRect()\n const vw = window.innerWidth\n const vh = window.innerHeight\n\n let placement = position\n if (placement === 'auto') {\n if (rect.bottom + card.height + GAP <= vh) placement = 'bottom'\n else if (rect.top - card.height - GAP >= 0) placement = 'top'\n else if (rect.right + card.width + GAP <= vw) placement = 'right'\n else placement = 'left'\n }\n\n let top: number\n let left: number\n\n switch (placement) {\n case 'top':\n top = rect.top - card.height - GAP\n left = rect.left + rect.width / 2 - card.width / 2\n break\n case 'left':\n top = rect.top + rect.height / 2 - card.height / 2\n left = rect.left - card.width - GAP\n break\n case 'right':\n top = rect.top + rect.height / 2 - card.height / 2\n left = rect.right + GAP\n break\n default: // bottom\n top = rect.bottom + GAP\n left = rect.left + rect.width / 2 - card.width / 2\n break\n }\n\n // Keep the card fully on screen.\n left = Math.max(8, Math.min(left, vw - card.width - 8))\n top = Math.max(8, Math.min(top, vh - card.height - 8))\n\n this.cardTarget.style.top = `${top}px`\n this.cardTarget.style.left = `${left}px`\n this.cardTarget.dataset.placement = placement\n\n this.positionArrow(placement, rect, top, left)\n }\n\n // Nudges the arrow so it points at the target's center, not the card's.\n private positionArrow (placement: string, rect: DOMRect, top: number, left: number) {\n const card = this.cardTarget.getBoundingClientRect()\n const arrow = this.arrowTarget.style\n\n if (placement === 'top' || placement === 'bottom') {\n const targetCenter = rect.left + rect.width / 2\n const offset = Math.max(12, Math.min(targetCenter - left, card.width - 12))\n arrow.left = `${offset}px`\n arrow.top = ''\n } else {\n const targetCenter = rect.top + rect.height / 2\n const offset = Math.max(12, Math.min(targetCenter - top, card.height - 12))\n arrow.top = `${offset}px`\n arrow.left = ''\n }\n }\n\n private center () {\n const card = this.cardTarget.getBoundingClientRect()\n this.cardTarget.style.top = `${Math.max(8, window.innerHeight / 2 - card.height / 2)}px`\n this.cardTarget.style.left = `${Math.max(8, window.innerWidth / 2 - card.width / 2)}px`\n this.cardTarget.dataset.placement = 'center'\n }\n\n private focusCard () {\n requestAnimationFrame(() => {\n if (this.active) this.cardTarget.focus()\n })\n }\n\n // Re-triggers the midwest_motion @starting-style entry on step transitions.\n // The initial show is handled by @starting-style firing when the card's\n // `hidden` is removed; subsequent steps need an explicit re-trigger since the\n // card stays in the DOM. Toggling `hidden` on the motion element triggers\n // @starting-style again; the rAF ensures both DOM writes land in the same\n // paint so there is no blank-card flash.\n private replayMotion (placement: string) {\n const el = this.motionTarget\n const dir: Record<string, string> = { bottom: 'up', top: 'down', right: 'left', left: 'right' }\n\n el.classList.remove('from-up', 'from-down', 'from-left', 'from-right')\n const from = dir[placement]\n if (from) el.classList.add(`from-${from}`)\n\n el.hidden = true\n requestAnimationFrame(() => { if (this.active) el.hidden = false })\n }\n\n private teardown () {\n this.active = false\n this.clearHighlight()\n // Close any open confirmation popovers before hiding the card.\n this.element.querySelectorAll<HTMLElement>('[popover]').forEach((el) => {\n try { el.hidePopover() } catch { /* already hidden */ }\n })\n this.overlayTarget.hidden = true\n this.cardTarget.hidden = true\n document.removeEventListener('keydown', this.handleKeydown, true)\n window.removeEventListener('resize', this.reposition)\n window.removeEventListener('scroll', this.reposition, true)\n this.previousFocus?.focus()\n this.previousFocus = null\n }\n\n private handleOpen = (event: Event) => {\n const detail = (event as CustomEvent).detail ?? {}\n const id = String(detail.id ?? '').replace('#', '')\n if (id === this.element.id) this.start()\n }\n\n private reposition = () => {\n if (!this.active) return\n const step = this.steps[this.index]\n const target = step.selector ? document.querySelector<HTMLElement>(step.selector) : null\n if (target) this.position(target, step.position)\n else this.center()\n }\n\n private handleKeydown = (event: KeyboardEvent) => {\n if (!this.active) return\n\n switch (event.key) {\n case 'Escape':\n event.preventDefault()\n this.cancel()\n break\n case 'ArrowRight':\n event.preventDefault()\n this.next()\n break\n case 'ArrowLeft':\n event.preventDefault()\n this.back()\n break\n case 'Tab':\n this.trapTab(event)\n break\n }\n }\n\n // Keep Tab focus within the card while the tour is active.\n private trapTab (event: KeyboardEvent) {\n const focusable = Array.from(this.cardTarget.querySelectorAll<HTMLElement>(FOCUSABLE))\n .filter((el) => !el.hidden && el.offsetParent !== null && getComputedStyle(el).visibility !== 'hidden')\n if (focusable.length === 0) return\n\n const first = focusable[0]\n const last = focusable[focusable.length - 1]\n const active = document.activeElement\n\n if (event.shiftKey) {\n if (active === first || active === this.cardTarget || !this.cardTarget.contains(active)) {\n event.preventDefault()\n last.focus()\n }\n } else if (active === last || !this.cardTarget.contains(active)) {\n event.preventDefault()\n first.focus()\n }\n }\n}\n"],"names":[],"mappings":"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"}
@@ -0,0 +1,38 @@
1
+ import { Controller } from '@hotwired/stimulus';
2
+
3
+ class PageTransition extends Controller {
4
+ static values = {
5
+ style: { type: String, default: "fade" },
6
+ duration: { type: String, default: "" },
7
+ easing: { type: String, default: "" }
8
+ };
9
+ injectedMeta = null;
10
+ connect() {
11
+ if (this.styleValue === "none")
12
+ return;
13
+ if (!document.querySelector('meta[name="view-transition"]')) {
14
+ const meta = document.createElement("meta");
15
+ meta.name = "view-transition";
16
+ meta.content = "same-origin";
17
+ document.head.appendChild(meta);
18
+ this.injectedMeta = meta;
19
+ }
20
+ document.documentElement.dataset.midwestPageTransition = this.styleValue;
21
+ if (this.durationValue) {
22
+ document.documentElement.style.setProperty("--page-transition-duration", this.durationValue);
23
+ }
24
+ if (this.easingValue) {
25
+ document.documentElement.style.setProperty("--page-transition-easing", this.easingValue);
26
+ }
27
+ }
28
+ disconnect() {
29
+ this.injectedMeta?.remove();
30
+ this.injectedMeta = null;
31
+ delete document.documentElement.dataset.midwestPageTransition;
32
+ document.documentElement.style.removeProperty("--page-transition-duration");
33
+ document.documentElement.style.removeProperty("--page-transition-easing");
34
+ }
35
+ }
36
+
37
+ export { PageTransition as default };
38
+ //# sourceMappingURL=page_transition_component_controller.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"page_transition_component_controller.js","sources":["../../../../../../../app/components/midwest/page_transition_component/page_transition_component_controller.ts"],"sourcesContent":["import { Controller } from '@hotwired/stimulus'\n\n// Enables Turbo View Transitions by injecting the <meta name=\"view-transition\">\n// tag that Turbo 8 requires to wrap navigations in document.startViewTransition(),\n// and by writing `data-midwest-page-transition` onto <html> so the CSS keyframe\n// rules scope to the chosen style. Custom duration/easing are pushed as CSS custom\n// properties on <html> so they win over the layer defaults without !important.\n//\n// Values\n// style — transition key, one of:\n// \"fade\" | \"slide-left\" | \"slide-right\" | \"slide-up\" |\n// \"slide-down\" | \"scale\" | \"none\"\n// duration — optional resolved CSS value (e.g. \"var(--duration-fast)\", \"200ms\")\n// easing — optional resolved CSS value (e.g. \"var(--ease-emphasized)\")\nexport default class PageTransition extends Controller<HTMLElement> {\n static values = {\n style: { type: String, default: 'fade' },\n duration: { type: String, default: '' },\n easing: { type: String, default: '' }\n }\n\n declare styleValue: string\n declare durationValue: string\n declare easingValue: string\n\n private injectedMeta: HTMLMetaElement | null = null\n\n connect () {\n // `style: :none` means \"install no transitions at all.\"\n if (this.styleValue === 'none') return\n\n // Inject the Turbo View Transitions meta tag if not already present. We\n // track what we injected so we can remove it precisely on disconnect.\n if (!document.querySelector('meta[name=\"view-transition\"]')) {\n const meta = document.createElement('meta')\n meta.name = 'view-transition'\n meta.content = 'same-origin'\n document.head.appendChild(meta)\n this.injectedMeta = meta\n }\n\n // The CSS uses this attribute to scope ::view-transition-* animations.\n document.documentElement.dataset.midwestPageTransition = this.styleValue\n\n // Per-call timing overrides — win over the layer defaults without !important.\n if (this.durationValue) {\n document.documentElement.style.setProperty('--page-transition-duration', this.durationValue)\n }\n if (this.easingValue) {\n document.documentElement.style.setProperty('--page-transition-easing', this.easingValue)\n }\n }\n\n disconnect () {\n this.injectedMeta?.remove()\n this.injectedMeta = null\n delete document.documentElement.dataset.midwestPageTransition\n document.documentElement.style.removeProperty('--page-transition-duration')\n document.documentElement.style.removeProperty('--page-transition-easing')\n }\n}\n"],"names":[],"mappings":";;AAcA,MAAqB,uBAAuB,UAAwB,CAAA;AAAA,EAClE,OAAO,MAAS,GAAA;AAAA,IACd,KAAO,EAAA,EAAE,IAAM,EAAA,MAAA,EAAQ,SAAS,MAAO,EAAA;AAAA,IACvC,QAAU,EAAA,EAAE,IAAM,EAAA,MAAA,EAAQ,SAAS,EAAG,EAAA;AAAA,IACtC,MAAQ,EAAA,EAAE,IAAM,EAAA,MAAA,EAAQ,SAAS,EAAG,EAAA;AAAA,GACtC,CAAA;AAAA,EAMQ,YAAuC,GAAA,IAAA,CAAA;AAAA,EAE/C,OAAW,GAAA;AAET,IAAA,IAAI,KAAK,UAAe,KAAA,MAAA;AAAQ,MAAA,OAAA;AAIhC,IAAA,IAAI,CAAC,QAAA,CAAS,aAAc,CAAA,8BAA8B,CAAG,EAAA;AAC3D,MAAM,MAAA,IAAA,GAAO,QAAS,CAAA,aAAA,CAAc,MAAM,CAAA,CAAA;AAC1C,MAAA,IAAA,CAAK,IAAO,GAAA,iBAAA,CAAA;AACZ,MAAA,IAAA,CAAK,OAAU,GAAA,aAAA,CAAA;AACf,MAAS,QAAA,CAAA,IAAA,CAAK,YAAY,IAAI,CAAA,CAAA;AAC9B,MAAA,IAAA,CAAK,YAAe,GAAA,IAAA,CAAA;AAAA,KACtB;AAGA,IAAS,QAAA,CAAA,eAAA,CAAgB,OAAQ,CAAA,qBAAA,GAAwB,IAAK,CAAA,UAAA,CAAA;AAG9D,IAAA,IAAI,KAAK,aAAe,EAAA;AACtB,MAAA,QAAA,CAAS,eAAgB,CAAA,KAAA,CAAM,WAAY,CAAA,4BAAA,EAA8B,KAAK,aAAa,CAAA,CAAA;AAAA,KAC7F;AACA,IAAA,IAAI,KAAK,WAAa,EAAA;AACpB,MAAA,QAAA,CAAS,eAAgB,CAAA,KAAA,CAAM,WAAY,CAAA,0BAAA,EAA4B,KAAK,WAAW,CAAA,CAAA;AAAA,KACzF;AAAA,GACF;AAAA,EAEA,UAAc,GAAA;AACZ,IAAA,IAAA,CAAK,cAAc,MAAO,EAAA,CAAA;AAC1B,IAAA,IAAA,CAAK,YAAe,GAAA,IAAA,CAAA;AACpB,IAAO,OAAA,QAAA,CAAS,gBAAgB,OAAQ,CAAA,qBAAA,CAAA;AACxC,IAAS,QAAA,CAAA,eAAA,CAAgB,KAAM,CAAA,cAAA,CAAe,4BAA4B,CAAA,CAAA;AAC1E,IAAS,QAAA,CAAA,eAAA,CAAgB,KAAM,CAAA,cAAA,CAAe,0BAA0B,CAAA,CAAA;AAAA,GAC1E;AACF;;;;"}
@@ -0,0 +1,67 @@
1
+ import { Controller } from '@hotwired/stimulus';
2
+
3
+ class Popover extends Controller {
4
+ animating = false;
5
+ closeTimer = null;
6
+ connect() {
7
+ this.element.addEventListener("beforetoggle", this.onBeforeToggle);
8
+ }
9
+ disconnect() {
10
+ this.element.removeEventListener("beforetoggle", this.onBeforeToggle);
11
+ this.cleanUp();
12
+ }
13
+ onBeforeToggle = (event) => {
14
+ const toggle = event;
15
+ if (toggle.newState === "open") {
16
+ if (this.closeTimer) {
17
+ clearTimeout(this.closeTimer);
18
+ this.closeTimer = null;
19
+ }
20
+ this.element.classList.remove("is-closing");
21
+ this.animating = false;
22
+ return;
23
+ }
24
+ if (toggle.newState !== "closed")
25
+ return;
26
+ if (window.matchMedia("(width < 700px)").matches)
27
+ return;
28
+ if (!this.element.classList.contains("midwest-motion"))
29
+ return;
30
+ if (this.animating)
31
+ return;
32
+ event.preventDefault();
33
+ this.animating = true;
34
+ this.element.classList.add("is-closing");
35
+ this.closeTimer = setTimeout(() => {
36
+ this.closeTimer = null;
37
+ this.element.style.display = "none";
38
+ this.element.style.transition = "none";
39
+ this.element.hidePopover();
40
+ this.animating = false;
41
+ requestAnimationFrame(() => {
42
+ this.element.style.removeProperty("display");
43
+ this.element.style.removeProperty("transition");
44
+ this.element.classList.remove("is-closing");
45
+ });
46
+ }, this.exitDuration());
47
+ };
48
+ cleanUp() {
49
+ if (this.closeTimer) {
50
+ clearTimeout(this.closeTimer);
51
+ this.closeTimer = null;
52
+ }
53
+ this.element.classList.remove("is-closing");
54
+ this.element.style.removeProperty("transition");
55
+ this.animating = false;
56
+ }
57
+ exitDuration() {
58
+ const durations = getComputedStyle(this.element).transitionDuration.split(",").map((s) => {
59
+ const n = parseFloat(s);
60
+ return s.trim().endsWith("ms") ? n : n * 1e3;
61
+ });
62
+ return Math.max(0, ...durations);
63
+ }
64
+ }
65
+
66
+ export { Popover as default };
67
+ //# sourceMappingURL=popover_component_controller.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"popover_component_controller.js","sources":["../../../../../../../app/components/midwest/popover_component/popover_component_controller.ts"],"sourcesContent":["import { Controller } from '@hotwired/stimulus'\n\n// Plays the motion exit animation *before* the native popover close fires.\n// Without this, Chromium recalculates `position-try-fallbacks` the moment\n// `:popover-open` is removed, which jumps the popover to a different anchor\n// position while it is still visible. By deferring the actual close until after\n// the animation, the recalculation happens while the element is already\n// transparent — invisible to the user.\nexport default class Popover extends Controller<HTMLElement> {\n private animating = false\n private closeTimer: ReturnType<typeof setTimeout> | null = null\n\n connect () {\n this.element.addEventListener('beforetoggle', this.onBeforeToggle)\n }\n\n disconnect () {\n this.element.removeEventListener('beforetoggle', this.onBeforeToggle)\n this.cleanUp()\n }\n\n private onBeforeToggle = (event: Event) => {\n const toggle = event as ToggleEvent\n\n // If the popover reopens during the exit animation, cancel it cleanly.\n if (toggle.newState === 'open') {\n if (this.closeTimer) { clearTimeout(this.closeTimer); this.closeTimer = null }\n this.element.classList.remove('is-closing')\n this.animating = false\n return\n }\n\n if (toggle.newState !== 'closed') return\n // Anchor positioning is only active on desktop.\n if (window.matchMedia('(width < 700px)').matches) return\n // Only intercept motion-driven popovers; non-motion close is instant so there\n // is no visible jump to fix.\n if (!this.element.classList.contains('midwest-motion')) return\n // We are the one calling hidePopover() after the animation — let it through.\n if (this.animating) return\n\n event.preventDefault()\n this.animating = true\n this.element.classList.add('is-closing')\n\n this.closeTimer = setTimeout(() => {\n this.closeTimer = null\n // Set display:none *before* hidePopover() so that when :popover-open is\n // removed and position-try-fallbacks recalculates, the element is already\n // out of the rendering tree — the recalculated position is never painted.\n this.element.style.display = 'none'\n this.element.style.transition = 'none'\n this.element.hidePopover()\n this.animating = false\n requestAnimationFrame(() => {\n this.element.style.removeProperty('display')\n this.element.style.removeProperty('transition')\n this.element.classList.remove('is-closing')\n })\n }, this.exitDuration())\n }\n\n private cleanUp () {\n if (this.closeTimer) { clearTimeout(this.closeTimer); this.closeTimer = null }\n this.element.classList.remove('is-closing')\n this.element.style.removeProperty('transition')\n this.animating = false\n }\n\n private exitDuration (): number {\n const durations = getComputedStyle(this.element)\n .transitionDuration.split(',')\n .map((s) => {\n const n = parseFloat(s)\n return s.trim().endsWith('ms') ? n : n * 1000\n })\n return Math.max(0, ...durations)\n }\n}\n"],"names":[],"mappings":"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"}