Invalid alias reference to a QML component
Solution 1:
Working code below.
The issue is that while the MapQuickItem appears to be in the namespace of your myfile.qml component, it actually is not. Delegates are actually components themselves and start a new namespace. You can think of delegates ending up in a new anonymous component that cannot refer to ids in the surrounding component it appears in.
However, while it can't refer to ids in the surrounding component, it can refer to component ids in the visual hierarchy of components. So, you can refer to root (the id of this file's component itself) in the hierarchy of components that were instantiated when this visual hierarchy is built at run time.
From there, you can advertise the Map component which is private to this component on the root object as an alias and then refer to it via the root reference in MapItemView.
It's all a bit confusing at first but makes sense when you start to realize that components are clusters of QML defined by files, Components, or delegate: definitions. Intra-component id references are fine but external references have to either be passed down as properties or in delegate situations reference through the hierarchy of components upward. And then a child QML object of a component must be advertised as an alias to give external access.
More info here:
https://doc.qt.io/qt-5/qtqml-documents-scope.html
import QtQuick 2.11
import QtQuick.Controls 2.4
import QtLocation 5.11
import QtPositioning 5.11
import QtQuick.Window 2.11
Window {
id: root; width: 800; height: 600;
visible: true
property alias map: map
Plugin { id: mapPlugin; name: "osm"; }
ListModel {
id: myModel
ListElement { latitude: 48.2351164; longitude: 6.8986936; }
}
Map {
id: map
anchors.fill: parent
plugin: mapPlugin
center: QtPositioning.coordinate(48.2351164, 6.8986936)
zoomLevel: 19
property real scale: map.scaleFactor()
onScaleChanged: {
console.log(">>> scale from map component", scale);
}
// function reimplemented from qdeclarativegeomapquickitem.cpp
function scaleFactor() {
return Math.pow(0.5, map.maximumZoomLevel - map.zoomLevel);
}
MapItemView {
model: myModel
delegate: MapQuickItem {
anchorPoint.x: myRect.width / 2
anchorPoint.y: myRect.height / 2
width: myRect.width
height: myRect.height
zoomLevel: map.maximumZoomLevel // set the zoomLevel (1:1 scale)
coordinate: QtPositioning.coordinate(model.latitude, model.longitude)
sourceItem: Rectangle {
id: myRect
readonly property int radius: 50
property real scale: root.map.scale
onScaleChanged: {
myCanvas.requestPaint();
}
width: radius * 2
height: radius * 2
color: "transparent"
Canvas {
id: myCanvas
anchors.fill: parent
onPaint: {
var width = myRect.width;
var height = myRect.height;
var centreX = width / 2;
var centreY = height / 2;
var ctx = getContext("2d");
ctx.reset();
if (scale > 0.1) {
ctx.fillStyle = "blue";
ctx.globalAlpha = 1;
ctx.beginPath();
ctx.moveTo(centreX, centreY);
ctx.arc(centreX, centreY, myRect.radius, 0, Math.PI * 2, false);
ctx.closePath();
ctx.fill();
}
}
}
}
}
}
}
}