[gnome-maps/wip/gtk4-and-libshumate] WIP: Port to GTK 4 and libshumate
- From: Marcus Lundblad <mlundblad src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-maps/wip/gtk4-and-libshumate] WIP: Port to GTK 4 and libshumate
- Date: Thu, 11 Aug 2022 22:21:19 +0000 (UTC)
commit dd83cffb6c2868261296ceee97409efd23656641
Author: Marcus Lundblad <ml dfupdate se>
Date: Thu Jun 30 23:11:19 2022 +0200
WIP: Port to GTK 4 and libshumate
data/gnome-maps.css | 8 +-
data/ui/context-menu.ui | 85 +++----
data/ui/export-view-dialog.ui | 122 +++------
data/ui/favorites-popover.ui | 34 +--
data/ui/headerbar-left.ui | 71 ++----
data/ui/headerbar-right.ui | 28 +-
data/ui/instruction-row.ui | 31 +--
data/ui/layers-popover.ui | 96 +++----
data/ui/main-window.ui | 65 ++---
data/ui/osm-account-dialog.ui | 441 ++++++++++++++++----------------
data/ui/osm-edit-address.ui | 60 ++---
data/ui/osm-edit-dialog.ui | 465 ++++++++++++++--------------------
data/ui/osm-type-list-row.ui | 29 +--
data/ui/osm-type-popover.ui | 10 +-
data/ui/place-bar.ui | 59 ++---
data/ui/place-buttons.ui | 55 +---
data/ui/place-list-row.ui | 72 +++---
data/ui/place-popover.ui | 31 +--
data/ui/place-view.ui | 61 ++---
data/ui/route-entry.ui | 38 +--
data/ui/send-to-dialog.ui | 96 +++----
data/ui/sidebar.ui | 348 +++++++++++--------------
data/ui/transit-arrival-row.ui | 122 ++++-----
data/ui/transit-itinerary-row.ui | 75 +++---
data/ui/transit-leg-row.ui | 339 +++++++++++--------------
data/ui/transit-more-row.ui | 51 ++--
data/ui/transit-options-panel.ui | 113 ++++-----
data/ui/transit-route-label.ui | 4 +-
data/ui/transit-stop-row.ui | 52 ++--
data/ui/zoom-in-dialog.ui | 39 +--
lib/maps-file-tile-source.c | 289 ++++++++++-----------
lib/maps-file-tile-source.h | 8 +-
lib/maps-sync-map-source.c | 91 +++++++
lib/maps-sync-map-source.h | 73 ++++++
lib/meson.build | 10 +-
meson.build | 6 +-
org.gnome.Maps.json | 47 +---
src/application.js | 27 +-
src/contextMenu.js | 97 ++++---
src/epaf.js | 4 +-
src/exportViewDialog.js | 85 ++++---
src/favoritesPopover.js | 12 +-
src/geoJSONShapeLayer.js | 2 +
src/geoJSONSource.js | 151 +++++------
src/gpxShapeLayer.js | 2 +
src/graphHopperTransit.js | 10 +-
src/kmlShapeLayer.js | 2 +
src/layersPopover.js | 26 +-
src/main.js | 12 +-
src/mainWindow.js | 193 +++++---------
src/mapBubble.js | 64 ++++-
src/mapMarker.js | 201 +++++++--------
src/mapSource.js | 41 ++-
src/mapView.js | 324 ++++++++++++++---------
src/mapWalker.js | 67 +----
src/osmEditDialog.js | 59 +++--
src/osmTypeListRow.js | 3 +-
src/osmTypePopover.js | 17 +-
src/osmTypeSearchEntry.js | 10 +-
src/placeBar.js | 34 +--
src/placeButtons.js | 38 ++-
src/placeEntry.js | 49 +++-
src/placeMarker.js | 4 +-
src/placePopover.js | 22 +-
src/placeView.js | 29 ++-
src/placeViewImage.js | 28 +-
src/printLayout.js | 15 +-
src/routeEntry.js | 16 +-
src/searchPopover.js | 58 +++--
src/sendToDialog.js | 22 +-
src/shapeLayer.js | 19 +-
src/sidebar.js | 113 ++++++---
src/storedRoute.js | 10 +-
src/transitArrivalMarker.js | 11 +-
src/transitArrivalRow.js | 19 +-
src/transitBoardMarker.js | 80 +++---
src/transitLegRow.js | 34 +--
src/transitOptionsPanel.js | 34 ++-
src/transitPrintLayout.js | 12 +-
src/transitRouteLabel.js | 22 +-
src/transitWalkMarker.js | 11 +-
src/transitplugins/openTripPlanner.js | 6 +-
src/transitplugins/opendataCH.js | 14 +-
src/transitplugins/resrobot.js | 14 +-
src/turnPointMarker.js | 23 +-
src/userLocationMarker.js | 52 ++--
src/utils.js | 18 +-
src/zoomInDialog.js | 11 +-
88 files changed, 2786 insertions(+), 3065 deletions(-)
---
diff --git a/data/gnome-maps.css b/data/gnome-maps.css
index 55e60fb9..d43e0a6c 100644
--- a/data/gnome-maps.css
+++ b/data/gnome-maps.css
@@ -92,10 +92,10 @@
}
.route-label {
- padding-left: 2px;
- padding-right: 2px;
- padding-top: 2px;
- padding-bottom: 2px;
+ padding-left: 3px;
+ padding-right: 3px;
+ padding-top: 3px;
+ padding-bottom: 3px;
min-width: 16px;
min-height: 16px;
font-size: smaller;
diff --git a/data/ui/context-menu.ui b/data/ui/context-menu.ui
index 7fcb6734..07100c3e 100644
--- a/data/ui/context-menu.ui
+++ b/data/ui/context-menu.ui
@@ -1,56 +1,37 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <!-- interface-requires gtk+ 3.0 -->
- <template class="Gjs_ContextMenu" parent="GtkMenu">
- <property name="visible">False</property>
- <child>
- <object class="GtkMenuItem" id="routeFromHereItem">
- <property name="name">route-from-here-item</property>
- <property name="label" translatable="yes">Route from here</property>
- <property name="visible">True</property>
- </object>
- </child>
- <child>
- <object class="GtkMenuItem" id="addIntermediateDestinationItem">
- <property name="name">add-itermediate-destination-item</property>
- <property name="label" translatable="yes">Add intermediate destination</property>
- <property name="visible">True</property>
- <property name="sensitive">False</property>
- </object>
- </child>
- <child>
- <object class="GtkMenuItem" id="routeToHereItem">
- <property name="name">route-to-here-item</property>
- <property name="label" translatable="yes">Route to here</property>
- <property name="visible">True</property>
- </object>
- </child>
- <child>
- <object class="GtkSeparatorMenuItem">
- <property name="visible">True</property>
- </object>
- </child>
- <child>
- <object class="GtkMenuItem" id="whatsHereItem">
- <property name="name">whats-here-item</property>
- <property name="label" translatable="yes">What’s here?</property>
- <property name="visible">True</property>
- </object>
- </child>
- <child>
- <object class="GtkMenuItem" id="geoURIItem">
- <property name="name">geo-uri-item</property>
- <property name="label" translatable="yes">Copy Location</property>
- <property name="visible">True</property>
- </object>
- </child>
-
- <child>
- <object class="GtkMenuItem" id="addOSMLocationItem">
- <property name="name">add-osm-location-item</property>
- <property name="label" translatable="yes">Add to OpenStreetMap</property>
- <property name="visible">True</property>
- </object>
- </child>
+ <menu id="context-menu">
+ <section>
+ <item>
+ <attribute name="label" translatable="yes">Route from here</attribute>
+ <attribute name="action">win.route-from-here</attribute>
+ </item>
+ <item>
+ <attribute name="label" translatable="yes">Add intermediate destination</attribute>
+ <attribute name="action">win.add-intermediate-destination</attribute>
+ </item>
+ <item>
+ <attribute name="label" translatable="yes">Route to here</attribute>
+ <attribute name="action">win.route-to-here</attribute>
+ </item>
+ </section>
+ <section>
+ <item>
+ <attribute name="label" translatable="yes">What's here?</attribute>
+ <attribute name="action">win.whats-here</attribute>
+ </item>
+ <item>
+ <attribute name="label" translatable="yes">Copy location</attribute>
+ <attribute name="action">win.copy-location</attribute>
+ </item>
+ <item>
+ <attribute name="label" translatable="yes">Add to OpenStreetMap</attribute>
+ <attribute name="action">win.add-osm-location</attribute>
+ </item>
+ </section>
+ </menu>
+ <template class="Gjs_ContextMenu" parent="GtkPopoverMenu">
+ <property name="menu-model">context-menu</property>
+ <property name="has-arrow">False</property>
</template>
</interface>
diff --git a/data/ui/export-view-dialog.ui b/data/ui/export-view-dialog.ui
index 040e390e..c2824de1 100644
--- a/data/ui/export-view-dialog.ui
+++ b/data/ui/export-view-dialog.ui
@@ -1,61 +1,45 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_ExportViewDialog" parent="GtkDialog">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
<property name="use_header_bar">1</property>
- <property name="resizable">False</property>
+ <property name="resizable">0</property>
+ <property name="title" translatable="1">Export view</property>
<child internal-child="headerbar">
<object class="GtkHeaderBar" id="headerBar">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="show_close_button">False</property>
- <property name="title" translatable="yes">Export view</property>
+ <property name="show-title-buttons">0</property>
<style>
<class name="titlebar"/>
</style>
- <child>
+ <child type="start">
<object class="GtkButton" id="cancelButton">
- <property name="label" translatable="yes">_Cancel</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="use_underline">True</property>
+ <property name="label" translatable="1">_Cancel</property>
+ <property name="focusable">1</property>
+ <property name="use_underline">1</property>
<style>
<class name="text-button"/>
</style>
</object>
- <packing>
- <property name="pack_type">start</property>
- </packing>
</child>
- <child>
+ <child type="end">
<object class="GtkButton" id="exportButton">
- <property name="label" translatable="yes">_Export</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="can_default">True</property>
- <property name="has_default">True</property>
- <property name="receives_default">True</property>
+ <property name="label" translatable="1">_Export</property>
+ <property name="focusable">1</property>
+ <property name="receives_default">1</property>
<property name="valign">center</property>
- <property name="use_underline">True</property>
+ <property name="use_underline">1</property>
<style>
<class name="suggested-action"/>
<class name="text-button"/>
</style>
</object>
- <packing>
- <property name="pack_type">end</property>
- </packing>
</child>
</object>
</child>
- <child internal-child="vbox">
+ <child>
<object class="GtkBox" id="contentArea">
<child>
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="margin_start">5</property>
<property name="margin_end">5</property>
<property name="margin_top">5</property>
@@ -64,72 +48,48 @@
<property name="column_spacing">8</property>
<child>
<object class="GtkFrame" id="frame">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label_xalign">0</property>
- <property name="shadow_type">out</property>
<property name="valign">start</property>
- <child>
- <object class="GtkDrawingArea" id="previewArea">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
+ <property name="child">
+ <object class="GtkImage" id="previewArea">
+ <property name="vexpand">True</property>
+ <property name="hexpand">True</property>
</object>
- </child>
+ </property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="row-span">3</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- <property name="width">1</property>
- <property name="height">3</property>
- </packing>
</child>
<child>
<object class="GtkEntry" id="filenameEntry">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">start</property>
- <property name="activates_default">True</property>
+ <property name="activates_default">1</property>
<property name="width_chars">32</property>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">0</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
</child>
<child>
- <object class="GtkFileChooserButton" id="fileChooserButton">
- <property name="visible">True</property>
+ <object class="GtkButton" id="fileChooserButton">
<property name="can_focus">False</property>
<property name="valign">start</property>
<property name="vexpand">True</property>
- <property name="action">select-folder</property>
- <property name="local_only">False</property>
- </object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">1</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkCheckButton" id="layersCheckButton">
- <property name="label" translatable="yes">Include route and markers</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="xalign">0</property>
- <property name="draw_indicator">True</property>
- <property name="active">True</property>
+ <child>
+ <object class="GtkImage" id="favorites-button-image">
+ <property name="icon-size">normal</property>
+ <property name="icon-name">folder-open-symbolic</property>
+ </object>
+ </child>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">2</property>
- <property name="width">1</property>
- <property name="height">1</property>
- </packing>
</child>
</object>
</child>
diff --git a/data/ui/favorites-popover.ui b/data/ui/favorites-popover.ui
index 130f0a3d..15d17667 100644
--- a/data/ui/favorites-popover.ui
+++ b/data/ui/favorites-popover.ui
@@ -1,45 +1,39 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <!-- interface-requires gtk+ 3.10 -->
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_FavoritesPopover" parent="GtkPopover">
- <property name="visible">False</property>
- <property name="no_show_all">True</property>
- <property name="hexpand">False</property>
+ <property name="hexpand">0</property>
<property name="width-request">320</property>
<property name="height-request">400</property>
<style>
<class name="maps-popover"/>
</style>
- <child>
+ <property name="child">
<object class="GtkGrid" id="mainGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
<property name="row_spacing">6</property>
- <property name="margin">6</property>
+ <property name="margin-start">6</property>
+ <property name="margin-end">6</property>
+ <property name="margin-top">6</property>
+ <property name="margin-bottom">6</property>
<child>
<object class="GtkEntry" id="entry">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
+ <property name="focusable">1</property>
</object>
</child>
<child>
<object class="GtkScrolledWindow" id="scrolledWindow">
<property name="hscrollbar_policy">never</property>
- <property name="shadow_type">in</property>
- <property name="visible">True</property>
- <property name="vexpand">True</property>
- <child>
+ <property name="vexpand">1</property>
+ <property name="child">
<object class="GtkListBox" id="list">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="expand">True</property>
- <property name="activate_on_single_click">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
</object>
- </child>
+ </property>
</object>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/headerbar-left.ui b/data/ui/headerbar-left.ui
index aa293360..c36d77e5 100644
--- a/data/ui/headerbar-left.ui
+++ b/data/ui/headerbar-left.ui
@@ -1,25 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.22.0 -->
<interface>
- <requires lib="gtk+" version="3.22"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_HeaderBarLeft" parent="GtkBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="spacing">6</property>
<child>
<object class="GtkButton" id="gotoUserLocationButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">center</property>
<property name="action-name">win.goto-user-location</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Go to
current location</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Go to
current location</property>
<style>
<class name="image-button"/>
</style>
<child>
<object class="GtkImage" id="track-user-button-image">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
+ <property name="icon-size">normal</property>
<property name="icon-name">find-location-symbolic</property>
</object>
</child>
@@ -27,58 +22,44 @@
</child>
<child>
<object class="GtkMenuButton" id="layersButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">center</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Choose
map type</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Choose map
type</property>
<style>
<class name="image-button"/>
</style>
<child>
<object class="GtkImage" id="layers-button-image">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
+ <property name="icon-size">normal</property>
<property name="icon-name">layers-button-symbolic</property>
</object>
</child>
</object>
</child>
<child>
- <object class="GtkBox">
- <property name="visible">True</property>
- <style>
- <class name="linked"/>
- </style>
+ <object class="GtkButton">
+ <property name="focusable">1</property>
+ <property name="valign">center</property>
+ <property name="action-name">win.zoom-out</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Zoom
out</property>
<child>
- <object class="GtkButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="valign">center</property>
- <property name="action-name">win.zoom-out</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Zoom
out</property>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
- <property name="icon-name">zoom-out-symbolic</property>
- </object>
- </child>
+ <object class="GtkImage">
+ <property name="icon-size">normal</property>
+ <property name="icon-name">zoom-out-symbolic</property>
</object>
</child>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton">
+ <property name="focusable">1</property>
+ <property name="valign">center</property>
+ <property name="action-name">win.zoom-in</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Zoom
in</property>
<child>
- <object class="GtkButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="valign">center</property>
- <property name="action-name">win.zoom-in</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Zoom
in</property>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
- <property name="icon-name">zoom-in-symbolic</property>
- </object>
- </child>
+ <object class="GtkImage">
+ <property name="icon-size">normal</property>
+ <property name="icon-name">zoom-in-symbolic</property>
</object>
</child>
</object>
diff --git a/data/ui/headerbar-right.ui b/data/ui/headerbar-right.ui
index a806b64c..06a94057 100644
--- a/data/ui/headerbar-right.ui
+++ b/data/ui/headerbar-right.ui
@@ -1,17 +1,14 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.22.0 -->
<interface>
- <requires lib="gtk+" version="3.22"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_HeaderBarRight" parent="GtkBox">
- <property name="visible">True</property>
- <property name="no-show-all">True</property>
- <property name="can_focus">False</property>
<property name="spacing">6</property>
<child>
<object class="GtkButton" id="printRouteButton">
+ <property name="visible">0</property>
<property name="name">print-route</property>
- <property name="can-focus">True</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Print
Route</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Print
Route</property>
<property name="action-name">win.print-route</property>
<property name="valign">center</property>
<style>
@@ -19,7 +16,6 @@
</style>
<child>
<object class="GtkImage" id="print-route-button-image">
- <property name="visible">True</property>
<property name="icon-name">document-print-symbolic</property>
</object>
</child>
@@ -27,17 +23,15 @@
</child>
<child>
<object class="GtkMenuButton" id="favoritesButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">center</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Toggle
favorites</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Toggle
favorites</property>
<style>
<class name="image-button"/>
</style>
<child>
<object class="GtkImage" id="favorites-button-image">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
+ <property name="icon-size">normal</property>
<property name="icon-name">bookmarks-symbolic</property>
</object>
</child>
@@ -45,18 +39,16 @@
</child>
<child>
<object class="GtkToggleButton" id="toggleSidebarButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">center</property>
<property name="action-name">win.toggle-sidebar</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Toggle
route planner</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Toggle
route planner</property>
<style>
<class name="image-button"/>
</style>
<child>
<object class="GtkImage" id="toggle-sidebar-button-image">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
+ <property name="icon-size">normal</property>
<property name="icon-name">route-button-symbolic</property>
</object>
</child>
diff --git a/data/ui/instruction-row.ui b/data/ui/instruction-row.ui
index 1e3cf1d1..92bf52f5 100644
--- a/data/ui/instruction-row.ui
+++ b/data/ui/instruction-row.ui
@@ -1,24 +1,19 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.14"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_InstructionRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkBox" id="instructionBox">
<property name="name">instruction-box</property>
<property name="height_request">48</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="spacing">6</property>
<property name="baseline_position">top</property>
<child>
<object class="GtkImage" id="directionImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="margin-start">2</property>
<property name="margin-end">2</property>
- <!-- width: 32 + spacing * 2 -->
<property name="width-request">44</property>
+ <property name="icon-size">GTK_ICON_SIZE_LARGE</property>
<style>
<class name="sidebar-icon"/>
</style>
@@ -26,35 +21,29 @@
</child>
<child>
<object class="GtkLabel" id="instructionLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
- <!-- Somehow we need this xalign, otherwise multi-line -->
- <!-- labels does not get left-aligned. -->
<property name="xalign">0</property>
<property name="margin-top">3</property>
<property name="margin-bottom">3</property>
- <property name="use_underline">True</property>
- <property name="wrap">True</property>
+ <property name="use_underline">1</property>
+ <property name="wrap">1</property>
<property name="ellipsize">end</property>
<property name="width_chars">20</property>
<property name="max_width_chars">20</property>
<property name="lines">3</property>
- <property name="expand">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
</object>
</child>
<child>
<object class="GtkLabel" id="distanceLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">end</property>
- <property name="use_underline">True</property>
- <property name="wrap">True</property>
+ <property name="use_underline">1</property>
<property name="lines">3</property>
<property name="margin_end">5</property>
</object>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/layers-popover.ui b/data/ui/layers-popover.ui
index b423a7a3..ed5adeb7 100644
--- a/data/ui/layers-popover.ui
+++ b/data/ui/layers-popover.ui
@@ -1,108 +1,94 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <!-- interface-requires gtk+ 3.10 -->
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_LayersPopover" parent="GtkPopover">
- <child>
+ <property name="child">
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">center</property>
<property name="valign">center</property>
<property name="row_spacing">5</property>
- <property name="margin">5</property>
+ <property name="margin-start">5</property>
+ <property name="margin-end">5</property>
+ <property name="margin-top">5</property>
+ <property name="margin-bottom">5</property>
+ <!-- disable the map type swithers for now, as we only have street right now...-->
+ <!--
<child>
- <object class="GtkRadioButton" id="streetLayerButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="draw-indicator">False</property>
+ <object class="GtkToggleButton" id="streetLayerButton">
<style>
<class name="layer-radio-button"/>
</style>
<child>
- <object class="GtkImage" id="streetLayerImage">
- <property name="visible">True</property>
- </object>
+ <object class="GtkImage" id="streetLayerImage"/>
</child>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
</child>
<child>
- <object class="GtkRadioButton" id="aerialLayerButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="draw-indicator">False</property>
+ <object class="GtkToggleButton" id="aerialLayerButton">
<style>
<class name="layer-radio-button"/>
</style>
<child>
- <object class="GtkImage" id="aerialLayerImage">
- <property name="visible">True</property>
- </object>
+ <object class="GtkImage" id="aerialLayerImage"/>
</child>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">1</property>
- </packing>
</child>
+ -->
<child>
<object class="GtkBox">
- <property name="orientation">GTK_ORIENTATION_HORIZONTAL</property>
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<child>
<object class="GtkLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_START</property>
- <property name="label" translatable="yes">Show Scale</property>
+ <property name="hexpand">1</property>
+ <property name="halign">start</property>
+ <property name="label" translatable="1">Show Scale</property>
</object>
</child>
<child>
<object class="GtkCheckButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="action-name">win.show-scale</property>
</object>
</child>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">3</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">3</property>
- </packing>
</child>
<child>
<object class="GtkListBox" id="layersListBox">
<property name="name">layers-list-box</property>
- <property name="visible">false</property>
- <property name="can_focus">False</property>
+ <property name="visible">0</property>
<property name="selection-mode">none</property>
<style>
<class name="frame"/>
</style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">4</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">4</property>
- </packing>
</child>
<child>
<object class="GtkButton" id="loadLayerButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="label" translatable="yes" comments="Translators: This string uses ellipsis
character">Open Shape Layer…</property>
+ <property name="focusable">1</property>
+ <property name="label" translatable="1" comments="Translators: This string uses ellipsis
character">Open Shape Layer…</property>
<property name="action-name">win.open-shape-layer</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">5</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">5</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/main-window.ui b/data/ui/main-window.ui
index a80a2985..e804f111 100644
--- a/data/ui/main-window.ui
+++ b/data/ui/main-window.ui
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <!-- interface-requires gtk+ 3.0 -->
+ <requires lib="gtk" version="4.0"/>
<menu id="hamburgerMenu">
<section>
<item>
@@ -26,78 +26,47 @@
<template class="Gjs_MainWindow" parent="GtkApplicationWindow">
<property name="width-request">300</property>
<property name="height-request">500</property>
- <property name="window-position">center</property>
- <property name="title" translatable="yes">Maps</property>
+ <property name="title" translatable="1">Maps</property>
<child type="titlebar">
<object class="GtkHeaderBar" id="headerBar">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="show-close-button">True</property>
<style>
<class name="titlebar"/>
</style>
- <child>
+ <child type="end">
<object class="GtkMenuButton">
- <property name="visible">True</property>
<property name="halign">end</property>
<property name="valign">center</property>
<property name="menu-model">hamburgerMenu</property>
- <accelerator key="F10" signal="clicked"/>
- <child internal-child="accessible">
- <object class="AtkObject">
- <property name="accessible-name" translatable="yes">Open main menu</property>
- </object>
- </child>
- <style>
- <class name="image-button"/>
- </style>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="icon-size">1</property>
- <property name="icon-name">open-menu-symbolic</property>
- </object>
- </child>
+ <property name="tooltip-text" translatable="1">Open main menu</property>
+ <property name="icon-name">open-menu-symbolic</property>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
</object>
</child>
<child>
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<child>
<object class="GtkBox" id="placeBarContainer">
- <property name="visible">True</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">1</property>
- <property name="width">1</property>
- </packing>
</child>
<child>
<object class="GtkRevealer" id="actionBarRevealer">
- <property name="visible">True</property>
- <property name="reveal-child">False</property>
<property name="transition-type">slide-up</property>
- <child>
- <object class="GtkActionBar" id="actionBar">
- <property name="visible">True</property>
- </object>
- </child>
+ <property name="child">
+ <object class="GtkActionBar" id="actionBar"/>
+ </property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">2</property>
+ <property name="column-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">2</property>
- <property name="width">2</property>
- </packing>
</child>
</object>
</child>
</template>
</interface>
-
diff --git a/data/ui/osm-account-dialog.ui b/data/ui/osm-account-dialog.ui
index ee30d3d9..31d636ee 100644
--- a/data/ui/osm-account-dialog.ui
+++ b/data/ui/osm-account-dialog.ui
@@ -1,247 +1,240 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_OSMAccountDialog" parent="GtkDialog">
- <property name="can_focus">False</property>
- <property name="type">popup</property>
- <property name="type_hint">dialog</property>
<property name="width_request">500</property>
- <property name="title" translatable="yes">OpenStreetMap Account</property>
- <child internal-child="vbox">
+ <property name="title" translatable="1">OpenStreetMap Account</property>
+ <child>
<object class="GtkBox" id="contentArea">
<child>
<object class="GtkStack" id="stack">
- <property name="visible">True</property>
- <property name="transition-type">GTK_STACK_TRANSITION_TYPE_SLIDE_RIGHT</property>
+ <property name="transition-type">slide-right</property>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="row-spacing">10</property>
- <property name="margin">20</property>
- <child>
- <object class="GtkLabel">
- <property name="label" translatable="yes"><span weight="bold" size="x-large">Sign
in to edit maps</span></property>
- <property name="use_markup">True</property>
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- <property name="justify">GTK_JUSTIFY_CENTER</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- <property name="width">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel">
- <property name="label" translatable="yes">Help to improve the map, using an
+ <object class="GtkStackPage">
+ <property name="name">sign-in</property>
+ <property name="child">
+ <object class="GtkGrid">
+ <property name="row-spacing">10</property>
+ <property name="margin-start">20</property>
+ <property name="margin-end">20</property>
+ <property name="margin-top">20</property>
+ <property name="margin-bottom">20</property>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1"><span weight="bold"
size="x-large">Sign in to edit maps</span></property>
+ <property name="use_markup">1</property>
+ <property name="hexpand">1</property>
+ <property name="halign">center</property>
+ <property name="justify">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="column-span">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1">Help to improve the map, using an
OpenStreetMap account.</property>
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- <property name="justify">GTK_JUSTIFY_CENTER</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- <property name="width">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel">
- <property name="label" translatable="yes">Sign in to authorize access in a web browser.
+ <property name="hexpand">1</property>
+ <property name="halign">center</property>
+ <property name="justify">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ <property name="column-span">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1">Sign in to authorize access in a web browser.
Then fill in the obtained verification code here in the next step.</property>
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="wrap">True</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- <property name="justify">GTK_JUSTIFY_CENTER</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">2</property>
- <property name="width">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkSpinner" id="signInSpinner">
- <property name="visible">False</property>
- <property name="height_request">16</property>
- <property name="width_request">16</property>
- <property name="can_focus">False</property>
- <property name="active">True</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="hexpand">True</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkLinkButton">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="label" translatable="yes">Sign up</property>
- <property name="uri">https://www.openstreetmap.org/user/new</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="hexpand">True</property>
+ <property name="hexpand">1</property>
+ <property name="wrap">1</property>
+ <property name="halign">center</property>
+ <property name="justify">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">2</property>
+ <property name="column-span">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkSpinner" id="signInSpinner">
+ <property name="height_request">16</property>
+ <property name="width_request">16</property>
+ <property name="spinning">True</property>
+ <property name="halign">end</property>
+ <property name="hexpand">1</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLinkButton">
+ <property name="focusable">1</property>
+ <property name="label" translatable="1">Sign up</property>
+ <property name="uri">https://www.openstreetmap.org/user/new</property>
+ <property name="halign">end</property>
+ <property name="hexpand">1</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="signInButton">
+ <property name="halign">end</property>
+ <property name="label" translatable="1">Sign In</property>
+ <style>
+ <class name="suggested-action"/>
+ </style>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="errorLabel">
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="use-markup">1</property>
+ <style>
+ <class name="warning"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">4</property>
+ </layout>
+ </object>
+ </child>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="signInButton">
- <property name="visible">True</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="label" translatable="yes">Sign In</property>
- <style>
- <class name="suggested-action"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="errorLabel">
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="use-markup">True</property>
- <style>
- <class name="warning"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">4</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">sign-in</property>
- </packing>
</child>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="row-spacing">10</property>
- <property name="column-spacing">10</property>
- <property name="margin">20</property>
- <child>
- <object class="GtkLabel">
- <property name="visible">True</property>
- <property name="wrap">True</property>
- <property name="label" translatable="yes">Copy verification code shown when authorizing
access in the browser</property>
- </object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- <property name="width">2</property>
- </packing>
- </child>
- <child>
- <object class="GtkEntry" id="verificationEntry">
- <property name="visible">True</property>
- <property name="placeholder-text" translatable="yes">Verification code</property>
- <property name="hexpand">True</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="verifyButton">
- <property name="visible">True</property>
- <property name="sensitive">False</property>
- <property name="label" translatable="yes">Verify</property>
- <property name="hexpand">False</property>
- <property name="halign">GTK_ALIGN_END</property>
- <style>
- <class name="suggested-action"/>
- </style>
+ <object class="GtkStackPage">
+ <property name="name">verify</property>
+ <property name="child">
+ <object class="GtkGrid">
+ <property name="row-spacing">10</property>
+ <property name="column-spacing">10</property>
+ <property name="margin-start">20</property>
+ <property name="margin-end">20</property>
+ <property name="margin-top">20</property>
+ <property name="margin-bottom">20</property>
+ <child>
+ <object class="GtkLabel">
+ <property name="wrap">1</property>
+ <property name="label" translatable="1">Copy verification code shown when
authorizing access in the browser</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="column-span">2</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkEntry" id="verificationEntry">
+ <property name="placeholder-text" translatable="1">Verification code</property>
+ <property name="hexpand">1</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="verifyButton">
+ <property name="sensitive">0</property>
+ <property name="label" translatable="1">Verify</property>
+ <property name="hexpand">0</property>
+ <property name="halign">end</property>
+ <style>
+ <class name="suggested-action"/>
+ </style>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">1</property>
+ </layout>
+ </object>
+ </child>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top-attach">1</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">verify</property>
- </packing>
</child>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="row-spacing">10</property>
- <property name="margin">20</property>
- <child>
- <object class="GtkLabel">
- <property name="label" translatable="yes"><span weight="bold"
size="x-large">Signed In</span></property>
- <property name="use_markup">True</property>
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel">
- <property name="label" translatable="yes">Your OpenStreetMap account is
active.</property>
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="icon-name">avatar-default-symbolic</property>
- <property name="pixel-size">64</property>
- <property name="opacity">0.33</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">2</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="signedInUserLabel">
- <property name="visible">True</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">3</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="signOutButton">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Sign Out</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
+ <object class="GtkStackPage">
+ <property name="name">logged-in</property>
+ <property name="child">
+ <object class="GtkGrid">
+ <property name="row-spacing">10</property>
+ <property name="margin-start">20</property>
+ <property name="margin-end">20</property>
+ <property name="margin-top">20</property>
+ <property name="margin-bottom">20</property>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1"><span weight="bold"
size="x-large">Signed In</span></property>
+ <property name="use_markup">1</property>
+ <property name="hexpand">1</property>
+ <property name="halign">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1">Your OpenStreetMap account is
active.</property>
+ <property name="hexpand">1</property>
+ <property name="halign">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkImage">
+ <property name="icon-name">avatar-default-symbolic</property>
+ <property name="pixel-size">64</property>
+ <property name="opacity">0.33</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">2</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="signedInUserLabel">
+ <layout>
+ <property name="column">0</property>
+ <property name="row">3</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="signOutButton">
+ <property name="label" translatable="1">Sign Out</property>
+ <property name="halign">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">4</property>
+ </layout>
+ </object>
+ </child>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">4</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">logged-in</property>
- </packing>
</child>
</object>
</child>
diff --git a/data/ui/osm-edit-address.ui b/data/ui/osm-edit-address.ui
index 1a36f87a..b69c42f5 100644
--- a/data/ui/osm-edit-address.ui
+++ b/data/ui/osm-edit-address.ui
@@ -1,59 +1,53 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_OSMEditAddress" parent="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<style>
<class name="linked"/>
</style>
<child>
<object class="GtkEntry" id="street">
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="placeholder_text" translatable="yes">Street</property>
+ <property name="hexpand">1</property>
+ <property name="placeholder_text" translatable="1">Street</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="column-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- <property name="width">2</property>
- </packing>
</child>
<child>
<object class="GtkEntry" id="number">
- <property name="visible">True</property>
- <property name="hexpand">False</property>
- <property name="placeholder_text" translatable="yes">House number</property>
+ <property name="hexpand">0</property>
+ <property name="placeholder_text" translatable="1">House number</property>
<property name="width_chars">3</property>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkEntry" id="post">
- <property name="visible">True</property>
- <property name="hexpand">False</property>
- <property name="placeholder_text" translatable="yes">Postal code</property>
+ <property name="hexpand">0</property>
+ <property name="placeholder_text" translatable="1">Postal code</property>
<property name="width_chars">5</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
</child>
<child>
<object class="GtkEntry" id="city">
- <property name="visible">True</property>
- <property name="hexpand">True</property>
- <property name="placeholder_text" translatable="yes" comments="This is the place name as it would be
written in a postal address (typically coming after the postal code)">City</property>
+ <property name="hexpand">1</property>
+ <property name="placeholder_text" translatable="1" comments="This is the place name as it would be
written in a postal address (typically coming after the postal code)">City</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">1</property>
+ <property name="column-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">1</property>
- <property name="width">2</property>
- </packing>
</child>
</template>
</interface>
diff --git a/data/ui/osm-edit-dialog.ui b/data/ui/osm-edit-dialog.ui
index ba059ee6..07742386 100644
--- a/data/ui/osm-edit-dialog.ui
+++ b/data/ui/osm-edit-dialog.ui
@@ -1,139 +1,120 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_OSMEditDialog" parent="GtkDialog">
- <property name="can_focus">False</property>
- <property name="type">popup</property>
- <property name="type_hint">dialog</property>
<property name="width_request">500</property>
<property name="height_request">500</property>
- <child internal-child="vbox">
+ <property name="use-header-bar">True</property>
+ <property name="title" translatable="True" context="dialog title">Edit on OpenStreetMap</property>
+ <child>
<object class="GtkBox" id="contentArea">
<child>
<object class="GtkStack" id="stack">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="homogeneous">True</property>
<property name="transition_type">crossfade</property>
<child>
- <object class="GtkGrid" id="loadingGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <child>
- <object class="GtkSpinner" id="loadingSpinner">
- <property name="height_request">32</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="hexpand">True</property>
- <property name="vexpand">True</property>
- <property name="active">True</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
- </child>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">loading</property>
- </packing>
- </child>
- <child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="orientation">vertical</property>
- <property name="margin">20</property>
- <child>
- <object class="GtkGrid" id="editorGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="row-spacing">12</property>
- <property name="column-spacing">6</property>
- <property name="margin-bottom">12</property>
+ <property name="child">
+ <object class="GtkGrid" id="loadingGrid">
<child>
- <object class="GtkLabel" id="typeLabel">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">Type</property>
- <property name="halign">GTK_ALIGN_END</property>
- <style>
- <class name="dim-label"/>
- </style>
+ <object class="GtkSpinner" id="loadingSpinner">
+ <property name="height_request">32</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ <property name="spinning">True</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
</child>
+ </object>
+ </property>
+ </object>
+ </child>
+ <child>
+ <object class="GtkStackPage">
+ <property name="name">editor</property>
+ <property name="child">
+ <object class="GtkGrid">
+ <property name="orientation">vertical</property>
+ <property name="margin-start">20</property>
+ <property name="margin-end">20</property>
+ <property name="margin-top">20</property>
+ <property name="margin-bottom">20</property>
<child>
- <object class="GtkButton" id="typeButton">
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="hexpand">True</property>
+ <object class="GtkGrid" id="editorGrid">
+ <property name="row-spacing">12</property>
+ <property name="column-spacing">6</property>
+ <property name="margin-bottom">12</property>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="row-spacing">5</property>
- <property name="column-spacing">5</property>
- <child>
- <object class="GtkLabel" id="typeValueLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">None</property>
- </object>
- </child>
+ <object class="GtkLabel" id="typeLabel">
+ <property name="visible">0</property>
+ <property name="label" translatable="1">Type</property>
+ <property name="halign">end</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="typeButton">
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="hexpand">1</property>
<child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="hexpand">True</property>
- <property name="icon-name">go-next-symbolic</property>
+ <object class="GtkGrid">
+ <property name="row-spacing">5</property>
+ <property name="column-spacing">5</property>
+ <child>
+ <object class="GtkLabel" id="typeValueLabel">
+ <property name="label" translatable="1">None</property>
+ </object>
+ </child>
+ <child>
+ <object class="GtkImage">
+ <property name="halign">end</property>
+ <property name="hexpand">1</property>
+ <property name="icon-name">go-next-symbolic</property>
+ </object>
+ </child>
</object>
</child>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
</child>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">0</property>
- </packing>
</child>
- </object>
- </child>
- <child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="vexpand">True</property>
- <property name="valign">GTK_ALIGN_END</property>
<child>
- <object class="GtkMenuButton" id="addFieldButton">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="popover">addFieldPopover</property>
- <property name="direction">GTK_ARROW_UP</property>
+ <object class="GtkGrid">
+ <property name="vexpand">1</property>
+ <property name="valign">end</property>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="row-spacing">5</property>
- <property name="column-spacing">5</property>
+ <object class="GtkMenuButton" id="addFieldButton">
+ <property name="focusable">1</property>
+ <property name="popover">addFieldPopover</property>
+ <property name="direction">up</property>
<child>
- <object class="GtkLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">Add Field</property>
- </object>
- </child>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="icon-name">go-up-symbolic</property>
+ <object class="GtkGrid">
+ <property name="row-spacing">5</property>
+ <property name="column-spacing">5</property>
+ <child>
+ <object class="GtkLabel">
+ <property name="label" translatable="1">Add Field</property>
+ </object>
+ </child>
+ <child>
+ <object class="GtkImage">
+ <property name="icon-name">go-up-symbolic</property>
+ </object>
+ </child>
</object>
</child>
</object>
@@ -141,132 +122,104 @@
</object>
</child>
</object>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">editor</property>
- </packing>
</child>
<child>
- <object class="GtkGrid" id="uploadGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="margin_start">15</property>
- <property name="margin_end">15</property>
- <property name="margin_top">15</property>
- <property name="margin_bottom">15</property>
- <property name="row-spacing">5</property>
- <child>
- <object class="GtkLabel" id="commentLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">Comment</property>
- <property name="halign">GTK_ALIGN_START</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkFrame">
- <property name="visible">True</property>
+ <object class="GtkStackPage">
+ <property name="name">upload</property>
+ <property name="child">
+ <object class="GtkGrid" id="uploadGrid">
+ <property name="margin_start">15</property>
+ <property name="margin_end">15</property>
+ <property name="margin_top">15</property>
+ <property name="margin_bottom">15</property>
+ <property name="row-spacing">5</property>
<child>
- <object class="GtkTextView" id="commentTextView">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="hexpand">True</property>
- <property name="vexpand">True</property>
+ <object class="GtkLabel" id="commentLabel">
+ <property name="label" translatable="1">Comment</property>
+ <property name="halign">start</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
</object>
</child>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">2</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="uploadInfoLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">Map changes will be visible on all maps that
use
+ <child>
+ <object class="GtkFrame">
+ <property name="child">
+ <object class="GtkTextView" id="commentTextView">
+ <property name="focusable">1</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ </object>
+ </property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">2</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="uploadInfoLabel">
+ <property name="label" translatable="1">Map changes will be visible on all maps that
use
OpenStreetMap data.</property>
- <property name="halign">GTK_ALIGN_START</property>
- <style>
- <class name="dim-label"/>
- </style>
+ <property name="halign">start</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">3</property>
+ </layout>
+ </object>
+ </child>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">3</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">upload</property>
- </packing>
</child>
<child>
- <object class="GtkGrid" id="typeSearchGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="margin_start">60</property>
- <property name="margin_end">60</property>
- <property name="margin_top">15</property>
- <property name="margin_bottom">30</property>
- <property name="row-spacing">5</property>
- <!--
- <child>
- <object class="Gjs_OSMTypeSearchEntry" id="typeSearchEntry">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="hexpand">True</property>
- <property name="margin_start">10</property>
- <property name="margin_end">10</property>
- <property name="margin_bottom">10</property>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
- </child>
- -->
- <child>
- <object class="GtkLabel" id="recentTypesLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">Recently Used</property>
- <property name="halign">GTK_ALIGN_START</property>
- <style>
- <class name="dim-label"/>
- </style>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkListBox" id="recentTypesListBox">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="selection-mode">none</property>
- <style>
- <class name="frame"/>
- </style>
+ <object class="GtkStackPage">
+ <property name="name">select-type</property>
+ <property name="child">
+ <object class="GtkGrid" id="typeSearchGrid">
+ <property name="margin_start">60</property>
+ <property name="margin_end">60</property>
+ <property name="margin_top">15</property>
+ <property name="margin_bottom">30</property>
+ <property name="row-spacing">5</property>
+ <child>
+ <object class="GtkLabel" id="recentTypesLabel">
+ <property name="label" translatable="1">Recently Used</property>
+ <property name="halign">start</property>
+ <style>
+ <class name="dim-label"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkListBox" id="recentTypesListBox">
+ <property name="focusable">1</property>
+ <property name="selection-mode">none</property>
+ <style>
+ <class name="frame"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">2</property>
+ </layout>
+ </object>
+ </child>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">2</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">select-type</property>
- </packing>
</child>
</object>
</child>
@@ -274,80 +227,44 @@ OpenStreetMap data.</property>
</child>
<child type="titlebar">
<object class="GtkHeaderBar" id="headerBar">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="show-close-button">False</property>
- <property name="title" translatable="yes" context="dialog title">Edit on OpenStreetMap</property>
- <child>
+ <property name="show-title-buttons">0</property>
+ <child type="start">
<object class="GtkButton" id="cancelButton">
- <property name="label" translatable="yes">Cancel</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
+ <property name="label" translatable="1">Cancel</property>
+ <property name="focusable">1</property>
</object>
- <packing>
- <property name="pack-type">start</property>
- </packing>
</child>
- <child>
+ <child type="start">
<object class="GtkButton" id="backButton">
- <property name="visible">False</property>
- <property name="can_focus">True</property>
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">go-previous-symbolic</property>
<property name="pixel_size">16</property>
</object>
</child>
</object>
- <packing>
- <property name="pack-type">start</property>
- </packing>
</child>
- <child>
+ <child type="end">
<object class="GtkButton" id="nextButton">
- <property name="label" translatable="yes">Next</property>
- <property name="visible">True</property>
- <property name="sensitive">False</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
+ <property name="label" translatable="1">Next</property>
+ <property name="sensitive">0</property>
+ <property name="focusable">1</property>
+ <property name="receives_default">1</property>
<style>
<class name="default"/>
</style>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
</object>
</child>
</template>
<object class="GtkPopover" id="addFieldPopover">
- <property name="visible">False</property>
- <child>
+ <property name="child">
<object class="GtkGrid" id="addFieldPopoverGrid">
- <property name="visible">True</property>
- <property name="orientation">GTK_ORIENTATION_VERTICAL</property>
+ <property name="orientation">vertical</property>
</object>
- </child>
- </object>
- <object class="GtkPopover" id="hintPopover">
- <property name="visible">False</property>
- <property name="position">GTK_POS_BOTTOM</property>
- <child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="margin">5</property>
- <child>
- <object class="GtkLabel" id="hintLabel">
- <property name="visible">True</property>
- <property name="wrap">True</property>
- <property name="width-chars">20</property>
- <property name="max-width-chars">40</property>
- </object>
- </child>
- </object>
- </child>
+ </property>
</object>
</interface>
diff --git a/data/ui/osm-type-list-row.ui b/data/ui/osm-type-list-row.ui
index 05fbb6ac..79c7dcec 100644
--- a/data/ui/osm-type-list-row.ui
+++ b/data/ui/osm-type-list-row.ui
@@ -1,29 +1,26 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_OSMTypeListRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="row-homogeneous">True</property>
- <property name="margin">5</property>
+ <property name="row-homogeneous">1</property>
+ <property name="margin-start">5</property>
+ <property name="margin-end">5</property>
+ <property name="margin-top">5</property>
+ <property name="margin-bottom">5</property>
<child>
<object class="GtkLabel" id="name">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
<property name="valign">end</property>
- <property name="hexpand">True</property>
- <property name="use_markup">False</property>
+ <property name="hexpand">1</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/osm-type-popover.ui b/data/ui/osm-type-popover.ui
index 4ae9e7fb..74c5ed71 100644
--- a/data/ui/osm-type-popover.ui
+++ b/data/ui/osm-type-popover.ui
@@ -1,15 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_OSMTypePopover" parent="Gjs_SearchPopover">
- <property name="position">GTK_POS_BOTTOM</property>
- <property name="modal">False</property>
<child>
<object class="GtkListBox" id="list">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="expand">True</property>
- <property name="activate_on_single_click">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
</object>
</child>
</template>
diff --git a/data/ui/place-bar.ui b/data/ui/place-bar.ui
index 14f187bc..c61d822a 100644
--- a/data/ui/place-bar.ui
+++ b/data/ui/place-bar.ui
@@ -1,49 +1,34 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_PlaceBar" parent="GtkRevealer">
- <property name="visible">True</property>
<property name="transition_type">slide-up</property>
- <property name="reveal_child">False</property>
- <child>
+ <property name="child">
<object class="GtkActionBar" id="actionbar">
- <property name="visible">True</property>
<child>
- <object class="GtkEventBox" id="eventbox">
- <property name="visible">True</property>
+ <object class="GtkBox" id="box">
+ <property name="orientation">vertical</property>
+ <property name="spacing">6</property>
<child>
- <object class="GtkBox" id="box">
- <property name="visible">True</property>
- <property name="orientation">vertical</property>
+ <object class="GtkBox">
+ <property name="hexpand">1</property>
<property name="spacing">6</property>
<child>
- <object class="GtkBox">
- <property name="visible">True</property>
- <property name="orientation">horizontal</property>
- <property name="hexpand">True</property>
- <property name="spacing">6</property>
- <child>
- <object class="GtkLabel" id="title">
- <style>
- <class name="title-2"/>
- </style>
- <property name="visible">True</property>
- <property name="ellipsize">end</property>
- </object>
- </child>
+ <object class="GtkLabel" id="title">
+ <style>
+ <class name="title-2"/>
+ </style>
+ <property name="ellipsize">end</property>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="altSendToButton">
+ <property name="visible">0</property>
<child>
- <object class="GtkButton" id="altSendToButton">
- <property name="visible">False</property>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="icon_name">send-to-symbolic</property>
- <property name="tooltip_text" translatable="yes" comments="Translators: This is
a tooltip">Share location</property>
- </object>
- </child>
+ <object class="GtkImage">
+ <property name="icon_name">send-to-symbolic</property>
+ <property name="tooltip_text" translatable="1" comments="Translators: This is a
tooltip">Share location</property>
</object>
- <packing>
- <property name="pack_type">end</property>
- </packing>
</child>
</object>
</child>
@@ -52,8 +37,6 @@
</object>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
-
-
diff --git a/data/ui/place-buttons.ui b/data/ui/place-buttons.ui
index bace12aa..4f9be1d1 100644
--- a/data/ui/place-buttons.ui
+++ b/data/ui/place-buttons.ui
@@ -1,37 +1,26 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_PlaceButtons" parent="GtkBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="orientation">horizontal</property>
<property name="spacing">6</property>
<child>
<object class="GtkButton" id="routeButton">
<property name="name">bubble-route-button</property>
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Add to
new route</property>
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Add to new
route</property>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="orientation">horizontal</property>
<property name="spacing">6</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">route-button-symbolic</property>
<property name="pixel_size">16</property>
</object>
</child>
<child>
<object class="GtkLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes" comments="Translators: This is the button to find
a route to a place">Directions</property>
+ <property name="label" translatable="1" comments="Translators: This is the button to find a
route to a place">Directions</property>
</object>
</child>
</object>
@@ -44,61 +33,43 @@
<child>
<object class="GtkButton" id="sendToButton">
<property name="name">bubble-send-to-button</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Share
location</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Share
location</property>
<child>
<object class="GtkImage" id="sendToButtonImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">send-to-symbolic</property>
<property name="pixel_size">16</property>
</object>
</child>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
<child>
<object class="GtkButton" id="favoriteButton">
<property name="name">bubble-favorite-button</property>
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Mark as
favorite</property>
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Mark as
favorite</property>
<child>
<object class="GtkImage" id="favoriteButtonImage">
<property name="name">bubble-favorite-button-image</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">starred-symbolic</property>
<property name="pixel_size">16</property>
</object>
</child>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
<child>
<object class="GtkButton" id="editButton">
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Edit on
OpenStreetMap</property>
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Edit on
OpenStreetMap</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">document-edit-symbolic</property>
<property name="pixel_size">16</property>
</object>
</child>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
</template>
</interface>
diff --git a/data/ui/place-list-row.ui b/data/ui/place-list-row.ui
index dc476583..af687608 100644
--- a/data/ui/place-list-row.ui
+++ b/data/ui/place-list-row.ui
@@ -1,81 +1,71 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.18.3 -->
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_PlaceListRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
- <property name="row-homogeneous">True</property>
- <property name="margin">5</property>
+ <property name="row-homogeneous">1</property>
+ <property name="margin-start">5</property>
+ <property name="margin-end">5</property>
+ <property name="margin-top">5</property>
+ <property name="margin-bottom">5</property>
<child>
<object class="GtkImage" id="icon">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="pixel_size">32</property>
<property name="margin_end">12</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="row-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- <property name="height">2</property>
- </packing>
</child>
<child>
<object class="GtkImage" id="typeIcon">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="valign">center</property>
<property name="halign">end</property>
- <property name="hexpand">True</property>
+ <property name="hexpand">1</property>
<property name="margin_start">10</property>
<property name="pixel_size">16</property>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ <property name="row-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">0</property>
- <property name="height">2</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="name">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
<property name="valign">end</property>
- <property name="hexpand">True</property>
- <property name="use_markup">True</property>
+ <property name="hexpand">1</property>
+ <property name="use_markup">1</property>
<property name="ellipsize">end</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="details">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
<property name="valign">start</property>
- <property name="hexpand">True</property>
- <property name="use_markup">True</property>
+ <property name="hexpand">1</property>
+ <property name="use_markup">1</property>
<property name="ellipsize">end</property>
<style>
<class name="subtitle"/>
<class name="dim-label"/>
</style>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">1</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
-
diff --git a/data/ui/place-popover.ui b/data/ui/place-popover.ui
index 4ec01987..f4fed434 100644
--- a/data/ui/place-popover.ui
+++ b/data/ui/place-popover.ui
@@ -1,47 +1,36 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <!-- interface-requires gtk+ 3.10 -->
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_PlacePopover" parent="Gjs_SearchPopover">
<property name="visible">False</property>
<property name="hexpand">False</property>
- <property name="modal">False</property>
<property name="height-request">320</property>
<style>
<class name="maps-popover"/>
</style>
<child>
<object class="GtkGrid" id="mainGrid">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
+ <property name="focusable">1</property>
<property name="orientation">vertical</property>
<child>
<object class="GtkStack" id="stack">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="transition-type">crossfade</property>
<style>
<class name="maps-stack"/>
</style>
<child>
<object class="GtkScrolledWindow" id="scrolledWindow">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="hscrollbar_policy">never</property>
- <property name="shadow_type">in</property>
- <child>
+ <property name="child">
<object class="GtkListBox" id="list">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="expand">True</property>
- <property name="activate_on_single_click">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
</object>
- </child>
+ </property>
</object>
</child>
<child>
<object class="GtkSpinner" id="spinner">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">center</property>
<property name="valign">center</property>
<property name="width_request">16</property>
@@ -50,9 +39,7 @@
</child>
<child>
<object class="GtkLabel" id="noResultsLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">No results found</property>
+ <property name="label" translatable="1">No results found</property>
<property name="width_request">16</property>
<property name="height_request">16</property>
<style>
@@ -62,9 +49,7 @@
</child>
<child>
<object class="GtkLabel" id="errorLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="label" translatable="yes">An error has occurred</property>
+ <property name="label" translatable="1">An error has occurred</property>
<property name="width_request">16</property>
<property name="height_request">16</property>
<style>
diff --git a/data/ui/place-view.ui b/data/ui/place-view.ui
index 14421bbf..1dbd9e16 100644
--- a/data/ui/place-view.ui
+++ b/data/ui/place-view.ui
@@ -1,13 +1,9 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.18.3 -->
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<object class="GtkStack" id="bubble-main-stack">
- <property name="visible">True</property>
<child>
<object class="GtkBox" id="bubble-main-box">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
<child>
<object class="Gjs_PlaceViewImage" id="bubble-thumbnail">
@@ -17,8 +13,7 @@
</child>
<child>
<object class="GtkSeparator" id="thumbnail-separator">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
+ <property name="visible">0</property>
<style>
<class name="no-margin-separator"/>
</style>
@@ -26,29 +21,24 @@
</child>
<child>
<object class="GtkBox" id="title-box">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
- <property name="margin">18</property>
+ <property name="margin-start">18</property>
+ <property name="margin-end">18</property>
+ <property name="margin-top">18</property>
+ <property name="margin-bottom">18</property>
<property name="spacing">12</property>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="orientation">horizontal</property>
<property name="spacing">12</property>
<child>
<object class="GtkLabel" id="label-title">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
- <property name="expand">True</property>
- <property name="wrap">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ <property name="wrap">1</property>
<property name="max_width_chars">30</property>
<property name="xalign">0</property>
<style>
@@ -58,14 +48,11 @@
</child>
<child>
<object class="GtkButton" id="send-to-button-alt">
- <property name="visible">False</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a
tooltip">Share location</property>
+ <property name="visible">0</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a
tooltip">Share location</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">send-to-symbolic</property>
<property name="pixel_size">16</property>
</object>
@@ -76,11 +63,11 @@
</child>
<child>
<object class="GtkLabel" id="native-name">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
+ <property name="visible">0</property>
<property name="halign">start</property>
- <property name="expand">True</property>
- <property name="wrap">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ <property name="wrap">1</property>
<property name="max_width_chars">30</property>
<property name="xalign">0</property>
<property name="margin-top">6</property>
@@ -93,35 +80,27 @@
</child>
<child>
<object class="GtkLabel" id="address-label">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
<property name="xalign">0</property>
- <property name="use_markup">True</property>
- <property name="wrap">True</property>
+ <property name="use_markup">1</property>
+ <property name="wrap">1</property>
</object>
</child>
<child>
<object class="GtkBox" id="place-buttons">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="orientation">vertical</property>
</object>
</child>
</object>
</child>
<child>
- <object class="GtkGrid" id="bubble-content-area">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- </object>
+ <object class="GtkGrid" id="bubble-content-area"/>
</child>
</object>
</child>
<child>
<object class="GtkSpinner" id="bubble-spinner">
- <property name="visible">True</property>
- <property name="active">False</property>
+ <property name="spinning">False</property>
</object>
</child>
</object>
diff --git a/data/ui/route-entry.ui b/data/ui/route-entry.ui
index b186e453..02d36954 100644
--- a/data/ui/route-entry.ui
+++ b/data/ui/route-entry.ui
@@ -1,48 +1,32 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.10"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_RouteEntry" parent="GtkGrid">
- <property name="visible">True</property>
- <property name="orientation">horizontal</property>
- <property name="hexpand">False</property>
+ <property name="hexpand">0</property>
<child>
- <object class="GtkEventBox" id="iconEventBox">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <child>
- <object class="GtkImage" id="icon">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="margin-end">8</property>
- <property name="margin-start">13</property>
- <property name="width-request">16</property>
- <property name="icon-name">maps-point-end-symbolic</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a tooltip">Drag
to change order of the route</property>
- </object>
- </child>
+ <object class="GtkImage" id="icon">
+ <property name="margin-end">8</property>
+ <property name="margin-start">13</property>
+ <property name="width-request">16</property>
+ <property name="icon-name">maps-point-end-symbolic</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a tooltip">Drag to
change order of the route</property>
</object>
</child>
<child>
<object class="GtkGrid" id="entryGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="width_request">230</property>
- <property name="hexpand">False</property>
+ <property name="hexpand">0</property>
</object>
</child>
<child>
<object class="GtkButton" id="button">
- <property name="visible">True</property>
- <property name="no_show_all">True</property>
- <property name="can-focus">True</property>
+ <property name="focusable">1</property>
<property name="valign">center</property>
<property name="height-request">31</property>
<property name="margin-start">4</property>
<property name="margin-end">10</property>
<child>
- <object class="GtkImage" id="buttonImage">
- <property name="visible">True</property>
- </object>
+ <object class="GtkImage" id="buttonImage"/>
</child>
</object>
</child>
diff --git a/data/ui/send-to-dialog.ui b/data/ui/send-to-dialog.ui
index 433643fb..0c474d26 100644
--- a/data/ui/send-to-dialog.ui
+++ b/data/ui/send-to-dialog.ui
@@ -1,19 +1,15 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.18.3 -->
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_SendToDialog" parent="GtkDialog">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
<property name="use_header_bar">1</property>
<property name="width-request">360</property>
- <property name="title" translatable="yes">Open Location</property>
+ <property name="title" translatable="1">Open Location</property>
<child type="action">
<object class="GtkButton" id="cancelButton">
- <property name="label" translatable="yes">_Cancel</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="use_underline">True</property>
+ <property name="label" translatable="1">_Cancel</property>
+ <property name="focusable">1</property>
+ <property name="use_underline">1</property>
<style>
<class name="text-button"/>
</style>
@@ -22,38 +18,35 @@
<action-widgets>
<action-widget response="cancel">cancelButton</action-widget>
</action-widgets>
- <child internal-child="vbox">
+ <child>
<object class="GtkBox" id="contentArea">
- <property name="visible">True</property>
<property name="orientation">vertical</property>
- <property name="margin">18</property>
+ <property name="margin-start">18</property>
+ <property name="margin-end">18</property>
+ <property name="margin-top">18</property>
+ <property name="margin-bottom">18</property>
<property name="spacing">12</property>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
<property name="orientation">vertical</property>
<property name="spacing">12</property>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
<property name="orientation">vertical</property>
<child>
<object class="GtkLabel" id="summaryLabel">
- <property name="visible">True</property>
- <property name="selectable">true</property>
- <property name="label">…</property>
- <property name="justify">left</property>
+ <property name="selectable">1</property>
+ <property name="label">…</property>
<property name="halign">start</property>
- <property name="wrap">True</property>
+ <property name="wrap">1</property>
<property name="xalign">0</property>
</object>
</child>
<child>
<object class="GtkLabel" id="summaryUrl">
- <property name="visible">True</property>
- <property name="selectable">true</property>
- <property name="use-markup">true</property>
- <property name="label">…</property>
+ <property name="selectable">1</property>
+ <property name="use-markup">1</property>
+ <property name="label">…</property>
<property name="xalign">0</property>
<property name="width-request">0</property>
<property name="ellipsize">end</property>
@@ -63,21 +56,17 @@
</child>
<child>
<object class="GtkBox">
- <property name="visible">True</property>
- <property name="orientation">horizontal</property>
<property name="spacing">6</property>
<child>
<object class="GtkButton" id="copyButton">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Copy</property>
- <property name="hexpand">True</property>
+ <property name="label" translatable="1">Copy</property>
+ <property name="hexpand">1</property>
</object>
</child>
<child>
<object class="GtkButton" id="emailButton">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Send To…</property>
- <property name="hexpand">True</property>
+ <property name="label" translatable="1">Send To…</property>
+ <property name="hexpand">1</property>
</object>
</child>
</object>
@@ -86,71 +75,62 @@
</child>
<child>
<object class="GtkScrolledWindow" id="scrolledWindow">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="hscrollbar_policy">never</property>
- <property name="vexpand">True</property>
- <child>
+ <property name="vexpand">1</property>
+ <property name="child">
<object class="GtkListBox" id="list">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="selection_mode">single</property>
<child>
<object class="GtkListBoxRow" id="weatherRow">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <child>
+ <property name="focusable">1</property>
+ <property name="child">
<object class="GtkGrid" id="weatherGrid">
- <property name="visible">True</property>
- <property name="orientation">horizontal</property>
<property name="column_spacing">12</property>
- <property name="margin">6</property>
+ <property name="margin-start">6</property>
+ <property name="margin-end">6</property>
+ <property name="margin-top">6</property>
+ <property name="margin-bottom">6</property>
<child>
<object class="GtkImage" id="weatherIcon">
- <property name="visible">True</property>
<property name="pixel_size">32</property>
<property name="halign">start</property>
</object>
</child>
<child>
- <object class="GtkLabel" id='weatherLabel'>
- <property name="visible">True</property>
+ <object class="GtkLabel" id="weatherLabel">
<property name="margin-end">10</property>
</object>
</child>
</object>
- </child>
+ </property>
</object>
</child>
<child>
<object class="GtkListBoxRow" id="clocksRow">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <child>
+ <property name="focusable">1</property>
+ <property name="child">
<object class="GtkGrid" id="clocksGrid">
- <property name="visible">True</property>
- <property name="orientation">horizontal</property>
<property name="column_spacing">12</property>
- <property name="margin">6</property>
+ <property name="margin-start">6</property>
+ <property name="margin-end">6</property>
+ <property name="margin-top">6</property>
+ <property name="margin-bottom">6</property>
<child>
<object class="GtkImage" id="clocksIcon">
- <property name="visible">True</property>
<property name="pixel_size">32</property>
<property name="halign">start</property>
</object>
</child>
<child>
<object class="GtkLabel" id="clocksLabel">
- <property name="visible">True</property>
<property name="margin-end">10</property>
</object>
</child>
</object>
- </child>
+ </property>
</object>
</child>
</object>
- </child>
+ </property>
</object>
</child>
</object>
diff --git a/data/ui/sidebar.ui b/data/ui/sidebar.ui
index ab7b3890..e7ff872c 100644
--- a/data/ui/sidebar.ui
+++ b/data/ui/sidebar.ui
@@ -1,46 +1,33 @@
<?xml version="1.0" encoding="UTF-8"?>
-<!-- Generated with glade 3.18.3 -->
<interface>
- <requires lib="gtk+" version="3.10"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_Sidebar" parent="GtkRevealer">
- <property name="visible">True</property>
<property name="transition_type">slide-left</property>
<property name="transition_duration">400</property>
<property name="halign">end</property>
- <property name="valign">fill</property>
<style>
<class name="maps-sidebar"/>
</style>
- <child>
+ <property name="child">
<object class="GtkGrid" id="sidebar">
<property name="name">sidebar</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="vexpand">True</property>
- <property name="valign">fill</property>
- <property name="column_homogeneous">True</property>
+ <property name="vexpand">1</property>
+ <property name="column_homogeneous">1</property>
<property name="orientation">vertical</property>
<property name="width_request">320</property>
<property name="row_spacing">2</property>
<child>
<object class="GtkBox" id="mode-chooser">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">center</property>
<property name="margin-top">10</property>
<child>
- <object class="GtkRadioButton" id="modePedestrianToggle">
+ <object class="GtkToggleButton" id="modePedestrianToggle">
<property name="name">mode-pedestrian-toggle</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="draw_indicator">False</property>
+ <property name="receives_default">1</property>
<property name="height-request">32</property>
<property name="width-request">42</property>
<child>
<object class="GtkImage" id="mode-pedestrian-image">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">route-pedestrian-symbolic</property>
</object>
</child>
@@ -50,19 +37,14 @@
</object>
</child>
<child>
- <object class="GtkRadioButton" id="modeBikeToggle">
+ <object class="GtkToggleButton" id="modeBikeToggle">
<property name="name">mode-bike-toggle</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="draw_indicator">False</property>
+ <property name="receives_default">1</property>
<property name="group">modePedestrianToggle</property>
<property name="height-request">32</property>
<property name="width-request">42</property>
<child>
<object class="GtkImage" id="mode-bike-image">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">route-bike-symbolic</property>
</object>
</child>
@@ -72,20 +54,15 @@
</object>
</child>
<child>
- <object class="GtkRadioButton" id="modeCarToggle">
+ <object class="GtkToggleButton" id="modeCarToggle">
<property name="name">mode-car-toggle</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="active">True</property>
- <property name="draw_indicator">False</property>
+ <property name="receives_default">1</property>
+ <property name="active">1</property>
<property name="group">modeBikeToggle</property>
<property name="height-request">32</property>
<property name="width-request">42</property>
<child>
<object class="GtkImage" id="mode-car-image">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="icon-name">route-car-symbolic</property>
</object>
</child>
@@ -95,19 +72,14 @@
</object>
</child>
<child>
- <object class="GtkRadioButton" id="modeTransitToggle">
+ <object class="GtkToggleButton" id="modeTransitToggle">
<property name="name">mode-transit-toggle</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="draw_indicator">False</property>
+ <property name="receives_default">1</property>
<property name="group">modeCarToggle</property>
<property name="height-request">32</property>
<property name="width-request">42</property>
<child>
<object class="GtkImage" id="mode-transit-image">
- <property name="visible">False</property>
- <property name="can_focus">False</property>
<property name="icon-name">route-transit-symbolic</property>
</object>
</child>
@@ -116,44 +88,32 @@
</style>
</object>
</child>
- <style>
- <class name="linked"/>
- </style>
</object>
</child>
<child>
<object class="GtkListBox" id="entryList">
<property name="name">sidebar-entry-list</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="selection-mode">GTK_SELECTION_NONE</property>
+ <property name="selection-mode">none</property>
</object>
</child>
<child>
<object class="GtkGrid" id="sidebar-route-info-wrapper">
- <property name="visible">True</property>
- <property name="hexpand">False</property>
+ <property name="hexpand">0</property>
<child>
<object class="GtkGrid" id="sidebar-route-info">
<property name="name">sidebar-route-info</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="margin_start">17</property>
<property name="margin_end">17</property>
<property name="margin_top">12</property>
- <property name="hexpand">true</property>
+ <property name="hexpand">1</property>
<child>
<object class="GtkLabel" id="timeInfo">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="halign">start</property>
- <property name="hexpand">true</property>
+ <property name="hexpand">1</property>
</object>
</child>
<child>
<object class="GtkLabel" id="distanceInfo">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<property name="margin_start">10</property>
</object>
</child>
@@ -163,205 +123,187 @@
</child>
<child>
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="valign">fill</property>
- <property name="vexpand">True</property>
- <property name="hexpand_set">True</property>
+ <property name="vexpand">1</property>
+ <property name="hexpand_set">1</property>
<style>
<class name="frame"/>
</style>
<child>
<object class="GtkRevealer" id="transitRevealer">
- <child>
+ <property name="child">
<object class="GtkStack" id="transitHeader">
- <property name="visible">True</property>
- <property name="transition-type">GTK_STACK_TRANSITION_TYPE_SLIDE_LEFT_RIGHT</property>
+ <property name="transition-type">slide-left-right</property>
</object>
- </child>
+ </property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkStack" id="instructionStack">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<child>
<object class="GtkScrolledWindow" id="instructionWindow">
<property name="name">instruction-window</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="valign">fill</property>
- <property name="vexpand">True</property>
- <property name="margin">1</property>
+ <property name="vexpand">1</property>
+ <property name="margin-start">1</property>
+ <property name="margin-end">1</property>
+ <property name="margin-top">1</property>
+ <property name="margin-bottom">1</property>
<property name="hscrollbar_policy">never</property>
- <child>
+ <property name="child">
<object class="GtkListBox" id="instructionList">
<property name="name">instruction-list</property>
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="valign">fill</property>
- <property name="hexpand">True</property>
+ <property name="hexpand">1</property>
</object>
- </child>
+ </property>
</object>
</child>
<child>
<object class="GtkScrolledWindow" id="transitWindow">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="valign">fill</property>
- <property name="vexpand">True</property>
- <property name="margin">1</property>
+ <property name="vexpand">1</property>
+ <property name="margin-start">1</property>
+ <property name="margin-end">1</property>
+ <property name="margin-top">1</property>
+ <property name="margin-bottom">1</property>
<property name="hscrollbar_policy">never</property>
- <child>
+ <property name="child">
<object class="GtkStack" id="transitListStack">
- <property name="visible">True</property>
- <property
name="transition-type">GTK_STACK_TRANSITION_TYPE_SLIDE_LEFT_RIGHT</property>
- <property name="vhomogeneous">False</property>
+ <property name="transition-type">slide-left-right</property>
+ <property name="vhomogeneous">0</property>
<child>
- <object class="GtkListBox" id="transitOverviewListBox">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">overview</property>
- </packing>
+ <property name="child">
+ <object class="GtkListBox" id="transitOverviewListBox"/>
+ </property>
+ </object>
</child>
<child>
- <object class="GtkListBox" id="transitItineraryListBox">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="selection-mode">GTK_SELECTION_NONE</property>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">itinerary</property>
- </packing>
+ <property name="child">
+ <object class="GtkListBox" id="transitItineraryListBox">
+ <property name="selection-mode">none</property>
+ </object>
+ </property>
+ </object>
</child>
</object>
- </child>
+ </property>
</object>
</child>
<child>
<object class="GtkSpinner" id="instructionSpinner">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="active">True</property>
+ <property name="spinning">True</property>
+ <property name="halign">center</property>
+ <property name="valign">center</property>
+ <property name="width_request">16</property>
+ <property name="height_request">16</property>
</object>
</child>
<child>
<object class="GtkLabel" id="errorLabel">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
<style>
<class name="dim-label"/>
</style>
</object>
</child>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">1</property>
- </packing>
</child>
</object>
</child>
<child>
<object class="GtkStack" id="linkButtonStack">
<child>
- <object class="GtkLinkButton">
- <property name="label" translatable="yes">Route search by GraphHopper</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="use_action_appearance">False</property>
- <property name="relief">none</property>
- <property name="uri">https://graphhopper.com</property>
- <style>
- <class name="small-label"/>
- </style>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">turnByTurn</property>
- </packing>
- </child>
- <child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="halign">GTK_ALIGN_END</property>
- <child>
- <object class="GtkLabel" id="transitAttributionLabel">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
- <property name="use_markup">True</property>
+ <property name="child">
+ <object class="GtkLinkButton">
+ <property name="label" translatable="1">Route search by GraphHopper</property>
+ <property name="focusable">1</property>
+ <property name="receives_default">1</property>
+ <property name="uri">https://graphhopper.com</property>
<style>
<class name="small-label"/>
</style>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkMenuButton">
- <property name="visible">True</property>
- <property name="popover">transitDisclaimerPopover</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="margin-top">5</property>
- <property name="margin-bottom">5</property>
- <property name="margin-end">5</property>
- <property name="margin-start">5</property>
- <style>
- <class name="flat"/>
- </style>
+ </property>
+ </object>
+ </child>
+ <child>
+ <object class="GtkStackPage">
+ <property name="name">transit</property>
+ <property name="child">
+ <object class="GtkGrid">
+ <property name="halign">end</property>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
+ <object class="GtkLabel" id="transitAttributionLabel">
+ <property name="focusable">1</property>
+ <property name="receives_default">1</property>
+ <property name="use_markup">1</property>
+ <style>
+ <class name="small-label"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkMenuButton">
+ <property name="popover">transitDisclaimerPopover</property>
+ <property name="halign">end</property>
+ <property name="margin-top">5</property>
+ <property name="margin-bottom">5</property>
+ <property name="margin-end">5</property>
+ <property name="margin-start">5</property>
+ <style>
+ <class name="flat"/>
+ </style>
<child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- <property name="hexpand">False</property>
- <property name="icon-name">dialog-information-symbolic</property>
+ <object class="GtkGrid">
+ <property name="valign">center</property>
+ <child>
+ <object class="GtkImage">
+ <property name="halign">center</property>
+ <property name="hexpand">0</property>
+ <property name="icon-name">dialog-information-symbolic</property>
+ </object>
+ </child>
</object>
</child>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
</child>
</object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">transit</property>
- </packing>
</child>
</object>
</child>
</object>
- </child>
+ </property>
</template>
<object class="GtkPopover" id="transitDisclaimerPopover">
- <property name="visible">False</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
<child>
<object class="GtkLabel">
- <property name="visible">True</property>
<property name="margin-top">5</property>
<property name="margin-bottom">5</property>
<property name="margin-start">5</property>
<property name="margin-end">5</property>
- <property name="label" translatable="yes">Routing itineraries for public transit is provided by
third-party
+ <property name="label" translatable="1">Routing itineraries for public transit is provided by
third-party
services.
GNOME can not guarantee correctness of the itineraries and schedules shown.
Note that some providers might not include all available modes of transportation,
@@ -371,74 +313,66 @@ Names and brands shown are to be considered as registered trademarks when applic
</object>
</child>
</object>
- </child>
+ </property>
</object>
<object class="GtkGrid" id="transitItineraryHeader">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<style>
<class name="shaded"/>
</style>
<child>
<object class="GtkButton" id="transitItineraryBackButton">
- <property name="visible">True</property>
<property name="margin-start">6</property>
<property name="margin-end">6</property>
<property name="margin-top">4</property>
<property name="margin-bottom">4</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="halign">start</property>
<child>
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
+ <property name="valign">center</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">False</property>
+ <property name="hexpand">0</property>
<property name="icon-name">go-previous-symbolic</property>
</object>
</child>
</object>
</child>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="transitItineraryTimeLabel">
- <property name="visible">True</property>
<property name="margin-start">6</property>
<property name="margin-end">6</property>
<property name="margin-top">4</property>
<property name="margin-bottom">4</property>
- <property name="hexpand">False</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="hexpand">0</property>
+ <property name="halign">start</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="transitItineraryDurationLabel">
- <property name="visible">True</property>
<property name="margin-start">6</property>
<property name="margin-end">6</property>
<property name="margin-top">4</property>
<property name="margin-bottom">4</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="hexpand">1</property>
+ <property name="halign">start</property>
<style>
<class name="dim-label"/>
</style>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">2</property>
- <property name="top-attach">0</property>
- </packing>
</child>
</object>
</interface>
diff --git a/data/ui/transit-arrival-row.ui b/data/ui/transit-arrival-row.ui
index 73a42bb1..2c8a1cbf 100644
--- a/data/ui/transit-arrival-row.ui
+++ b/data/ui/transit-arrival-row.ui
@@ -1,77 +1,59 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.14"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitArrivalRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<child>
- <object class="GtkEventBox" id="eventBox">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
+ <object class="GtkGrid" id="grid">
+ <property name="margin-top">6</property>
+ <property name="row-spacing">12</property>
<child>
- <object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="margin-top">6</property>
- <property name="margin-bottom">0</property>
- <property name="row-spacing">12</property>
- <child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="margin-start">12</property>
- <property name="margin-end">12</property>
- <property name="icon-name">maps-point-end-symbolic</property>
- <style>
- <class name="sidebar-icon"/>
- </style>
- </object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="arrivalLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_START</property>
- <property name="max-width-chars">25</property>
- <property name="ellipsize">PANGO_ELLIPSIZE_END</property>
- </object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="timeLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="halign">GTK_ALIGN_END</property>
- <property name="margin-start">6</property>
- <property name="margin-end">18</property>
- <attributes>
- <attribute name="font-features" value="tnum"/>
- </attributes>
- </object>
- <packing>
- <property name="left-attach">2</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkSeparator" id="separator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">1</property>
- <property name="width">3</property>
- </packing>
- </child>
+ <object class="GtkImage">
+ <property name="margin-start">12</property>
+ <property name="margin-end">12</property>
+ <property name="icon-name">maps-point-end-symbolic</property>
+ <style>
+ <class name="sidebar-icon"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="arrivalLabel">
+ <property name="hexpand">1</property>
+ <property name="halign">start</property>
+ <property name="max-width-chars">25</property>
+ <property name="ellipsize">end</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="timeLabel">
+ <property name="halign">end</property>
+ <property name="margin-start">6</property>
+ <property name="margin-end">18</property>
+ <attributes>
+ <attribute name="font-features" value="tnum"></attribute>
+ </attributes>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkSeparator" id="separator">
+ <property name="valign">center</property>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">1</property>
+ <property name="column-span">3</property>
+ </layout>
</object>
</child>
</object>
diff --git a/data/ui/transit-itinerary-row.ui b/data/ui/transit-itinerary-row.ui
index 9ef1ddaf..8a238a32 100644
--- a/data/ui/transit-itinerary-row.ui
+++ b/data/ui/transit-itinerary-row.ui
@@ -1,72 +1,71 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.14"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitItineraryRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="margin">13</property>
+ <property name="margin-start">13</property>
+ <property name="margin-end">13</property>
+ <property name="margin-top">13</property>
+ <property name="margin-bottom">13</property>
<property name="column_spacing">13</property>
<property name="row-spacing">2</property>
<child>
<object class="GtkLabel" id="timeLabel">
- <property name="visible">True</property>
- <property name="expand">False</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="hexpand">0</property>
+ <property name="vexpand">0</property>
+ <property name="halign">start</property>
<attributes>
- <attribute name="font-features" value="tnum"/>
+ <attribute name="font-features" value="tnum"></attribute>
</attributes>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">0</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="durationLabel">
- <property name="visible">True</property>
- <property name="expand">True</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ <property name="halign">start</property>
<attributes>
- <attribute name="font-features" value="tnum"/>
+ <attribute name="font-features" value="tnum"></attribute>
</attributes>
<style>
<class name="dim-label"/>
</style>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">1</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">1</property>
- </packing>
</child>
<child>
<object class="GtkGrid" id="summaryGrid">
- <property name="visible">True</property>
- <property name="expand">True</property>
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
<property name="column-spacing">5</property>
+ <layout>
+ <property name="row">1</property>
+ <property name="column">0</property>
+ <property name="column-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">1</property>
- <property name="left-attach">0</property>
- <property name="width">2</property>
- </packing>
</child>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<property name="icon-name">go-next-symbolic</property>
<property name="pixel-size">16</property>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">2</property>
+ <property name="row-span">2</property>
+ <property name="column-span">2</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">2</property>
- <property name="height">2</property>
- <property name="width">2</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/transit-leg-row.ui b/data/ui/transit-leg-row.ui
index 2d27feb4..9a9747dd 100644
--- a/data/ui/transit-leg-row.ui
+++ b/data/ui/transit-leg-row.ui
@@ -1,258 +1,211 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.14"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitLegRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
<child>
- <object class="GtkEventBox" id="eventBox">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
+ <object class="GtkGrid" id="grid">
+ <property name="row-spacing">3</property>
<child>
- <object class="GtkGrid" id="grid">
- <property name="visible">True</property>
- <property name="margin-top">0</property>
- <property name="margin-bottom">0</property>
- <property name="row-spacing">3</property>
- <child>
- <object class="GtkImage" id="modeImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="margin-start">12</property>
- <property name="margin-end">12</property>
- <property name="halign">GTK_ALIGN_START</property>
- <style>
- <class name="sidebar-icon"/>
- </style>
- </object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- <property name="height">2</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="fromLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="halign">GTK_ALIGN_START</property>
- <property name="max-width-chars">25</property>
- <property name="ellipsize">PANGO_ELLIPSIZE_END</property>
- </object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkGrid" id="routeGrid">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="halign">GTK_ALIGN_START</property>
- <property name="hexpand">True</property>
- </object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="timeLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="margin-start">6</property>
- <property name="margin-end">18</property>
- <property name="hexpand">False</property>
- <property name="halign">GTK_ALIGN_END</property>
- <attributes>
- <attribute name="font-features" value="tnum"/>
- </attributes>
- </object>
- <packing>
- <property name="left-attach">2</property>
- <property name="top-attach">0</property>
- <property name="height">2</property>
- </packing>
- </child>
+ <object class="GtkImage" id="modeImage">
+ <property name="margin-start">12</property>
+ <property name="margin-end">12</property>
+ <property name="halign">start</property>
+ <style>
+ <class name="sidebar-icon"/>
+ </style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ <property name="row-span">2</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="fromLabel">
+ <property name="halign">start</property>
+ <property name="max-width-chars">25</property>
+ <property name="ellipsize">end</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkGrid" id="routeGrid">
+ <property name="halign">start</property>
+ <property name="hexpand">1</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">1</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkLabel" id="timeLabel">
+ <property name="margin-start">6</property>
+ <property name="margin-end">18</property>
+ <property name="hexpand">0</property>
+ <property name="halign">end</property>
+ <attributes>
+ <attribute name="font-features" value="tnum"></attribute>
+ </attributes>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ <property name="row-span">2</property>
+ </layout>
</object>
</child>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
</child>
-
<child>
<object class="GtkRevealer" id="detailsRevealer">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<property name="margin-start">15</property>
<property name="margin-end">15</property>
<property name="row-spacing">1</property>
<child>
<object class="GtkLabel" id="agencyLabel">
- <property name="visible">False</property>
- <property name="use-markup">True</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="visible">0</property>
+ <property name="use-markup">1</property>
+ <property name="halign">start</property>
<property name="max_width_chars">30</property>
- <property name="ellipsize">PANGO_ELLIPSIZE_END</property>
+ <property name="ellipsize">end</property>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">0</property>
+ <property name="column-span">3</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">0</property>
- <property name="width">3</property>
- </packing>
</child>
<child>
<object class="GtkSeparator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
+ <property name="hexpand">1</property>
+ <property name="valign">center</property>
+ <layout>
+ <property name="row">1</property>
+ <property name="column">0</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">1</property>
- <property name="left-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkButton" id="collapsButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a
tooltip">Hide intermediate stops and information</property>
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a
tooltip">Hide intermediate stops and information</property>
<style>
<class name="small-circular"/>
</style>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<property name="icon-name">go-up-symbolic</property>
<property name="pixel-size">8</property>
</object>
</child>
+ <layout>
+ <property name="row">1</property>
+ <property name="column">1</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">1</property>
- <property name="left-attach">1</property>
- </packing>
</child>
<child>
<object class="GtkSeparator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
+ <property name="hexpand">1</property>
+ <property name="valign">center</property>
+ <layout>
+ <property name="row">1</property>
+ <property name="column">2</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">1</property>
- <property name="left-attach">2</property>
- </packing>
</child>
<child>
<object class="GtkListBox" id="instructionList">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
+ <layout>
+ <property name="row">2</property>
+ <property name="column">0</property>
+ <property name="column-span">3</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">2</property>
- <property name="left-attach">0</property>
- <property name="width">3</property>
- </packing>
</child>
-
</object>
- </child>
+ </property>
+ <layout>
+ <property name="row">1</property>
+ <property name="column">0</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">1</property>
- <property name="left-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkStack" id="footerStack">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
<child>
- <object class="GtkGrid">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <child>
- <object class="GtkSeparator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="expandButton">
- <property name="visible">True</property>
- <property name="can-focus">True</property>
- <property name="tooltip-text" translatable="yes" comments="Translators: This is a
tooltip">Show intermediate stops and information</property>
- <style>
- <class name="small-circular"/>
- </style>
+ <object class="GtkStackPage">
+ <property name="name">expander</property>
+ <property name="child">
+ <object class="GtkGrid">
<child>
- <object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="icon-name">go-down-symbolic</property>
- <property name="pixel-size">8</property>
+ <object class="GtkSeparator">
+ <property name="hexpand">1</property>
+ <property name="valign">center</property>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">0</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="expandButton">
+ <property name="focusable">1</property>
+ <property name="tooltip-text" translatable="1" comments="Translators: This is a
tooltip">Show intermediate stops and information</property>
+ <style>
+ <class name="small-circular"/>
+ </style>
+ <child>
+ <object class="GtkImage">
+ <property name="icon-name">go-down-symbolic</property>
+ <property name="pixel-size">8</property>
+ </object>
+ </child>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">1</property>
+ </layout>
+ </object>
+ </child>
+ <child>
+ <object class="GtkSeparator">
+ <property name="hexpand">1</property>
+ <property name="valign">center</property>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">2</property>
+ </layout>
</object>
</child>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkSeparator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">2</property>
- </packing>
- </child>
+ </property>
</object>
- <packing>
- <property name="name">expander</property>
- </packing>
</child>
<child>
- <object class="GtkSeparator">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">separator</property>
- </packing>
+ <property name="child">
+ <object class="GtkSeparator">
+ <property name="hexpand">1</property>
+ <property name="valign">center</property>
+ </object>
+ </property>
+ </object>
</child>
+ <layout>
+ <property name="row">2</property>
+ <property name="column">0</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">2</property>
- <property name="left-attach">0</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/transit-more-row.ui b/data/ui/transit-more-row.ui
index 7de5b98a..fd5f823d 100644
--- a/data/ui/transit-more-row.ui
+++ b/data/ui/transit-more-row.ui
@@ -1,40 +1,43 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitMoreRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="margin">13</property>
+ <property name="margin-start">13</property>
+ <property name="margin-end">13</property>
+ <property name="margin-top">13</property>
+ <property name="margin-bottom">13</property>
<child>
<object class="GtkStack" id="stack">
- <property name="visible">True</property>
<child>
- <object class="GtkLabel" id="label">
- <property name="visible">True</property>
- <property name="expand">True</property>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">label</property>
- </packing>
+ <property name="child">
+ <object class="GtkLabel" id="label">
+ <property name="hexpand">1</property>
+ <property name="vexpand">1</property>
+ </object>
+ </property>
+ </object>
</child>
<child>
- <object class="GtkSpinner">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="active">True</property>
- </object>
- <packing>
+ <object class="GtkStackPage">
<property name="name">spinner</property>
- </packing>
+ <property name="child">
+ <object class="GtkSpinner">
+ <property name="spinning">True</property>
+ </object>
+ </property>
+ </object>
</child>
+ <layout>
+ <property name="row">0</property>
+ <property name="column">0</property>
+ </layout>
</object>
- <packing>
- <property name="top-attach">0</property>
- <property name="left-attach">0</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/transit-options-panel.ui b/data/ui/transit-options-panel.ui
index a11acfa0..8169ab13 100644
--- a/data/ui/transit-options-panel.ui
+++ b/data/ui/transit-options-panel.ui
@@ -1,14 +1,12 @@
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitOptionsPanel" parent="GtkGrid">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="no-show-all">True</property>
<style>
<class name="shaded"/>
</style>
<child>
<object class="GtkComboBoxText" id="transitTimeOptionsComboBox">
- <property name="visible">True</property>
<property name="active_id">leaveNow</property>
<property name="margin_start">6</property>
<property name="margin_end">6</property>
@@ -19,91 +17,83 @@
<item translatable="yes" id="leaveBy" comments="Indicates searching for itineraries leaving at the
specified time at the earliest">Leave By</item>
<item translatable="yes" id="arriveBy" comments="Indicates searching for itineraries arriving no
later than the specified time">Arrive By</item>
</items>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkEntry" id="transitTimeEntry">
- <property name="visible">False</property>
- <property name="width_chars">5</property>
+ <property name="max-width-chars">5</property>
<property name="margin_start">3</property>
<property name="margin_end">3</property>
<property name="margin_top">4</property>
<property name="margin_bottom">4</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">1</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkMenuButton" id="transitDateButton">
- <property name="visible">False</property>
<property name="popover">transitDatePopover</property>
<property name="margin_start">3</property>
<property name="margin_end">3</property>
<property name="margin_top">4</property>
<property name="margin_bottom">4</property>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">2</property>
- <property name="top_attach">0</property>
- </packing>
</child>
<child>
<object class="GtkMenuButton" id="transitParametersMenuButton">
- <property name="visible">True</property>
<property name="popover">transitParametersPopover</property>
- <property name="halign">GTK_ALIGN_END</property>
+ <property name="halign">end</property>
<property name="margin_start">3</property>
<property name="margin_end">6</property>
<property name="margin_top">4</property>
<property name="margin_bottom">4</property>
+ <property name="hexpand">true</property>
<child>
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="valign">GTK_ALIGN_CENTER</property>
+ <property name="valign">center</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can_focus">False</property>
- <property name="halign">GTK_ALIGN_CENTER</property>
- <property name="hexpand">True</property>
+ <property name="halign">center</property>
+ <property name="hexpand">1</property>
<property name="icon-name">view-more-symbolic</property>
</object>
</child>
</object>
</child>
+ <layout>
+ <property name="column">3</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left_attach">3</property>
- <property name="top_attach">0</property>
- </packing>
</child>
</template>
<object class="GtkPopover" id="transitDatePopover">
- <property name="visible">False</property>
- <child>
- <object class="GtkCalendar" id="transitDateCalendar">
- <property name="visible">True</property>
- </object>
- </child>
+ <property name="child">
+ <object class="GtkCalendar" id="transitDateCalendar"/>
+ </property>
</object>
<object class="GtkPopover" id="transitParametersPopover">
- <property name="visible">False</property>
- <child>
+ <property name="child">
<object class="GtkGrid">
- <property name="visible">True</property>
- <property name="margin">6</property>
- <property name="orientation">GTK_ORIENTATION_VERTICAL</property>
+ <property name="margin-start">6</property>
+ <property name="margin-end">6</property>
+ <property name="margin-top">6</property>
+ <property name="margin-bottom">6</property>
+ <property name="orientation">vertical</property>
<child>
<object class="GtkLabel">
- <property name="visible">True</property>
- <property name="halign">GTK_ALIGN_START</property>
- <property name="label" translatable="yes" comments="Header indicating selected modes of
transit">Show</property>
+ <property name="halign">start</property>
+ <property name="label" translatable="1" comments="Header indicating selected modes of
transit">Show</property>
<property name="margin_start">6</property>
<style>
<class name="dim-label"/>
@@ -112,48 +102,41 @@
</child>
<child>
<object class="GtkCheckButton" id="busCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Buses</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Buses</property>
</object>
</child>
<child>
<object class="GtkCheckButton" id="tramCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Trams</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Trams</property>
</object>
</child>
<child>
<object class="GtkCheckButton" id="trainCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Trains</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Trains</property>
</object>
</child>
<child>
<object class="GtkCheckButton" id="subwayCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Subway</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Subway</property>
</object>
</child>
<child>
<object class="GtkCheckButton" id="ferryCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Ferries</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Ferries</property>
</object>
</child>
<child>
<object class="GtkCheckButton" id="airplaneCheckButton">
- <property name="visible">True</property>
- <property name="active">True</property>
- <property name="label" translatable="yes">Airplanes</property>
+ <property name="active">1</property>
+ <property name="label" translatable="1">Airplanes</property>
</object>
</child>
</object>
- </child>
+ </property>
</object>
</interface>
-
diff --git a/data/ui/transit-route-label.ui b/data/ui/transit-route-label.ui
index 423f7826..c9f67f07 100644
--- a/data/ui/transit-route-label.ui
+++ b/data/ui/transit-route-label.ui
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="utf-8"?>
<interface>
- <requires lib="gtk+" version="3.14"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitRouteLabel" parent="GtkLabel">
<property name="visible">True</property>
<property name="use-markup">True</property>
@@ -13,6 +13,8 @@
<property name="margin-end">3</property>
<property name="hexpand">False</property>
<property name="halign">GTK_ALIGN_START</property>
+ <property name="yalign">1.0</property>
+ <property name="xalign">0.6</property>
<style>
<class name="route-label"/>
</style>
diff --git a/data/ui/transit-stop-row.ui b/data/ui/transit-stop-row.ui
index 1cd02ba9..6b7e4fdd 100644
--- a/data/ui/transit-stop-row.ui
+++ b/data/ui/transit-stop-row.ui
@@ -1,58 +1,48 @@
-<?xml version="1.0" encoding="utf-8"?>
+<?xml version="1.0" encoding="UTF-8"?>
<interface>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_TransitStopRow" parent="GtkListBoxRow">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <child>
+ <property name="child">
<object class="GtkGrid" id="grid">
- <property name="visible">True</property>
<child>
<object class="GtkImage">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="margin-start">0</property>
<property name="margin-end">6</property>
<property name="icon-name">maps-point-end-symbolic</property>
<style>
<class name="sidebar-icon"/>
</style>
+ <layout>
+ <property name="column">0</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">0</property>
- <property name="top-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="nameLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="hexpand">True</property>
- <property name="halign">GTK_ALIGN_START</property>
+ <property name="hexpand">1</property>
+ <property name="halign">start</property>
<property name="max-width-chars">25</property>
- <property name="ellipsize">PANGO_ELLIPSIZE_END</property>
+ <property name="ellipsize">end</property>
+ <layout>
+ <property name="column">1</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">1</property>
- <property name="top-attach">0</property>
- </packing>
</child>
<child>
<object class="GtkLabel" id="timeLabel">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="halign">GTK_ALIGN_END</property>
+ <property name="halign">end</property>
<property name="margin-start">6</property>
- <property name="margin-end">0</property>
<attributes>
- <attribute name="font-features" value="tnum"/>
+ <attribute name="font-features" value="tnum"></attribute>
</attributes>
+ <layout>
+ <property name="column">2</property>
+ <property name="row">0</property>
+ </layout>
</object>
- <packing>
- <property name="left-attach">2</property>
- <property name="top-attach">0</property>
- </packing>
</child>
</object>
- </child>
+ </property>
</template>
</interface>
diff --git a/data/ui/zoom-in-dialog.ui b/data/ui/zoom-in-dialog.ui
index 359dd46c..bb6753d3 100644
--- a/data/ui/zoom-in-dialog.ui
+++ b/data/ui/zoom-in-dialog.ui
@@ -1,53 +1,38 @@
<?xml version="1.0" encoding="UTF-8"?>
<interface>
- <requires lib="gtk+" version="3.12"/>
+ <requires lib="gtk" version="4.0"/>
<template class="Gjs_ZoomInDialog" parent="GtkDialog">
- <property name="can_focus">False</property>
- <property name="type">popup</property>
- <property name="type_hint">dialog</property>
<property name="width_request">400</property>
<property name="height_request">150</property>
- <child internal-child="vbox">
+ <child>
<object class="GtkBox" id="contentArea">
- <property name="visible">True</property>
<child>
<object class="GtkLabel">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Zoom in to add location!</property>
+ <property name="label" translatable="1">Zoom in to add location!</property>
</object>
</child>
</object>
</child>
<child type="titlebar">
<object class="GtkHeaderBar" id="headerBar">
- <property name="visible">True</property>
- <property name="can-focus">False</property>
- <property name="show-close-button">False</property>
- <child>
+ <property name="show-title-buttons">0</property>
+ <child type="start">
<object class="GtkButton" id="cancelButton">
- <property name="label" translatable="yes">Cancel</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
+ <property name="label" translatable="1">Cancel</property>
+ <property name="focusable">1</property>
</object>
- <packing>
- <property name="pack-type">start</property>
- </packing>
</child>
- <child>
+ <child type="end">
<object class="GtkButton" id="zoomInButton">
- <property name="label" translatable="yes">Zoom In</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">True</property>
+ <property name="label" translatable="1">Zoom In</property>
+ <property name="focusable">1</property>
+ <property name="receives_default">1</property>
<style>
<class name="default"/>
</style>
</object>
- <packing>
- <property name="pack-type">end</property>
- </packing>
</child>
</object>
</child>
</template>
-</interface>
\ No newline at end of file
+</interface>
diff --git a/lib/maps-file-tile-source.c b/lib/maps-file-tile-source.c
index 61e5f060..fdabbd60 100644
--- a/lib/maps-file-tile-source.c
+++ b/lib/maps-file-tile-source.c
@@ -17,7 +17,7 @@
* Author: Jonas Danielsson <jonas threetimestwo org>
*/
-#include <champlain/champlain.h>
+#include <shumate/shumate.h>
#include <gio/gio.h>
#include <glib.h>
#include <glib-object.h>
@@ -41,8 +41,10 @@ enum {
PROP_PATH,
PROP_MAX_ZOOM,
PROP_MIN_ZOOM,
- PROP_WORLD
-
+ PROP_WORLD_LEFT,
+ PROP_WORLD_TOP,
+ PROP_WORLD_RIGHT,
+ PROP_WORLD_BOTTOM
};
struct _MapsFileTileSourcePrivate
@@ -51,7 +53,10 @@ struct _MapsFileTileSourcePrivate
gchar *extension;
gint max_zoom;
gint min_zoom;
- ChamplainBoundingBox *world;
+ double world_left;
+ double world_top;
+ double world_right;
+ double world_bottom;
long min_x;
long min_y;
@@ -59,17 +64,7 @@ struct _MapsFileTileSourcePrivate
long max_y;
};
-typedef struct
-{
- ChamplainMapSource *map_source;
- ChamplainTile *tile;
-} CallbackData;
-
-G_DEFINE_TYPE_WITH_PRIVATE (MapsFileTileSource, maps_file_tile_source, CHAMPLAIN_TYPE_TILE_SOURCE)
-
-static void fill_tile (ChamplainMapSource *map_source,
- ChamplainTile *tile);
-
+G_DEFINE_TYPE_WITH_PRIVATE (MapsFileTileSource, maps_file_tile_source, SHUMATE_TYPE_MAP_SOURCE)
static void
maps_file_tile_source_set_property (GObject *object,
@@ -112,8 +107,20 @@ maps_file_tile_source_get_property (GObject *object,
g_value_set_uint (value, tile_source->priv->max_zoom);
break;
- case PROP_WORLD:
- g_value_set_boxed (value, tile_source->priv->world);
+ case PROP_WORLD_LEFT:
+ g_value_set_double (value, tile_source->priv->world_left);
+ break;
+
+ case PROP_WORLD_TOP:
+ g_value_set_double (value, tile_source->priv->world_top);
+ break;
+
+ case PROP_WORLD_RIGHT:
+ g_value_set_double (value, tile_source->priv->world_right);
+ break;
+
+ case PROP_WORLD_BOTTOM:
+ g_value_set_double (value, tile_source->priv->world_bottom);
break;
default:
@@ -141,26 +148,22 @@ maps_file_tile_source_finalize (GObject *object)
G_OBJECT_CLASS (maps_file_tile_source_parent_class)->finalize (object);
}
-static guint
-get_max_zoom_level (ChamplainMapSource *source)
-{
- MapsFileTileSource *tile_source = (MapsFileTileSource *) source;
-
- return tile_source->priv->max_zoom;
-}
-
-static guint
-get_min_zoom_level (ChamplainMapSource *source)
-{
- MapsFileTileSource *tile_source = (MapsFileTileSource *) source;
+static void
+fill_tile_async (ShumateMapSource *source,
+ ShumateTile *tile,
+ GCancellable *cancellable,
+ GAsyncReadyCallback callback,
+ gpointer user_data);
- return tile_source->priv->min_zoom;
-}
+static gboolean
+fill_tile_finish (ShumateMapSource *map_source,
+ GAsyncResult *result,
+ GError **error);
static void
maps_file_tile_source_class_init (MapsFileTileSourceClass *klass)
{
- ChamplainMapSourceClass *map_source_class = CHAMPLAIN_MAP_SOURCE_CLASS (klass);
+ ShumateMapSourceClass *map_source_class = SHUMATE_MAP_SOURCE_CLASS (klass);
GObjectClass *object_class = G_OBJECT_CLASS (klass);
GParamSpec *pspec;
@@ -168,9 +171,8 @@ maps_file_tile_source_class_init (MapsFileTileSourceClass *klass)
object_class->dispose = maps_file_tile_source_dispose;
object_class->get_property = maps_file_tile_source_get_property;
object_class->set_property = maps_file_tile_source_set_property;
- map_source_class->get_max_zoom_level = get_max_zoom_level;
- map_source_class->get_min_zoom_level = get_min_zoom_level;
- map_source_class->fill_tile = fill_tile;
+ map_source_class->fill_tile_async = fill_tile_async;
+ map_source_class->fill_tile_finish = fill_tile_finish;
/**
* MapsFileTileSource:path:
@@ -216,19 +218,59 @@ maps_file_tile_source_class_init (MapsFileTileSourceClass *klass)
g_object_class_install_property (object_class, PROP_MAX_ZOOM, pspec);
/**
- * MapsFileTileSource:world:
+ * MapsFileTileSource:world_left:
*
- * Set a bounding box to limit the world to. No tiles will be loaded
- * outside of this bounding box. It will not be possible to scroll outside
- * of this bounding box.
+ * The leftmost of the world bounding box.
*
*/
- pspec = g_param_spec_boxed ("world",
- "The world",
- "The bounding box to limit the #ChamplainView to",
- CHAMPLAIN_TYPE_BOUNDING_BOX,
- G_PARAM_READABLE);
- g_object_class_install_property (object_class, PROP_WORLD, pspec);
+ pspec = g_param_spec_double ("worl-left",
+ "Boundingbox left",
+ "The leftmost coordinate of the world boundingbox",
+ -180,
+ 180,
+ -180,
+ G_PARAM_READABLE);
+
+ /**
+ * MapsFileTileSource:world_top:
+ *
+ * The top of the world bounding box.
+ *
+ */
+ pspec = g_param_spec_double ("worl-top",
+ "Boundingbox top",
+ "The topmost coordinate of the world boundingbox",
+ -90,
+ 90,
+ 90,
+ G_PARAM_READABLE);
+ /**
+ * MapsFileTileSource:world_right:
+ *
+ * The rightmost of the world bounding box.
+ *
+ */
+ pspec = g_param_spec_double ("worl-right",
+ "Boundingbox right",
+ "The rightmost coordinate of the world boundingbox",
+ -180,
+ 180,
+ 180,
+ G_PARAM_READABLE);
+
+ /**
+ * MapsFileTileSource:world_bottom:
+ *
+ * The bottommost of the world bounding box.
+ *
+ */
+ pspec = g_param_spec_double ("worl-bottom",
+ "Boundingbox bottom",
+ "The bottommost coordinate of the world boundingbox",
+ -90,
+ 90,
+ -90,
+ G_PARAM_READABLE);
}
static void
@@ -239,11 +281,14 @@ maps_file_tile_source_init (MapsFileTileSource *tile_source)
tile_source->priv->extension = NULL;
tile_source->priv->max_zoom = -1;
tile_source->priv->min_zoom = 21;
- tile_source->priv->world = NULL;
tile_source->priv->min_x = G_MAXLONG;
tile_source->priv->min_y = G_MAXLONG;
tile_source->priv->max_x = 0;
tile_source->priv->max_y = 0;
+ tile_source->priv->world_left = -180;
+ tile_source->priv->world_top = 90;
+ tile_source->priv->world_right = 180;
+ tile_source->priv->world_bottom = -90;
}
static gboolean
@@ -474,9 +519,9 @@ maps_file_tile_source_prepare (MapsFileTileSource *tile_source,
g_return_val_if_fail (MAPS_IS_FILE_TILE_SOURCE (tile_source), FALSE);
g_return_val_if_fail (tile_source->priv->path != NULL, FALSE);
- ChamplainMapSource *source = (ChamplainMapSource *) tile_source;
+ ShumateMapSource *source = (ShumateMapSource *) tile_source;
gboolean ret = TRUE;
- guint tile_size = champlain_map_source_get_tile_size (source);
+ guint tile_size = shumate_map_source_get_tile_size (source);
if (!get_zoom_levels (tile_source, error)) {
ret = FALSE;
@@ -488,20 +533,19 @@ maps_file_tile_source_prepare (MapsFileTileSource *tile_source,
goto out;
}
- tile_source->priv->world = champlain_bounding_box_new ();
- tile_source->priv->world->left = champlain_map_source_get_longitude (source,
+ tile_source->priv->world_left = shumate_map_source_get_longitude (source,
tile_source->priv->min_zoom,
tile_source->priv->min_x *
tile_size);
- tile_source->priv->world->right = champlain_map_source_get_longitude (source,
+ tile_source->priv->world_right = shumate_map_source_get_longitude (source,
tile_source->priv->min_zoom,
(tile_source->priv->max_x + 1) *
tile_size);
- tile_source->priv->world->top = champlain_map_source_get_latitude (source,
+ tile_source->priv->world_top = shumate_map_source_get_latitude (source,
tile_source->priv->min_zoom,
tile_source->priv->min_y *
tile_size);
- tile_source->priv->world->bottom = champlain_map_source_get_latitude (source,
+ tile_source->priv->world_bottom = shumate_map_source_get_latitude (source,
tile_source->priv->min_zoom,
(tile_source->priv->max_y + 1) *
tile_size);
@@ -510,131 +554,56 @@ maps_file_tile_source_prepare (MapsFileTileSource *tile_source,
}
static void
-tile_rendered_cb (ChamplainTile *tile,
- gpointer data,
- guint size,
- gboolean error,
- CallbackData *user_data)
-{
- ChamplainMapSource *map_source = user_data->map_source;
- ChamplainMapSource *next_source;
-
- g_signal_handlers_disconnect_by_func (tile, tile_rendered_cb, user_data);
- g_slice_free (CallbackData, user_data);
-
- next_source = champlain_map_source_get_next_source (map_source);
-
- if (!error)
- {
- ChamplainTileSource *tile_source = CHAMPLAIN_TILE_SOURCE (map_source);
- ChamplainTileCache *tile_cache = champlain_tile_source_get_cache (tile_source);
-
- if (tile_cache && data)
- champlain_tile_cache_store_tile (tile_cache, tile, data, size);
-
- champlain_tile_set_fade_in (tile, TRUE);
- champlain_tile_set_state (tile, CHAMPLAIN_STATE_DONE);
- champlain_tile_display_content (tile);
- }
- else if (next_source)
- champlain_map_source_fill_tile (next_source, tile);
-
- g_object_unref (map_source);
- g_object_unref (tile);
-}
-
-static void
-tile_loaded_cb (GFile *file,
- GAsyncResult *res,
- CallbackData *user_data)
+fill_tile_async (ShumateMapSource *source,
+ ShumateTile *tile,
+ GCancellable *cancellable,
+ GAsyncReadyCallback callback,
+ gpointer user_data)
{
- ChamplainMapSource *map_source = user_data->map_source;
- ChamplainMapSource *next_source = champlain_map_source_get_next_source (map_source);
- ChamplainTile *tile = user_data->tile;
- CallbackData *data;
- ChamplainRenderer *renderer;
- guint8 *content;
- gsize length;
-
- g_slice_free (CallbackData, user_data);
-
- if (!g_file_load_contents_finish (file, res, (char **) &content, &length, NULL, NULL))
- {
- goto load_next;
- }
-
- renderer = champlain_map_source_get_renderer (map_source);
- g_return_if_fail (CHAMPLAIN_IS_RENDERER (renderer));
-
- data = g_slice_new (CallbackData);
- data->map_source = map_source;
-
- g_signal_connect (tile, "render-complete", G_CALLBACK (tile_rendered_cb), data);
-
- champlain_renderer_set_data (renderer, content, length);
- champlain_renderer_render (renderer, tile);
-
- return;
-
-load_next:
- if (next_source)
- champlain_map_source_fill_tile (next_source, tile);
-
- goto cleanup;
+ g_return_if_fail (MAPS_IS_FILE_TILE_SOURCE (source));
- champlain_tile_set_fade_in (tile, TRUE);
- champlain_tile_set_state (tile, CHAMPLAIN_STATE_DONE);
- champlain_tile_display_content (tile);
-
-cleanup:
- g_object_unref (tile);
- g_object_unref (map_source);
-}
-
-static void
-fill_tile (ChamplainMapSource *map_source,
- ChamplainTile *tile)
-{
- g_return_if_fail (MAPS_IS_FILE_TILE_SOURCE (map_source));
- g_return_if_fail (CHAMPLAIN_IS_TILE (tile));
-
- MapsFileTileSource *tile_source = MAPS_FILE_TILE_SOURCE (map_source);
- CallbackData *callback_data;
+ MapsFileTileSource *tile_source = MAPS_FILE_TILE_SOURCE (source);
GFile *file;
gchar *path = NULL;
-
- if (champlain_tile_get_state (tile) == CHAMPLAIN_STATE_DONE)
- return;
+ g_autoptr(GTask) task = NULL;
path = g_strdup_printf("%s/%d/%d/%d.%s",
tile_source->priv->path,
- champlain_tile_get_zoom_level (tile),
- champlain_tile_get_x (tile),
- champlain_tile_get_y (tile),
+ shumate_tile_get_zoom_level (tile),
+ shumate_tile_get_x (tile),
+ shumate_tile_get_y (tile),
tile_source->priv->extension);
file = g_file_new_for_path (path);
+ task = g_task_new (source, cancellable, callback, user_data);
+ g_task_set_source_tag (task, fill_tile_async);
+
if (g_file_query_exists(file, NULL))
{
- callback_data = g_slice_new (CallbackData);
- callback_data->tile = tile;
- callback_data->map_source = map_source;
-
- g_object_ref (map_source);
- g_object_ref (tile);
-
g_file_load_contents_async (file, NULL,
- (GAsyncReadyCallback) tile_loaded_cb,
- callback_data);
+ callback,
+ user_data);
+
+ g_task_return_boolean (task, TRUE);
}
else
{
- ChamplainMapSource *next_source = champlain_map_source_get_next_source (map_source);
-
- if (CHAMPLAIN_IS_MAP_SOURCE (next_source))
- champlain_map_source_fill_tile (next_source, tile);
+ g_task_return_boolean (task, FALSE);
}
g_object_unref (file);
g_free (path);
}
+
+static gboolean
+fill_tile_finish (ShumateMapSource *map_source,
+ GAsyncResult *result,
+ GError **error)
+{
+ MapsFileTileSource *self = (MapsFileTileSource *) map_source;
+
+ g_return_val_if_fail (MAPS_IS_FILE_TILE_SOURCE (self), FALSE);
+ g_return_val_if_fail (g_task_is_valid (result, self), FALSE);
+
+ return g_task_propagate_boolean (G_TASK (result), error);
+}
diff --git a/lib/maps-file-tile-source.h b/lib/maps-file-tile-source.h
index 9b432e04..f7c88e15 100644
--- a/lib/maps-file-tile-source.h
+++ b/lib/maps-file-tile-source.h
@@ -20,7 +20,7 @@
#ifndef _MAPS_FILE_TILE_SOURCE_H_
#define _MAPS_FILE_TILE_SOURCE_H_
-#include <champlain/champlain.h>
+#include <shumate/shumate.h>
G_BEGIN_DECLS
@@ -55,19 +55,19 @@ typedef struct _MapsFileTileSourceClass MapsFileTileSourceClass;
*/
struct _MapsFileTileSource
{
- ChamplainTileSource parent_instance;
+ ShumateMapSource parent_instance;
MapsFileTileSourcePrivate *priv;
};
struct _MapsFileTileSourceClass
{
- ChamplainTileSourceClass parent_class;
+ ShumateMapSourceClass parent_class;
};
GType maps_file_tile_source_get_type (void);
-gboolean maps_file_tile_source_prepare (MapsFileTileSource *tile_source, GError **error);
+gboolean maps_file_tile_source_prepare (MapsFileTileSource *data_source, GError **error);
G_END_DECLS
#endif /* _MAPS_FILE_TILE_SOURCE_H_ */
diff --git a/lib/maps-sync-map-source.c b/lib/maps-sync-map-source.c
new file mode 100644
index 00000000..34a16488
--- /dev/null
+++ b/lib/maps-sync-map-source.c
@@ -0,0 +1,91 @@
+/*
+ * Copyright (c) 2022 Marcus Lundblad
+ *
+ * GNOME Maps 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; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * GNOME Maps 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 GNOME Maps; if not, see <http://www.gnu.org/licenses/>.
+ *
+ * Author: Marcus Lundblad <ml dfupdate se>
+ */
+
+#include <shumate/shumate.h>
+#include <glib.h>
+#include <glib-object.h>
+#include <stdlib.h>
+
+#include "maps-sync-map-source.h"
+
+G_DEFINE_ABSTRACT_TYPE (MapsSyncMapSource, maps_sync_map_source, SHUMATE_TYPE_MAP_SOURCE)
+
+static void
+fill_tile_async (ShumateMapSource *source,
+ ShumateTile *tile,
+ GCancellable *cancellable,
+ GAsyncReadyCallback callback,
+ gpointer user_data);
+
+static gboolean
+fill_tile_finish (ShumateMapSource *map_source,
+ GAsyncResult *result,
+ GError **error);
+
+static void
+maps_sync_map_source_class_init (MapsSyncMapSourceClass *klass)
+{
+ ShumateMapSourceClass *map_source_class = SHUMATE_MAP_SOURCE_CLASS (klass);
+
+ map_source_class->fill_tile_async = fill_tile_async;
+ map_source_class->fill_tile_finish = fill_tile_finish;
+
+ klass->fill_tile = NULL;
+}
+
+static void
+maps_sync_map_source_init (MapsSyncMapSource *map_source)
+{
+ map_source->priv = maps_sync_map_source_get_instance_private (map_source);
+}
+
+static void
+fill_tile_async (ShumateMapSource *source,
+ ShumateTile *tile,
+ GCancellable *cancellable,
+ GAsyncReadyCallback callback,
+ gpointer user_data)
+{
+ g_return_if_fail (MAPS_IS_SYNC_MAP_SOURCE (source));
+ MapsSyncMapSource *self = MAPS_SYNC_MAP_SOURCE(source);
+
+ g_autoptr(GTask) task = NULL;
+
+ // TODO: this gives a null gobject cast runtime error...
+ MAPS_SYNC_MAP_SOURCE_GET_CLASS (self)->fill_tile (self, tile);
+
+ task = g_task_new (source, cancellable, callback, user_data);
+ g_task_set_source_tag (task, fill_tile_async);
+
+
+ g_task_return_boolean (task, TRUE);
+}
+
+static gboolean
+fill_tile_finish (ShumateMapSource *map_source,
+ GAsyncResult *result,
+ GError **error)
+{
+ MapsSyncMapSource *self = (MapsSyncMapSource *) map_source;
+
+ g_return_val_if_fail (MAPS_IS_SYNC_MAP_SOURCE (self), FALSE);
+ g_return_val_if_fail (g_task_is_valid (result, self), FALSE);
+
+ return g_task_propagate_boolean (G_TASK (result), error);
+}
diff --git a/lib/maps-sync-map-source.h b/lib/maps-sync-map-source.h
new file mode 100644
index 00000000..8f0d6463
--- /dev/null
+++ b/lib/maps-sync-map-source.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2022 Marcus Lundblad
+ *
+ * GNOME Maps 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; either version 2 of the License, or (at your
+ * option) any later version.
+ *
+ * GNOME Maps 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 GNOME Maps; if not, see <http://www.gnu.org/licenses/>.
+ *
+ * Author: Marcus Lundblad <ml dfupdate se>
+ */
+
+#ifndef _MAPS_SYNC_MAP_SOURCE_H_
+#define _MAPS_SYNC_MAP_SOURCE_H_
+
+#include <shumate/shumate.h>
+
+G_BEGIN_DECLS
+
+#define MAPS_TYPE_SYNC_MAP_SOURCE maps_sync_map_source_get_type ()
+
+#define MAPS_SYNC_MAP_SOURCE(obj) \
+ (G_TYPE_CHECK_INSTANCE_CAST ((obj), MAPS_TYPE_SYNC_MAP_SOURCE, MapsSyncMapSource))
+
+#define MAPS_SYNC_MAP_SOURCE_CLASS(klass) \
+ (G_TYPE_CHECK_CLASS_CAST ((klass), MAPS_TYPE_SYNC_MAP_SOURCE, MapsSyncMapSourceClass))
+
+#define MAPS_IS_SYNC_MAP_SOURCE(obj) \
+ (G_TYPE_CHECK_INSTANCE_TYPE ((obj), MAPS_TYPE_SYNC_MAP_SOURCE))
+
+#define MAPS_IS_SYNC_MAP_SOURCE_CLASS(klass) \
+ (G_TYPE_CHECK_CLASS_TYPE ((klass), MAPS_TYPE_SYNC_MAP_SOURCE))
+
+#define MAPS_SYNC_MAP_SOURCE_GET_CLASS(obj) \
+ (G_TYPE_INSTANCE_GET_CLASS ((obj), MAPS_TYPE_SYNC_MAP_SOURCE, MapsSyncMapSourceClass))
+
+typedef struct _MapsSyncMapSourcePrivate MapsSyncMapSourcePrivate;
+
+typedef struct _MapsSyncMapSource MapsSyncMapSource;
+typedef struct _MapsSyncMapSourceClass MapsSyncMapSourceClass;
+
+/**
+ * MapsSyncMapSource:
+ *
+ * The #MapsSyncMapSource structure contains only private data
+ * and should be accessed using the provided API
+ *
+ */
+struct _MapsSyncMapSource
+{
+ ShumateMapSource parent_instance;
+
+ MapsSyncMapSourcePrivate *priv;
+};
+
+struct _MapsSyncMapSourceClass
+{
+ ShumateMapSourceClass parent_class;
+
+ void (*fill_tile) (MapsSyncMapSource *self,
+ ShumateTile *tile);
+};
+
+GType maps_sync_map_source_get_type (void);
+
+#endif /* _MAPS_SYNC_MAP_SOURCE_H_ */
diff --git a/lib/meson.build b/lib/meson.build
index 8de63691..ba6251a9 100644
--- a/lib/meson.build
+++ b/lib/meson.build
@@ -6,7 +6,8 @@ headers_private = files(
'maps-osm-object.h',
'maps-osm-way.h',
'maps-osm-relation.h',
- 'maps-osm-oauth-proxy-call.h'
+ 'maps-osm-oauth-proxy-call.h',
+ 'maps-sync-map-source.h'
)
sources = files(
@@ -17,7 +18,8 @@ sources = files(
'maps-osm-object.c',
'maps-osm-way.c',
'maps-osm-relation.c',
- 'maps-osm-oauth-proxy-call.c'
+ 'maps-osm-oauth-proxy-call.c',
+ 'maps-sync-map-source.c'
)
cflags = [
@@ -47,8 +49,8 @@ gnome.generate_gir(
includes: [
'GLib-2.0',
'GObject-2.0',
- 'Champlain-0.12',
- 'Rest-0.7'
+ 'Rest-0.7',
+ 'Shumate-1.0'
],
install: true,
install_dir_gir: join_paths(pkgdatadir, 'gir-' + maps_gir_version),
diff --git a/meson.build b/meson.build
index a9e018f3..2380f1c8 100644
--- a/meson.build
+++ b/meson.build
@@ -34,13 +34,13 @@ glib = dependency('glib-2.0', version: '>= 2.66.0')
gio = dependency('gio-2.0', version: '>= 2.44.0')
gjs = dependency('gjs-1.0', version: '>= 1.69.2')
girepository = dependency('gobject-introspection-1.0', version: '>= 0.10.1')
-gtk3 = dependency('gtk+-3.0', version: '>= 3.22.0')
+gtk4 = dependency('gtk4')
geoclue2 = dependency('geoclue-2.0', version: '>= 0.12.99')
-handy = dependency('libhandy-1', version: '>= 1.5.0')
+libadwaita = dependency('libadwaita-1')
gweather = dependency('gweather4', version: '>= 3.90.0')
libmaps_deps = [
- dependency('champlain-0.12', version: '>= 0.12.14'),
+ dependency('shumate-1.0'),
dependency('libxml-2.0'),
dependency('rest-0.7', version: '>= 0.7.90')
]
diff --git a/org.gnome.Maps.json b/org.gnome.Maps.json
index bb2e1196..be095983 100644
--- a/org.gnome.Maps.json
+++ b/org.gnome.Maps.json
@@ -90,51 +90,18 @@
]
},
{
- "name": "cogl",
- "config-opts": [
- "--disable-cogl-gst",
- "--enable-xlib-egl-platform",
- "--enable-wayland-egl-platform"
- ],
- "sources": [
- {
- "type": "archive",
- "url": "https://download.gnome.org/sources/cogl/1.22/cogl-1.22.8.tar.xz",
- "sha256": "a805b2b019184710ff53d0496f9f0ce6dcca420c141a0f4f6fcc02131581d759"
- }
- ]
- },
- {
- "name": "clutter",
+ "name" : "libshumate",
+ "buildsystem": "meson",
"config-opts": [
- "--enable-egl-backend",
- "--enable-wayland-backend"
+ "-Ddemos=false",
+ "-Dgtk_doc=false",
+ "-Dvapi=false"
],
- "sources": [
- {
- "type": "archive",
- "url": "https://download.gnome.org/sources/clutter/1.26/clutter-1.26.4.tar.xz",
- "sha256": "8b48fac159843f556d0a6be3dbfc6b083fc6d9c58a20a49a6b4919ab4263c4e6"
- }
- ]
- },
- {
- "name": "clutter-gtk",
- "sources": [
- {
- "type": "archive",
- "url": "https://download.gnome.org/sources/clutter-gtk/1.8/clutter-gtk-1.8.4.tar.xz",
- "sha256": "521493ec038973c77edcb8bc5eac23eed41645117894aaee7300b2487cb42b06"
- }
- ]
- },
- {
- "name" : "libchamplain",
- "buildsystem": "meson",
"sources" : [
{
"type" : "git",
- "url" : "https://gitlab.gnome.org/GNOME/libchamplain.git"
+ "url" : "https://gitlab.gnome.org/GNOME/libshumate.git",
+ "branch" : "main"
}
]
},
diff --git a/src/application.js b/src/application.js
index e45a2d93..d21f8d29 100644
--- a/src/application.js
+++ b/src/application.js
@@ -20,13 +20,13 @@
* Zeeshan Ali (Khattak) <zeeshanak gnome org>
*/
+import Gdk from 'gi://Gdk';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
import Geocode from 'gi://GeocodeGlib';
import Gio from 'gi://Gio';
import Gtk from 'gi://Gtk';
-import GtkClutter from 'gi://GtkClutter';
-import Hdy from 'gi://Handy';
+import Adw from 'gi://Adw';
import {Geoclue} from './geoclue.js';
import * as GeocodeFactory from './geocode.js';
@@ -140,9 +140,6 @@ export class Application extends Gtk.Application {
vfunc_startup() {
super.vfunc_startup();
- GtkClutter.init(null);
- Hdy.init();
-
Utils.loadStyleSheet(Gio.file_new_for_uri('resource:///org/gnome/Maps/application.css'));
Application.application = this;
@@ -163,11 +160,13 @@ export class Application extends Gtk.Application {
}, Application.settings);
- this._styleManager = Hdy.StyleManager.get_default();
- this._styleManager.set_color_scheme(Hdy.ColorScheme.PREFER_LIGHT);
+ this._styleManager = Adw.StyleManager.get_default();
+ this._styleManager.set_color_scheme(Adw.ColorScheme.PREFER_LIGHT);
+
+ let display = Gdk.Display.get_default();
- Gtk.IconTheme.get_default().append_search_path(GLib.build_filenamev([pkg.pkgdatadir,
- 'icons']));
+ Gtk.IconTheme.get_for_display(display).add_search_path(
+ GLib.build_filenamev([pkg.pkgdatadir, 'icons']));
this._initPlaceStore();
}
@@ -355,8 +354,18 @@ export class Application extends Gtk.Application {
}
_onWindowDestroy(window) {
+ log('onWindowDestroy');
this._mainWindow = null;
}
+
+ vfunc_shutdown() {
+ // need to unparent popover children to avoid GTK warnings on exit
+ if (this._mainWindow) {
+ this._mainWindow.placeEntry.popover.unparent();
+ }
+ this._mainWindow.sidebar.unparentSearchPopovers();
+ super.vfunc_shutdown();
+ }
}
GObject.registerClass({
diff --git a/src/contextMenu.js b/src/contextMenu.js
index 0b71b08e..cad3877a 100644
--- a/src/contextMenu.js
+++ b/src/contextMenu.js
@@ -36,7 +36,7 @@ import {RouteQuery} from './routeQuery.js';
import * as Utils from './utils.js';
import {ZoomInDialog} from './zoomInDialog.js';
-export class ContextMenu extends Gtk.Menu {
+export class ContextMenu extends Gtk.PopoverMenu {
constructor(params) {
let mapView = params.mapView;
delete params.mapView;
@@ -49,44 +49,63 @@ export class ContextMenu extends Gtk.Menu {
this._mapView = mapView;
this._mainWindow = mainWindow;
this._buttonGesture =
- new Gtk.GestureSingle({ widget: this._mapView,
- button: Gdk.BUTTON_SECONDARY });
- this._buttonGesture.connect('end', this._onButtonRelease.bind(this));
-
- this._whatsHereItem.connect('activate',
- this._onWhatsHereActivated.bind(this));
- this._geoURIItem.connect('activate',
- this._onGeoURIActivated.bind(this));
- this._addOSMLocationItem.connect('activate',
- this._onAddOSMLocationActivated.bind(this));
- this._routeFromHereItem.connect('activate',
- this._onRouteFromHereActivated.bind(this));
- this._addIntermediateDestinationItem.connect('activate',
- this._onAddIntermediateDestinationActivated.bind(this));
- this._routeToHereItem.connect('activate',
- this._onRouteToHereActivated.bind(this));
+ new Gtk.GestureSingle({ button: Gdk.BUTTON_SECONDARY });
+ this._mapView.add_controller(this._buttonGesture);
+ this._buttonGesture.connect('begin', (g, s) => this._onOpenMenu(g, s));
+
+ this._routeFromHereAction =
+ this._mainWindow.lookup_action('route-from-here');
+ this._addIntermediateDestinationAction =
+ this._mainWindow.lookup_action('add-intermediate-destination');
+ this._routeToHereAction =
+ this._mainWindow.lookup_action('route-to-here');
+
+ let whatsHereAction =
+ this._mainWindow.lookup_action('whats-here');
+ let copyLocationAction =
+ this._mainWindow.lookup_action('copy-location');
+ let addOSMLocationAction =
+ this._mainWindow.lookup_action('add-osm-location');
+
+ whatsHereAction.connect('activate',
+ () => this._onWhatsHereActivated());
+ copyLocationAction.connect('activate',
+ () => this._onCopyLocationActivated());
+ addOSMLocationAction.connect('activate',
+ () => this._onAddOSMLocationActivated());
+ this._routeFromHereAction.connect('activate',
+ () => this._onRouteFromHereActivated());
+ this._addIntermediateDestinationAction.connect('activate',
+ () => this._onAddIntermediateDestinationActivated());
+ this._routeToHereAction.connect('activate',
+ () => this._onRouteToHereActivated());
Application.routeQuery.connect('notify::points',
- this._routingUpdate.bind(this));
+ () => this._routingUpdate());
this._routingUpdate();
+ this.set_parent(this._mapView);
}
- _onButtonRelease(gesture, sequence) {
- let event = gesture.get_last_event(sequence);
- let [, x, y] = event.get_coords();
- this._longitude = this._mapView.view.x_to_longitude(x);
- this._latitude = this._mapView.view.y_to_latitude(y);
+ _onOpenMenu(gesture, sequence) {
+ let [_, x, y] = gesture.get_point(sequence);
+ let viewport = this._mapView.map.viewport;
+ /* we can't get the allocated width before showing, so use a
+ * best-effort offset to get the top-left corner close to the pointer
+ */
+ let rect = new Gdk.Rectangle({ x: x, y: y, width: 200, height: 0 });
- // Need idle to avoid Clutter dead-lock on re-entrance
- GLib.idle_add(null, () => this.popup_at_pointer(event));
+ [this._latitude, this._longitude] = viewport.widget_coords_to_location(this._mapView, x, y);
+
+ this.pointing_to = rect;
+ this.popup();
}
_routingUpdate() {
let query = Application.routeQuery;
let numPoints = query.points.length;
- this._routeFromHereItem.sensitive = numPoints < RouteQuery.MAX_QUERY_POINTS;
- this._routeToHereItem.sensitive = numPoints < RouteQuery.MAX_QUERY_POINTS;
- this._addIntermediateDestinationItem.sensitive =
+ this._routeFromHereAction.enabled = numPoints < RouteQuery.MAX_QUERY_POINTS;
+ this._routeToHereAction.enabled = numPoints < RouteQuery.MAX_QUERY_POINTS;
+ this._addIntermediateDestinationAction.enabled =
query.filledPoints.length >= 2 && numPoints < RouteQuery.MAX_QUERY_POINTS;
}
@@ -133,15 +152,14 @@ export class ContextMenu extends Gtk.Menu {
});
}
- _onGeoURIActivated() {
+ _onCopyLocationActivated() {
let location = new Location({ latitude: this._latitude,
longitude: this._longitude,
accuracy: 0 });
- let display = Gdk.Display.get_default();
- let clipboard = Gtk.Clipboard.get_default(display);
+ let clipboard = this.get_clipboard();
let uri = location.to_uri(GeocodeGlib.LocationURIScheme.GEO);
- clipboard.set_text(uri, uri.length);
+ clipboard.set(uri);
}
_onAddOSMLocationActivated() {
@@ -165,17 +183,18 @@ export class ContextMenu extends Gtk.Menu {
_addOSMLocation() {
let osmEdit = Application.osmEdit;
+ let viewport = this._mapView.map.viewport;
- if (this._mapView.view.get_zoom_level() < OSMEdit.MIN_ADD_LOCATION_ZOOM_LEVEL) {
+ if (viewport.zoom_level < OSMEdit.MIN_ADD_LOCATION_ZOOM_LEVEL) {
let zoomInDialog =
new ZoomInDialog({ longitude: this._longitude,
latitude: this._latitude,
- view: this._mapView.view,
+ map: this._mapView.map,
transient_for: this._mainWindow,
modal: true });
zoomInDialog.connect('response', () => zoomInDialog.destroy());
- zoomInDialog.show_all();
+ zoomInDialog.show();
return;
}
@@ -195,11 +214,5 @@ export class ContextMenu extends Gtk.Menu {
}
GObject.registerClass({
- Template: 'resource:///org/gnome/Maps/ui/context-menu.ui',
- InternalChildren: [ 'whatsHereItem',
- 'geoURIItem',
- 'addOSMLocationItem',
- 'routeFromHereItem',
- 'addIntermediateDestinationItem',
- 'routeToHereItem' ],
+ Template: 'resource:///org/gnome/Maps/ui/context-menu.ui'
}, ContextMenu);
diff --git a/src/epaf.js b/src/epaf.js
index 8235e8f5..93254328 100644
--- a/src/epaf.js
+++ b/src/epaf.js
@@ -23,7 +23,7 @@
// Google encoded polyline decoder
// https://developers.google.com/maps/documentation/utilities/polylinealgorithm
-import Champlain from 'gi://Champlain';
+import Shumate from 'gi://Shumate';
function _decodeValue(data, index) {
let b;
@@ -61,7 +61,7 @@ export function decode(data) {
// first value is absolute, rest are relative to previous value
lat += latdelta;
lon += londelta;
- polyline.push(new Champlain.Coordinate({
+ polyline.push(new Shumate.Coordinate({
latitude: lat * 1e-5,
longitude: lon * 1e-5
}));
diff --git a/src/exportViewDialog.js b/src/exportViewDialog.js
index baffe2e1..a4f1d9df 100644
--- a/src/exportViewDialog.js
+++ b/src/exportViewDialog.js
@@ -22,6 +22,8 @@ import Gdk from 'gi://Gdk';
import GLib from 'gi://GLib';
import Gio from 'gi://Gio';
import GObject from 'gi://GObject';
+import Graphene from 'gi://Graphene';
+import Gsk from 'gi://Gsk';
import Gtk from 'gi://Gtk';
import * as Utils from './utils.js';
@@ -36,8 +38,8 @@ export class ExportViewDialog extends Gtk.Dialog {
};
constructor(params) {
- let surface = params.surface;
- delete params.surface;
+ let paintable = params.paintable;
+ delete params.paintable;
let latitude = params.latitude;
delete params.latitude;
@@ -48,17 +50,23 @@ export class ExportViewDialog extends Gtk.Dialog {
let mapView = params.mapView;
delete params.mapView;
+ let width = params.width;
+ delete params.width;
+
+ let height = params.height;
+ delete params.height;
+
params.use_header_bar = true;
super(params);
- this._surface = surface;
+ this._paintable = paintable;
this._mapView = mapView;
+ this._width = width;
+ this._height = height;
this._cancelButton.connect('clicked', () => this.response(ExportViewDialog.Response.CANCEL));
this._exportButton.connect('clicked', () => this._exportView());
this._filenameEntry.connect('changed', () => this._onFileNameChanged());
- this._fileChooserButton.connect('file-set', () => this._onFolderChanged());
- this._layersCheckButton.connect('toggled', () => this._includeLayersChanged());
-
+ this._fileChooserButton.connect('clicked', () => this._onFileChooserClicked());
this._folder = GLib.get_user_special_dir(GLib.UserDirectory.DIRECTORY_PICTURES);
if (!this._folder)
@@ -66,7 +74,6 @@ export class ExportViewDialog extends Gtk.Dialog {
this._filenameEntry.text = this._fileName =
this._getName(latitude, longitude);
- this._fileChooserButton.set_current_folder(this._folder);
this._setupPreviewArea();
}
@@ -80,25 +87,26 @@ export class ExportViewDialog extends Gtk.Dialog {
}
_setupPreviewArea() {
- let [surfaceWidth, surfaceHeight] = this._mapView.view.get_size();
-
- let width = _PREVIEW_WIDTH;
- this._scaleFactor = width / surfaceWidth;
- let height = surfaceHeight * this._scaleFactor;
+ this._scaleFactor = _PREVIEW_WIDTH / this._width;
+ let previewHeight = this._height * this._scaleFactor;
- this._previewArea.set_size_request(width, height);
- this._previewArea.connect('draw',
- (w, cr) => this._drawPreview(w, cr));
+ this._previewArea.width_request = _PREVIEW_WIDTH;
+ this._previewArea.height_request = previewHeight;
+ this._previewArea.paintable = this._paintable;
}
- _drawPreview(widget, cr) {
- cr.setOperator(Cairo.Operator.CLEAR);
- cr.paint();
- cr.setOperator(Cairo.Operator.OVER);
+ _onFileChooserClicked() {
+ let folderChooser = new Gtk.FileChooserNative();
- cr.scale(this._scaleFactor, this._scaleFactor);
- cr.setSourceSurface(this._surface, 0, 0);
- cr.paint();
+ folderChooser.set_current_folder(Gio.File.new_for_path(this._folder));
+ folderChooser.connect('response',
+ (widget, response) => {
+ if (response === Gtk.ResponseType.ACCEPT)
+ this._onFolderChanged(folderChooser.get_current_folder().get_path());
+
+ folderChooser.destroy();
+ });
+ folderChooser.show();
}
_onFileNameChanged() {
@@ -118,9 +126,7 @@ export class ExportViewDialog extends Gtk.Dialog {
}
}
- _onFolderChanged() {
- let folder = this._fileChooserButton.get_filename();
-
+ _onFolderChanged(folder) {
if (!GLib.file_test(folder, GLib.FileTest.IS_DIR)) {
this._exportButton.sensitive= false;
return;
@@ -135,12 +141,25 @@ export class ExportViewDialog extends Gtk.Dialog {
}
_exportView() {
- let [width, height] = this._mapView.view.get_size();
- let pixbuf = Gdk.pixbuf_get_from_surface(this._surface, 0, 0, width, height);
+ let point = new Graphene.Point();
+ let rect = new Graphene.Rect();
+
+ point.init(0, 0);
+ rect.init(0, 0, this._width, this._height);
+
+ let snapshot = Gtk.Snapshot.new();
+
+ this._paintable.snapshot(snapshot,
+ this._paintable.get_intrinsic_width(),
+ this._paintable.get_intrinsic_height());
+
+ let node = snapshot.to_node();
+ let renderer = this._mapView.get_native().get_renderer();
+ let texture = renderer.render_texture(node, rect);
let path = GLib.build_filenamev([this._folder, this._fileName]);
try {
- pixbuf.savev(path, "png", [], []);
+ texture.save_to_png(path);
this.response(ExportViewDialog.Response.SUCCESS);
} catch(e) {
Utils.debug('failed to export view: ' + e.message);
@@ -169,13 +188,6 @@ export class ExportViewDialog extends Gtk.Dialog {
dialog.show_all();
}
}
-
- _includeLayersChanged() {
- let includeLayers = this._layersCheckButton.get_active();
-
- this._surface = this._mapView.view.to_surface(includeLayers);
- this._previewArea.queue_draw();
- }
}
GObject.registerClass({
@@ -184,6 +196,5 @@ GObject.registerClass({
'cancelButton',
'filenameEntry',
'fileChooserButton',
- 'previewArea',
- 'layersCheckButton' ],
+ 'previewArea'],
}, ExportViewDialog);
diff --git a/src/favoritesPopover.js b/src/favoritesPopover.js
index 45d8fe15..9f3cc98e 100644
--- a/src/favoritesPopover.js
+++ b/src/favoritesPopover.js
@@ -33,7 +33,6 @@ export class FavoritesPopover extends Gtk.Popover {
let mapView = params.mapView;
delete params.mapView;
- params.transitions_enabled = false;
super(params);
this._mapView = mapView;
@@ -88,7 +87,16 @@ export class FavoritesPopover extends Gtk.Popover {
}
_updateList() {
- this._list.forall((row) => row.destroy());
+ let listRows = [];
+
+ for (let row of this._list) {
+ if (row instanceof Gtk.ListBoxRow)
+ listRows.push(row);
+ }
+
+ for (let row of listRows) {
+ this._list.remove(row);
+ }
let rows = 0;
this._model.foreach((model, path, iter) => {
diff --git a/src/geoJSONShapeLayer.js b/src/geoJSONShapeLayer.js
index 68ab7fbd..bb295ee6 100644
--- a/src/geoJSONShapeLayer.js
+++ b/src/geoJSONShapeLayer.js
@@ -18,6 +18,7 @@
*/
import GObject from 'gi://GObject';
+import Shumate from 'gi://Shumate';
import {GeoJSONSource} from './geoJSONSource.js';
import {ShapeLayer} from './shapeLayer.js';
@@ -39,6 +40,7 @@ export class GeoJSONShapeLayer extends ShapeLayer {
this._mapSource = new GeoJSONSource({ mapView: this._mapView,
markerLayer: this._markerLayer });
+ this._overlayLayer = new Shumate.MapLayer({ map_source: this._mapSource });
}
getName() {
diff --git a/src/geoJSONSource.js b/src/geoJSONSource.js
index f0b6e5ef..46b89ddb 100644
--- a/src/geoJSONSource.js
+++ b/src/geoJSONSource.js
@@ -19,10 +19,12 @@
*/
import Cairo from 'cairo';
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
+import Gdk from 'gi://Gdk';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
+import Shumate from 'gi://Shumate';
+
+import GnomeMaps from 'gi://GnomeMaps';
import {BoundingBox} from './boundingBox.js';
import * as Geojsonvt from './geojsonvt/geojsonvt.js';
@@ -38,7 +40,7 @@ const TileFeature = { POINT: 1,
LINESTRING: 2,
POLYGON: 3 };
-export class GeoJSONSource extends Champlain.TileSource {
+export class GeoJSONSource extends GnomeMaps.SyncMapSource {
constructor(params) {
super();
@@ -46,46 +48,21 @@ export class GeoJSONSource extends Champlain.TileSource {
this._mapView = params.mapView;
this._markerLayer = params.markerLayer;
this._bbox = new BoundingBox();
- this._tileSize = Service.getService().tiles.street.tile_size;
+ this.tile_size = Service.getService().tiles.street.tile_size;
+ this.max_zoom_level = 20;
+ this.min_zoom_level = 0;
}
get bbox() {
return this._bbox;
}
- vfunc_get_tile_size() {
- return this._tileSize;
- }
-
- vfunc_get_max_zoom_level() {
- return 20;
- }
-
- vfunc_get_min_zoom_level() {
- return 0;
- }
-
- vfunc_get_id() {
- return 'GeoJSONSource';
- }
-
- vfunc_get_name() {
- return 'GeoJSONSource';
- }
-
vfunc_fill_tile(tile) {
- if (tile.get_state() === Champlain.State.DONE)
+ if (tile.get_state() === Shumate.State.DONE)
return;
- tile.connect('render-complete', (tile, data, size, error) => {
- if(!error) {
- tile.set_state(Champlain.State.DONE);
- tile.display_content();
- } else if(this.next_source)
- this.next_source.fill_tile(tile);
- });
-
- GLib.idle_add(tile, () => this._renderTile(tile));
+ tile.set_state(Shumate.State.DONE);
+ this._renderTile(tile);
}
_validate([lon, lat]) {
@@ -206,72 +183,68 @@ export class GeoJSONSource extends Champlain.TileSource {
parse(json) {
this._parseInternal(json);
- this._tileIndex = Geojsonvt.geojsonvt(json, { extent: this._tileSize,
- maxZoom: 20 });
+ this._tileIndex = Geojsonvt.geojsonvt(json, { extent: this.tile_size,
+ maxZoom: this.max_zoom_level });
this._clampBBox();
}
_renderTile(tile) {
let tileJSON = this._tileIndex.getTile(tile.zoom_level, tile.x, tile.y);
- let content = new Clutter.Canvas({ width: this._tileSize,
- height: this._tileSize });
- tile.content = new Clutter.Actor({ width: this._tileSize,
- height: this._tileSize,
- content: content });
-
- content.connect('draw', (canvas, cr) => {
- tile.set_surface(cr.getTarget());
- cr.setOperator(Cairo.Operator.CLEAR);
- cr.paint();
- cr.setOperator(Cairo.Operator.OVER);
- cr.setFillRule(Cairo.FillRule.EVEN_ODD);
-
- if (!tileJSON) {
- tile.emit('render-complete', null, 0, false);
+ let surface = new Cairo.ImageSurface(Cairo.Format.ARGB32,
+ this.tile_size, this.tile_size);
+ let cr = new Cairo.Context(surface);
+
+ cr.setOperator(Cairo.Operator.CLEAR);
+ cr.paint();
+ cr.setOperator(Cairo.Operator.OVER);
+ cr.setFillRule(Cairo.FillRule.EVEN_ODD);
+
+ if (!tileJSON) {
+ return;
+ }
+
+ tileJSON.features.forEach((feature) => {
+ if (feature.type === TileFeature.POINT)
return;
- }
- tileJSON.features.forEach((feature) => {
- if (feature.type === TileFeature.POINT)
- return;
-
- let geoJSONStyleObj = GeoJSONStyle.parseSimpleStyle(feature.tags);
-
- feature.geometry.forEach((geometry) => {
- let first = true;
- cr.moveTo(0, 0);
- cr.setLineWidth(geoJSONStyleObj.lineWidth);
- cr.setSourceRGBA(geoJSONStyleObj.color.red,
- geoJSONStyleObj.color.green,
- geoJSONStyleObj.color.blue,
- geoJSONStyleObj.alpha);
-
- geometry.forEach(function(coord) {
- if (first) {
- cr.moveTo(coord[0], coord[1]);
- first = false;
- } else {
- cr.lineTo(coord[0], coord[1]);
- }
- });
+ let geoJSONStyleObj = GeoJSONStyle.parseSimpleStyle(feature.tags);
+
+ feature.geometry.forEach((geometry) => {
+ let first = true;
+ cr.moveTo(0, 0);
+ cr.setLineWidth(geoJSONStyleObj.lineWidth);
+ cr.setSourceRGBA(geoJSONStyleObj.color.red,
+ geoJSONStyleObj.color.green,
+ geoJSONStyleObj.color.blue,
+ geoJSONStyleObj.alpha);
+
+ geometry.forEach(function(coord) {
+ if (first) {
+ cr.moveTo(coord[0], coord[1]);
+ first = false;
+ } else {
+ cr.lineTo(coord[0], coord[1]);
+ }
});
- if (feature.type === TileFeature.POLYGON) {
- cr.closePath();
- cr.strokePreserve();
- cr.setSourceRGBA(geoJSONStyleObj.fillColor.red,
- geoJSONStyleObj.fillColor.green,
- geoJSONStyleObj.fillColor.blue,
- geoJSONStyleObj.fillAlpha);
- cr.fill();
- } else {
- cr.stroke();
- }
});
-
- tile.emit('render-complete', null, 0, false);
+ if (feature.type === TileFeature.POLYGON) {
+ cr.closePath();
+ cr.strokePreserve();
+ cr.setSourceRGBA(geoJSONStyleObj.fillColor.red,
+ geoJSONStyleObj.fillColor.green,
+ geoJSONStyleObj.fillColor.blue,
+ geoJSONStyleObj.fillAlpha);
+ cr.fill();
+ } else {
+ cr.stroke();
+ }
});
- content.invalidate();
+ tile.paintable =
+ Gdk.Texture.new_for_pixbuf(Gdk.pixbuf_get_from_surface(surface, 0, 0,
+ this.tile_size,
+ this.tile_size));
+ tile.state = Shumate.State.DONE;
}
}
diff --git a/src/gpxShapeLayer.js b/src/gpxShapeLayer.js
index d684e2ce..28c37e6a 100644
--- a/src/gpxShapeLayer.js
+++ b/src/gpxShapeLayer.js
@@ -18,6 +18,7 @@
*/
import GObject from 'gi://GObject';
+import Shumate from 'gi://Shumate';
import {GeoJSONSource} from './geoJSONSource.js';
import {ShapeLayer} from './shapeLayer.js';
@@ -39,6 +40,7 @@ export class GpxShapeLayer extends ShapeLayer {
this._mapSource = new GeoJSONSource({ mapView: this._mapView,
markerLayer: this._markerLayer });
+ this._overlayLayer = new Shumate.MapLayer({ map_source: this._mapSource });
}
_parseContent() {
diff --git a/src/graphHopperTransit.js b/src/graphHopperTransit.js
index e60aff80..76d6411b 100644
--- a/src/graphHopperTransit.js
+++ b/src/graphHopperTransit.js
@@ -25,7 +25,7 @@
* routing for walking legs
*/
-import Champlain from 'gi://Champlain';
+import Shumate from 'gi://Shumate';
import {Application} from './application.js';
import {Location} from './location.js';
@@ -64,10 +64,10 @@ export function createWalkingLeg(from, to, fromName, toName, route) {
// create a straight-line "as the crow flies" polyline between two places
function createStraightPolyline(fromLoc, toLoc) {
- return [new Champlain.Coordinate({ latitude: fromLoc.latitude,
- longitude: fromLoc.longitude }),
- new Champlain.Coordinate({ latitude: toLoc.latitude,
- longitude: toLoc.longitude })];
+ return [new Shumate.Coordinate({ latitude: fromLoc.latitude,
+ longitude: fromLoc.longitude }),
+ new Shumate.Coordinate({ latitude: toLoc.latitude,
+ longitude: toLoc.longitude })];
}
var _walkingRoutes = [];
diff --git a/src/kmlShapeLayer.js b/src/kmlShapeLayer.js
index cee3997f..c71541d6 100644
--- a/src/kmlShapeLayer.js
+++ b/src/kmlShapeLayer.js
@@ -18,6 +18,7 @@
*/
import GObject from 'gi://GObject';
+import Shumate from 'gi://Shumate';
import {GeoJSONSource} from './geoJSONSource.js';
import {ShapeLayer} from './shapeLayer.js';
@@ -39,6 +40,7 @@ export class KmlShapeLayer extends ShapeLayer {
this._mapSource = new GeoJSONSource({ mapView: this._mapView,
markerLayer: this._markerLayer });
+ this._overlayLayer = new Shumate.MapLayer({ map_source: this._mapSource });
}
_parseContent() {
diff --git a/src/layersPopover.js b/src/layersPopover.js
index 9297b152..d14b0005 100644
--- a/src/layersPopover.js
+++ b/src/layersPopover.js
@@ -17,11 +17,11 @@
* Author: Dario Di Nucci <linkin88mail gmail com>
*/
-import Champlain from 'gi://Champlain';
+import Adw from 'gi://Adw';
import GObject from 'gi://GObject';
import Gtk from 'gi://Gtk';
import Gdk from 'gi://Gdk';
-import Handy from 'gi://Handy';
+import Shumate from 'gi://Shumate';
import {Application} from './application.js';
import * as MapSource from './mapSource.js';
@@ -67,13 +67,11 @@ export class LayersPopover extends Gtk.Popover {
constructor(params) {
super({ width_request: 200,
- no_show_all: true,
- transitions_enabled: false,
visible: false });
this._mapView = params.mapView;
- this._aerialLayerButton.join_group(this._streetLayerButton);
+ //this._aerialLayerButton.join_group(this._streetLayerButton);
this.get_style_context().add_class('maps-popover');
@@ -88,6 +86,10 @@ export class LayersPopover extends Gtk.Popover {
row.set_header(header);
});
+ this._loadLayerButton.connect('clicked', () => this.popdown());
+
+ // for now let's disable the map type swithery, as we only have street
+ /*
this._layerPreviews = {
street: {
source: MapSource.createStreetSource(),
@@ -133,8 +135,10 @@ export class LayersPopover extends Gtk.Popover {
this._mapView.connect("map-type-changed", (_mapView, type) => {
this.setMapType(type);
});
+ */
}
+ /*
_setLayerPreviews() {
this._setLayerPreviewImage('street');
this._setLayerPreviewImage('aerial');
@@ -193,10 +197,16 @@ export class LayersPopover extends Gtk.Popover {
this._aerialLayerButton.active = true;
}
}
+ */
_onRemoveClicked(row) {
this._mapView.removeShapeLayer(row.shapeLayer);
- if (this._layersListBox.get_children().length <= 0)
+ let numLayers = 0;
+
+ for (let layer of this._layersListBox) {
+ numLayers++;
+ }
+ if (numLayers <= 0)
this._layersListBox.hide();
}
@@ -211,10 +221,10 @@ export class LayersPopover extends Gtk.Popover {
GObject.registerClass({
Template: 'resource:///org/gnome/Maps/ui/layers-popover.ui',
- InternalChildren: [ 'streetLayerButton',
+ InternalChildren: [ /*'streetLayerButton',
'aerialLayerButton',
'streetLayerImage',
- 'aerialLayerImage',
+ 'aerialLayerImage',*/
'layersListBox',
'loadLayerButton' ]
}, LayersPopover);
diff --git a/src/main.js b/src/main.js
index d46faa94..b7f0b87b 100644
--- a/src/main.js
+++ b/src/main.js
@@ -20,21 +20,17 @@
* Zeeshan Ali (Khattak) <zeeshanak gnome org>
*/
-import 'gi://Champlain?version=0.12';
-import 'gi://Clutter?version=1.0';
-import 'gi://Cogl?version=1.0';
+import 'gi://Adw?version=1';
import 'gi://GeocodeGlib?version=1.0';
-import 'gi://Gdk?version=3.0';
+import 'gi://Gdk?version=4.0';
import 'gi://GdkPixbuf?version=2.0';
import 'gi://Gio?version=2.0';
import 'gi://GLib?version=2.0';
import 'gi://GObject?version=2.0';
-import 'gi://Gtk?version=3.0';
-import 'gi://GtkChamplain?version=0.12';
-import 'gi://GtkClutter?version=1.0';
+import 'gi://Gtk?version=4.0';
import 'gi://GWeather?version=4.0';
-import 'gi://Handy?version=1';
import 'gi://Rest?version=0.7';
+import 'gi://Shumate?version=1.0';
import 'gi://Soup?version=2.4';
import * as system from 'system';
diff --git a/src/mainWindow.js b/src/mainWindow.js
index ff7d0326..af3b165a 100644
--- a/src/mainWindow.js
+++ b/src/mainWindow.js
@@ -22,12 +22,12 @@
import gettext from 'gettext';
-import Champlain from 'gi://Champlain';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
import Gdk from 'gi://Gdk';
import Gio from 'gi://Gio';
import Gtk from 'gi://Gtk';
+import Shumate from 'gi://Shumate';
import {Application} from './application.js';
import {ContextMenu} from './contextMenu.js';
@@ -90,6 +90,10 @@ export class MainWindow extends Gtk.ApplicationWindow {
return this._placeEntry;
}
+ get sidebar() {
+ return this._sidebar;
+ }
+
constructor(params) {
super(params);
@@ -98,7 +102,9 @@ export class MainWindow extends Gtk.ApplicationWindow {
this._mapView = new MapView({
mapType: this.application.local_tile_path ?
MapView.MapType.LOCAL : undefined,
- mainWindow: this });
+ mainWindow: this,
+ hexpand: true,
+ vexpand: true });
this._grid.attach(this._mapView, 0, 0, 1, 1);
@@ -106,9 +112,6 @@ export class MainWindow extends Gtk.ApplicationWindow {
this._sidebar = this._createSidebar();
- this._contextMenu = new ContextMenu({ mapView: this._mapView,
- mainWindow: this });
-
if (pkg.name.endsWith('.Devel'))
this.get_style_context().add_class('devel');
@@ -119,9 +122,10 @@ export class MainWindow extends Gtk.ApplicationWindow {
this._initDND();
this._initPlaceBar();
- this._grid.attach(this._sidebar, 1, 0, 1, 2);
+ this._contextMenu = new ContextMenu({ mapView: this._mapView,
+ mainWindow: this });
- this._grid.show_all();
+ this._grid.attach(this._sidebar, 1, 0, 1, 2);
/* for some reason, setting the title of the window through the .ui
* template does not work anymore (maybe has something to do with
@@ -138,7 +142,6 @@ export class MainWindow extends Gtk.ApplicationWindow {
margin_start: _PLACE_ENTRY_MARGIN,
margin_end: _PLACE_ENTRY_MARGIN,
max_width_chars: 50,
- loupe: true,
matchRoute: true });
placeEntry.connect('notify::place', () => {
if (placeEntry.place) {
@@ -148,7 +151,10 @@ export class MainWindow extends Gtk.ApplicationWindow {
let popover = placeEntry.popover;
popover.connect('selected', () => this._mapView.grab_focus());
- this._mapView.view.connect('button-press-event', () => popover.hide());
+
+ this._buttonPressGesture = new Gtk.GestureSingle();
+ this._mapView.add_controller(this._buttonPressGesture);
+ this._buttonPressGesture.connect('begin', () => popover.popdown());
return placeEntry;
}
@@ -162,7 +168,7 @@ export class MainWindow extends Gtk.ApplicationWindow {
_initPlaceBar() {
this._placeBar = new PlaceBar({ mapView: this._mapView, visible: true });
- this._placeBarContainer.add(this._placeBar);
+ this._placeBarContainer.append(this._placeBar);
this.application.bind_property('selected-place',
this._placeBar, 'place',
@@ -170,20 +176,11 @@ export class MainWindow extends Gtk.ApplicationWindow {
}
_initDND() {
- this.drag_dest_set(Gtk.DestDefaults.DROP, null, 0);
- this.drag_dest_add_uri_targets();
+ this._dropTarget = Gtk.DropTarget.new(Gio.File, Gdk.DragAction.COPY);
+ this.add_controller(this._dropTarget);
- this.connect('drag-motion', (widget, ctx, x, y, time) => {
- Gdk.drag_status(ctx, Gdk.DragAction.COPY, time);
- return true;
- });
-
- this.connect('drag-data-received', (widget, ctx, x, y, data, info, time) => {
- let files = data.get_uris().map(Gio.file_new_for_uri);
- if (this._mapView.openShapeLayers(files))
- Gtk.drag_finish(ctx, true, false, time);
- else
- Gtk.drag_finish(ctx, false, false, time);
+ this._dropTarget.connect('drop', (target, value, x, y, data) => {
+ return this._mapView.openShapeLayers([value]);
});
}
@@ -211,11 +208,11 @@ export class MainWindow extends Gtk.ApplicationWindow {
},
'zoom-in': {
accels: ['plus', '<Primary>plus', 'KP_Add', '<Primary>KP_Add', 'equal', '<Primary>equal'],
- onActivate: () => this._mapView.view.zoom_in()
+ onActivate: () => this._mapView.zoomIn()
},
'zoom-out': {
accels: ['minus', '<Primary>minus', 'KP_Subtract', '<Primary>KP_Subtract'],
- onActivate: () => this._mapView.view.zoom_out()
+ onActivate: () => this._mapView.zoomOut()
},
'show-scale': {
accels: ['<Primary>S'],
@@ -236,7 +233,13 @@ export class MainWindow extends Gtk.ApplicationWindow {
},
'export-as-image': {
onActivate: () => this._onExportActivated()
- }
+ },
+ 'route-from-here': {},
+ 'add-intermediate-destination': {},
+ 'route-to-here': {},
+ 'whats-here': {},
+ 'copy-location': {},
+ 'add-osm-location': {}
};
// when aerial tiles are available, add shortcuts to switch
@@ -256,67 +259,38 @@ export class MainWindow extends Gtk.ApplicationWindow {
}
_initSignals() {
- this.connect('delete-event', this._quit.bind(this));
- this.connect('configure-event',
- this._onConfigureEvent.bind(this));
+ this.connect('close-request', () => this._quit());
+ this.connect('notify::default-width', () => this._onSizeChanged());
+ this.connect('notify::default-height', () => this._onSizeChanged());
- this.connect('window-state-event',
- this._onWindowStateEvent.bind(this));
+ this.connect('notify::is-maximized', () => this._onMaximizedChanged());
+ // TODO: GTK4, is this needed?
+ /*
this._mapView.view.connect('button-press-event', () => {
// Can not call something that will generate clutter events
// from a clutter event-handler. So use an idle.
GLib.idle_add(null, () => this._mapView.grab_focus());
});
+ */
- /*
- * If the currently focused widget is an entry then we will
- * hijack the key-press to the main window and make sure that
- * they reach the entry before they can be swallowed as accelerator.
- */
- /* TODO: GTK 4. This should probably be handled by something like
- * setting the map view as key capture widget for the search entry
- */
- this.connect('key-press-event', (window, event) => {
- let focusWidget = window.get_focus();
- let keyval = event.get_keyval()[1];
- let keys = [Gdk.KEY_plus, Gdk.KEY_KP_Add,
- Gdk.KEY_minus, Gdk.KEY_KP_Subtract,
- Gdk.KEY_equal];
- let isPassThroughKey = keys.indexOf(keyval) !== -1;
-
- /* if no entry is focused, and the key is not one we should treat
- * as a zoom accelerator when no entry is focused, focus the
- * main search entry in the headebar to propaget the keypress there
- */
- if (!(focusWidget instanceof Gtk.Entry) && !isPassThroughKey) {
- /* if the search entry does not handle the event, pass it on
- * instead of activating the entry
- */
- if (this._placeEntry.handle_event(event) === Gdk.EVENT_PROPAGATE)
- return false;
-
- this._placeEntry.has_focus = true;
- focusWidget = this._placeEntry;
- }
+ //this._placeEntry.set_key_capture_widget(this)
- if (focusWidget instanceof Gtk.Entry)
- return focusWidget.event(event);
+ let viewport = this._mapView.map.viewport;
- return false;
- });
+ viewport.connect('notify::zoom-level',
+ this._updateZoomButtonsSensitivity.bind(this));
+ viewport.connect('notify::max-zoom-level',
+ this._updateZoomButtonsSensitivity.bind(this));
+ viewport.connect('notify::min-zoom-level',
+ this._updateZoomButtonsSensitivity.bind(this));
- this._mapView.view.connect('notify::zoom-level',
- this._updateZoomButtonsSensitivity.bind(this));
- this._mapView.view.connect('notify::max-zoom-level',
- this._updateZoomButtonsSensitivity.bind(this));
- this._mapView.view.connect('notify::min-zoom-level',
- this._updateZoomButtonsSensitivity.bind(this));
+ this._updateZoomButtonsSensitivity();
}
_updateZoomButtonsSensitivity() {
- let zoomLevel = this._mapView.view.zoom_level;
- let maxZoomLevel = this._mapView.view.max_zoom_level;
- let minZoomLevel = this._mapView.view.min_zoom_level;
+ let zoomLevel = this._mapView.map.viewport.zoom_level;
+ let maxZoomLevel = this._mapView.map.viewport.max_zoom_level;
+ let minZoomLevel = this._mapView.map.viewport.min_zoom_level;
let zoomInAction = this.lookup_action("zoom-in");
let zoomOutAction = this.lookup_action("zoom-out");
@@ -345,7 +319,7 @@ export class MainWindow extends Gtk.ApplicationWindow {
this._headerBar.pack_end(this._headerBarRight);
this._placeEntry = this._createPlaceEntry();
- this._headerBar.custom_title = this._placeEntry;
+ this._headerBar.title_widget = this._placeEntry;
Application.geoclue.connect('notify::state',
this._updateLocationSensitivity.bind(this));
@@ -357,8 +331,8 @@ export class MainWindow extends Gtk.ApplicationWindow {
this._actionBarRight = new HeaderBarRight({ mapView: this._mapView });
this._actionBar.pack_end(this._actionBarRight);
- this.connect('size-allocate', () => {
- let [width, height] = this.get_size();
+ this.connect('notify::default-width', () => {
+ let width = this.default_width;
if (width < _ADAPTIVE_VIEW_WIDTH) {
this.application.adaptive_mode = true;
this._headerBarLeft.hide();
@@ -378,18 +352,12 @@ export class MainWindow extends Gtk.ApplicationWindow {
}
_saveWindowGeometry() {
- let window = this.get_window();
- let state = window.get_state();
-
- if (state & Gdk.WindowState.MAXIMIZED)
+ if (this.maximized)
return;
// GLib.Variant.new() can handle arrays just fine
- let size = this.get_size();
- Application.settings.set('window-size', size);
-
- let position = this.get_position();
- Application.settings.set('window-position', position);
+ Application.settings.set('window-size',
+ [this.default_width, this.default_height]);
}
_restoreWindowGeometry() {
@@ -399,18 +367,11 @@ export class MainWindow extends Gtk.ApplicationWindow {
this.set_default_size(width, height);
}
- let position = Application.settings.get('window-position');
- if (position.length === 2) {
- let [x, y] = position;
-
- this.move(x, y);
- }
-
if (Application.settings.get('window-maximized'))
this.maximize();
}
- _onConfigureEvent(widget, event) {
+ _onSizeChanged() {
if (this._configureId !== 0) {
GLib.source_remove(this._configureId);
this._configureId = 0;
@@ -423,15 +384,8 @@ export class MainWindow extends Gtk.ApplicationWindow {
});
}
- _onWindowStateEvent(widget, event) {
- let window = widget.get_window();
- let state = window.get_state();
-
- if (state & Gdk.WindowState.FULLSCREEN)
- return;
-
- let maximized = (state & Gdk.WindowState.MAXIMIZED);
- Application.settings.set('window-maximized', maximized);
+ _onMaximizedChanged() {
+ Application.settings.set('window-maximized', this.maximized);
}
_quit() {
@@ -479,36 +433,29 @@ export class MainWindow extends Gtk.ApplicationWindow {
});
}
- _activateExport() {
- let view = this._mapView.view;
- let surface = view.to_surface(true);
- let bbox = view.get_bounding_box();
- let [latitude, longitude] = bbox.get_center();
+ _onExportActivated() {
+ let {x, y, width, height} = this._mapView.get_allocation();
+ let paintable = new Gtk.WidgetPaintable({ widget: this._mapView });
+ let [latitude, longitude] =
+ this._mapView.map.viewport.widget_coords_to_location(this._mapView.map,
+ width / 2,
+ height / 2);
+
+ log('lat, lon: ' + [latitude, longitude]);
let dialog = new ExportViewDialog({
transient_for: this,
modal: true,
- surface: surface,
+ paintable: paintable,
latitude: latitude,
longitude: longitude,
+ width: width,
+ height: height,
mapView: this._mapView
});
dialog.connect('response', () => dialog.destroy());
- dialog.show_all();
- }
-
- _onExportActivated() {
- if (this._mapView.view.state === Champlain.State.DONE) {
- this._activateExport();
- } else {
- let notifyId = this._mapView.view.connect('notify::state', () => {
- if (this._mapView.view.state === Champlain.State.DONE) {
- this._mapView.view.disconnect(notifyId);
- this._activateExport();
- }
- });
- }
+ dialog.show();
}
_printRouteActivate() {
diff --git a/src/mapBubble.js b/src/mapBubble.js
index 88f29775..cc74dd04 100644
--- a/src/mapBubble.js
+++ b/src/mapBubble.js
@@ -22,6 +22,7 @@
import Gio from 'gi://Gio';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
+import Graphene from 'gi://Graphene';
import Gtk from 'gi://Gtk';
import {Application} from './application.js';
@@ -48,10 +49,6 @@ export class MapBubble extends Gtk.Popover {
let mapView = params.mapView;
delete params.mapView;
- params.relative_to = mapView;
- params.transitions_enabled = false;
- params.modal = false;
-
super(params);
let content = new PlaceView({ place, mapView, visible: true });
@@ -59,9 +56,9 @@ export class MapBubble extends Gtk.Popover {
let scrolledWindow = new MapBubbleScrolledWindow({ visible: true,
propagateNaturalWidth: true,
propagateNaturalHeight: true,
- hscrollbarPolicy: Gtk.PolicyType.NEVER });
- scrolledWindow.add(content);
- this.add(scrolledWindow);
+ hscrollbarPolicy: Gtk.PolicyType.NEVER,
+ child: content });
+ this.child = scrolledWindow;
this.get_style_context().add_class("map-bubble");
}
@@ -70,6 +67,39 @@ export class MapBubble extends Gtk.Popover {
GObject.registerClass(MapBubble);
export class MapBubbleScrolledWindow extends Gtk.ScrolledWindow {
+ /*
+ vfunc_get_request_mode() {
+ return Gtk.SizeRequestMode.HEIGHT_FOR_WIDTH;
+ }
+ */
+
+ /*
+ vfunc_measure(orientation, forSize) {
+ log('measure: ' + orientation + ', ' + forSize);
+
+ let [cm, cn, cbx, cby] = this.child.measure(orientation, forSize);
+
+ log('child measure: ' + cm + ', ' + cn);
+
+ // TODO: fix
+ return [500, 500, null, null];
+
+ if (orientation === Gtk.Orientation.HORIZONTAL) {
+ let windowHeight = this.get_toplevel().get_allocated_height() - HEIGHT_MARGIN;
+ let [min, nat] = this.get_child().get_preferred_height_for_width(width);
+ min = Math.min(min, windowHeight);
+ nat = Math.min(nat, windowHeight);
+ return [min, nat, 0, 0];
+ } else {
+ let [min, nat] = this.get_child().get_preferred_width();
+ min = Math.min(min, MAX_CONTENT_WIDTH);
+ nat = Math.min(nat, MAX_CONTENT_WIDTH);
+ return [min, nat, 0, 0];
+ }
+ }
+ */
+
+ /*
vfunc_get_preferred_width() {
let [min, nat] = this.get_child().get_preferred_width();
min = Math.min(min, MAX_CONTENT_WIDTH);
@@ -84,17 +114,29 @@ export class MapBubbleScrolledWindow extends Gtk.ScrolledWindow {
nat = Math.min(nat, windowHeight);
return [min, nat];
}
+ */
- vfunc_draw(cr) {
+ /*
+ vfunc_snapshot(snapshot) {
let popover = this.get_ancestor(Gtk.Popover);
if (popover) {
- let [{x, y, width, height}, baseline] = this.get_allocated_size();
+ let {x, y, width, height} = this.get_allocation();
+ let rect = new Graphene.Rect();
+ log('allocation: ' + [x, y]);
+
+ rect.init(x, y, width, height);
+
+ let cr = snapshot.append_cairo(rect);
// clip the top corners to the rounded corner
+
let radius = popover.get_style_context()
.get_property(Gtk.STYLE_PROPERTY_BORDER_RADIUS, popover.get_state_flags())
* this.scale_factor;
+ // TODO: how to do this?
+ let radius = 0;
+
// bottom left
cr.moveTo(0, height);
cr.lineTo(0, radius);
@@ -103,10 +145,12 @@ export class MapBubbleScrolledWindow extends Gtk.ScrolledWindow {
cr.lineTo(width, height);
cr.clip();
+ cr.$dispose();
}
- return super.vfunc_draw(cr);
+ super.vfunc_snapshot(snapshot);
}
+ */
}
GObject.registerClass(MapBubbleScrolledWindow);
diff --git a/src/mapMarker.js b/src/mapMarker.js
index 8e3842cc..e58ab905 100644
--- a/src/mapMarker.js
+++ b/src/mapMarker.js
@@ -20,19 +20,19 @@
*/
import Cairo from 'cairo';
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
import Gdk from 'gi://Gdk';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
+import Graphene from 'gi://Graphene';
import Gtk from 'gi://Gtk';
+import Shumate from 'gi://Shumate';
import {Application} from './application.js';
import {MapBubble} from './mapBubble.js';
import {MapWalker} from './mapWalker.js';
import * as Utils from './utils.js';
-export class MapMarker extends Champlain.Marker {
+export class MapMarker extends Shumate.Marker {
constructor(params) {
let place = params.place;
@@ -50,12 +50,17 @@ export class MapMarker extends Champlain.Marker {
this._place = place;
this._mapView = mapView;
+ this._image = new Gtk.Image({ icon_size: Gtk.IconSize.NORMAL });
+ this.child = this._image;
+
this.connect('notify::size', this._translateMarkerPosition.bind(this));
if (this._mapView) {
- this._view = this._mapView.view;
- this.connect('notify::selected', this._onMarkerSelected.bind(this));
- this.connect('button-press', this._onButtonPress.bind(this));
- this.connect('touch-event', this._onTouchEvent.bind(this));
+ this._viewport = this._mapView.map.viewport;
+
+ this._buttonPressGesture = new Gtk.GestureSingle();
+ this.add_controller(this._buttonPressGesture);
+ this._buttonPressGesture.connect('begin',
+ () => this._onMarkerSelected());
// Some markers are draggable, we want to sync the marker location and
// the location saved in the GeocodePlace
@@ -70,12 +75,12 @@ export class MapMarker extends Champlain.Marker {
this.place.connect('notify::location', this._onLocationChanged.bind(this));
- this._view.bind_property('latitude', this, 'view-latitude',
- GObject.BindingFlags.DEFAULT);
- this._view.bind_property('longitude', this, 'view-longitude',
- GObject.BindingFlags.DEFAULT);
- this._view.bind_property('zoom-level', this, 'view-zoom-level',
- GObject.BindingFlags.DEFAULT);
+ this._viewport.bind_property('latitude', this, 'view-latitude',
+ GObject.BindingFlags.DEFAULT);
+ this._viewport.bind_property('longitude', this, 'view-longitude',
+ GObject.BindingFlags.DEFAULT);
+ this._viewport.bind_property('zoom-level', this, 'view-zoom-level',
+ GObject.BindingFlags.DEFAULT);
this.connect('notify::view-latitude', this._onViewUpdated.bind(this));
this.connect('notify::view-longitude', this._onViewUpdated.bind(this));
this.connect('notify::view-zoom-level', this._onViewUpdated.bind(this));
@@ -84,60 +89,6 @@ export class MapMarker extends Champlain.Marker {
Application.application.connect('notify::adaptive-mode', this._onAdaptiveModeChanged.bind(this));
}
- get surface() {
- return this._surface;
- }
-
- set surface(v) {
- this._surface = v;
- }
-
- vfunc_get_surface() {
- return this._surface;
- }
-
- vfunc_set_surface(surface) {
- this._surface = surface;
- }
-
- _actorFromIconName(name, size, color) {
- try {
- let theme = Gtk.IconTheme.get_default();
- let pixbuf;
-
- if (color) {
- let info = theme.lookup_icon(name, size, 0);
- pixbuf = info.load_symbolic(color, null, null, null)[0];
- } else {
- pixbuf = theme.load_icon(name, size, 0);
- }
-
- let canvas = new Clutter.Canvas({ width: pixbuf.get_width(),
- height: pixbuf.get_height() });
-
- canvas.connect('draw', (canvas, cr) => {
- cr.setOperator(Cairo.Operator.CLEAR);
- cr.paint();
- cr.setOperator(Cairo.Operator.OVER);
-
- Gdk.cairo_set_source_pixbuf(cr, pixbuf, 0, 0);
- cr.paint();
-
- this._surface = cr.getTarget();
- });
-
- let actor = new Clutter.Actor();
- actor.set_content(canvas);
- actor.set_size(pixbuf.get_width(), pixbuf.get_height());
- canvas.invalidate();
-
- return actor;
- } catch (e) {
- Utils.debug('Failed to load image: %s'.format(e.message));
- return null;
- }
- }
-
_onButtonPress(marker, event) {
// Zoom in on marker on double-click
if (event.get_click_count() > 1) {
@@ -191,6 +142,7 @@ export class MapMarker extends Champlain.Marker {
if (this._place.name) {
this._bubble = new MapBubble({ place: this._place,
mapView: this._mapView });
+ this._bubble.set_parent(this._mapView);
}
}
@@ -203,13 +155,14 @@ export class MapMarker extends Champlain.Marker {
}
_positionBubble(bubble) {
- let [tx, ty, tz] = this.get_translation();
- let x = this._view.longitude_to_x(this.longitude);
- let y = this._view.latitude_to_y(this.latitude);
- let mapSize = this._mapView.get_allocation();
-
- let pos = new Gdk.Rectangle({ x: x + tx - this.bubbleSpacing,
- y: y + ty - this.bubbleSpacing,
+ let [x, y] =
+ this._viewport.location_to_widget_coords(this._mapView.map,
+ this.latitude,
+ this.longitude);
+ let mapSize = this._mapView.map.get_allocation();
+
+ let pos = new Gdk.Rectangle({ x: x - this.bubbleSpacing,
+ y: y - this.bubbleSpacing,
width: this.width + this.bubbleSpacing * 2,
height: this.height + this.bubbleSpacing * 2 });
bubble.pointing_to = pos;
@@ -232,7 +185,7 @@ export class MapMarker extends Champlain.Marker {
_hideBubbleOn(signal, duration) {
let sourceId = null;
- let signalId = this._view.connect(signal, () => {
+ let signalId = this._viewport.connect(signal, () => {
if (sourceId)
GLib.source_remove(sourceId);
else
@@ -253,16 +206,7 @@ export class MapMarker extends Champlain.Marker {
// We still listening for the signal to refresh
// the existent timeout
if (!sourceId)
- this._view.disconnect(signalId);
- });
-
- Utils.once(this, 'notify::selected', () => {
- // When the marker gets deselected, we need to ensure
- // that the timeout callback is not called anymore.
- if (sourceId) {
- GLib.source_remove(sourceId);
- this._view.disconnect(signalId);
- }
+ this._viewport.disconnect(signalId);
});
}
@@ -282,12 +226,10 @@ export class MapMarker extends Champlain.Marker {
this.selected = false;
});
- let viewTouchEventSignalId =
- this._view.connect('touch-event', () => this.set_selected(false));
-
let goingToSignalId = this._mapView.connect('going-to', () => {
this.set_selected(false);
});
+ /*
let buttonPressSignalId =
this._view.connect('button-press-event', () => {
this.set_selected(false);
@@ -304,28 +246,32 @@ export class MapMarker extends Champlain.Marker {
this.set_selected(false);
}
});
+ */
Utils.once(this.bubble, 'closed', () => {
this._mapView.disconnect(markerSelectedSignalId);
this._mapView.disconnect(goingToSignalId);
- this._view.disconnect(buttonPressSignalId);
- this._view.disconnect(viewTouchEventSignalId);
- this.disconnect(parentSetSignalId);
- this.disconnect(dragMotionSignalId);
+ //this._view.disconnect(buttonPressSignalId);
+ //this._view.disconnect(viewTouchEventSignalId);
+ //this.disconnect(parentSetSignalId);
+ //this.disconnect(dragMotionSignalId);
- this._bubble.destroy();
+ //this._bubble.destroy();
delete this._bubble;
});
}
_isInsideView() {
- let [tx, ty, tz] = this.get_translation();
- let x = this._view.longitude_to_x(this.longitude);
- let y = this._view.latitude_to_y(this.latitude);
- let mapSize = this._mapView.get_allocation();
-
- return x + tx + this.width > 0 && x + tx < mapSize.width &&
- y + ty + this.height > 0 && y + ty < mapSize.height;
+ let [x, y] = this._viewport.location_to_widget_coords(this._mapView.map,
+ this.latitude,
+ this.longitude);
+ let markerSize = this.get_allocation();
+ let mapSize = this._mapView.map.get_allocation();
+ let tx = markerSize.width / 2;
+ let ty = markerSize.height / 2;
+
+ return x + tx/2 > 0 && x - tx/2 < mapSize.width &&
+ y + ty/2 > 0 && y - ty/2 < mapSize.height;
}
_onViewUpdated() {
@@ -338,6 +284,7 @@ export class MapMarker extends Champlain.Marker {
}
showBubble() {
+ log('showBubble: ' + this.bubble + ', ' + this._isInsideView());
if (this.bubble && !this.bubble.visible && this._isInsideView() &&
!Application.application.adaptive_mode) {
this._initBubbleSignals();
this.bubble.show();
@@ -367,43 +314,69 @@ export class MapMarker extends Champlain.Marker {
}
goToAndSelect(animate) {
- Utils.once(this, 'gone-to', () => this.selected = true);
+ Utils.once(this, 'gone-to', () => {
+ if (this.bubble)
+ this.showBubble();
+ });
this.goTo(animate);
}
_onMarkerSelected() {
- if (this.selected) {
- if (this.bubble) {
+ if (this.bubble) {
+ if (!this._bubble.visible) {
this.showBubble();
Application.application.selected_place = this._place;
+ } else {
+ this.hideBubble();
+ Application.application.selected_place = null;
}
} else {
- this.hideBubble();
- Application.application.selected_place = null;
+ if (!Application.application.selected_place)
+ Application.application.selected_place = this._place;
+ else
+ Application.application.selected_place = null;
}
}
_onAdaptiveModeChanged() {
- if (this.selected) {
- if (!Application.application.adaptive_mode) {
- this.showBubble();
- } else {
- this.hideBubble();
- }
+ if (!Application.application.adaptive_mode) {
+ this.showBubble();
+ } else {
+ this.hideBubble();
+ }
+ }
+
+ _paintableFromIconName(name, size, color) {
+ let display = Gdk.Display.get_default();
+ let theme = Gtk.IconTheme.get_for_display(display);
+ let iconPaintable = theme.lookup_icon(name, null, size,
+ this.scale_factor,
+ Gtk.TextDirection.NONE, 0);
+
+ if (color) {
+ let snapshot = Gtk.Snapshot.new();
+ let rect = new Graphene.Rect();
+
+ iconPaintable.snapshot_symbolic(snapshot, size, size, [color]);
+ rect.init(0, 0, size, size);
+
+ let node = snapshot.to_node();
+ let renderer = this._mapView.get_native().get_renderer();
+
+ return renderer.render_texture(node, rect);
+ } else {
+ return iconPaintable;
}
}
}
GObject.registerClass({
- Implements: [Champlain.Exportable],
Abstract: true,
Signals: {
'gone-to': { }
},
Properties: {
- 'surface': GObject.ParamSpec.override('surface',
- Champlain.Exportable),
'view-latitude': GObject.ParamSpec.double('view-latitude', '', '',
GObject.ParamFlags.READABLE |
GObject.ParamFlags.WRITABLE,
diff --git a/src/mapSource.js b/src/mapSource.js
index 55c12a33..b874d7d5 100644
--- a/src/mapSource.js
+++ b/src/mapSource.js
@@ -17,7 +17,8 @@
* Author: Jonas Danielsson <jonas threetimestwo org>
*/
-import Champlain from 'gi://Champlain';
+import GLib from 'gi://GLib';
+import Shumate from 'gi://Shumate';
import * as Service from './service.js';
import * as Utils from './utils.js';
@@ -25,6 +26,38 @@ import * as Utils from './utils.js';
const _FILE_CACHE_SIZE_LIMIT = (10 * 1024 * 1024); /* 10Mb */
const _MEMORY_CACHE_SIZE_LIMIT = 100; /* number of tiles */
+/* Converts a tile URI format from Champlain style to Shumate style.
+ * e.g. from
+ * https://tile.openstreetmap.org/#Z#/#X#/#Y#.png
+ * to
+ * https://tile.openstreetmap.org/{Z}/{X}/{Y}.png
+ */
+function convertUriFormatFromChamplain(uriFormat) {
+ return uriFormat.replace('#Z#', '{z}').replace('#X#', '{x}').replace('#Y#', '{y}');
+}
+
+function createTileDownloader(source) {
+ let template = convertUriFormatFromChamplain(source.uri_format);
+
+ log('template: ' + template);
+
+ return new Shumate.TileDownloader({ url_template: template });
+}
+
+function createRasterRenderer(source) {
+ return new Shumate.RasterRenderer({
+ id: source.id,
+ name: source.name,
+ license: source.license,
+ license_uri: source.license_uri,
+ min_zoom_level: source.min_zoom_level,
+ max_zoom_level: source.max_zoom_level,
+ tile_size: source.tile_size,
+ projection: Shumate.MapProjection.MERCATOR,
+ data_source: createTileDownloader(source)
+ });
+}
+
function _createTileSource(source) {
let tileSource = new Champlain.NetworkTileSource({
id: source.id,
@@ -73,13 +106,13 @@ function _createCachedSource(source) {
}
export function createAerialSource() {
- return _createCachedSource(Service.getService().tiles.aerial);
+ return createRasterRenderer(Service.getService().tiles.aerial);
}
export function createStreetSource() {
- return _createCachedSource(Service.getService().tiles.street);
+ return createRasterRenderer(Service.getService().tiles.street);
}
export function createPrintSource() {
- return _createCachedSource(Service.getService().tiles.print);
+ return createRasterRenderer(Service.getService().tiles.print);
}
diff --git a/src/mapView.js b/src/mapView.js
index 5aa43155..65c45585 100644
--- a/src/mapView.js
+++ b/src/mapView.js
@@ -19,15 +19,13 @@
* Author: Zeeshan Ali (Khattak) <zeeshanak gnome org>
*/
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
import GObject from 'gi://GObject';
+import Gdk from 'gi://Gdk';
import GeocodeGlib from 'gi://GeocodeGlib';
import Gio from 'gi://Gio';
import GLib from 'gi://GLib';
import Gtk from 'gi://Gtk';
-import GtkChamplain from 'gi://GtkChamplain';
-import Handy from 'gi://Handy';
+import Shumate from 'gi://Shumate';
import GnomeMaps from 'gi://GnomeMaps';
@@ -55,6 +53,7 @@ import * as Utils from './utils.js';
const _LOCATION_STORE_TIMEOUT = 500;
const MapMinZoom = 2;
+const MapMaxZoom = 19;
/* threashhold for route color luminance when we consider it more or less
* as white, and draw an outline on the path */
@@ -77,7 +76,7 @@ const DASHED_ROUTE_LINE_GAP_LENGTH = 5;
// Maximum limit of file size (20 MB) that can be loaded without user confirmation
const FILE_SIZE_LIMIT_MB = 20;
-export class MapView extends GtkChamplain.Embed {
+export class MapView extends Gtk.Overlay {
static MapType = {
LOCAL: 'MapsLocalSource',
@@ -102,8 +101,9 @@ export class MapView extends GtkChamplain.Embed {
let isValid = Application.routeQuery.isValid();
this._routingOpen = value && isValid;
- this._routeLayers.forEach((routeLayer) => routeLayer.visible = value && isValid);
- this._instructionMarkerLayer.visible = value && isValid;
+ // TODO: bring it back when the layers are working
+ //this._routeLayers.forEach((routeLayer) => routeLayer.visible = value && isValid);
+ //this._instructionMarkerLayer.visible = value && isValid;
if (!value)
this.routeShowing = false;
this.notify('routingOpen');
@@ -118,20 +118,30 @@ export class MapView extends GtkChamplain.Embed {
this.notify('routeShowing');
}
- constructor(params) {
- super();
+ get mapSource() {
+ return this._mapSource;
+ }
- let mapType = params.mapType || this._getStoredMapType();
+ constructor(params) {
+ let mapTypeParam = params.mapType;
delete params.mapType;
- this._mainWindow = params.mainWindow;
+ let mainWindow = params.mainWindow;
delete params.mainWindow;
+ super(params);
+
+ this._mainWindow = mainWindow;
this._storeId = 0;
- this.view = this._initView();
- this._initLayers();
+ this.map = this._initMap();
+
+ this.child = this.map;
- this.setMapType(mapType);
+ this._initLicense();
+ this.setMapType(mapTypeParam ?? this._getStoredMapType());
+
+ this._initScale();
+ this._initLayers();
if (Application.normalStartup)
this._goToStoredLocation();
@@ -145,66 +155,102 @@ export class MapView extends GtkChamplain.Embed {
this._connectRouteSignals();
}
- _initScale(view) {
+ zoomIn() {
+ let zoom = this.map.viewport.zoom_level;
+ let maxZoom = this.map.viewport.max_zoom_level;
+ let fraction = zoom - Math.floor(zoom);
+
+ this.map.go_to_duration = 200;
+ this.map.go_to_full(this.map.viewport.latitude,
+ this.map.viewport.longitude,
+ Math.min(fraction < 0.7 ?
+ Math.floor(zoom + 1) : Math.floor(zoom + 2),
+ maxZoom));
+ this.map.go_to_duration = 0;
+ }
+
+ zoomOut() {
+ let zoom = this.map.viewport.zoom_level;
+ let minZoom = this.map.viewport.min_zoom_level;
+ let fraction = zoom - Math.floor(zoom);
+
+ this.map.go_to_duration = 200;
+ this.map.go_to_full(this.map.viewport.latitude,
+ this.map.viewport.longitude,
+ Math.max(fraction > 0.3 ?
+ Math.floor(zoom) : Math.floor(zoom - 1),
+ minZoom));
+ this.map.go_to_duration = 0;
+ }
+
+ _initScale() {
let showScale = Application.settings.get('show-scale');
- this._scale = new Champlain.Scale({ visible: showScale });
- this._scale.connect_view(view);
+ this._scale = new Shumate.Scale({ visible: showScale,
+ viewport: this.map.viewport,
+ halign: Gtk.Align.START,
+ valign: Gtk.Align.END });
if (Utils.getMeasurementSystem() === Utils.METRIC_SYSTEM)
- this._scale.unit = Champlain.Unit.KM;
+ this._scale.unit = Shumate.Unit.METRIC;
else
- this._scale.unit = Champlain.Unit.MILES;
+ this._scale.unit = Shumate.Unit.IMPERIAL;
+
+ this.add_overlay(this._scale);
+ }
- this._scale.set_x_expand(true);
- this._scale.set_y_expand(true);
- this._scale.set_x_align(Clutter.ActorAlign.START);
- this._scale.set_y_align(Clutter.ActorAlign.END);
- view.add_child(this._scale);
+ _initLicense() {
+ this._license = new Shumate.License({ halign: Gtk.Align.END,
+ valign: Gtk.Align.END });
+ this.add_overlay(this._license);
}
- _initView() {
- let view = this.get_view();
+ _initMap() {
+ let map = new Shumate.Map();
- view.min_zoom_level = MapMinZoom;
- view.goto_animation_mode = Clutter.AnimationMode.EASE_IN_OUT_CUBIC;
- view.reactive = true;
- view.kinetic_mode = true;
- view.horizontal_wrap = true;
+ map.viewport.max_zoom_level = MapMaxZoom;
+ map.viewport.min_zoom_level = MapMinZoom;
- view.connect('notify::latitude', this._onViewMoved.bind(this));
+ map.viewport.connect('notify::latitude', this._onViewMoved.bind(this));
// switching map type will set view min-zoom-level from map source
- view.connect('notify::min-zoom-level', () => {
- if (view.min_zoom_level < MapMinZoom) {
- view.min_zoom_level = MapMinZoom;
+ map.viewport.connect('notify::min-zoom-level', () => {
+ if (map.viewport.min_zoom_level < MapMinZoom) {
+ map.viewport.min_zoom_level = MapMinZoom;
}
});
Application.settings.connect('changed::show-scale',
this._onShowScaleChanged.bind(this));
- this._initScale(view);
- return view;
+ return map;
}
/* create and store a route layer, pass true to get a dashed line */
- _createRouteLayer(dashed, lineColor, width) {
- let red = Color.parseColor(lineColor, 0);
- let green = Color.parseColor(lineColor, 1);
- let blue = Color.parseColor(lineColor, 2);
- // Clutter uses a 0-255 range for color components
- let strokeColor = new Clutter.Color({ red: red * 255,
- blue: blue * 255,
- green: green * 255,
- alpha: 255 });
- let routeLayer = new Champlain.PathLayer({ stroke_width: width,
- stroke_color: strokeColor });
+ _createRouteLayer(dashed, lineColor, outlineColor, width) {
+ let strokeColor = new Gdk.RGBA({ red: Color.parseColor(lineColor, 0),
+ green: Color.parseColor(lineColor, 1),
+ blue: Color.parseColor(lineColor, 2),
+ alpha: 1.0 });
+ let routeLayer = new Shumate.PathLayer({ viewport: this.map.viewport,
+ stroke_width: width,
+ stroke_color: strokeColor });
if (dashed)
routeLayer.set_dash([DASHED_ROUTE_LINE_FILLED_LENGTH,
DASHED_ROUTE_LINE_GAP_LENGTH]);
+ if (outlineColor) {
+ let outlineStrokeColor =
+ new Gdk.RGBA({ red: Color.parseColor(outlineColor, 0),
+ green: Color.parseColor(outlineColor, 1),
+ blue: Color.parseColor(outlineColor, 2),
+ alpha: 1.0 });
+
+ routeLayer.outline_color = outlineStrokeColor;
+ routeLayer.outline_width = 1.0;
+ }
+
this._routeLayers.push(routeLayer);
- this.view.add_layer(routeLayer);
+ this.map.insert_layer_behind(routeLayer, this._instructionMarkerLayer);
return routeLayer;
}
@@ -213,23 +259,30 @@ export class MapView extends GtkChamplain.Embed {
this._routeLayers.forEach((routeLayer) => {
routeLayer.remove_all();
routeLayer.visible = false;
- this.view.remove_layer(routeLayer);
+ this.map.remove_layer(routeLayer);
});
this._routeLayers = [];
}
_initLayers() {
- let mode = Champlain.SelectionMode.SINGLE;
+ let mode = Gtk.SelectionMode.MULTIPLE;
- this._userLocationLayer = new Champlain.MarkerLayer({ selection_mode: mode });
- this.view.add_layer(this._userLocationLayer);
+ this._userLocationLayer =
+ new Shumate.MarkerLayer({ selection_mode: mode,
+ viewport: this.map.viewport });
+ this.map.add_layer(this._userLocationLayer);
- this._placeLayer = new Champlain.MarkerLayer({ selection_mode: mode });
- this.view.add_layer(this._placeLayer);
+ this._placeLayer =
+ new Shumate.MarkerLayer({ selection_mode: mode,
+ viewport: this.map.viewport });
+ this.map.insert_layer_above(this._placeLayer, this._userLocationLayer);
- this._instructionMarkerLayer = new Champlain.MarkerLayer({ selection_mode: mode });
- this.view.add_layer(this._instructionMarkerLayer);
+ this._instructionMarkerLayer =
+ new Shumate.MarkerLayer({ selection_mode: mode,
+ viewport: this.map.viewport });
+ this.map.insert_layer_above(this._instructionMarkerLayer,
+ this._placeLayer);
ShapeLayer.SUPPORTED_TYPES.push(GeoJSONShapeLayer);
ShapeLayer.SUPPORTED_TYPES.push(KmlShapeLayer);
@@ -238,11 +291,6 @@ export class MapView extends GtkChamplain.Embed {
this._routeLayers = [];
}
- _ensureInstructionLayerAboveRouteLayers() {
- this.view.remove_layer(this._instructionMarkerLayer);
- this.view.add_layer(this._instructionMarkerLayer);
- }
-
_connectRouteSignals() {
let route = Application.routingDelegator.graphHopper.route;
let transitPlan = Application.routingDelegator.transitRouter.plan;
@@ -276,7 +324,12 @@ export class MapView extends GtkChamplain.Embed {
this.routeShowing = false;
});
- query.connect('notify', () => this.routingOpen = query.isValid());
+ query.connect('notify', () => {
+ this.routingOpen = query.isValid();
+ this._clearRouteLayers();
+ this._instructionMarkerLayer.remove_all();
+ this.routeShowing = false;
+ });
}
_getStoredMapType() {
@@ -300,21 +353,36 @@ export class MapView extends GtkChamplain.Embed {
if (this._mapType && this._mapType === mapType)
return;
- let overlay_sources = this.view.get_overlay_sources();
+ //let overlay_sources = this.view.get_overlay_sources();
this._mapType = mapType;
if (mapType !== MapView.MapType.LOCAL) {
let tiles = Service.getService().tiles;
+ let mapSource;
if (mapType === MapView.MapType.AERIAL && tiles.aerial)
- this.view.map_source = MapSource.createAerialSource();
+ mapSource = MapSource.createAerialSource();
else
- this.view.map_source = MapSource.createStreetSource();
+ mapSource = MapSource.createStreetSource();
+
+ let mapLayer = new Shumate.MapLayer({ map_source: mapSource,
+ viewport: this.map.viewport });
+
+ // update license
+ if (this._mapSource)
+ this._license.remove_map_source(this._mapSource);
+
+ this._license.append_map_source(mapSource);
+
+ this.map.add_layer(mapLayer);
+ this._mapSource = mapSource;
+
+ this.map.viewport.set_reference_map_source(mapSource);
Application.settings.set('map-type', mapType);
} else {
- let renderer = new Champlain.ImageRenderer();
+ let renderer = new Shumate.RasterRenderer();
let source = new GnomeMaps.FileTileSource({
path: Utils.getBufferText(Application.application.local_tile_path),
renderer: renderer,
@@ -334,7 +402,7 @@ export class MapView extends GtkChamplain.Embed {
}
}
- overlay_sources.forEach((source) => this.view.add_overlay_source(source, 255));
+ //overlay_sources.forEach((source) => this.view.add_overlay_source(source, 255));
this.emit("map-type-changed", mapType);
}
@@ -346,10 +414,16 @@ export class MapView extends GtkChamplain.Embed {
_checkIfFileSizeNeedsConfirmation(files) {
let confirmLoad = false;
let totalFileSizeMB = 0;
- files.forEach((file) => {
- totalFileSizeMB += file.query_info(Gio.FILE_ATTRIBUTE_STANDARD_SIZE,
+ let file;
+ let i = 0;
+
+ do {
+ let file = files.get_item(i);
+
+ totalFileSizeMB += file.query_info(Gio.FILE_ATTRIBUTE_STANDARD_SIZE,
0, null).get_size();
- });
+ i++;
+ } while (file);
totalFileSizeMB = totalFileSizeMB / (1024 * 1024);
if (totalFileSizeMB > FILE_SIZE_LIMIT_MB) {
confirmLoad = true;
@@ -403,9 +477,11 @@ export class MapView extends GtkChamplain.Embed {
_loadShapeLayers(files) {
let bbox = new BoundingBox();
- this._remainingFilesToLoad = files.length;
+ this._remainingFilesToLoad = files.get_n_items();
+
+ for (let i = 0; i < files.get_n_items(); i++) {
+ let file = files.get_item(i);
- files.forEach((file) => {
try {
let i = this._findShapeLayerIndex(file);
let layer = (i > -1) ? this.shapeLayerStore.get_item(i) : null;
@@ -421,7 +497,7 @@ export class MapView extends GtkChamplain.Embed {
let msg = _("Failed to open layer");
Utils.showDialog(msg, Gtk.MessageType.ERROR, this._mainWindow);
}
- });
+ }
}
removeShapeLayer(shapeLayer) {
@@ -447,7 +523,7 @@ export class MapView extends GtkChamplain.Embed {
store: false });
let marker = new PlaceMarker({ place: place,
mapView: this });
- this._placeLayer.add_marker(marker);
+ this._showPlaceMarker(marker);
marker.goToAndSelect(true);
} catch(e) {
let msg = _("Failed to open GeoURI");
@@ -462,7 +538,7 @@ export class MapView extends GtkChamplain.Embed {
let marker = new PlaceMarker({ place: place,
mapView: this });
- this._placeLayer.add_marker(marker);
+ this._showPlaceMarker(marker);
marker.goToAndSelect(true);
} else {
Utils.showDialog(error, Gtk.MessageType.ERROR, this._mainWindow);
@@ -481,19 +557,32 @@ export class MapView extends GtkChamplain.Embed {
}
gotoAntipode() {
- let lat = -this.view.latitude;
- let lon = this.view.longitude > 0 ?
- this.view.longitude - 180 : this.view.longitude + 180;
+ let lat = -this.map.viewport.latitude;
+ let lon = this.map.viewport.longitude > 0 ?
+ this.map.viewport.longitude - 180 :
+ this.map.viewport.longitude + 180;
let place =
new Place({ location: new Location({ latitude: lat,
longitude: lon }),
- initialZoom: this.view.zoom_level });
+ initialZoom: this.map.viewport.zoom_level });
new MapWalker(place, this).goTo(true);
}
+ _getViewBBox() {
+ let {x, y, width, height} = this.get_allocation();
+ let [top, left] = this.map.viewport.widget_coords_to_location(0, 0);
+ let [bottom, right] =
+ this.map.viewport.widget_coords_to_location(width - 1, height - 1);
+
+ return new BoundingBox({ left: left,
+ top: top,
+ right: right,
+ bottom: bottom });
+ }
+
userLocationVisible() {
- let box = this.view.get_bounding_box();
+ let box = this._getViewBBox();
return box.covers(this._userLocation.latitude, this._userLocation.longitude);
}
@@ -512,7 +601,6 @@ export class MapView extends GtkChamplain.Embed {
let place = Application.geoclue.place;
this._userLocation = new UserLocationMarker({ place: place,
mapView: this });
- this._userLocationLayer.remove_all();
this._userLocation.addToLayer(this._userLocationLayer);
}
@@ -522,10 +610,11 @@ export class MapView extends GtkChamplain.Embed {
}
_storeLocation() {
- let zoom = this.view.zoom_level;
- let location = [this.view.latitude, this.view.longitude];
+ let viewport = this.map.viewport;
+ let zoom = viewport.zoom_level;
+ let location = [viewport.latitude, viewport.longitude];
- /* protect agains situations where the Champlain view was already
+ /* protect agains situations where the map view was already
* disposed, in this case zoom will be set to the GObject property
* getter
*/
@@ -544,25 +633,27 @@ export class MapView extends GtkChamplain.Embed {
let [lat, lon] = location;
let zoom = Application.settings.get('zoom-level');
- if (zoom >= this.view.min_zoom_level &&
- zoom <= this.view.max_zoom_level)
- this.view.zoom_level = Application.settings.get('zoom-level');
- else
- Utils.debug('Invalid initial zoom level: ' + zoom);
-
if (lat >= MapView.MIN_LATITUDE && lat <= MapView.MAX_LATITUDE &&
- lon >= MapView.MIN_LONGITUDE && lon <= MapView.MAX_LONGITUDE)
- this.view.center_on(location[0], location[1]);
- else
+ lon >= MapView.MIN_LONGITUDE && lon <= MapView.MAX_LONGITUDE) {
+ this.map.viewport.latitude = lat;
+ this.map.viewport.longitude = lon;
+ if (zoom >= this.map.viewport.min_zoom_level &&
+ zoom <= this.map.viewport.max_zoom_level) {
+ this.map.viewport.zoom_level = zoom;
+ } else {
+ Utils.debug('Invalid initial zoom level: ' + zoom);
+ }
+ } else {
Utils.debug('Invalid initial coordinates: ' + lat + ', ' + lon);
+ }
} else {
/* bounding box. for backwards compatibility, not used anymore */
let bbox = new BoundingBox({ top: location[0],
bottom: location[1],
left: location[2],
right: location[3] });
- this.view.connect("notify::realized", () => {
- if (this.view.realized)
+ this.map.connect("notify::realized", () => {
+ if (this.map.realized)
this.gotoBBox(bbox, true);
});
}
@@ -583,13 +674,13 @@ export class MapView extends GtkChamplain.Embed {
left : bbox.left,
right : bbox.right })
});
- new MapWalker(place, this).goTo(true, linear);
+ new MapWalker(place, this).zoomToFit();
}
getZoomLevelFittingBBox(bbox) {
- let mapSource = this.view.get_map_source();
+ let mapSource = this._mapSource;
let goodSize = false;
- let zoomLevel = this.view.max_zoom_level;
+ let zoomLevel = this.map.viewport.max_zoom_level;
do {
@@ -597,15 +688,15 @@ export class MapView extends GtkChamplain.Embed {
let minY = mapSource.get_y(zoomLevel, bbox.bottom);
let maxX = mapSource.get_x(zoomLevel, bbox.right);
let maxY = mapSource.get_y(zoomLevel, bbox.top);
+ let {x, y, width, height} = this.get_allocation();
- if (minY - maxY <= this.view.height &&
- maxX - minX <= this.view.width)
+ if (minY - maxY <= height && maxX - minX <= width)
goodSize = true;
else
zoomLevel--;
- if (zoomLevel <= this.view.min_zoom_level) {
- zoomLevel = this.view.min_zoom_level;
+ if (zoomLevel <= this.map.viewport.min_zoom_level) {
+ zoomLevel = this.map.viewport.min_zoom_level;
goodSize = true;
}
} while (!goodSize);
@@ -686,11 +777,11 @@ export class MapView extends GtkChamplain.Embed {
this._placeLayer.remove_all();
routeLayer = this._createRouteLayer(false, TURN_BY_TURN_ROUTE_COLOR,
- ROUTE_LINE_WIDTH);
+ null, ROUTE_LINE_WIDTH);
route.path.forEach((polyline) => routeLayer.add_node(polyline));
this.routingOpen = true;
- this._ensureInstructionLayerAboveRouteLayers();
+ //this._ensureInstructionLayerAboveRouteLayers();
this._showDestinationTurnpoints();
this.gotoBBox(route.bbox);
@@ -729,15 +820,11 @@ export class MapView extends GtkChamplain.Embed {
let hasOutline = Color.relativeLuminance(color) >
OUTLINE_LUMINANCE_THREASHHOLD;
let routeLayer;
- let outlineRouteLayer;
+ let lineWidth = ROUTE_LINE_WIDTH + (hasOutline ? 2 : 0);
- /* draw an outline by drawing a background path layer if needed
- * TODO: maybe we should add support for outlined path layers in
- * libchamplain */
- if (hasOutline)
- outlineRouteLayer = this._createRouteLayer(dashed, outlineColor,
- ROUTE_LINE_WIDTH + 2);
- routeLayer = this._createRouteLayer(dashed, color, ROUTE_LINE_WIDTH);
+ routeLayer = this._createRouteLayer(dashed, color,
+ hasOutline ? outlineColor : null,
+ lineWidth);
/* if this is a walking leg and not at the start, "stitch" it
* together with the end point of the previous leg, as the walk
@@ -749,11 +836,6 @@ export class MapView extends GtkChamplain.Embed {
routeLayer.add_node(lastPoint);
}
- if (hasOutline) {
- leg.polyline.forEach((function (polyline) {
- outlineRouteLayer.add_node(polyline);
- }));
- }
leg.polyline.forEach((function (polyline) {
routeLayer.add_node(polyline);
}));
@@ -766,9 +848,7 @@ export class MapView extends GtkChamplain.Embed {
routeLayer.add_node(firstPoint);
}
- });
-
- this._ensureInstructionLayerAboveRouteLayers();
+ })
itinerary.legs.forEach((leg, index) => {
let previousLeg = index === 0 ? null : itinerary.legs[index - 1];
@@ -839,7 +919,7 @@ GObject.registerClass({
'going-to-user-location': {},
'gone-to-user-location': {},
'view-moved': {},
- 'marker-selected': { param_types: [Champlain.Marker] },
+ 'marker-selected': { param_types: [Shumate.Marker] },
'map-type-changed': { param_types: [GObject.TYPE_STRING] }
},
}, MapView);
diff --git a/src/mapWalker.js b/src/mapWalker.js
index 925ea5bb..728148ab 100644
--- a/src/mapWalker.js
+++ b/src/mapWalker.js
@@ -21,7 +21,6 @@
* Damián Nohales <damiannohales gmail com>
*/
-import Clutter from 'gi://Clutter';
import GObject from 'gi://GObject';
import {BoundingBox} from './boundingBox.js';
@@ -39,7 +38,7 @@ export class MapWalker extends GObject.Object {
super();
this.place = place;
this._mapView = mapView;
- this._view = mapView.view;
+ this._viewport = mapView.map.viewport;
this._boundingBox = this._createBoundingBox(this.place);
}
@@ -62,7 +61,7 @@ export class MapWalker extends GObject.Object {
zoom = this.place.initialZoom;
} else {
zoom = PlaceZoom.getZoomLevelForPlace(this.place) ??
- this._view.max_zoom_level;
+ this._viewport.max_zoom_level;
/* If the place has a bounding box, use the lower of the default
* zoom level based on the place's type and the zoom level needed
@@ -78,9 +77,9 @@ export class MapWalker extends GObject.Object {
}
}
- this._view.zoom_level = zoom;
- this._view.center_on(this.place.location.latitude,
- this.place.location.longitude);
+ this._mapView.map.go_to_full(this.place.location.latitude,
+ this.place.location.longitude,
+ zoom);
}
goTo(animate, linear) {
@@ -90,44 +89,15 @@ export class MapWalker extends GObject.Object {
this._mapView.emit('going-to');
if (!animate) {
- this._view.center_on(this.place.location.latitude,
- this.place.location.longitude);
+ this._mapView.map.center_on(this.place.location.latitude,
+ this.place.location.longitude);
this.emit('gone-to');
return;
- }
-
- let fromLocation = new Location({ latitude: this._view.get_center_latitude(),
- longitude: this._view.get_center_longitude() });
- this._updateGoToDuration(fromLocation);
-
- if (linear) {
- this._view.goto_animation_mode = Clutter.AnimationMode.LINEAR;
- Utils.once(this._view, 'animation-completed',
- this.zoomToFit.bind(this));
- this._view.go_to(this.place.location.latitude,
- this.place.location.longitude);
} else {
- /* Lets first ensure that both current and destination location are visible
- * before we start the animated journey towards destination itself. We do this
- * to create the zoom-out-then-zoom-in effect that many map implementations
- * do. This not only makes the go-to animation look a lot better visually but
- * also give user a good idea of where the destination is compared to current
- * location.
- */
- this._view.goto_animation_mode = Clutter.AnimationMode.EASE_IN_CUBIC;
- this._ensureVisible(fromLocation);
-
- Utils.once(this._view, 'animation-completed', () => {
- this._view.goto_animation_mode = Clutter.AnimationMode.EASE_OUT_CUBIC;
- this._view.go_to(this.place.location.latitude,
- this.place.location.longitude);
-
- Utils.once(this._view, 'animation-completed::go-to', () => {
- this.zoomToFit();
- this._view.goto_animation_mode = Clutter.AnimationMode.EASE_IN_OUT_CUBIC;
- this.emit('gone-to');
- });
- });
+ this._mapView.map.go_to(this.place.location.latitude,
+ this.place.location.longitude);
+ Utils.once(this._mapView.map, 'animation-completed::go-to',
+ () => this.emit('gone-to'));
}
}
@@ -176,21 +146,6 @@ export class MapWalker extends GObject.Object {
return true;
}
-
- _updateGoToDuration(fromLocation) {
- let toLocation = this.place.location;
-
- let distance = fromLocation.get_distance_from(toLocation);
- let duration = (distance / _MAX_DISTANCE) * _MAX_ANIMATION_DURATION;
-
- // Clamp duration
- duration = Math.max(_MIN_ANIMATION_DURATION,
- Math.min(duration, _MAX_ANIMATION_DURATION));
-
- // We divide by two because Champlain treats both go_to and
- // ensure_visible as 'goto' journeys with its own duration.
- this._view.goto_animation_duration = duration / 2;
- }
}
GObject.registerClass({
diff --git a/src/osmEditDialog.js b/src/osmEditDialog.js
index 2a7e05b8..4c0faf49 100644
--- a/src/osmEditDialog.js
+++ b/src/osmEditDialog.js
@@ -335,7 +335,8 @@ export class OSMEditDialog extends Gtk.Dialog {
this._cancellable = new Gio.Cancellable();
this._cancellable.connect(() => this.response(OSMEditDialog.Response.CANCELLED));
- this.connect('delete-event', () => this._cancellable.cancel());
+ this.connect('response', () => this._cancellable.cancel());
+ this.connect('close-request', () => this._cancellable.cancel());
this._isEditing = false;
this._nextButton.connect('clicked', () => this._onNextClicked());
@@ -475,10 +476,15 @@ export class OSMEditDialog extends Gtk.Dialog {
let recentTypes = OSMTypes.recentTypesStore.recentTypes;
if (recentTypes.length > 0) {
- let children = this._recentTypesListBox.get_children();
+ let children = [];
- for (let i = 0; i < children.length; i++) {
- this._recentTypesListBox.remove(children[i]);
+ for (let child of this._recentTypesListBox) {
+ if (child instanceof Gtk.ListBoxRow)
+ children.push(child);
+ }
+
+ for (let child of children) {
+ this._recentTypesListBox.remove(child);
}
this._recentTypesLabel.visible = true;
@@ -563,7 +569,7 @@ export class OSMEditDialog extends Gtk.Dialog {
let statusMessage =
error ? error.message : OSMConnection.getStatusMessage(status);
let messageDialog =
- new Gtk.MessageDialog({ transient_for: this.get_toplevel(),
+ new Gtk.MessageDialog({ transient_for: this.get_root(),
destroy_with_parent: true,
message_type: Gtk.MessageType.ERROR,
buttons: Gtk.ButtonsType.OK,
@@ -571,8 +577,8 @@ export class OSMEditDialog extends Gtk.Dialog {
text: _("An error has occurred"),
secondary_text: statusMessage });
- messageDialog.run();
- messageDialog.destroy();
+ messageDialog.connect('response', () => messageDialog.destroy());
+ messageDialog.show();
this.response(OSMEditDialog.Response.ERROR);
}
@@ -590,8 +596,7 @@ export class OSMEditDialog extends Gtk.Dialog {
}
_addOSMEditDeleteButton(fieldSpec) {
- let deleteButton = Gtk.Button.new_from_icon_name('user-trash-symbolic',
- Gtk.IconSize.BUTTON);
+ let deleteButton = Gtk.Button.new_from_icon_name('user-trash-symbolic');
let styleContext = deleteButton.get_style_context();
let rows = fieldSpec.rows || 1;
@@ -632,11 +637,13 @@ export class OSMEditDialog extends Gtk.Dialog {
}
_showHintPopover(entry, hint) {
- if (this._hintPopover.visible) {
+ if (this._hintPopover && this._hintPopover.visible) {
this._hintPopover.popdown();
+ this._hintPopover = null;
} else {
- this._hintPopover.relative_to = entry;
- this._hintLabel.label = hint;
+ let label = new Gtk.Label({ label: hint });
+ this._hintPopover = new Gtk.Popover({ child: label });
+ this._hintPopover.set_parent(entry);
this._hintPopover.popup();
}
}
@@ -665,8 +672,13 @@ export class OSMEditDialog extends Gtk.Dialog {
entry.placeholder_text = fieldSpec.placeHolder;
entry.connect('changed', () => {
- if (fieldSpec.rewriteFunc)
- entry.text = fieldSpec.rewriteFunc(entry.text);
+ if (fieldSpec.rewriteFunc) {
+ let rewrittenText = fieldSpec.rewriteFunc(entry.text);
+
+ if (rewrittenText !== entry.text)
+ entry.text = rewrittenText;
+ }
+
this._osmObject.set_tag(fieldSpec.tag, entry.text);
this._validateTextEntry(fieldSpec, entry);
@@ -710,12 +722,16 @@ export class OSMEditDialog extends Gtk.Dialog {
this._nextButton.sensitive = true;
});
+ // TODO: this doesn't work in GTK4, since SpinButton doesn't extend
+ // Entry, maybe put the hint button beside the spin button?
+ /*
if (fieldSpec.hint) {
spinbutton.secondary_icon_name = 'dialog-information-symbolic';
spinbutton.connect('icon-press', (iconPos, event) => {
this._showHintPopover(spinbutton, fieldSpec.hint);
});
}
+ */
this._editorGrid.attach(spinbutton, 1, this._currentRow, 1, 1);
spinbutton.show();
@@ -775,12 +791,15 @@ export class OSMEditDialog extends Gtk.Dialog {
/* update visible items in the "Add Field" popover */
_updateAddFieldMenu() {
/* clear old items */
- let children = this._addFieldPopoverGrid.get_children();
let hasAllFields = true;
+ let children = [];
+
+ for (let child of this._addFieldPopoverGrid) {
+ children.push(child);
+ }
- for (let i = 0; i < children.length; i++) {
- let button = children[i];
- button.destroy();
+ for (let child of children) {
+ this._addFieldPopoverGrid.remove(child);
}
/* add selectable items */
@@ -810,6 +829,7 @@ export class OSMEditDialog extends Gtk.Dialog {
button.connect('clicked', () => {
this._addFieldButton.active = false;
+ this._addFieldPopover.popdown();
this._addOSMField(fieldSpec);
/* add a "placeholder" empty OSM tag to keep the add field
* menu updated, these tags will be filtered out if nothing
@@ -898,6 +918,7 @@ GObject.registerClass({
'stack',
'editorGrid',
'commentTextView',
+ 'addFieldPopover',
'addFieldPopoverGrid',
'addFieldButton',
'typeSearchGrid',
@@ -906,7 +927,5 @@ GObject.registerClass({
'typeValueLabel',
'recentTypesLabel',
'recentTypesListBox',
- 'hintPopover',
- 'hintLabel',
'headerBar'],
}, OSMEditDialog);
diff --git a/src/osmTypeListRow.js b/src/osmTypeListRow.js
index 84bb0c48..81940e0e 100644
--- a/src/osmTypeListRow.js
+++ b/src/osmTypeListRow.js
@@ -25,11 +25,12 @@ import Gtk from 'gi://Gtk';
export class OSMTypeListRow extends Gtk.ListBoxRow {
constructor(props) {
- this._type = props.type;
+ let type = props.type;
delete props.type;
super(props);
+ this._type = type;
this._name.label = this._type.title;
}
diff --git a/src/osmTypePopover.js b/src/osmTypePopover.js
index 5a3d30e2..b4026f98 100644
--- a/src/osmTypePopover.js
+++ b/src/osmTypePopover.js
@@ -37,10 +37,23 @@ export class OSMTypePopover extends SearchPopover {
}
showMatches(matches) {
- this._list.foreach((row) => this._list.remove(row));
+ let rows = [];
+
+ for (let row of this._list) {
+ rows.push(row);
+ }
+ for (let row of rows) {
+ this._list.remove(row);
+ }
matches.forEach((type) => this._addRow(type));
- this.show();
+
+ let {x, y, width, height} = this.get_parent().get_allocation();
+
+ // Magic number to make the alignment pixel perfect.
+ this.width_request = width + 20;
+
+ this.popup();
}
_addRow(type) {
diff --git a/src/osmTypeSearchEntry.js b/src/osmTypeSearchEntry.js
index 74ee6544..fc14ec21 100644
--- a/src/osmTypeSearchEntry.js
+++ b/src/osmTypeSearchEntry.js
@@ -33,13 +33,9 @@ export class OSMTypeSearchEntry extends Gtk.SearchEntry {
constructor(props) {
super(props);
- this._popover = new OSMTypePopover({relative_to: this});
-
- this.connect('size-allocate', (widget, allocation) => {
- /* Magic number to make the alignment pixel perfect. */
- let width_request = allocation.width + 20;
- this._popover.width_request = width_request;
- });
+ this._popover = new OSMTypePopover({ entry: this });
+ this._popover.set_parent(this);
+ this.set_key_capture_widget(this._popover);
this.connect('search-changed', this._onSearchChanged.bind(this));
this.connect('activate', this._onSearchChanged.bind(this));
diff --git a/src/placeBar.js b/src/placeBar.js
index 6db74564..69634f4f 100644
--- a/src/placeBar.js
+++ b/src/placeBar.js
@@ -19,7 +19,6 @@
* Author: James Westman <james flyingpimonster net>
*/
-import Clutter from 'gi://Clutter';
import Gdk from 'gi://Gdk';
import GeocodeGlib from 'gi://GeocodeGlib';
import GObject from 'gi://GObject';
@@ -43,15 +42,19 @@ export class PlaceBar extends Gtk.Revealer {
this._buttons = new PlaceButtons({ mapView: this._mapView });
this._buttons.initSendToButton(this._altSendToButton);
this._buttons.connect('place-edited', this._onPlaceEdited.bind(this));
- this._box.add(this._buttons);
+ this._box.append(this._buttons);
- this._multipress = new Gtk.GestureMultiPress({ widget: this._eventbox });
- this._multipress.connect('released', this._onEventBoxClicked.bind(this));
+ this._click = new Gtk.GestureClick();
+ this._box.add_controller(this._click);
+ this._click.connect('released', this._onBoxClicked.bind(this));
Application.application.connect('notify::adaptive-mode', this._updateVisibility.bind(this));
this.connect('notify::place', this._updatePlace.bind(this));
- this._mapView.view.connect('touch-event', this._onMapClickEvent.bind(this));
+ this._mapClick = new Gtk.GestureSingle();
+ this._mapView.add_controller(this._mapClick);
+
+ this._mapClick.connect('begin', this._onMapClickEvent.bind(this));
}
_updatePlace() {
@@ -83,7 +86,7 @@ export class PlaceBar extends Gtk.Revealer {
}
}
- _onEventBoxClicked() {
+ _onBoxClicked() {
if (this.place.isCurrentLocation) {
if (this._currentLocationView) {
this._box.remove(this._currentLocationView);
@@ -113,21 +116,8 @@ export class PlaceBar extends Gtk.Revealer {
}
_onMapClickEvent(view, event) {
- switch (event.type()) {
- case Clutter.EventType.TOUCH_BEGIN:
- this._tapped = true;
- break;
- case Clutter.EventType.TOUCH_UPDATE:
- this._tapped = false;
- case Clutter.EventType.TOUCH_END:
- case Clutter.EventType.TOUCH_CANCEL:
- if (this._tapped) {
- Application.application.selected_place = null;
- }
- break;
- }
-
- return Clutter.EVENT_PROPAGATE;
+ Application.application.selected_place = null;
+ this.reveal_child = false;
}
}
@@ -136,7 +126,6 @@ GObject.registerClass({
InternalChildren: [ 'actionbar',
'altSendToButton',
'box',
- 'eventbox',
'title' ],
Properties: {
'place': GObject.ParamSpec.object('place',
@@ -147,3 +136,4 @@ GObject.registerClass({
GeocodeGlib.Place)
},
}, PlaceBar);
+
diff --git a/src/placeButtons.js b/src/placeButtons.js
index 05aac8bf..c5e1f031 100644
--- a/src/placeButtons.js
+++ b/src/placeButtons.js
@@ -71,11 +71,18 @@ export class PlaceButtons extends Gtk.Box {
initSendToButton(button) {
button.connect('clicked', () => {
- let dialog = new SendToDialog({ transient_for: this.get_toplevel(),
+ let dialog = new SendToDialog({ transient_for: this.get_root(),
modal: true,
mapView: this._mapView,
place: this._place });
- dialog.connect('response', () => dialog.destroy());
+ dialog.connect('response', () => {
+ dialog.destroy();
+ this._popup();
+ });
+ /* on GTK 4 the popover gets overlayead over the dialog,
+ * so close the popover when not in adaptive mode
+ */
+ this._popdown();
dialog.show();
});
}
@@ -135,13 +142,19 @@ export class PlaceButtons extends Gtk.Box {
let osmEdit = Application.osmEdit;
/* if the user is not already signed in, show the account dialog */
if (!osmEdit.isSignedIn) {
- let dialog = osmEdit.createAccountDialog(this.get_toplevel(), true);
+ let dialog = osmEdit.createAccountDialog(this.get_root(), true);
+ /* on GTK 4 the popover gets overlayead over the dialog,
+ * so close the popover when not in adaptive mode
+ */
+ this._popdown();
dialog.show();
dialog.connect('response', (dialog, response) => {
dialog.destroy();
if (response === OSMAccountDialog.Response.SIGNED_IN)
this._edit();
+ else
+ this._popup();
});
return;
@@ -150,10 +163,25 @@ export class PlaceButtons extends Gtk.Box {
this._edit();
}
+ // popdown the parent popove(when not in adaptive mode)
+ _popdown() {
+ if (!Application.application.adaptive_mode)
+ this.get_ancestor(Gtk.Popover).popdown();
+ }
+
+ _popup() {
+ if (!Application.application.adaptive_mode)
+ this.get_ancestor(Gtk.Popover).popup();
+ }
+
_edit() {
let osmEdit = Application.osmEdit;
- let dialog = osmEdit.createEditDialog(this.get_toplevel(), this._place);
+ let dialog = osmEdit.createEditDialog(this.get_root(), this._place);
+ /* on GTK 4 the popover gets overlayead over the dialog,
+ * so close the popover when not in adaptive mode
+ */
+ this._popdown();
dialog.show();
dialog.connect('response', (dialog, response) => {
dialog.destroy();
@@ -169,6 +197,8 @@ export class PlaceButtons extends Gtk.Box {
default:
break;
}
+
+ this._popup();
});
}
}
diff --git a/src/placeEntry.js b/src/placeEntry.js
index 74f9df97..81a2342d 100644
--- a/src/placeEntry.js
+++ b/src/placeEntry.js
@@ -68,9 +68,11 @@ export class PlaceEntry extends Gtk.SearchEntry {
this._placeText = '';
}
- this.text = this._placeText;
+ if (this.text !== this._placeText)
+ this._setTextWithoutTriggerSearch(this._placeText);
this._place = p;
+
this.notify('place');
}
@@ -88,10 +90,6 @@ export class PlaceEntry extends Gtk.SearchEntry {
let mapView = props.mapView;
delete props.mapView;
- if (!props.loupe)
- props.primary_icon_name = null;
- delete props.loupe;
-
let maxChars = props.maxChars;
delete props.maxChars;
@@ -112,9 +110,14 @@ export class PlaceEntry extends Gtk.SearchEntry {
this._cache = {};
// clear cache when view moves, as result are location-dependent
- this._mapView.view.connect('notify::latitude', () => this._cache = {});
+ this._mapView.map.viewport.connect('notify::latitude', () => this._cache = {});
// clear cache when zoom level changes, to allow limiting location bias
- this._mapView.view.connect('notify::zoom-level', () => this._cache = {});
+ this._mapView.map.viewport.connect('notify::zoom-level', () => this._cache = {});
+ }
+
+ _setTextWithoutTriggerSearch(text) {
+ this._setText = text;
+ this.text = text;
}
_onSearchChanged() {
@@ -125,6 +128,10 @@ export class PlaceEntry extends Gtk.SearchEntry {
if (this._cancellable)
return;
+ // don't trigger a search when setting explicit text (such as reordering points)
+ if (this.text === this._setText)
+ return;
+
/* start search if more than the threshold number of characters have
* been entered, or if the first character is in the ideographic CJK
* block, as for these, shorter strings could be meaningful
@@ -147,7 +154,8 @@ export class PlaceEntry extends Gtk.SearchEntry {
this._doSearch();
}
} else {
- this._popover.hide();
+ this._popover.popdown();
+ this.grab_focus();
if (this.text.length === 0)
this.place = null;
this._previousSearch = null;
@@ -164,24 +172,41 @@ export class PlaceEntry extends Gtk.SearchEntry {
_createPopover(numVisible, maxChars) {
let popover = new PlacePopover({ num_visible: numVisible,
- relative_to: this,
+ entry: this,
maxChars: maxChars });
+ popover.set_parent(this);
+ this.set_key_capture_widget(popover);
+ // TODO: implement vfunc_size_allocate here?...
+ /*
this.connect('size-allocate', (widget, allocation) => {
// Magic number to make the alignment pixel perfect.
let width_request = allocation.width + 20;
// set at least 320 px width to avoid too narrow in the sidebar
popover.width_request = Math.max(width_request, 320);
});
+ */
popover.connect('selected', (widget, place) => {
this.place = place;
- popover.hide();
+ popover.popdown();
});
+ //this._keyController = new Gtk.EventControllerKey();
+ //this.add_controller(this._keyController);
+ //this._keyController.connect('key-pressed',
+ // this._onKeyPressed.bind(this));
+
+ // TODO: set position...
+
return popover;
}
+ _onKeyPressed(controller, keyval, keycode, state) {
+ log('onKeyPressed');
+ return true;
+ }
+
_completionVisibleFunc(model, iter) {
let place = model.get_value(iter, PlaceStore.Columns.PLACE);
let type = model.get_value(iter, PlaceStore.Columns.TYPE);
@@ -280,8 +305,8 @@ export class PlaceEntry extends Gtk.SearchEntry {
this._previousSearch = this.text;
GeocodeFactory.getGeocoder().search(this.text,
- this._mapView.view.latitude,
- this._mapView.view.longitude,
+ this._mapView.map.viewport.latitude,
+ this._mapView.map.viewport.longitude,
this._cancellable,
(places, error) => {
this._cancellable = null;
diff --git a/src/placeMarker.js b/src/placeMarker.js
index 25a0fe9e..b80b02f0 100644
--- a/src/placeMarker.js
+++ b/src/placeMarker.js
@@ -20,6 +20,7 @@
*/
import GObject from 'gi://GObject';
+import Gtk from 'gi://Gtk';
import {MapMarker} from './mapMarker.js';
@@ -28,7 +29,8 @@ export class PlaceMarker extends MapMarker {
constructor(params) {
super(params);
- this.add_actor(this._actorFromIconName('mark-location', 32));
+ this._image.icon_name = 'mark-location';
+ this._image.icon_size = Gtk.IconSize.LARGE;
}
get anchor() {
diff --git a/src/placePopover.js b/src/placePopover.js
index c2af1c33..c1abce6a 100644
--- a/src/placePopover.js
+++ b/src/placePopover.js
@@ -36,11 +36,9 @@ export class PlacePopover extends SearchPopover {
let maxChars = props.maxChars;
delete props.maxChars;
- props.transitions_enabled = false;
super(props);
this._maxChars = maxChars;
- this._entry = this.relative_to;
this._list.connect('row-activated', (list, row) => {
if (row)
@@ -63,16 +61,26 @@ export class PlacePopover extends SearchPopover {
this.connect('unmap', (popover) => popover.hide());
}
+ _showPopover() {
+ let {x, y, width, height} = this._entry.get_allocation();
+
+ // Magic number to make the alignment pixel perfect.
+ this.width_request = width + 20;
+ this.popup();
+ }
+
showSpinner() {
this._spinner.start();
this._stack.visible_child = this._spinner;
if (!this.visible)
- this.show();
+ this._showPopover();
+
+ this._numResults = 0;
}
showResult() {
- if (this._spinner.active)
+ if (this._spinner.spinning)
this._spinner.stop();
this._stack.visible_child = this._scrolledWindow;
@@ -82,7 +90,7 @@ export class PlacePopover extends SearchPopover {
this._list.select_row(row);
if (!this.visible)
- this.show();
+ this._showPopover();
}
showNoResult() {
@@ -90,6 +98,7 @@ export class PlacePopover extends SearchPopover {
this._spinner.stop();
this._stack.visible_child = this._noResultsLabel;
+ this._numResults = 0;
}
showError() {
@@ -97,6 +106,7 @@ export class PlacePopover extends SearchPopover {
this._spinner.stop();
this._stack.visible_child = this._errorLabel;
+ this._numResults = 0;
}
updateResult(places, searchString) {
@@ -114,6 +124,8 @@ export class PlacePopover extends SearchPopover {
i++;
});
+ this._numResults = i;
+
// remove remaining rows
let row = this._list.get_row_at_index(i);
diff --git a/src/placeView.js b/src/placeView.js
index 6d0e4e58..ce76dcee 100644
--- a/src/placeView.js
+++ b/src/placeView.js
@@ -86,12 +86,12 @@ export class PlaceView extends Gtk.Box {
this._mainBox = ui.bubbleMainBox;
this._addressLabel = ui.addressLabel;
- this.add(this._mainStack);
+ this.append(this._mainStack);
let placeButtons = new PlaceButtons({ place: this._place,
mapView: mapView });
placeButtons.connect('place-edited', this._onPlaceEdited.bind(this));
- ui.placeButtons.add(placeButtons);
+ ui.placeButtons.append(placeButtons);
if (this.place.isCurrentLocation) {
/* Current Location bubbles have a slightly different layout, to
@@ -175,11 +175,11 @@ export class PlaceView extends Gtk.Box {
}
get loading() {
- return this._spinner.active;
+ return this._spinner.spinning;
}
set loading(val) {
this._mainStack.set_visible_child(val ? this._spinner : this._mainBox);
- this._spinner.active = val;
+ this._spinner.spinning = val;
}
updatePlaceDetails() {
@@ -484,7 +484,7 @@ export class PlaceView extends Gtk.Box {
content.forEach(({ type, label, icon, linkUrl, info, grid }) => {
let separator = new Gtk.Separator({ visible: true });
separator.get_style_context().add_class('no-margin-separator');
- this._placeDetails.add(separator);
+ this._placeDetails.append(separator);
let box = new Gtk.Box({ orientation: Gtk.Orientation.HORIZONTAL,
visible: true,
@@ -501,7 +501,6 @@ export class PlaceView extends Gtk.Box {
if (icon) {
let widget = new Gtk.Image({ icon_name: icon,
visible: true,
- xalign: 1,
valign: Gtk.Align.START,
halign: Gtk.Align.END });
@@ -509,14 +508,14 @@ export class PlaceView extends Gtk.Box {
widget.tooltip_markup = label;
}
- box.add(widget);
+ box.append(widget);
} else if (label) {
let widget = new Gtk.Label({ label: label.italics(),
visible: true,
use_markup: true,
yalign: 0,
halign: Gtk.Align.END });
- box.add(widget);
+ box.append(widget);
}
if (linkUrl) {
@@ -574,8 +573,8 @@ export class PlaceView extends Gtk.Box {
}
}
- box.add(widget);
- this._placeDetails.add(box);
+ box.append(widget);
+ this._placeDetails.append(box);
});
}
@@ -628,7 +627,15 @@ export class PlaceView extends Gtk.Box {
// clear the view widgets to be able to re-populate an updated place
_clearView() {
- this._placeDetails.get_children().forEach((child) => this._placeDetails.remove(child));
+ let details = [];
+
+ for (let detail of this._placeDetails) {
+ details.push(detail);
+ }
+
+ for (let detail of details) {
+ this._placeDetails.remove(detail);
+ }
}
// called when the place's location changes (e.g. for the current location)
diff --git a/src/placeViewImage.js b/src/placeViewImage.js
index 44670d59..cc50cf09 100644
--- a/src/placeViewImage.js
+++ b/src/placeViewImage.js
@@ -22,6 +22,7 @@
import Cairo from 'cairo';
import Gdk from 'gi://Gdk';
import GObject from 'gi://GObject';
+import Graphene from 'gi://Graphene';
import Gtk from 'gi://Gtk';
/* The maximum aspect ratio, after which the image will be cropped vertically */
@@ -50,13 +51,19 @@ export class PlaceViewImage extends Gtk.DrawingArea {
this.queue_resize();
}
- vfunc_draw(cr) {
- let [{x, y, width, height}, baseline] = this.get_allocated_size();
+ vfunc_snapshot(snapshot) {
+ let {x, y, width, height} = this.get_allocation();
if (this._pixbuf === null || width === 0 || height === 0) {
return;
}
+ let rect = new Graphene.Rect();
+
+ rect.init(x, y, width, height);
+
+ let cr = snapshot.append_cairo(rect);
+
width *= this.scale_factor;
height *= this.scale_factor;
@@ -82,13 +89,27 @@ export class PlaceViewImage extends Gtk.DrawingArea {
cr.paint();
cr.restore();
- return false;
+ super.vfunc_snapshot(snapshot);
+ cr.$dispose();
}
vfunc_get_request_mode() {
return Gtk.SizeRequestMode.HEIGHT_FOR_WIDTH;
}
+ vfunc_measure(orientation, forSize) {
+ if (orientation === Gtk.Orientation.VERTICAL) {
+ if (this._pixbuf) {
+ let height = (this._pixbuf.height / this._pixbuf.width) * forSize;
+ return [height, height, 0, 0];
+ } else {
+ return [0, 0, 0, 0];
+ }
+ } else {
+ return [forSize, forSize, 0, 0];
+ }
+ }
+ /*
vfunc_get_preferred_height_for_width(width) {
if (this._pixbuf) {
let height = (this._pixbuf.height / this._pixbuf.width) * width;
@@ -97,6 +118,7 @@ export class PlaceViewImage extends Gtk.DrawingArea {
return [0, 0];
}
}
+ */
}
GObject.registerClass(PlaceViewImage);
diff --git a/src/printLayout.js b/src/printLayout.js
index 858e174f..4a7245a9 100644
--- a/src/printLayout.js
+++ b/src/printLayout.js
@@ -18,13 +18,12 @@
*/
import Cairo from 'cairo';
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
import Gdk from 'gi://Gdk';
import GObject from 'gi://GObject';
import Gtk from 'gi://Gtk';
import Pango from 'gi://Pango';
import PangoCairo from 'gi://PangoCairo';
+import Shumate from 'gi://Shumate';
import {Application} from './application.js';
import * as Color from './color.js';
@@ -33,10 +32,10 @@ import * as MapSource from './mapSource.js';
import {TurnPointMarker} from './turnPointMarker.js';
import * as Utils from './utils.js';
-const _STROKE_COLOR = new Clutter.Color({ red: 0,
- blue: 255,
- green: 0,
- alpha: 255 });
+const _STROKE_COLOR = new Gdk.RGBA({ red: 0.0,
+ blue: 1.0,
+ green: 0.0,
+ alpha: 1.0 });
const _STROKE_WIDTH = 5.0;
/* All following constants are ratios of surface size to page size */
@@ -177,8 +176,8 @@ export class PrintLayout extends GObject.Object {
}
_addRouteLayer(view) {
- let routeLayer = new Champlain.PathLayer({ stroke_width: _STROKE_WIDTH,
- stroke_color: _STROKE_COLOR });
+ let routeLayer = new Shumate.PathLayer({ stroke_width: _STROKE_WIDTH,
+ stroke_color: _STROKE_COLOR });
view.add_layer(routeLayer);
this._route.path.forEach((node) => routeLayer.add_node(node));
}
diff --git a/src/routeEntry.js b/src/routeEntry.js
index 5d2018ed..ed7e286a 100644
--- a/src/routeEntry.js
+++ b/src/routeEntry.js
@@ -56,18 +56,15 @@ export class RouteEntry extends Gtk.Grid {
this._entryGrid.attach(this.entry, 0, 0, 1, 1);
// There is no GdkWindow on the widget until it is realized
- this._icon.connect('realize', function(icon) {
- if (icon.window && icon.window.get_cursor())
- return;
-
- icon.window.set_cursor(Gdk.Cursor.new(Gdk.CursorType.HAND1));
+ this.icon.connect('realize', (icon) => {
+ icon.set_cursor(Gdk.Cursor.new_from_name('grab', null));
});
switch (this._type) {
case RouteEntry.Type.FROM:
let query = Application.routeQuery;
this._buttonImage.icon_name = 'list-add-symbolic';
- this._icon.icon_name = 'maps-point-start-symbolic';
+ this.icon.icon_name = 'maps-point-start-symbolic';
/* Translators: this is add via location tooltip */
this._button.tooltip_text = _("Add via location");
query.connect('notify::points', () => {
@@ -77,13 +74,13 @@ export class RouteEntry extends Gtk.Grid {
break;
case RouteEntry.Type.VIA:
this._buttonImage.icon_name = 'list-remove-symbolic';
- this._icon.icon_name = 'maps-point-end-symbolic';
+ this.icon.icon_name = 'maps-point-end-symbolic';
/* Translators: this is remove via location tooltip */
this._button.tooltip_text = _("Remove via location");
break;
case RouteEntry.Type.TO:
this._buttonImage.icon_name = 'route-reverse-symbolic';
- this._icon.icon_name = 'maps-point-end-symbolic';
+ this.icon.icon_name = 'maps-point-end-symbolic';
/* Translators: this is reverse route tooltip */
this._button.tooltip_text = _("Reverse route");
break;
@@ -117,9 +114,8 @@ export class RouteEntry extends Gtk.Grid {
GObject.registerClass({
Template: 'resource:///org/gnome/Maps/ui/route-entry.ui',
- Children: [ 'iconEventBox' ],
+ Children: [ 'icon' ],
InternalChildren: [ 'entryGrid',
- 'icon',
'button',
'buttonImage' ]
}, RouteEntry);
diff --git a/src/searchPopover.js b/src/searchPopover.js
index cb184b21..f56b5127 100644
--- a/src/searchPopover.js
+++ b/src/searchPopover.js
@@ -29,53 +29,57 @@ import Gtk from 'gi://Gtk';
export class SearchPopover extends Gtk.Popover {
constructor(props) {
+ let entry = props.entry;
+ delete props.entry;
+
super(props);
- this._entry = this.relative_to;
+ this._entry = entry;
// We need to propagate events to the listbox so that we can
// keep typing while selecting a place. But we do not want to
// propagate the 'enter' key press if there is a selection.
- this._keyController =
- new Gtk.EventControllerKey({ widget: this._entry });
+ this._keyController = new Gtk.EventControllerKey();
+ this.add_controller(this._keyController);
this._keyController.connect('key-pressed',
this._propagateKeys.bind(this));
- this._buttonPressGesture = new Gtk.GestureSingle({ widget: this._entry });
+ this._buttonPressGesture = new Gtk.GestureSingle();
+ this._entry.add_controller(this._buttonPressGesture);
this._buttonPressGesture.connect('begin',
() => this._list.unselect_all());
+
+ this._numResults = 0;
}
_propagateKeys(controller, keyval, keycode, state) {
+ log('propagateKeys: ' + keyval + ', ' + keycode);
if (keyval === Gdk.KEY_Escape) {
this.hide();
this._list.unselect_all();
- return true;
- }
-
- if (keyval === Gdk.KEY_Return ||
- keyval === Gdk.KEY_KP_ENTER ||
- keyval === Gdk.KEY_ISO_Enter) {
+ } else if (keyval === Gdk.KEY_Return ||
+ keyval === Gdk.KEY_KP_ENTER ||
+ keyval === Gdk.KEY_ISO_Enter) {
// If we get an 'enter' keypress and we have a selected
// row, we do not want to propagate the event.
let row = this._list.get_selected_row();
+
+ log('enter, row: ' + row);
+
if (this.visible && row) {
row.activate();
- return true;
} else {
- return false;
+ controller.forward(this._entry);
}
- }
-
- if (keyval === Gdk.KEY_KP_Up ||
- keyval === Gdk.KEY_Up ||
- keyval === Gdk.KEY_KP_Down ||
- keyval === Gdk.KEY_Down) {
+ } else if (keyval === Gdk.KEY_KP_Up ||
+ keyval === Gdk.KEY_Up ||
+ keyval === Gdk.KEY_KP_Down ||
+ keyval === Gdk.KEY_Down) {
- let length = this._list.get_children().length;
+ let length = this._numResults;
if (length === 0) {
- return false;
+ controller.forward(this._entry);
}
let direction = (keyval === Gdk.KEY_KP_Up || keyval === Gdk.KEY_Up) ? -1 : 1;
@@ -93,10 +97,18 @@ export class SearchPopover extends Gtk.Popover {
} else {
this._list.unselect_all();
}
- return true;
+ } else {
+ if (keyval === Gdk.KEY_space) {
+ /* forwarding space seems to not work for some reason,
+ * work around by manually injecting a space into the entry string
+ */
+ this._entry.set_text(this._entry.text + ' ');
+ this._entry.set_position(this._entry.text.length);
+ } else {
+ this._entry.grab_focus();
+ controller.forward(this._entry);
+ }
}
-
- return false;
}
/* Selects given row and ensures that it is visible. */
diff --git a/src/sendToDialog.js b/src/sendToDialog.js
index 435b7b37..caa4ae96 100644
--- a/src/sendToDialog.js
+++ b/src/sendToDialog.js
@@ -124,7 +124,7 @@ export class SendToDialog extends Gtk.Dialog {
});
/* Hide the list box if it is empty */
- if (this._list.get_children().length == 0) {
+ if (!this._list.get_first_child()) {
this._scrolledWindow.hide();
}
}
@@ -153,7 +153,7 @@ export class SendToDialog extends Gtk.Dialog {
}
_getOSMURI() {
- let view = this._mapView.view;
+ let viewport = this._mapView.map.viewport;
let place = this._place;
let base = 'https://openstreetmap.org';
@@ -165,16 +165,15 @@ export class SendToDialog extends Gtk.Dialog {
return '%s?mlat=%f&mlon=%f&zoom=%d'.format(base,
this._location.latitude,
this._location.longitude,
- view.zoom_level);
+ viewport.zoom_level);
}
}
_copySummary() {
let summary = '%s\n%s'.format(this._getSummary(), this._getOSMURI());
+ let clipboard = this.get_clipboard();
- let display = Gdk.Display.get_default();
- let clipboard = Gtk.Clipboard.get_default(display);
- clipboard.set_text(summary, -1);
+ clipboard.set(summary);
this.response(SendToDialog.Response.SUCCESS);
}
@@ -188,7 +187,7 @@ export class SendToDialog extends Gtk.Dialog {
Gio.app_info_launch_default_for_uri(uri, this._getAppLaunchContext());
} catch(e) {
Utils.showDialog(_("Failed to open URI"), Gtk.MessageType.ERROR,
- this.get_toplevel());
+ this);
Utils.debug('failed to open URI: %s'.format(e.message));
}
@@ -196,20 +195,17 @@ export class SendToDialog extends Gtk.Dialog {
}
_getAppLaunchContext() {
- let timestamp = Gtk.get_current_event_time();
- let display = Gdk.Display.get_default();
let ctx = Gdk.Display.get_default().get_app_launch_context();
- let screen = display.get_default_screen();
- ctx.set_timestamp(timestamp);
- ctx.set_screen(screen);
+ // GdkAppLaunchContext uses second-precision timestamps
+ ctx.set_timestamp(GLib.get_real_time() / 1000000);
return ctx;
}
_activateRow(row) {
if (row === this._weatherRow || row === this._clocksRow) {
- let timestamp = Gtk.get_current_event_time();
+ let timestamp = GLib.get_real_time() / 1000000;
let action;
let appId;
diff --git a/src/shapeLayer.js b/src/shapeLayer.js
index 18ac5170..c188e8d6 100644
--- a/src/shapeLayer.js
+++ b/src/shapeLayer.js
@@ -17,9 +17,10 @@
* Author: Hashem Nasarat <hashem riseup net>
*/
-import Champlain from 'gi://Champlain';
import Gio from 'gi://Gio';
import GObject from 'gi://GObject';
+import Gtk from 'gi://Gtk';
+import Shumate from 'gi://Shumate';
import {GeoJSONShapeLayer} from './geoJSONShapeLayer.js';
import * as Utils from './utils.js';
@@ -53,8 +54,8 @@ export class ShapeLayer extends GObject.Object {
null
).get_attribute_string(Gio.FILE_ATTRIBUTE_STANDARD_DISPLAY_NAME);
- this._markerLayer = new Champlain.MarkerLayer({
- selection_mode: Champlain.SelectionMode.SINGLE
+ this._markerLayer = new Shumate.MarkerLayer({
+ selection_mode: Gtk.SelectionMode.SINGLE
});
this._mapSource = null;
}
@@ -69,10 +70,10 @@ export class ShapeLayer extends GObject.Object {
set visible(v) {
if (v && !this._visible) {
- this._mapView.view.add_overlay_source(this._mapSource, 255);
+ this._mapView.view.add_layer(this._overlayLayer);
this._markerLayer.show_all_markers();
} else if (!v && this._visible) {
- this._mapView.view.remove_overlay_source(this._mapSource);
+ this._mapView.view.remove_layer(this._overlayLayer);
this._markerLayer.hide_all_markers();
}
this._visible = v;
@@ -95,8 +96,8 @@ export class ShapeLayer extends GObject.Object {
if (!status)
throw new Error(_("failed to load file"));
this._parseContent();
- this._mapView.view.add_layer(this._markerLayer);
- this._mapView.view.add_overlay_source(this._mapSource, 255);
+ this._mapView.map.add_layer(this._markerLayer);
+ this._mapView.map.add_layer(this._overlayLayer);
} catch (e) {
Utils.debug(e);
error = true;
@@ -110,8 +111,8 @@ export class ShapeLayer extends GObject.Object {
}
unload() {
- this._mapView.view.remove_layer(this._markerLayer);
- this._mapView.view.remove_overlay_source(this._mapSource);
+ this._mapView.map.remove_layer(this._markerLayer);
+ this._mapView.map.remove_layer(this._overlayLayer);
}
}
diff --git a/src/sidebar.js b/src/sidebar.js
index 372ca737..5a44c2a8 100644
--- a/src/sidebar.js
+++ b/src/sidebar.js
@@ -129,13 +129,16 @@ export class Sidebar extends Gtk.Revealer {
}
_initQuerySignals() {
+ this._numRouteEntries = 0;
this._query.connect('point-added', (obj, point, index) => {
this._createRouteEntry(index, point);
+ this._numRouteEntries++;
});
this._query.connect('point-removed', (obj, point, index) => {
let row = this._entryList.get_row_at_index(index);
- row.destroy();
+ this._entryList.remove(row);
+ this._numRouteEntries--;
});
}
@@ -148,7 +151,7 @@ export class Sidebar extends Gtk.Revealer {
let type;
if (index === 0)
type = RouteEntry.Type.FROM;
- else if (index === this._entryList.get_children().length)
+ else if (index === this._numRouteEntries)
type = RouteEntry.Type.TO;
else
type = RouteEntry.Type.VIA;
@@ -158,7 +161,8 @@ export class Sidebar extends Gtk.Revealer {
mapView: this._mapView });
// add handler overriding tab focus behavior on route entries
- routeEntry.entry.connect('focus', this._onRouteEntryFocus.bind(this));
+ // TODO: how to set up tab handling using GTK4?
+ //routeEntry.entry.connect('focus', this._onRouteEntryFocus.bind(this));
// add handler for
routeEntry.entry.connect('notify::place', () => {
this._onRouteEntrySelectedPlace(routeEntry.entry);
@@ -167,7 +171,7 @@ export class Sidebar extends Gtk.Revealer {
if (type === RouteEntry.Type.FROM) {
routeEntry.button.connect('clicked', () => {
- let lastIndex = this._entryList.get_children().length;
+ let lastIndex = this._numRouteEntries;
this._query.addPoint(lastIndex - 1);
// focus on the newly added point's entry
this._entryList.get_row_at_index(lastIndex - 1).get_child().entry.grab_focus();
@@ -175,7 +179,7 @@ export class Sidebar extends Gtk.Revealer {
this.connect('notify::child-revealed', () => {
if (this.child_revealed)
- routeEntry.entry.grab_focus_without_selecting();
+ routeEntry.entry.grab_focus();
});
} else if (type === RouteEntry.Type.VIA) {
routeEntry.button.connect('clicked', () => {
@@ -216,12 +220,12 @@ export class Sidebar extends Gtk.Revealer {
}
_onRouteEntrySelectedPlace(entry) {
- let index = this._getIndexForRouteEntry(entry);
+ let [index, numEntries] = this._getIndexForRouteEntryAndNumEntries(entry);
/* if a new place is selected and it's not the last entry, focus next
* entry
*/
- if (entry.place && index < this._entryList.get_children().length - 1) {
+ if (entry.place && index < numEntries - 1) {
let nextPlaceEntry =
this._entryList.get_row_at_index(index + 1).get_child().entry;
@@ -230,15 +234,27 @@ export class Sidebar extends Gtk.Revealer {
}
}
- _getIndexForRouteEntry(entry) {
- for (let i = 0; i < this._entryList.get_children().length; i++) {
- let routeEntry = this._entryList.get_row_at_index(i).get_child();
+ _getIndexForRouteEntryAndNumEntries(entry) {
+ let index = 0;
+ let foundIndex = -1;
+
+ for (let item of this._entryList) {
+ let routeEntry = item.get_child();
if (routeEntry.entry === entry)
- return i;
+ foundIndex = index;
+
+ index++;
}
- return -1;
+ return [foundIndex, index];
+ }
+
+ // this is needed to be called on shutdown to avoid a GTK warning
+ unparentSearchPopovers() {
+ for (let item of this._entryList) {
+ item.get_child().entry.popover.unparent();
+ }
}
_initInstructionList() {
@@ -266,8 +282,13 @@ export class Sidebar extends Gtk.Revealer {
transitPlan.connect('no-more-results', () => {
// set the "load more" row to indicate no more results
- let numRows = this._transitOverviewListBox.get_children().length;
- let loadMoreRow = this._transitOverviewListBox.get_row_at_index(numRows - 2);
+ let loadMoreRow;
+
+ for (let row of this._transitOverviewListBox) {
+ if (row instanceof TransitMoreRow)
+ loadMoreRow = row;
+ }
+
loadMoreRow.showNoMore();
});
@@ -361,10 +382,23 @@ export class Sidebar extends Gtk.Revealer {
this._errorLabel.label = msg;
}
+ _clearListBox(listBox) {
+ let rows = [];
+
+ for (let row of listBox) {
+ if (row instanceof Gtk.ListBoxRow)
+ rows.push(row);
+ }
+
+ for (let row of rows) {
+ listBox.remove(row);
+ }
+ }
+
_clearTransitOverview() {
let listBox = this._transitOverviewListBox;
- listBox.forall(listBox.remove.bind(listBox));
+ this._clearListBox(listBox);
this._instructionStack.visible_child = this._transitWindow;
this._timeInfo.label = '';
this._distanceInfo.label = '';
@@ -372,7 +406,8 @@ export class Sidebar extends Gtk.Revealer {
_clearTransitItinerary() {
let listBox = this._transitItineraryListBox;
- listBox.forall(listBox.remove.bind(listBox));
+
+ this._clearListBox(listBox);
}
_updateTransitAttribution() {
@@ -469,8 +504,8 @@ export class Sidebar extends Gtk.Revealer {
_clearInstructions() {
let listBox = this._instructionList;
- listBox.forall(listBox.remove.bind(listBox));
+ this._clearListBox(listBox);
this._instructionStack.visible_child = this._instructionWindow;
this._timeInfo.label = '';
this._distanceInfo.label = '';
@@ -515,12 +550,12 @@ export class Sidebar extends Gtk.Revealer {
this._query.thaw_notify();
}
- _onDragDrop(row, context, x, y, time) {
+ _onDragDrop(row) {
let srcIndex = this._query.points.indexOf(this._draggedPoint);
let destIndex = row.get_index();
this._reorderRoutePoints(srcIndex, destIndex);
- Gtk.drag_finish(context, true, false, time);
+
return true;
}
@@ -546,7 +581,7 @@ export class Sidebar extends Gtk.Revealer {
}
// Drag ends, show the dragged row again.
- _onDragEnd(context, row) {
+ _onDragEnd(row) {
this._draggedPoint = null;
// Restore to natural height
@@ -555,14 +590,10 @@ export class Sidebar extends Gtk.Revealer {
}
// Drag begins, set the correct drag icon and hide the dragged row.
- _onDragBegin(context, row) {
+ _onDragBegin(source, row) {
let routeEntry = row.get_child();
- let width = row.get_allocated_width();
- let height = row.get_allocated_height();
- let surface = new Cairo.ImageSurface(Cairo.Format.ARGB32, width, height);
- let cr = new Cairo.Context(surface)
+ let {x, y, width, height} = row.get_allocation();
- row.draw(cr);
this._draggedPoint = routeEntry.point;
// Set a fixed height on the row to prevent the sidebar height
@@ -570,32 +601,32 @@ export class Sidebar extends Gtk.Revealer {
row.height_request = height;
row.get_child().hide();
- Gtk.drag_set_icon_surface(context, surface);
+ let paintable = new Gtk.WidgetPaintable(row);
+
+ source.set_icon(paintable, 0, 0);
}
// Set up drag and drop between RouteEntrys. The drag source is from a
// GtkEventBox that contains the start/end icon next in the entry. And
// the drag destination is the ListBox row.
_initRouteDragAndDrop(routeEntry) {
- let dragIcon = routeEntry.iconEventBox;
+ let dragIcon = routeEntry.icon;
let row = routeEntry.get_parent();
+ let dragSource = new Gtk.DragSource();
+
+ dragIcon.add_controller(dragSource);
- dragIcon.drag_source_set(Gdk.ModifierType.BUTTON1_MASK,
- null,
- Gdk.DragAction.MOVE);
- dragIcon.drag_source_add_image_targets();
+ dragSource.connect('drag-begin',
+ (source, drag, widget) => this._onDragBegin(source, row));
+ dragSource.connect('drag-end',
+ (source, dele, data) => this._onDragEnd(row));
- row.drag_dest_set(Gtk.DestDefaults.MOTION,
- null,
- Gdk.DragAction.MOVE);
- row.drag_dest_add_image_targets();
+ let dropTarget = Gtk.DropTarget.new(RouteEntry, Gdk.DragAction.MOVE);
- dragIcon.connect('drag-begin', (icon, context) => this._onDragBegin(context, row));
- dragIcon.connect('drag-end', (icon, context) => this._onDragEnd(context, row));
+ row.add_controller(dropTarget);
- row.connect('drag-leave', this._dragUnhighlightRow.bind(this, row));
- row.connect('drag-motion', this._onDragMotion.bind(this));
- row.connect('drag-drop', this._onDragDrop.bind(this));
+ dropTarget.connect('drop',
+ (target, value, x, y, data) => this._onDragDrop(target));
}
}
diff --git a/src/storedRoute.js b/src/storedRoute.js
index 1fbfef3f..094657d0 100644
--- a/src/storedRoute.js
+++ b/src/storedRoute.js
@@ -20,9 +20,9 @@
* Author: Jonas Danielsson <jonas threetimestwo org>
*/
-import Champlain from 'gi://Champlain';
import GObject from 'gi://GObject';
import Gtk from 'gi://Gtk';
+import Shumate from 'gi://Shumate';
import {Place} from './place.js';
import {Route, TurnPoint} from './route.js';
@@ -175,15 +175,15 @@ export class StoredRoute extends Place {
prop.path = prop.path.map((coordinate) => {
let lat = coordinate.latitude;
let lon = coordinate.longitude;
- return new Champlain.Coordinate({ latitude: lat,
- longitude: lon });
+ return new Shumate.Coordinate({ latitude: lat,
+ longitude: lon });
});
prop.turnPoints = prop.turnPoints.map((turnPoint) => {
let lat = turnPoint.coordinate.latitude;
let lon = turnPoint.coordinate.longitude;
- let coordinate = new Champlain.Coordinate({ latitude: lat,
- longitude: lon });
+ let coordinate = new Shumate.Coordinate({ latitude: lat,
+ longitude: lon });
return new TurnPoint({
coordinate: coordinate,
diff --git a/src/transitArrivalMarker.js b/src/transitArrivalMarker.js
index 506b3905..8a0c1560 100644
--- a/src/transitArrivalMarker.js
+++ b/src/transitArrivalMarker.js
@@ -49,15 +49,8 @@ export class TransitArrivalMarker extends MapMarker {
blue: bgBlue,
alpha: 1.0
});
- let actor =
- this._actorFromIconName('maps-point-end-symbolic', 0, color);
-
- this.add_actor(actor);
- }
-
- get anchor() {
- return { x: Math.floor(this.width / 2) - 1,
- y: Math.floor(this.height / 2) - 1 };
+ this._image.paintable =
+ this._paintableFromIconName('maps-point-end-symbolic', 16, color);
}
}
diff --git a/src/transitArrivalRow.js b/src/transitArrivalRow.js
index 023134ed..05e00e13 100644
--- a/src/transitArrivalRow.js
+++ b/src/transitArrivalRow.js
@@ -41,20 +41,14 @@ export class TransitArrivalRow extends Gtk.ListBoxRow {
this._arrivalLabel.label = Transit.getArrivalLabel(lastLeg);
this._timeLabel.label = lastLeg.prettyPrintArrivalTime();
- this._eventBox.connect('event', (widget, event) => {
- this._onEvent(event, lastLeg.toCoordinate);
- return true;
- });
+ this._buttonPressGesture = new Gtk.GestureSingle();
+ this.add_controller(this._buttonPressGesture);
+ this._buttonPressGesture.connect('begin',
+ () => this._onPress(lastLeg.toCoordinate));
}
- _onEvent(event, coord) {
- let [isButton, button] = event.get_button();
- let type = event.get_event_type();
-
- if (isButton && button === 1 && type === Gdk.EventType.BUTTON_PRESS) {
- this._mapView.view.zoom_level = 16;
- this._mapView.view.center_on(coord[0], coord[1]);
- }
+ _onPress(coord) {
+ this._mapView.map.go_to_full(coord[0], coord[1], 16);
}
}
@@ -62,6 +56,5 @@ GObject.registerClass({
Template: 'resource:///org/gnome/Maps/ui/transit-arrival-row.ui',
InternalChildren: ['arrivalLabel',
'timeLabel',
- 'eventBox',
'separator']
}, TransitArrivalRow);
diff --git a/src/transitBoardMarker.js b/src/transitBoardMarker.js
index 462727c4..2bc73182 100644
--- a/src/transitBoardMarker.js
+++ b/src/transitBoardMarker.js
@@ -20,7 +20,6 @@
*/
import Cairo from 'cairo';
-import Clutter from 'gi://Clutter';
import Gdk from 'gi://Gdk';
import GObject from 'gi://GObject';
import Gtk from 'gi://Gtk';
@@ -33,7 +32,7 @@ import * as TransitPlan from './transitPlan.js';
import * as Utils from './utils.js';
const ICON_SIZE = 12;
-const ACTOR_SIZE = 20;
+const MARKER_SIZE = 20;
/* threashhold for route color luminance when we consider it more or less
* as white, and draw an outline around the label
@@ -52,10 +51,11 @@ export class TransitBoardMarker extends MapMarker {
params.place = new Place({ location: location });
super(params);
- this.add_actor(this._createActor(leg));
+ this._image.pixel_size = MARKER_SIZE;
+ this._image.paintable = this._createPaintable(leg);
}
- /* Creates a Clutter actor for the given transit leg, showing the
+ /* Creates a Gdk.Paintable for the given transit leg, showing the
* corresponding transit type icon and rendered inside a circle using the
* foreground color of the icon taken from the transit legs text color
* attribute and background color taken from the transit legs color
@@ -64,7 +64,7 @@ export class TransitBoardMarker extends MapMarker {
* background color above a threshold to improve readability against the
* map background.
*/
- _createActor(leg) {
+ _createPaintable(leg) {
try {
let bgColor = leg.color ?? TransitPlan.DEFAULT_ROUTE_COLOR;
let fgColor =
@@ -84,45 +84,37 @@ export class TransitBoardMarker extends MapMarker {
blue: fgBlue,
alpha: 1.0
});
- let theme = Gtk.IconTheme.get_default();
- let info = theme.lookup_icon(leg.iconName, ICON_SIZE,
- Gtk.IconLookupFlags.FORCE_SIZE);
- let pixbuf = info.load_symbolic(fgRGBA, null, null, null)[0];
- let canvas = new Clutter.Canvas({ width: ACTOR_SIZE,
- height: ACTOR_SIZE });
-
-
- canvas.connect('draw', (canvas, cr) => {
- cr.setOperator(Cairo.Operator.CLEAR);
- cr.paint();
- cr.setOperator(Cairo.Operator.OVER);
-
- cr.setSourceRGB(bgRed, bgGreen, bgBlue);
- cr.arc(ACTOR_SIZE / 2, ACTOR_SIZE / 2, ACTOR_SIZE / 2,
- 0, Math.PI * 2);
- cr.fillPreserve();
-
- Gdk.cairo_set_source_pixbuf(cr, pixbuf,
- (ACTOR_SIZE - pixbuf.get_width()) / 2,
- (ACTOR_SIZE - pixbuf.get_height()) / 2);
- cr.paint();
-
- if (hasOutline) {
- cr.setSourceRGB(fgRed, fgGreen, fgBlue);
- cr.setLineWidth(1);
- cr.stroke();
- }
-
- this._surface = cr.getTarget();
- });
-
- let actor = new Clutter.Actor();
-
- actor.set_content(canvas);
- actor.set_size(ACTOR_SIZE, ACTOR_SIZE);
- canvas.invalidate();
-
- return actor;
+ let paintable = this._paintableFromIconName(leg.iconName,
+ ICON_SIZE, fgRGBA);
+
+ let surface = new Cairo.ImageSurface(Cairo.Format.ARGB32,
+ MARKER_SIZE, MARKER_SIZE);
+ let cr = new Cairo.Context(surface);
+ let pixbuf = Gdk.pixbuf_get_from_texture(paintable);
+
+ cr.setOperator(Cairo.Operator.CLEAR);
+ cr.paint();
+ cr.setOperator(Cairo.Operator.OVER);
+
+ cr.setSourceRGB(bgRed, bgGreen, bgBlue);
+ cr.arc(MARKER_SIZE / 2, MARKER_SIZE / 2, MARKER_SIZE / 2,
+ 0, Math.PI * 2);
+ cr.fillPreserve();
+
+ Gdk.cairo_set_source_pixbuf(cr, pixbuf,
+ (MARKER_SIZE - pixbuf.get_width()) / 2,
+ (MARKER_SIZE - pixbuf.get_height()) / 2);
+ cr.paint();
+
+ if (hasOutline) {
+ cr.setSourceRGB(fgRed, fgGreen, fgBlue);
+ cr.setLineWidth(1);
+ cr.stroke();
+ }
+
+ return Gdk.Texture.new_for_pixbuf(
+ Gdk.pixbuf_get_from_surface(surface, 0, 0,
+ MARKER_SIZE, MARKER_SIZE));
} catch (e) {
Utils.debug('Failed to load image: %s'.format(e.message));
return null;
diff --git a/src/transitLegRow.js b/src/transitLegRow.js
index 371dacab..cde05ee4 100644
--- a/src/transitLegRow.js
+++ b/src/transitLegRow.js
@@ -119,29 +119,22 @@ export class TransitLegRow extends Gtk.ListBoxRow {
}
});
- this._eventBox.connect('event', (widget, event) => {
- this._handleEventBox(event);
- return true;
- });
+ this._buttonPressGesture = new Gtk.GestureSingle();
+ this.add_controller(this._buttonPressGesture);
+ this._buttonPressGesture.connect('begin', () => this._onPress());
this._isExpanded = false;
}
- // Handle events received on the EventBox for expanding when clicking
- _handleEventBox(event) {
- let [isButton, button] = event.get_button();
- let type = event.get_event_type();
-
- if (isButton && button === 1 && type === Gdk.EventType.BUTTON_PRESS) {
- if (this._isExpanded) {
- this._collaps();
- } else {
- this._mapView.view.zoom_level = 16;
- this._mapView.view.center_on(this._leg.fromCoordinate[0],
- this._leg.fromCoordinate[1]);
- if (this._hasIntructions())
- this._expand();
- }
+ _onPress() {
+ if (this._isExpanded) {
+ this._collaps();
+ } else {
+ this._mapView.map.go_to_full(this._leg.fromCoordinate[0],
+ this._leg.fromCoordinate[1],
+ 16);
+ if (this._hasIntructions())
+ this._expand();
}
}
@@ -207,6 +200,5 @@ GObject.registerClass({
'detailsRevealer',
'agencyLabel',
'collapsButton',
- 'instructionList',
- 'eventBox']
+ 'instructionList']
}, TransitLegRow);
diff --git a/src/transitOptionsPanel.js b/src/transitOptionsPanel.js
index ee2abaa2..28c953f5 100644
--- a/src/transitOptionsPanel.js
+++ b/src/transitOptionsPanel.js
@@ -63,17 +63,19 @@ export class TransitOptionsPanel extends Gtk.Grid {
this._onTransitTimeOptionsComboboxChanged.bind(this));
this._transitTimeEntry.connect('activate',
this._onTransitTimeEntryActivated.bind(this));
+ this._eventControllerFocus = new Gtk.EventControllerFocus();
+ this._transitTimeEntry.add_controller(this._eventControllerFocus);
/* trigger an update of the query time as soon as focus leave the time
* entry, to allow the user to enter a time before selecting start
* and destination without having to press enter */
- this._transitTimeEntry.connect('focus-out-event',
+ this._eventControllerFocus.connect('leave',
this._onTransitTimeEntryActivated.bind(this));
- this._transitDateButton.popover.get_child().connect('day-selected-double-click',
+ this._transitDateButton.popover.get_child().connect('day-selected',
this._onTransitDateCalenderDaySelected.bind(this));
- this._transitDateButton.connect('toggled',
- this._onTransitDateButtonToogled.bind(this));
- this._transitParametersMenuButton.connect('toggled',
- this._onTransitParametersToggled.bind(this))
+ this._transitDateButton.popover.connect('closed',
+ this._onTransitDateClosed.bind(this));
+ this._transitParametersMenuButton.popover.connect('closed',
+ this._onTransitParametersClosed.bind(this))
}
_onTransitTimeOptionsComboboxChanged() {
@@ -125,8 +127,7 @@ export class TransitOptionsPanel extends Gtk.Grid {
_updateTransitDateButton(date) {
let calendar = this._transitDateButton.popover.get_child();
- calendar.select_month(date.get_month() - 1, date.get_year());
- calendar.select_day(date.get_day_of_month());
+ calendar.select_day(date);
this._transitDateButton.label =
/*
* Translators: this is a format string giving the equivalent to
@@ -153,9 +154,8 @@ export class TransitOptionsPanel extends Gtk.Grid {
}
}
- _onTransitDateButtonToogled() {
- if (!this._transitDateButton.active)
- this._onTransitDateCalenderDaySelected();
+ _onTransitDateClosed() {
+ this._onTransitDateCalenderDaySelected();
}
_createTransitOptions() {
@@ -188,14 +188,12 @@ export class TransitOptionsPanel extends Gtk.Grid {
return options;
}
- _onTransitParametersToggled() {
- if (!this._transitParametersMenuButton.active) {
- let options = this._createTransitOptions();
+ _onTransitParametersClosed() {
+ let options = this._createTransitOptions();
- if (!TransitOptions.equals(options, this._lastOptions)) {
- this._query.transitOptions = options;
- this._lastOptions = options;
- }
+ if (!TransitOptions.equals(options, this._lastOptions)) {
+ this._query.transitOptions = options;
+ this._lastOptions = options;
}
}
}
diff --git a/src/transitPrintLayout.js b/src/transitPrintLayout.js
index 4693edde..b4158cee 100644
--- a/src/transitPrintLayout.js
+++ b/src/transitPrintLayout.js
@@ -20,10 +20,10 @@
*/
import Cairo from 'cairo';
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
+import Gdk from 'gi://Gdk';
import GObject from 'gi://GObject';
import Pango from 'gi://Pango';
+import Shumate from 'gi://Shumate';
import * as Color from './color.js';
import * as Gfx from './gfx.js';
@@ -35,10 +35,10 @@ import {TransitBoardMarker} from './transitBoardMarker.js';
import {TransitWalkMarker} from './transitWalkMarker.js';
// stroke color for walking paths
-const _STROKE_COLOR = new Clutter.Color({ red: 0,
- blue: 0,
- green: 0,
- alpha: 255 });
+const _STROKE_COLOR = new Gdk.RGBA({ red: 0.0,
+ blue: 0.0,
+ green: 0.0,
+ alpha: 1.0 });
const _STROKE_WIDTH = 5.0;
// All following constants are ratios of surface size to page size
diff --git a/src/transitRouteLabel.js b/src/transitRouteLabel.js
index b8eebe2d..eb99a90c 100644
--- a/src/transitRouteLabel.js
+++ b/src/transitRouteLabel.js
@@ -22,6 +22,7 @@
import Cairo from 'cairo';
import GLib from 'gi://GLib';
import GObject from 'gi://GObject';
+import Graphene from 'gi://Graphene';
import Gtk from 'gi://Gtk';
import * as Color from './color.js';
@@ -52,7 +53,6 @@ export class TransitRouteLabel extends Gtk.Label {
super(params);
this._setLabel(leg, compact);
- this.connect('draw', this._onDraw.bind(this));
}
_setLabel(leg, compact) {
@@ -103,21 +103,29 @@ export class TransitRouteLabel extends Gtk.Label {
this.label = '<span foreground="#%s">%s</span>'.format(
textColor,
GLib.markup_escape_text(label, -1));
+
+ this.queue_draw();
}
/* I didn't find any easy/obvious way to override widget background color
* and getting rounded corner just using CSS styles, so doing a custom
* Cairo drawing of a "roundrect"
*/
- _onDraw(widget, cr) {
- let width = widget.get_allocated_width();
- let height = widget.get_allocated_height();
+ vfunc_snapshot(snapshot) {
+ let {x, y, width, height} = this.get_allocation();
+ let rect = new Graphene.Rect();
+
+ log('snapshot: ' + width + ', ' + height);
+
+ rect.init(0, 0, width, height);
+ let cr = snapshot.append_cairo(rect);
+
+ // clip off the badge, this seems to avoid some extra space at right/bottom with the CSS
Gfx.drawColoredBagde(cr, this._color,
this._hasOutline ? this._textColor : null,
- 0, 0, width, height);
-
- return false;
+ 0, 0, width - 3, height - 3);
+ super.vfunc_snapshot(snapshot);
}
}
diff --git a/src/transitWalkMarker.js b/src/transitWalkMarker.js
index c1221391..b9da6ee2 100644
--- a/src/transitWalkMarker.js
+++ b/src/transitWalkMarker.js
@@ -62,15 +62,8 @@ export class TransitWalkMarker extends MapMarker {
blue: bgBlue,
alpha: 1.0
});
- let actor =
- this._actorFromIconName('maps-point-start-symbolic', 0, color);
-
- this.add_actor(actor);
- }
-
- get anchor() {
- return { x: Math.floor(this.width / 2) - 1,
- y: Math.floor(this.height / 2) - 1 };
+ this._image.paintable =
+ this._paintableFromIconName('maps-point-start-symbolic', 16, color);
}
}
diff --git a/src/transitplugins/openTripPlanner.js b/src/transitplugins/openTripPlanner.js
index 9c80e910..ad2160fc 100644
--- a/src/transitplugins/openTripPlanner.js
+++ b/src/transitplugins/openTripPlanner.js
@@ -21,8 +21,8 @@
import gettext from 'gettext';
-import Champlain from 'gi://Champlain';
import GLib from 'gi://GLib';
+import Shumate from 'gi://Shumate';
import Soup from 'gi://Soup';
import {Application} from '../application.js';
@@ -1140,8 +1140,8 @@ export class OpenTripPlanner {
}
_createTurnpoint(step) {
- let coordinate = new Champlain.Coordinate({ latitude: step.lat,
- longitude: step.lon });
+ let coordinate = new Shumate.Coordinate({ latitude: step.lat,
+ longitude: step.lon });
let turnpoint = new TurnPoint({
coordinate: coordinate,
type: this._getTurnpointType(step),
diff --git a/src/transitplugins/opendataCH.js b/src/transitplugins/opendataCH.js
index e9431005..6ccab174 100644
--- a/src/transitplugins/opendataCH.js
+++ b/src/transitplugins/opendataCH.js
@@ -27,8 +27,8 @@
* https://transport.opendata.ch/docs.html
*/
-import Champlain from 'gi://Champlain';
import GLib from 'gi://GLib';
+import Shumate from 'gi://Shumate';
import Soup from 'gi://Soup';
import {Application} from '../application.js';
@@ -391,18 +391,18 @@ export class OpendataCH {
section.journey.passList.forEach((pass) => {
let coordinate = pass.location.coordinate;
- polyline.push(new Champlain.Coordinate({ latitude: coordinate.x,
- longitude: coordinate.y }));
+ polyline.push(new Shumate.Coordinate({ latitude: coordinate.x,
+ longitude: coordinate.y }));
});
} else {
let [departureX, departureY, arrivalX, arrivalY] =
this._getCoordsForSection(section, index, sections);
polyline =
- [new Champlain.Coordinate({ latitude: departureX,
- longitude: departureY }),
- new Champlain.Coordinate({ latitude: arrivalX,
- longitude: arrivalY })];
+ [new Shumate.Coordinate({ latitude: departureX,
+ longitude: departureY }),
+ new Shumate.Coordinate({ latitude: arrivalX,
+ longitude: arrivalY })];
}
return polyline;
diff --git a/src/transitplugins/resrobot.js b/src/transitplugins/resrobot.js
index d019640e..57931818 100644
--- a/src/transitplugins/resrobot.js
+++ b/src/transitplugins/resrobot.js
@@ -27,8 +27,8 @@
* https://www.trafiklab.se/api/resrobot-reseplanerare/dokumentation/sokresa
*/
-import Champlain from 'gi://Champlain';
import GLib from 'gi://GLib';
+import Shumate from 'gi://Shumate';
import Soup from 'gi://Soup';
import {Application} from '../application.js';
@@ -487,15 +487,15 @@ export class Resrobot {
polyline = [];
leg.Stops.Stop.forEach((stop) => {
- polyline.push(new Champlain.Coordinate({ latitude: stop.lat,
- longitude: stop.lon }));
+ polyline.push(new Shumate.Coordinate({ latitude: stop.lat,
+ longitude: stop.lon }));
});
} else {
polyline =
- [new Champlain.Coordinate({ latitude: leg.Origin.lat,
- longitude: leg.Origin.lon }),
- new Champlain.Coordinate({ latitude: leg.Destination.lat,
- longitude: leg.Destination.lon })];
+ [new Shumate.Coordinate({ latitude: leg.Origin.lat,
+ longitude: leg.Origin.lon }),
+ new Shumate.Coordinate({ latitude: leg.Destination.lat,
+ longitude: leg.Destination.lon })];
}
return polyline;
diff --git a/src/turnPointMarker.js b/src/turnPointMarker.js
index 5f0d9fda..87868b30 100644
--- a/src/turnPointMarker.js
+++ b/src/turnPointMarker.js
@@ -19,7 +19,6 @@
* Author: Dario Di Nucci <linkin88mail gmail com>
*/
-import Clutter from 'gi://Clutter';
import Gdk from 'gi://Gdk';
import GObject from 'gi://GObject';
@@ -64,18 +63,16 @@ export class TurnPointMarker extends MapMarker {
this._queryPoint = queryPoint;
- let actor;
if (this._queryPoint) {
- this.draggable = true;
- this.connect('drag-finish', () => this._onMarkerDrag());
- actor = this._actorFromIconName(turnPoint.iconName, 0);
+ this._image.paintable =
+ this._paintableFromIconName(turnPoint.iconName, 16);
} else {
let color = this._getColor(transitLeg);
- actor = this._actorFromIconName('maps-point-end-symbolic',
- 0,
+ this._image.paintable =
+ this._paintableFromIconName('maps-point-end-symbolic',
+ 16,
color);
}
- this.add_actor(actor);
}
_getColor(transitLeg) {
@@ -102,7 +99,6 @@ export class TurnPointMarker extends MapMarker {
let latitude = this.latitude;
let longitude = this.longitude;
- view.goto_animation_mode = Clutter.AnimationMode.LINEAR;
view.goto_duration = 0;
Utils.once(view, 'animation-completed', () => {
@@ -112,15 +108,6 @@ export class TurnPointMarker extends MapMarker {
view.go_to(this.latitude, this.longitude);
}
-
- _onMarkerDrag() {
- let query = Application.routeQuery;
- let place =
- new Place({ location: new Location({ latitude: this.latitude.toFixed(5),
- longitude: this.longitude.toFixed(5) }) });
-
- this._queryPoint.place = place;
- }
}
GObject.registerClass(TurnPointMarker);
diff --git a/src/userLocationMarker.js b/src/userLocationMarker.js
index 55d9d85f..f179ed21 100644
--- a/src/userLocationMarker.js
+++ b/src/userLocationMarker.js
@@ -19,47 +19,49 @@
* Author: Damián Nohales <damiannohales gmail com>
*/
-import Champlain from 'gi://Champlain';
-import Clutter from 'gi://Clutter';
import GObject from 'gi://GObject';
+import Shumate from 'gi://Shumate';
import {MapMarker} from './mapMarker.js';
-export class AccuracyCircleMarker extends Champlain.Point {
+export class AccuracyCircleMarker extends Shumate.Point {
constructor(params) {
let place = params.place;
delete params.place;
+ // TODO: set color using CSS...
+ /*
params.color = new Clutter.Color({ red: 0,
blue: 255,
green: 0,
alpha: 25 });
+ */
params.latitude = place.location.latitude;
params.longitude = place.location.longitude;
- params.reactive = false;
super(params);
this._place = place;
}
- refreshGeometry(view) {
+ refreshGeometry(mapView) {
this.latitude = this._place.location.latitude;
this.longitude = this._place.location.longitude;
- let zoom = view.zoom_level;
- let source = view.map_source;
+ let zoom = mapView.map.viewport.zoom_level;
+ let source = mapView.mapSource;
let metersPerPixel = source.get_meters_per_pixel(zoom,
this.latitude,
this.longitude);
let size = this._place.location.accuracy * 2 / metersPerPixel;
+ let {x, y, width, height} = mapView.get_allocation();
- if (size > view.width || size > view.height)
- this.hide();
+ if (size > width || size > height)
+ this.visible = false;
else {
this.size = size;
- this.show();
+ this.visible = true;
}
}
}
@@ -73,14 +75,15 @@ export class UserLocationMarker extends MapMarker {
this._accuracyMarker = new AccuracyCircleMarker({ place: this.place });
this.connect('notify::view-zoom-level',
- () => this._accuracyMarker.refreshGeometry(this._view));
- this._view.connect('notify::width',
- () => this._accuracyMarker.refreshGeometry(this._view));
- this._view.connect('notify::height',
- () => this._accuracyMarker.refreshGeometry(this._view));
- this._accuracyMarker.refreshGeometry(this._view);
+ () => this._accuracyMarker.refreshGeometry(this._mapView));
+ this._mapView.connect('notify::default-width',
+ () => this._accuracyMarker.refreshGeometry(this._mapView));
+ this._mapView.connect('notify::default-height',
+ () => this._accuracyMarker.refreshGeometry(this._mapView));
+ this._accuracyMarker.refreshGeometry(this._mapView);
this.place.connect('notify::location', () => this._updateLocation());
+ this._image.pixel_size = 24;
this._updateLocation();
this.connect('notify::visible', this._updateAccuracyCircle.bind(this));
@@ -101,26 +104,21 @@ export class UserLocationMarker extends MapMarker {
}
_updateLocation() {
- if (this._actor) {
- this._actor.destroy();
- delete this._actor;
- }
-
if (this.place.location.heading > -1) {
- this._actor = this._actorFromIconName('user-location-compass', 0);
- this._actor.set_pivot_point(0.5, 0.5);
- this._actor.set_rotation_angle(Clutter.RotateAxis.Z_AXIS, this.place.location.heading);
+ this._image.icon_name = 'user-location-compass';
+ // TODO: do rotation (using snapshot transformation
+ //this._actor.set_pivot_point(0.5, 0.5);
+ //this._actor.set_rotation_angle(Clutter.RotateAxis.Z_AXIS, this.place.location.heading);
} else {
- this._actor = this._actorFromIconName('user-location', 0);
+ this._image.icon_name = 'user-location';
}
- this.add_actor(this._actor);
this._updateAccuracyCircle();
}
_updateAccuracyCircle() {
if (this.visible && this.place.location.accuracy > 0) {
- this._accuracyMarker.refreshGeometry(this._view);
+ this._accuracyMarker.refreshGeometry(this._mapView);
} else {
this._accuracyMarker.visible = false;
}
diff --git a/src/utils.js b/src/utils.js
index 2cf6920b..38994b8f 100644
--- a/src/utils.js
+++ b/src/utils.js
@@ -88,9 +88,9 @@ export function once(obj, signal, callback) {
export function loadStyleSheet(file) {
let provider = new Gtk.CssProvider();
provider.load_from_file(file);
- Gtk.StyleContext.add_provider_for_screen(Gdk.Screen.get_default(),
- provider,
- Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION);
+ Gtk.StyleContext.add_provider_for_display(Gdk.Display.get_default(),
+ provider,
+ Gtk.STYLE_PROVIDER_PRIORITY_APPLICATION);
}
export function addActions(actionMap, entries, settings = null) {
@@ -302,11 +302,15 @@ function _load_icon(icon, loadCompleteCallback) {
}
function _load_themed_icon(icon, size, loadCompleteCallback) {
- let theme = Gtk.IconTheme.get_default();
- let info = theme.lookup_by_gicon(icon, size, 0);
+ let display = Gdk.Display.get_default();
+ let theme = Gtk.IconTheme.get_for_display(display);
+ // TODO: find the scale factor?
+ let paintable = theme.lookup_by_gicon(icon, size, 1,
+ Gtk.TextDirection.NONE, 0);
+ let filename = paintable.file.get_path();
try {
- let pixbuf = info.load_icon();
+ let pixbuf = GdkPixbuf.Pixbuf.new_from_file(filename);
loadCompleteCallback(pixbuf);
} catch(e) {
log("Failed to load pixbuf: " + e);
@@ -460,7 +464,7 @@ export function showDialog(msg, type, transientFor) {
text: msg });
messageDialog.connect('response', () => messageDialog.destroy());
- messageDialog.show_all();
+ messageDialog.show();
}
let decoder = new TextDecoder('utf-8');
diff --git a/src/zoomInDialog.js b/src/zoomInDialog.js
index c7fd7b6b..89eb07d1 100644
--- a/src/zoomInDialog.js
+++ b/src/zoomInDialog.js
@@ -32,8 +32,8 @@ export class ZoomInDialog extends Gtk.Dialog {
delete params.latitude;
let longitude = params.longitude;
delete params.longitude;
- let view = params.view;
- delete params.view;
+ let map = params.map;
+ delete params.map;
/* This is a construct-only property and cannot be set by GtkBuilder */
params.use_header_bar = true;
@@ -42,16 +42,15 @@ export class ZoomInDialog extends Gtk.Dialog {
this._latitude = latitude;
this._longitude = longitude;
- this._view = view;
+ this._map = map;
this._zoomInButton.connect('clicked', () => this._onZoomIn());
this._cancelButton.connect('clicked', () => this._onCancel());
}
_onZoomIn() {
- this._view.zoom_level = OSMEdit.MIN_ADD_LOCATION_ZOOM_LEVEL;
-
/* center on the position first selected */
- this._view.center_on(this._latitude, this._longitude);
+ this._map.go_to_full(this._latitude, this._longitude,
+ OSMEdit.MIN_ADD_LOCATION_ZOOM_LEVEL);
this.response(Gtk.ResponseType.OK);
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]