Commit 37a937f7 authored by Dennis Nienhüser's avatar Dennis Nienhüser
Browse files

Basic support for creating bookmarks

parent 4901acb7
......@@ -40,7 +40,6 @@ ApplicationWindow {
id: itemStack
anchors.fill: parent
focus: true
initialItem: mapItem
......@@ -75,7 +74,6 @@ ApplicationWindow {
anchors.fill: parent
visible: true
focus: true
// Theme settings.
projection: MarbleItem.Mercator
......@@ -154,7 +152,7 @@ ApplicationWindow {
anchors.fill: parent
propagateComposedEvents: true
onPressed: {
search.focus = true;
marbleMaps.focus = true;
mouse.accepted = false;
}
}
......@@ -232,6 +230,7 @@ ApplicationWindow {
right: parent.right
bottom: parent.bottom
}
map: marbleMaps
}
DeveloperDialog {
......
......@@ -55,6 +55,8 @@
<file alias="material/navigation.svg">material-icons/ic_navigation_48px.svg</file>
<file alias="material/access_time.svg">material-icons/ic_access_time_48px.svg</file>
<file alias="material/place.svg">material-icons/ic_place_black_48px.svg</file>
<file alias="material/star.svg">material-icons/ic_star_24px.svg</file>
<file alias="material/star_border.svg">material-icons/ic_star_border_24px.svg</file>
<file>RouteProfileRadioButton.qml</file>
<file>ScrollBar.qml</file>
</qresource>
......
......@@ -21,6 +21,7 @@ Item {
property var placemark: null
property bool condensed: true
property string actionIconSource: routeEditor.currentProfileIcon
property alias map: bookmarks.map
height: placemark === null ? 0 : Screen.pixelDensity * 6 + infoLayout.height
......@@ -33,7 +34,13 @@ Item {
}
onPlacemarkChanged: {
itemStack.state = placemark ? "place" : ""
if (placemark) {
bookmarkButton.bookmark = bookmarks.isBookmark(placemark.longitude, placemark.latitude)
itemStack.state = "place"
} else {
condensed = true
itemStack.state = ""
}
}
SystemPalette {
......@@ -46,12 +53,16 @@ Item {
color: palette.base
}
Bookmarks {
id: bookmarks
}
Column {
id: infoLayout
anchors {
bottom: parent.bottom
top: parent.top
left: parent.left
right: parent.right
right: bookmarkButton.left
margins: Screen.pixelDensity * 2
}
......@@ -123,6 +134,35 @@ Item {
}
}
Image {
id: bookmarkButton
anchors.right: parent.right
anchors.bottom: parent.bottom
anchors.margins: Screen.pixelDensity * 2
visible: root.height > 0 && !condensed
property bool bookmark: false
width: Screen.pixelDensity * 6
height: width
sourceSize.height: height
sourceSize.width: width
source: bookmark ? "qrc:/material/star.svg" : "qrc:/material/star_border.svg"
MouseArea {
id: touchArea
anchors.fill: parent
onClicked: {
if (bookmarkButton.bookmark) {
bookmarks.removeBookmark(root.placemark.longitude, root.placemark.latitude)
} else {
bookmarks.addBookmark(root.placemark.longitude, root.placemark.latitude, root.placemark.name, "Default")
}
bookmarkButton.bookmark = !bookmarkButton.bookmark
}
}
}
function ensureRouteHasDeparture() {
if (routing.routeRequestModel.count === 0) {
if (marbleMaps.positionAvailable) {
......
......@@ -50,30 +50,83 @@ Item {
backend.setSelectedPlacemark(index);
root.itemSelected();
searchResults.visible = false;
searchField.focus = true;
if (routingManager) {
routingManager.addSearchResultAsPlacemark(backend.selectedPlacemark);
}
placemarkDialog.placemark = backend.selectedPlacemark;
}
}
Rectangle {
id: background
visible: searchField.hasFocus && searchField.query === "" && bookmarks.model.count > 0
anchors.top: searchField.bottom
anchors.left: searchField.left
width: searchField.width
height: 2 * background.itemSpacing + (delegateHeight) * Math.min(4, bookmarksView.model.count)
color: palette.base
property int delegateHeight: 0
property double itemSpacing: Screen.pixelDensity * 1
MouseArea{
ListView {
id: bookmarksView
anchors.fill: parent
propagateComposedEvents: true
onPressed: {
searchField.focus = true;
mouse.accepted = false;
anchors.margins: background.itemSpacing
clip: true
model: bookmarks.model
delegate: Row {
spacing: background.itemSpacing
Image {
anchors.verticalCenter: parent.verticalCenter
source: iconPath.substr(0,1) === '/' ? "file://" + iconPath : iconPath
width: Screen.pixelDensity * 4
height: width
sourceSize.width: width
sourceSize.height: height
}
Text {
anchors.verticalCenter: parent.verticalCenter
anchors.leftMargin: Screen.pixelDensity * 2
text: display
font.pointSize: 18
color: palette.text
elide: Text.ElideMiddle
MouseArea {
anchors.fill: parent
onClicked: {
bookmarksView.currentIndex = index
placemarkDialog.focus = true
placemarkDialog.placemark = bookmarks.placemark(index);
marbleMaps.centerOn(placemarkDialog.placemark.longitude, placemarkDialog.placemark.latitude)
}
}
}
Component.onCompleted: {
if( background.delegateHeight !== height ) {
background.delegateHeight = height;
}
}
}
}
ScrollBar {
flickableItem: bookmarksView
}
}
SearchBackend {
id: backend
marbleQuickItem: root.marbleQuickItem
onSearchResultChanged: {
searchResults.model = model;
searchResults.visible = true;
searchField.focus = true;
}
onSearchFinished: searchField.busy = false
}
......@@ -93,4 +146,9 @@ Item {
onCompletionRequested: backend.setCompletionPrefix(query)
onCleared: searchResults.visible = false
}
Bookmarks {
id: bookmarks
map: root.marbleQuickItem
}
}
......@@ -19,6 +19,7 @@ Item {
height: field.height
property alias query: field.text
property alias hasFocus: field.activeFocus
property alias completionModel: completion.model
property bool busy: false
......@@ -100,11 +101,11 @@ Item {
MouseArea {
anchors.fill: parent
onClicked: {
field.text = "";
field.focus = true;
placemarkDialog.placemark = null;
itemStack.state = "";
routing.clearSearchResultPlacemarks();
field.text = "";
field.focus = true;
cleared();
}
}
......
......@@ -57,7 +57,9 @@ Item {
anchors.verticalCenter: parent.verticalCenter
width: height
height: placemarkName.height
source: iconPath
source: iconPath.substr(0,1) === '/' ? "file://" + iconPath : iconPath
sourceSize.width: width
sourceSize.height: height
fillMode: Image.Pad
}
......
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24"><path d="M12 17.27L18.18 21l-1.64-7.03L22 9.24l-7.19-.61L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21z"/></svg>
\ No newline at end of file
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24"><path d="M22 9.24l-7.19-.62L12 2 9.19 8.63 2 9.24l5.46 4.73L5.82 21 12 17.27 18.18 21l-1.63-7.03L22 9.24zM12 15.4l-3.76 2.27 1-4.28-3.32-2.88 4.38-.38L12 6.1l1.71 4.04 4.38.38-3.32 2.88 1 4.28L12 15.4z"/></svg>
\ No newline at end of file
......@@ -72,6 +72,20 @@ bool Bookmarks::isBookmark( qreal longitude, qreal latitude ) const
return false;
}
Placemark *Bookmarks::placemark(int row)
{
Placemark* placemark = new Placemark;
QModelIndex index = model()->index(row, 0);
GeoDataObject *object = model()->data(index, MarblePlacemarkModel::ObjectPointerRole ).value<GeoDataObject*>();
if (object->nodeType() == GeoDataTypes::GeoDataPlacemarkType) {
GeoDataPlacemark *geoDataPlacemark = static_cast<GeoDataPlacemark*>(object);
placemark->setGeoDataPlacemark(*geoDataPlacemark);
}
return placemark;
}
void Bookmarks::addBookmark( qreal longitude, qreal latitude, const QString &name, const QString &folderName )
{
if ( !m_marbleQuickItem || !m_marbleQuickItem->model()->bookmarkManager() ) {
......
......@@ -14,6 +14,7 @@
#include <QObject>
#include <QSortFilterProxyModel>
#include <GeoDataTreeModel.h>
#include "Placemark.h"
namespace Marble {
......@@ -58,6 +59,8 @@ public:
Q_INVOKABLE bool isBookmark( qreal longitude, qreal latitude ) const;
Q_INVOKABLE Placemark* placemark(int index);
public Q_SLOTS:
void addBookmark( qreal longitude, qreal latitude, const QString &name, const QString &folder );
void removeBookmark( qreal longitude, qreal latitude );
......
......@@ -570,24 +570,35 @@ namespace Marble
void MarbleQuickItem::selectPlacemarkAt(int x, int y)
{
auto const features = d->m_map.whichFeatureAt(QPoint(x, y));
QVector<GeoDataPlacemark const *> placemarks;
foreach(auto feature, features) {
if (feature->nodeType() == GeoDataTypes::GeoDataPlacemarkType) {
GeoDataPlacemark const * placemark = static_cast<const GeoDataPlacemark*>(feature);
if (d->m_placemark && placemark->coordinate() == d->m_placemark->placemark().coordinate()) {
d->m_placemark->deleteLater();
d->m_placemark = nullptr;
} else {
d->m_placemark->deleteLater();
d->m_placemark = new Placemark(this);
d->m_placemark->setGeoDataPlacemark(*placemark);
}
delete d->m_placemarkItem;
d->m_placemarkItem = nullptr;
updatePlacemarks();
return;
placemarks << static_cast<const GeoDataPlacemark*>(feature);
}
}
// Select bookmarks only if nothing else is found
qSort(placemarks.begin(), placemarks.end(), [] (GeoDataPlacemark const *a, GeoDataPlacemark const *b) {
int const left = a->visualCategory() == GeoDataFeature::Bookmark ? -1 : a->visualCategory();
int const right = b->visualCategory() == GeoDataFeature::Bookmark ? -1 : b->visualCategory();
return left > right;
});
foreach(auto placemark, placemarks) {
if (d->m_placemark && placemark->coordinate() == d->m_placemark->placemark().coordinate()) {
d->m_placemark->deleteLater();
d->m_placemark = nullptr;
} else {
d->m_placemark->deleteLater();
d->m_placemark = new Placemark(this);
d->m_placemark->setGeoDataPlacemark(*placemark);
}
delete d->m_placemarkItem;
d->m_placemarkItem = nullptr;
updatePlacemarks();
return;
}
if (d->m_placemark) {
d->m_placemark->deleteLater();
d->m_placemark = nullptr;
......
......@@ -16,6 +16,8 @@
#endif // HAVE_QT5_POSITIONING
#include <osm/OsmPlacemarkData.h>
#include "GeoDataStyle.h"
#include "GeoDataIconStyle.h"
namespace Marble {
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment