mirror of
https://github.com/tumic0/GPXSee.git
synced 2025-06-28 03:59:15 +02:00
Make the source projection of JNX and KMZ maps selectable
This commit is contained in:
@ -202,7 +202,7 @@ void IMGMap::draw(QPainter *painter, const QRectF &rect, Flags flags)
|
||||
}
|
||||
}
|
||||
|
||||
void IMGMap::setProjection(const Projection &projection)
|
||||
void IMGMap::setOutputProjection(const Projection &projection)
|
||||
{
|
||||
if (projection == _projection)
|
||||
return;
|
||||
|
@ -33,7 +33,7 @@ public:
|
||||
|
||||
void draw(QPainter *painter, const QRectF &rect, Flags flags);
|
||||
|
||||
void setProjection(const Projection &projection);
|
||||
void setOutputProjection(const Projection &projection);
|
||||
|
||||
void load();
|
||||
void unload();
|
||||
|
@ -84,15 +84,6 @@ bool JNXMap::readTiles()
|
||||
}
|
||||
}
|
||||
|
||||
QByteArray guid;
|
||||
if (!(readValue(dummy) && readString(guid)))
|
||||
return false;
|
||||
/* Use WebMercator projection for nakarte.tk maps */
|
||||
if (guid == "12345678-1234-1234-1234-123456789ABC")
|
||||
_projection = Projection(PCS::pcs(3857));
|
||||
else
|
||||
_projection = Projection(GCS::gcs(4326));
|
||||
|
||||
_zooms = QVector<Zoom>(lh.size());
|
||||
for (int i = 0; i < lh.count(); i++) {
|
||||
Zoom &z = _zooms[i];
|
||||
@ -104,21 +95,22 @@ bool JNXMap::readTiles()
|
||||
z.tiles = QVector<Tile>(l.count);
|
||||
for (quint32 j = 0; j < l.count; j++) {
|
||||
Tile &tile = z.tiles[j];
|
||||
qint32 top, right, bottom, left;
|
||||
quint16 width, height;
|
||||
|
||||
if (!(readValue(top) && readValue(right) && readValue(bottom)
|
||||
&& readValue(left) && readValue(width)
|
||||
&& readValue(height) && readValue(tile.size)
|
||||
&& readValue(tile.offset)))
|
||||
if (!(readValue(tile.top) && readValue(tile.right)
|
||||
&& readValue(tile.bottom) && readValue(tile.left)
|
||||
&& readValue(tile.width) && readValue(tile.height)
|
||||
&& readValue(tile.size) && readValue(tile.offset)))
|
||||
return false;
|
||||
|
||||
RectD rect(_projection.ll2xy(Coordinates(ic2dc(left), ic2dc(top))),
|
||||
_projection.ll2xy(Coordinates(ic2dc(right), ic2dc(bottom))));
|
||||
RectC llrect(Coordinates(ic2dc(tile.left), ic2dc(tile.top)),
|
||||
Coordinates(ic2dc(tile.right), ic2dc(tile.bottom)));
|
||||
RectD rect(_projection.ll2xy(llrect.topLeft()),
|
||||
_projection.ll2xy(llrect.bottomRight()));
|
||||
|
||||
if (j == 0) {
|
||||
ReferencePoint tl(PointD(0, 0), rect.topLeft());
|
||||
ReferencePoint br(PointD(width, height), rect.bottomRight());
|
||||
ReferencePoint br(PointD(tile.width, tile.height),
|
||||
rect.bottomRight());
|
||||
z.transform = Transform(tl, br);
|
||||
}
|
||||
|
||||
@ -143,6 +135,7 @@ JNXMap::JNXMap(const QString &fileName, QObject *parent)
|
||||
_valid(false)
|
||||
{
|
||||
_name = QFileInfo(fileName).fileName();
|
||||
_projection = Projection(GCS::gcs(4326));
|
||||
|
||||
if (!_file.open(QIODevice::ReadOnly)) {
|
||||
_errorString = fileName + ": " + _file.errorString();
|
||||
@ -267,3 +260,44 @@ void JNXMap::draw(QPainter *painter, const QRectF &rect, Flags flags)
|
||||
max[1] = rr.bottom();
|
||||
tree.Search(min, max, cb, &ctx);
|
||||
}
|
||||
|
||||
void JNXMap::setInputProjection(const Projection &projection)
|
||||
{
|
||||
if (projection == _projection)
|
||||
return;
|
||||
|
||||
_projection = projection;
|
||||
|
||||
for (int i = 0; i < _zooms.size(); i++) {
|
||||
Zoom &z = _zooms[i];
|
||||
|
||||
z.tree.RemoveAll();
|
||||
|
||||
for (int j = 0; j < z.tiles.size(); j++) {
|
||||
Tile &tile = z.tiles[j];
|
||||
|
||||
RectC llrect(Coordinates(ic2dc(tile.left), ic2dc(tile.top)),
|
||||
Coordinates(ic2dc(tile.right), ic2dc(tile.bottom)));
|
||||
RectD rect(_projection.ll2xy(llrect.topLeft()),
|
||||
_projection.ll2xy(llrect.bottomRight()));
|
||||
|
||||
if (j == 0) {
|
||||
ReferencePoint tl(PointD(0, 0), rect.topLeft());
|
||||
ReferencePoint br(PointD(tile.width, tile.height),
|
||||
rect.bottomRight());
|
||||
z.transform = Transform(tl, br);
|
||||
}
|
||||
|
||||
QRectF trect(z.transform.proj2img(rect.topLeft()),
|
||||
z.transform.proj2img(rect.bottomRight()));
|
||||
tile.pos = trect.topLeft();
|
||||
|
||||
qreal min[2], max[2];
|
||||
min[0] = trect.left();
|
||||
min[1] = trect.top();
|
||||
max[0] = trect.right();
|
||||
max[1] = trect.bottom();
|
||||
z.tree.Insert(min, max, &tile);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -36,6 +36,7 @@ public:
|
||||
|
||||
void draw(QPainter *painter, const QRectF &rect, Flags flags);
|
||||
|
||||
void setInputProjection(const Projection &projection);
|
||||
void setDevicePixelRatio(qreal /*deviceRatio*/, qreal mapRatio)
|
||||
{_mapRatio = mapRatio;}
|
||||
|
||||
@ -44,9 +45,12 @@ public:
|
||||
|
||||
private:
|
||||
struct Tile {
|
||||
QPointF pos;
|
||||
qint32 top, right, bottom, left;
|
||||
quint16 width, height;
|
||||
quint32 size;
|
||||
quint32 offset;
|
||||
|
||||
QPointF pos;
|
||||
};
|
||||
|
||||
struct Zoom {
|
||||
|
@ -28,13 +28,15 @@
|
||||
#define TL(m) ((m).bbox().topLeft())
|
||||
#define BR(m) ((m).bbox().bottomRight())
|
||||
|
||||
|
||||
KMZMap::Overlay::Overlay(const QString &path, const QSize &size,
|
||||
const RectC &bbox, double rotation) : _path(path), _bbox(bbox),
|
||||
_rotation(rotation), _img(0)
|
||||
const RectC &bbox, double rotation, const Projection *proj)
|
||||
: _path(path), _size(size), _bbox(bbox), _rotation(rotation), _img(0),
|
||||
_proj(proj)
|
||||
{
|
||||
ReferencePoint tl(PointD(0, 0), PointD(bbox.left(), bbox.top()));
|
||||
ReferencePoint tl(PointD(0, 0), _proj->ll2xy(bbox.topLeft()));
|
||||
ReferencePoint br(PointD(size.width(), size.height()),
|
||||
PointD(bbox.right(), bbox.bottom()));
|
||||
_proj->ll2xy(bbox.bottomRight()));
|
||||
|
||||
QTransform t;
|
||||
t.rotate(-rotation);
|
||||
@ -87,6 +89,24 @@ void KMZMap::Overlay::unload()
|
||||
_img = 0;
|
||||
}
|
||||
|
||||
void KMZMap::Overlay::setProjection(const Projection *proj)
|
||||
{
|
||||
_proj = proj;
|
||||
|
||||
ReferencePoint tl(PointD(0, 0), _proj->ll2xy(_bbox.topLeft()));
|
||||
ReferencePoint br(PointD(_size.width(), _size.height()),
|
||||
_proj->ll2xy(_bbox.bottomRight()));
|
||||
|
||||
QTransform t;
|
||||
t.rotate(-_rotation);
|
||||
QRectF b(0, 0, _size.width(), _size.height());
|
||||
QPolygonF ma = t.map(b);
|
||||
_bounds = ma.boundingRect();
|
||||
|
||||
_transform = Transform(tl, br);
|
||||
}
|
||||
|
||||
|
||||
bool KMZMap::resCmp(const Overlay &m1, const Overlay &m2)
|
||||
{
|
||||
qreal r1, r2;
|
||||
@ -150,7 +170,6 @@ void KMZMap::computeBounds()
|
||||
_bounds = QVector<Bounds>(_maps.count());
|
||||
for (int i = 0; i < _maps.count(); i++) {
|
||||
QRectF xy(offsets.at(i), _maps.at(i).bounds().size());
|
||||
|
||||
_bounds[i] = Bounds(_maps.at(i).bbox(), xy);
|
||||
_adjust = qMin(qMin(_maps.at(i).bounds().left(),
|
||||
_maps.at(i).bounds().top()), _adjust);
|
||||
@ -227,7 +246,7 @@ void KMZMap::groundOverlay(QXmlStreamReader &reader, QZipReader &zip)
|
||||
QSize size(ir.size());
|
||||
|
||||
if (size.isValid())
|
||||
_maps.append(Overlay(image, size, rect, rotation));
|
||||
_maps.append(Overlay(image, size, rect, rotation, &_projection));
|
||||
else
|
||||
reader.raiseError(image + ": Invalid image file");
|
||||
} else
|
||||
@ -282,6 +301,8 @@ KMZMap::KMZMap(const QString &fileName, QObject *parent)
|
||||
QByteArray xml(zip.fileData("doc.kml"));
|
||||
QXmlStreamReader reader(xml);
|
||||
|
||||
_projection = Projection(GCS::gcs(4326));
|
||||
|
||||
if (reader.readNextStartElement()) {
|
||||
if (reader.name() == QLatin1String("kml"))
|
||||
kml(reader, zip);
|
||||
@ -450,6 +471,20 @@ void KMZMap::unload()
|
||||
_zip = 0;
|
||||
}
|
||||
|
||||
void KMZMap::setInputProjection(const Projection &projection)
|
||||
{
|
||||
if (projection == _projection)
|
||||
return;
|
||||
|
||||
_projection = projection;
|
||||
|
||||
for (int i = 0; i < _maps.size(); i++)
|
||||
_maps[i].setProjection(&_projection);
|
||||
|
||||
_bounds.clear();
|
||||
computeBounds();
|
||||
}
|
||||
|
||||
void KMZMap::draw(QPainter *painter, const QRectF &rect, int mapIndex,
|
||||
Flags flags)
|
||||
{
|
||||
|
@ -1,6 +1,7 @@
|
||||
#ifndef KMZMAP_H
|
||||
#define KMZMAP_H
|
||||
|
||||
#include "projection.h"
|
||||
#include "transform.h"
|
||||
#include "rectd.h"
|
||||
#include "map.h"
|
||||
@ -34,6 +35,8 @@ public:
|
||||
void load();
|
||||
void unload();
|
||||
|
||||
void setInputProjection(const Projection &projection);
|
||||
|
||||
bool isValid() const {return _valid;}
|
||||
QString errorString() const {return _errorString;}
|
||||
|
||||
@ -41,18 +44,16 @@ private:
|
||||
class Overlay {
|
||||
public:
|
||||
Overlay(const QString &path, const QSize &size, const RectC &bbox,
|
||||
double rotation);
|
||||
double rotation, const Projection *proj);
|
||||
bool operator==(const Overlay &other) const
|
||||
{return _path == other._path;}
|
||||
|
||||
QPointF ll2xy(const Coordinates &c) const
|
||||
{return QPointF(_transform.proj2img(QPointF(c.lon(), c.lat())));}
|
||||
{return QPointF(_transform.proj2img(_proj->ll2xy(c)));}
|
||||
Coordinates xy2ll(const QPointF &p) const
|
||||
{
|
||||
PointD pp(_transform.img2proj(p));
|
||||
return Coordinates(pp.x(), pp.y());
|
||||
}
|
||||
{return _proj->xy2ll(_transform.img2proj(p));}
|
||||
|
||||
const QString &path() const {return _path;}
|
||||
const RectC &bbox() const {return _bbox;}
|
||||
const QRectF &bounds() const {return _bounds;}
|
||||
qreal resolution(const QRectF &rect) const;
|
||||
@ -63,13 +64,16 @@ private:
|
||||
void load(QZipReader *zip);
|
||||
void unload();
|
||||
|
||||
void setProjection(const Projection *proj);
|
||||
|
||||
private:
|
||||
QString _path;
|
||||
QSize _size;
|
||||
QRectF _bounds;
|
||||
RectC _bbox;
|
||||
qreal _rotation;
|
||||
Image *_img;
|
||||
|
||||
const Projection *_proj;
|
||||
Transform _transform;
|
||||
};
|
||||
|
||||
@ -112,6 +116,7 @@ private:
|
||||
int _mapIndex;
|
||||
QZipReader *_zip;
|
||||
qreal _adjust;
|
||||
Projection _projection;
|
||||
|
||||
bool _valid;
|
||||
QString _errorString;
|
||||
|
@ -49,7 +49,8 @@ public:
|
||||
virtual void load() {}
|
||||
virtual void unload() {}
|
||||
virtual void setDevicePixelRatio(qreal, qreal) {}
|
||||
virtual void setProjection(const Projection &) {}
|
||||
virtual void setOutputProjection(const Projection &) {}
|
||||
virtual void setInputProjection(const Projection &) {}
|
||||
|
||||
virtual bool isValid() const {return true;}
|
||||
virtual bool isReady() const {return true;}
|
||||
|
Reference in New Issue
Block a user