mirror of
https://github.com/tumic0/GPXSee.git
synced 2024-11-27 21:24:47 +01:00
Code cleanup
This commit is contained in:
parent
56061c93cb
commit
a4abed8f1f
@ -96,6 +96,7 @@ HEADERS += src/common/config.h \
|
|||||||
src/map/IMG/huffmanstream.h \
|
src/map/IMG/huffmanstream.h \
|
||||||
src/map/IMG/huffmantable.h \
|
src/map/IMG/huffmantable.h \
|
||||||
src/map/IMG/mapdata.h \
|
src/map/IMG/mapdata.h \
|
||||||
|
src/map/IMG/rastertile.h \
|
||||||
src/map/IMG/textpathitem.h \
|
src/map/IMG/textpathitem.h \
|
||||||
src/map/IMG/textpointitem.h \
|
src/map/IMG/textpointitem.h \
|
||||||
src/map/projection.h \
|
src/map/projection.h \
|
||||||
@ -257,6 +258,7 @@ SOURCES += src/main.cpp \
|
|||||||
src/map/IMG/huffmanstream.cpp \
|
src/map/IMG/huffmanstream.cpp \
|
||||||
src/map/IMG/huffmantable.cpp \
|
src/map/IMG/huffmantable.cpp \
|
||||||
src/map/IMG/mapdata.cpp \
|
src/map/IMG/mapdata.cpp \
|
||||||
|
src/map/IMG/rastertile.cpp \
|
||||||
src/map/IMG/textpathitem.cpp \
|
src/map/IMG/textpathitem.cpp \
|
||||||
src/map/IMG/textpointitem.cpp \
|
src/map/IMG/textpointitem.cpp \
|
||||||
src/map/maplist.cpp \
|
src/map/maplist.cpp \
|
||||||
|
406
src/map/IMG/rastertile.cpp
Normal file
406
src/map/IMG/rastertile.cpp
Normal file
@ -0,0 +1,406 @@
|
|||||||
|
#include <QFont>
|
||||||
|
#include <QPainter>
|
||||||
|
#include "textpathitem.h"
|
||||||
|
#include "textpointitem.h"
|
||||||
|
#include "bitmapline.h"
|
||||||
|
#include "style.h"
|
||||||
|
#include "rastertile.h"
|
||||||
|
|
||||||
|
|
||||||
|
#define AREA(rect) \
|
||||||
|
(rect.size().width() * rect.size().height())
|
||||||
|
|
||||||
|
static const QColor shieldColor(Qt::white);
|
||||||
|
static const QColor shieldBgColor1("#dd3e3e");
|
||||||
|
static const QColor shieldBgColor2("#379947");
|
||||||
|
static const QColor shieldBgColor3("#4a7fc1");
|
||||||
|
|
||||||
|
static QString convertUnits(const QString &str)
|
||||||
|
{
|
||||||
|
bool ok;
|
||||||
|
int number = str.toInt(&ok);
|
||||||
|
return ok ? QString::number(qRound(number * 0.3048)) : str;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int minPOIZoom(Style::POIClass cl)
|
||||||
|
{
|
||||||
|
switch (cl) {
|
||||||
|
case Style::Food:
|
||||||
|
case Style::Shopping:
|
||||||
|
case Style::Services:
|
||||||
|
return 27;
|
||||||
|
case Style::Accommodation:
|
||||||
|
case Style::Recreation:
|
||||||
|
return 25;
|
||||||
|
case Style::ManmadePlaces:
|
||||||
|
case Style::NaturePlaces:
|
||||||
|
case Style::Transport:
|
||||||
|
case Style::Community:
|
||||||
|
case Style::Elementary:
|
||||||
|
return 23;
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static QFont pixelSizeFont(int pixelSize)
|
||||||
|
{
|
||||||
|
QFont f;
|
||||||
|
f.setPixelSize(pixelSize);
|
||||||
|
return f;
|
||||||
|
}
|
||||||
|
|
||||||
|
static QFont *font(Style::FontSize size, Style::FontSize defaultSize
|
||||||
|
= Style::Normal)
|
||||||
|
{
|
||||||
|
/* The fonts must be initialized on first usage (after the QGuiApplication
|
||||||
|
instance is created) */
|
||||||
|
static QFont large = pixelSizeFont(16);
|
||||||
|
static QFont normal = pixelSizeFont(14);
|
||||||
|
static QFont small = pixelSizeFont(12);
|
||||||
|
static QFont extraSmall = pixelSizeFont(10);
|
||||||
|
|
||||||
|
switch (size) {
|
||||||
|
case Style::None:
|
||||||
|
return 0;
|
||||||
|
case Style::Large:
|
||||||
|
return &large;
|
||||||
|
case Style::Normal:
|
||||||
|
return &normal;
|
||||||
|
case Style::Small:
|
||||||
|
return &small;
|
||||||
|
case Style::ExtraSmall:
|
||||||
|
return &extraSmall;
|
||||||
|
default:
|
||||||
|
return font(defaultSize);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static QFont *poiFont(Style::FontSize size = Style::Normal)
|
||||||
|
{
|
||||||
|
static QFont poi = pixelSizeFont(10);
|
||||||
|
|
||||||
|
switch (size) {
|
||||||
|
case Style::None:
|
||||||
|
return 0;
|
||||||
|
default:
|
||||||
|
return &poi;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static const QColor *shieldBgColor(Label::Shield::Type type)
|
||||||
|
{
|
||||||
|
switch (type) {
|
||||||
|
case Label::Shield::USInterstate:
|
||||||
|
case Label::Shield::Hbox:
|
||||||
|
return &shieldBgColor1;
|
||||||
|
case Label::Shield::USShield:
|
||||||
|
case Label::Shield::Box:
|
||||||
|
return &shieldBgColor2;
|
||||||
|
case Label::Shield::USRound:
|
||||||
|
case Label::Shield::Oval:
|
||||||
|
return &shieldBgColor3;
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int minShieldZoom(Label::Shield::Type type)
|
||||||
|
{
|
||||||
|
switch (type) {
|
||||||
|
case Label::Shield::USInterstate:
|
||||||
|
case Label::Shield::Hbox:
|
||||||
|
return 17;
|
||||||
|
case Label::Shield::USShield:
|
||||||
|
case Label::Shield::Box:
|
||||||
|
return 19;
|
||||||
|
case Label::Shield::USRound:
|
||||||
|
case Label::Shield::Oval:
|
||||||
|
return 20;
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static qreal area(const QVector<QPointF> &polygon)
|
||||||
|
{
|
||||||
|
qreal area = 0;
|
||||||
|
|
||||||
|
for (int i = 0; i < polygon.size(); i++) {
|
||||||
|
int j = (i + 1) % polygon.size();
|
||||||
|
area += polygon.at(i).x() * polygon.at(j).y();
|
||||||
|
area -= polygon.at(i).y() * polygon.at(j).x();
|
||||||
|
}
|
||||||
|
area /= 2.0;
|
||||||
|
|
||||||
|
return area;
|
||||||
|
}
|
||||||
|
|
||||||
|
static QPointF centroid(const QVector<QPointF> &polygon)
|
||||||
|
{
|
||||||
|
qreal cx = 0, cy = 0;
|
||||||
|
qreal factor = 1.0 / (6.0 * area(polygon));
|
||||||
|
|
||||||
|
for (int i = 0; i < polygon.size(); i++) {
|
||||||
|
int j = (i + 1) % polygon.size();
|
||||||
|
qreal f = (polygon.at(i).x() * polygon.at(j).y() - polygon.at(j).x()
|
||||||
|
* polygon.at(i).y());
|
||||||
|
cx += (polygon.at(i).x() + polygon.at(j).x()) * f;
|
||||||
|
cy += (polygon.at(i).y() + polygon.at(j).y()) * f;
|
||||||
|
}
|
||||||
|
|
||||||
|
return QPointF(cx * factor, cy * factor);
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool rectNearPolygon(const QPolygonF &polygon, const QRectF &rect)
|
||||||
|
{
|
||||||
|
return (polygon.boundingRect().contains(rect)
|
||||||
|
&& (polygon.containsPoint(rect.topLeft(), Qt::OddEvenFill)
|
||||||
|
|| polygon.containsPoint(rect.topRight(), Qt::OddEvenFill)
|
||||||
|
|| polygon.containsPoint(rect.bottomLeft(), Qt::OddEvenFill)
|
||||||
|
|| polygon.containsPoint(rect.bottomRight(), Qt::OddEvenFill)));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void RasterTile::render()
|
||||||
|
{
|
||||||
|
QList<TextItem*> textItems;
|
||||||
|
|
||||||
|
processPoints(textItems);
|
||||||
|
processPolygons(textItems);
|
||||||
|
processLines(textItems);
|
||||||
|
|
||||||
|
_img.fill(Qt::transparent);
|
||||||
|
|
||||||
|
QPainter painter(&_img);
|
||||||
|
painter.setRenderHint(QPainter::SmoothPixmapTransform);
|
||||||
|
painter.setRenderHint(QPainter::Antialiasing);
|
||||||
|
painter.translate(-_xy.x(), -_xy.y());
|
||||||
|
|
||||||
|
drawPolygons(&painter);
|
||||||
|
drawLines(&painter);
|
||||||
|
drawTextItems(&painter, textItems);
|
||||||
|
//painter.setPen(Qt::red);
|
||||||
|
//painter.drawRect(QRect(_xy, _img.size()));
|
||||||
|
|
||||||
|
qDeleteAll(textItems);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::drawPolygons(QPainter *painter)
|
||||||
|
{
|
||||||
|
for (int n = 0; n < _style->drawOrder().size(); n++) {
|
||||||
|
for (int i = 0; i < _polygons.size(); i++) {
|
||||||
|
const MapData::Poly &poly = _polygons.at(i);
|
||||||
|
if (poly.type != _style->drawOrder().at(n))
|
||||||
|
continue;
|
||||||
|
const Style::Polygon &style = _style->polygon(poly.type);
|
||||||
|
|
||||||
|
painter->setPen(style.pen());
|
||||||
|
painter->setBrush(style.brush());
|
||||||
|
painter->drawPolygon(poly.points);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::drawLines(QPainter *painter)
|
||||||
|
{
|
||||||
|
painter->setBrush(Qt::NoBrush);
|
||||||
|
|
||||||
|
for (int i = 0; i < _lines.size(); i++) {
|
||||||
|
const MapData::Poly &poly = _lines.at(i);
|
||||||
|
const Style::Line &style = _style->line(poly.type);
|
||||||
|
|
||||||
|
if (style.background() == Qt::NoPen)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
painter->setPen(style.background());
|
||||||
|
painter->drawPolyline(poly.points);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < _lines.size(); i++) {
|
||||||
|
const MapData::Poly &poly = _lines.at(i);
|
||||||
|
const Style::Line &style = _style->line(poly.type);
|
||||||
|
|
||||||
|
if (!style.img().isNull())
|
||||||
|
BitmapLine::draw(painter, poly.points, style.img());
|
||||||
|
else if (style.foreground() != Qt::NoPen) {
|
||||||
|
painter->setPen(style.foreground());
|
||||||
|
painter->drawPolyline(poly.points);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::drawTextItems(QPainter *painter,
|
||||||
|
const QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < textItems.size(); i++)
|
||||||
|
textItems.at(i)->paint(painter);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::processPolygons(QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _polygons.size(); i++) {
|
||||||
|
MapData::Poly &poly = _polygons[i];
|
||||||
|
|
||||||
|
if (poly.label.text().isEmpty())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (_zoom <= 23 && (Style::isWaterArea(poly.type)
|
||||||
|
|| Style::isMilitaryArea(poly.type)
|
||||||
|
|| Style::isNatureReserve(poly.type))) {
|
||||||
|
const Style::Polygon &style = _style->polygon(poly.type);
|
||||||
|
TextPointItem *item = new TextPointItem(
|
||||||
|
centroid(poly.points).toPoint(), &poly.label.text(),
|
||||||
|
poiFont(), 0, &style.brush().color());
|
||||||
|
if (item->isValid() && !item->collides(textItems)
|
||||||
|
&& rectNearPolygon(poly.points, item->boundingRect()))
|
||||||
|
textItems.append(item);
|
||||||
|
else
|
||||||
|
delete item;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::processLines(QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
QRect tileRect(_xy, _img.size());
|
||||||
|
|
||||||
|
qStableSort(_lines);
|
||||||
|
|
||||||
|
if (_zoom >= 22)
|
||||||
|
processStreetNames(tileRect, textItems);
|
||||||
|
processShields(tileRect, textItems);
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::processStreetNames(const QRect &tileRect,
|
||||||
|
QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < _lines.size(); i++) {
|
||||||
|
MapData::Poly &poly = _lines[i];
|
||||||
|
const Style::Line &style = _style->line(poly.type);
|
||||||
|
|
||||||
|
if (style.img().isNull() && style.foreground() == Qt::NoPen)
|
||||||
|
continue;
|
||||||
|
if (poly.label.text().isEmpty()
|
||||||
|
|| style.textFontSize() == Style::None)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (Style::isContourLine(poly.type))
|
||||||
|
poly.label.setText(convertUnits(poly.label.text()));
|
||||||
|
|
||||||
|
const QFont *fnt = font(style.textFontSize(), Style::Small);
|
||||||
|
const QColor *color = style.textColor().isValid()
|
||||||
|
? &style.textColor() : 0;
|
||||||
|
|
||||||
|
TextPathItem *item = new TextPathItem(poly.points,
|
||||||
|
&poly.label.text(), tileRect, fnt, color);
|
||||||
|
if (item->isValid() && !item->collides(textItems))
|
||||||
|
textItems.append(item);
|
||||||
|
else
|
||||||
|
delete item;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::processShields(const QRect &tileRect,
|
||||||
|
QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
for (int type = FIRST_SHIELD; type <= LAST_SHIELD; type++) {
|
||||||
|
if (minShieldZoom(static_cast<Label::Shield::Type>(type)) > _zoom)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
QHash<Label::Shield, QPolygonF> shields;
|
||||||
|
QHash<Label::Shield, const Label::Shield*> sp;
|
||||||
|
|
||||||
|
for (int i = 0; i < _lines.size(); i++) {
|
||||||
|
const MapData::Poly &poly = _lines.at(i);
|
||||||
|
const Label::Shield &shield = poly.label.shield();
|
||||||
|
if (!shield.isValid() || shield.type() != type
|
||||||
|
|| !Style::isMajorRoad(poly.type))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
QPolygonF &p = shields[shield];
|
||||||
|
for (int j = 0; j < poly.points.size(); j++)
|
||||||
|
p.append(poly.points.at(j));
|
||||||
|
|
||||||
|
sp.insert(shield, &shield);
|
||||||
|
}
|
||||||
|
|
||||||
|
for (QHash<Label::Shield, QPolygonF>::const_iterator it
|
||||||
|
= shields.constBegin(); it != shields.constEnd(); ++it) {
|
||||||
|
const QPolygonF &p = it.value();
|
||||||
|
QRectF rect(p.boundingRect() & tileRect);
|
||||||
|
if (AREA(rect) < AREA(QRect(0, 0, _img.width()/4, _img.width()/4)))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
QMap<qreal, int> map;
|
||||||
|
QPointF center = rect.center();
|
||||||
|
for (int j = 0; j < p.size(); j++) {
|
||||||
|
QLineF l(p.at(j), center);
|
||||||
|
map.insert(l.length(), j);
|
||||||
|
}
|
||||||
|
|
||||||
|
QMap<qreal, int>::const_iterator jt = map.constBegin();
|
||||||
|
|
||||||
|
TextPointItem *item = new TextPointItem(
|
||||||
|
p.at(jt.value()).toPoint(), &(sp.value(it.key())->text()),
|
||||||
|
poiFont(), 0, &shieldColor, shieldBgColor(it.key().type()));
|
||||||
|
|
||||||
|
bool valid = false;
|
||||||
|
while (true) {
|
||||||
|
if (!item->collides(textItems)
|
||||||
|
&& tileRect.contains(item->boundingRect().toRect())) {
|
||||||
|
valid = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (++jt == map.constEnd())
|
||||||
|
break;
|
||||||
|
item->setPos(p.at(jt.value()).toPoint());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (valid)
|
||||||
|
textItems.append(item);
|
||||||
|
else
|
||||||
|
delete item;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RasterTile::processPoints(QList<TextItem*> &textItems)
|
||||||
|
{
|
||||||
|
qSort(_points);
|
||||||
|
|
||||||
|
for (int i = 0; i < _points.size(); i++) {
|
||||||
|
MapData::Point &point = _points[i];
|
||||||
|
const Style::Point &style = _style->point(point.type);
|
||||||
|
|
||||||
|
if (point.poi && _zoom < minPOIZoom(Style::poiClass(point.type)))
|
||||||
|
continue;
|
||||||
|
|
||||||
|
const QString *label = point.label.text().isEmpty()
|
||||||
|
? 0 : &(point.label.text());
|
||||||
|
const QImage *img = style.img().isNull() ? 0 : &style.img();
|
||||||
|
const QFont *fnt = point.poi
|
||||||
|
? poiFont(style.textFontSize()) : font(style.textFontSize());
|
||||||
|
const QColor *color = style.textColor().isValid()
|
||||||
|
? &style.textColor() : 0;
|
||||||
|
|
||||||
|
if ((!label || !fnt) && !img)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (Style::isSpot(point.type))
|
||||||
|
point.label.setText(convertUnits(point.label.text()));
|
||||||
|
if (Style::isSummit(point.type) && !point.label.text().isEmpty()) {
|
||||||
|
QStringList list = point.label.text().split(" ");
|
||||||
|
list.last() = convertUnits(list.last());
|
||||||
|
point.label = list.join(" ");
|
||||||
|
}
|
||||||
|
|
||||||
|
TextPointItem *item = new TextPointItem(QPoint(point.coordinates.lon(),
|
||||||
|
point.coordinates.lat()), label, fnt, img, color);
|
||||||
|
if (item->isValid() && !item->collides(textItems))
|
||||||
|
textItems.append(item);
|
||||||
|
else
|
||||||
|
delete item;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
49
src/map/IMG/rastertile.h
Normal file
49
src/map/IMG/rastertile.h
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
#ifndef RASTERTILE_H
|
||||||
|
#define RASTERTILE_H
|
||||||
|
|
||||||
|
#include <QImage>
|
||||||
|
#include "mapdata.h"
|
||||||
|
|
||||||
|
class QPainter;
|
||||||
|
class TextItem;
|
||||||
|
class Style;
|
||||||
|
|
||||||
|
class RasterTile
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
RasterTile() : _style(0), _zoom(0) {}
|
||||||
|
RasterTile(const Style *style, int zoom, const QRect &rect,
|
||||||
|
const QString &key, const QList<MapData::Poly> &polygons,
|
||||||
|
const QList<MapData::Poly> &lines, QList<MapData::Point> &points)
|
||||||
|
: _style(style), _zoom(zoom), _xy(rect.topLeft()),
|
||||||
|
_key(key), _img(rect.size(), QImage::Format_ARGB32_Premultiplied),
|
||||||
|
_polygons(polygons), _lines(lines), _points(points) {}
|
||||||
|
|
||||||
|
const QString &key() const {return _key;}
|
||||||
|
const QPoint &xy() const {return _xy;}
|
||||||
|
const QImage &img() const {return _img;}
|
||||||
|
|
||||||
|
void render();
|
||||||
|
|
||||||
|
private:
|
||||||
|
void drawPolygons(QPainter *painter);
|
||||||
|
void drawLines(QPainter *painter);
|
||||||
|
void drawTextItems(QPainter *painter, const QList<TextItem*> &textItems);
|
||||||
|
|
||||||
|
void processPolygons(QList<TextItem *> &textItems);
|
||||||
|
void processLines(QList<TextItem*> &textItems);
|
||||||
|
void processPoints(QList<TextItem*> &textItems);
|
||||||
|
void processShields(const QRect &tileRect, QList<TextItem*> &textItems);
|
||||||
|
void processStreetNames(const QRect &tileRect, QList<TextItem*> &textItems);
|
||||||
|
|
||||||
|
const Style *_style;
|
||||||
|
int _zoom;
|
||||||
|
QPoint _xy;
|
||||||
|
QString _key;
|
||||||
|
QImage _img;
|
||||||
|
QList<MapData::Poly> _polygons;
|
||||||
|
QList<MapData::Poly> _lines;
|
||||||
|
QList<MapData::Point> _points;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // RASTERTILE_H
|
@ -1,6 +1,5 @@
|
|||||||
#include <QFile>
|
#include <QFile>
|
||||||
#include <QPainter>
|
#include <QPainter>
|
||||||
#include <QFont>
|
|
||||||
#include <QPixmapCache>
|
#include <QPixmapCache>
|
||||||
#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
|
#if QT_VERSION < QT_VERSION_CHECK(5, 0, 0)
|
||||||
#include <QtCore>
|
#include <QtCore>
|
||||||
@ -8,14 +7,11 @@
|
|||||||
#include <QtConcurrent>
|
#include <QtConcurrent>
|
||||||
#endif // QT_VERSION < 5
|
#endif // QT_VERSION < 5
|
||||||
#include "common/rectc.h"
|
#include "common/rectc.h"
|
||||||
#include "common/wgs84.h"
|
|
||||||
#include "common/range.h"
|
#include "common/range.h"
|
||||||
#include "IMG/textpathitem.h"
|
#include "common/wgs84.h"
|
||||||
#include "IMG/textpointitem.h"
|
|
||||||
#include "IMG/bitmapline.h"
|
|
||||||
#include "IMG/style.h"
|
|
||||||
#include "IMG/img.h"
|
#include "IMG/img.h"
|
||||||
#include "IMG/gmap.h"
|
#include "IMG/gmap.h"
|
||||||
|
#include "IMG/rastertile.h"
|
||||||
#include "osm.h"
|
#include "osm.h"
|
||||||
#include "pcs.h"
|
#include "pcs.h"
|
||||||
#include "rectd.h"
|
#include "rectd.h"
|
||||||
@ -25,213 +21,6 @@
|
|||||||
#define TILE_SIZE 384
|
#define TILE_SIZE 384
|
||||||
#define TEXT_EXTENT 160
|
#define TEXT_EXTENT 160
|
||||||
|
|
||||||
#define AREA(rect) \
|
|
||||||
(rect.size().width() * rect.size().height())
|
|
||||||
|
|
||||||
class RasterTile
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
RasterTile() : _map(0) {}
|
|
||||||
RasterTile(IMGMap *map, const QPoint &xy, const QString &key)
|
|
||||||
: _map(map), _xy(xy), _key(key),
|
|
||||||
_img(TILE_SIZE, TILE_SIZE, QImage::Format_ARGB32_Premultiplied) {}
|
|
||||||
|
|
||||||
const QString &key() const {return _key;}
|
|
||||||
const QPoint &xy() const {return _xy;}
|
|
||||||
QImage &img() {return _img;}
|
|
||||||
QList<MapData::Poly> &polygons() {return _polygons;}
|
|
||||||
QList<MapData::Poly> &lines() {return _lines;}
|
|
||||||
QList<MapData::Point> &points() {return _points;}
|
|
||||||
|
|
||||||
void render()
|
|
||||||
{
|
|
||||||
QList<TextItem*> textItems;
|
|
||||||
|
|
||||||
QRect tileRect(_xy, QSize(TILE_SIZE, TILE_SIZE));
|
|
||||||
|
|
||||||
_map->processPoints(_points, textItems);
|
|
||||||
_map->processPolygons(_polygons, textItems);
|
|
||||||
_map->processLines(_lines, tileRect, textItems);
|
|
||||||
|
|
||||||
_img.fill(Qt::transparent);
|
|
||||||
|
|
||||||
QPainter painter(&_img);
|
|
||||||
painter.setRenderHint(QPainter::SmoothPixmapTransform);
|
|
||||||
painter.setRenderHint(QPainter::Antialiasing);
|
|
||||||
painter.translate(-_xy.x(), -_xy.y());
|
|
||||||
|
|
||||||
_map->drawPolygons(&painter, _polygons);
|
|
||||||
_map->drawLines(&painter, _lines);
|
|
||||||
_map->drawTextItems(&painter, textItems);
|
|
||||||
//painter.setPen(Qt::red);
|
|
||||||
//painter.drawRect(QRect(_xy, QSize(TILE_SIZE, TILE_SIZE)));
|
|
||||||
|
|
||||||
qDeleteAll(textItems);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
IMGMap *_map;
|
|
||||||
QPoint _xy;
|
|
||||||
QString _key;
|
|
||||||
QImage _img;
|
|
||||||
QList<MapData::Poly> _polygons;
|
|
||||||
QList<MapData::Poly> _lines;
|
|
||||||
QList<MapData::Point> _points;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
static const QColor shieldColor(Qt::white);
|
|
||||||
static const QColor shieldBgColor1("#dd3e3e");
|
|
||||||
static const QColor shieldBgColor2("#379947");
|
|
||||||
static const QColor shieldBgColor3("#4a7fc1");
|
|
||||||
|
|
||||||
static QString convertUnits(const QString &str)
|
|
||||||
{
|
|
||||||
bool ok;
|
|
||||||
int number = str.toInt(&ok);
|
|
||||||
return ok ? QString::number(qRound(number * 0.3048)) : str;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int minPOIZoom(Style::POIClass cl)
|
|
||||||
{
|
|
||||||
switch (cl) {
|
|
||||||
case Style::Food:
|
|
||||||
case Style::Shopping:
|
|
||||||
case Style::Services:
|
|
||||||
return 27;
|
|
||||||
case Style::Accommodation:
|
|
||||||
case Style::Recreation:
|
|
||||||
return 25;
|
|
||||||
case Style::ManmadePlaces:
|
|
||||||
case Style::NaturePlaces:
|
|
||||||
case Style::Transport:
|
|
||||||
case Style::Community:
|
|
||||||
case Style::Elementary:
|
|
||||||
return 23;
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static QFont pixelSizeFont(int pixelSize)
|
|
||||||
{
|
|
||||||
QFont f;
|
|
||||||
f.setPixelSize(pixelSize);
|
|
||||||
return f;
|
|
||||||
}
|
|
||||||
|
|
||||||
static QFont *font(Style::FontSize size, Style::FontSize defaultSize
|
|
||||||
= Style::Normal)
|
|
||||||
{
|
|
||||||
/* The fonts must be initialized on first usage (after the QGuiApplication
|
|
||||||
instance is created) */
|
|
||||||
static QFont large = pixelSizeFont(16);
|
|
||||||
static QFont normal = pixelSizeFont(14);
|
|
||||||
static QFont small = pixelSizeFont(12);
|
|
||||||
static QFont extraSmall = pixelSizeFont(10);
|
|
||||||
|
|
||||||
switch (size) {
|
|
||||||
case Style::None:
|
|
||||||
return 0;
|
|
||||||
case Style::Large:
|
|
||||||
return &large;
|
|
||||||
case Style::Normal:
|
|
||||||
return &normal;
|
|
||||||
case Style::Small:
|
|
||||||
return &small;
|
|
||||||
case Style::ExtraSmall:
|
|
||||||
return &extraSmall;
|
|
||||||
default:
|
|
||||||
return font(defaultSize);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static QFont *poiFont(Style::FontSize size = Style::Normal)
|
|
||||||
{
|
|
||||||
static QFont poi = pixelSizeFont(10);
|
|
||||||
|
|
||||||
switch (size) {
|
|
||||||
case Style::None:
|
|
||||||
return 0;
|
|
||||||
default:
|
|
||||||
return &poi;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static const QColor *shieldBgColor(Label::Shield::Type type)
|
|
||||||
{
|
|
||||||
switch (type) {
|
|
||||||
case Label::Shield::USInterstate:
|
|
||||||
case Label::Shield::Hbox:
|
|
||||||
return &shieldBgColor1;
|
|
||||||
case Label::Shield::USShield:
|
|
||||||
case Label::Shield::Box:
|
|
||||||
return &shieldBgColor2;
|
|
||||||
case Label::Shield::USRound:
|
|
||||||
case Label::Shield::Oval:
|
|
||||||
return &shieldBgColor3;
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static int minShieldZoom(Label::Shield::Type type)
|
|
||||||
{
|
|
||||||
switch (type) {
|
|
||||||
case Label::Shield::USInterstate:
|
|
||||||
case Label::Shield::Hbox:
|
|
||||||
return 17;
|
|
||||||
case Label::Shield::USShield:
|
|
||||||
case Label::Shield::Box:
|
|
||||||
return 19;
|
|
||||||
case Label::Shield::USRound:
|
|
||||||
case Label::Shield::Oval:
|
|
||||||
return 20;
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static qreal area(const QVector<QPointF> &polygon)
|
|
||||||
{
|
|
||||||
qreal area = 0;
|
|
||||||
|
|
||||||
for (int i = 0; i < polygon.size(); i++) {
|
|
||||||
int j = (i + 1) % polygon.size();
|
|
||||||
area += polygon.at(i).x() * polygon.at(j).y();
|
|
||||||
area -= polygon.at(i).y() * polygon.at(j).x();
|
|
||||||
}
|
|
||||||
area /= 2.0;
|
|
||||||
|
|
||||||
return area;
|
|
||||||
}
|
|
||||||
|
|
||||||
static QPointF centroid(const QVector<QPointF> &polygon)
|
|
||||||
{
|
|
||||||
qreal cx = 0, cy = 0;
|
|
||||||
qreal factor = 1.0 / (6.0 * area(polygon));
|
|
||||||
|
|
||||||
for (int i = 0; i < polygon.size(); i++) {
|
|
||||||
int j = (i + 1) % polygon.size();
|
|
||||||
qreal f = (polygon.at(i).x() * polygon.at(j).y() - polygon.at(j).x()
|
|
||||||
* polygon.at(i).y());
|
|
||||||
cx += (polygon.at(i).x() + polygon.at(j).x()) * f;
|
|
||||||
cy += (polygon.at(i).y() + polygon.at(j).y()) * f;
|
|
||||||
}
|
|
||||||
|
|
||||||
return QPointF(cx * factor, cy * factor);
|
|
||||||
}
|
|
||||||
|
|
||||||
static bool rectNearPolygon(const QPolygonF &polygon, const QRectF &rect)
|
|
||||||
{
|
|
||||||
return (polygon.boundingRect().contains(rect)
|
|
||||||
&& (polygon.containsPoint(rect.topLeft(), Qt::OddEvenFill)
|
|
||||||
|| polygon.containsPoint(rect.topRight(), Qt::OddEvenFill)
|
|
||||||
|| polygon.containsPoint(rect.bottomLeft(), Qt::OddEvenFill)
|
|
||||||
|| polygon.containsPoint(rect.bottomRight(), Qt::OddEvenFill)));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
IMGMap::IMGMap(const QString &fileName, QObject *parent)
|
IMGMap::IMGMap(const QString &fileName, QObject *parent)
|
||||||
: Map(parent), _projection(PCS::pcs(3857)), _valid(false)
|
: Map(parent), _projection(PCS::pcs(3857)), _valid(false)
|
||||||
{
|
{
|
||||||
@ -331,233 +120,22 @@ Coordinates IMGMap::xy2ll(const QPointF &p)
|
|||||||
return _projection.xy2ll(_transform.img2proj(p));
|
return _projection.xy2ll(_transform.img2proj(p));
|
||||||
}
|
}
|
||||||
|
|
||||||
void IMGMap::drawPolygons(QPainter *painter, const QList<MapData::Poly> &polygons)
|
void IMGMap::ll2xy(QList<MapData::Poly> &polys)
|
||||||
{
|
{
|
||||||
for (int n = 0; n < _data->style()->drawOrder().size(); n++) {
|
for (int i = 0; i < polys.size(); i++) {
|
||||||
for (int i = 0; i < polygons.size(); i++) {
|
MapData::Poly &poly = polys[i];
|
||||||
const MapData::Poly &poly = polygons.at(i);
|
|
||||||
if (poly.type != _data->style()->drawOrder().at(n))
|
|
||||||
continue;
|
|
||||||
const Style::Polygon &style = _data->style()->polygon(poly.type);
|
|
||||||
|
|
||||||
painter->setPen(style.pen());
|
|
||||||
painter->setBrush(style.brush());
|
|
||||||
painter->drawPolygon(poly.points);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::drawLines(QPainter *painter, const QList<MapData::Poly> &lines)
|
|
||||||
{
|
|
||||||
painter->setBrush(Qt::NoBrush);
|
|
||||||
|
|
||||||
for (int i = 0; i < lines.size(); i++) {
|
|
||||||
const MapData::Poly &poly = lines.at(i);
|
|
||||||
const Style::Line &style = _data->style()->line(poly.type);
|
|
||||||
|
|
||||||
if (style.background() == Qt::NoPen)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
painter->setPen(style.background());
|
|
||||||
painter->drawPolyline(poly.points);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int i = 0; i < lines.size(); i++) {
|
|
||||||
const MapData::Poly &poly = lines.at(i);
|
|
||||||
const Style::Line &style = _data->style()->line(poly.type);
|
|
||||||
|
|
||||||
if (!style.img().isNull())
|
|
||||||
BitmapLine::draw(painter, poly.points, style.img());
|
|
||||||
else if (style.foreground() != Qt::NoPen) {
|
|
||||||
painter->setPen(style.foreground());
|
|
||||||
painter->drawPolyline(poly.points);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::drawTextItems(QPainter *painter, const QList<TextItem*> &textItems)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < textItems.size(); i++)
|
|
||||||
textItems.at(i)->paint(painter);
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::processPolygons(QList<MapData::Poly> &polygons,
|
|
||||||
QList<TextItem*> &textItems)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < polygons.size(); i++) {
|
|
||||||
MapData::Poly &poly = polygons[i];
|
|
||||||
for (int j = 0; j < poly.points.size(); j++) {
|
|
||||||
QPointF &p = poly.points[j];
|
|
||||||
p = ll2xy(Coordinates(p.x(), p.y()));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (poly.label.text().isEmpty())
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (_zoom <= 23 && (Style::isWaterArea(poly.type)
|
|
||||||
|| Style::isMilitaryArea(poly.type)
|
|
||||||
|| Style::isNatureReserve(poly.type))) {
|
|
||||||
const Style::Polygon &style = _data->style()->polygon(poly.type);
|
|
||||||
TextPointItem *item = new TextPointItem(
|
|
||||||
centroid(poly.points).toPoint(), &poly.label.text(),
|
|
||||||
poiFont(), 0, &style.brush().color());
|
|
||||||
if (item->isValid() && !item->collides(textItems)
|
|
||||||
&& rectNearPolygon(poly.points, item->boundingRect()))
|
|
||||||
textItems.append(item);
|
|
||||||
else
|
|
||||||
delete item;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::processLines(QList<MapData::Poly> &lines, const QRect &tileRect,
|
|
||||||
QList<TextItem*> &textItems)
|
|
||||||
{
|
|
||||||
qStableSort(lines);
|
|
||||||
|
|
||||||
for (int i = 0; i < lines.size(); i++) {
|
|
||||||
MapData::Poly &poly = lines[i];
|
|
||||||
for (int j = 0; j < poly.points.size(); j++) {
|
for (int j = 0; j < poly.points.size(); j++) {
|
||||||
QPointF &p = poly.points[j];
|
QPointF &p = poly.points[j];
|
||||||
p = ll2xy(Coordinates(p.x(), p.y()));
|
p = ll2xy(Coordinates(p.x(), p.y()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_zoom >= 22)
|
|
||||||
processStreetNames(lines, tileRect, textItems);
|
|
||||||
processShields(lines, tileRect, textItems);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void IMGMap::processStreetNames(QList<MapData::Poly> &lines,
|
void IMGMap::ll2xy(QList<MapData::Point> &points)
|
||||||
const QRect &tileRect, QList<TextItem*> &textItems)
|
|
||||||
{
|
{
|
||||||
for (int i = 0; i < lines.size(); i++) {
|
|
||||||
MapData::Poly &poly = lines[i];
|
|
||||||
const Style::Line &style = _data->style()->line(poly.type);
|
|
||||||
|
|
||||||
if (style.img().isNull() && style.foreground() == Qt::NoPen)
|
|
||||||
continue;
|
|
||||||
if (poly.label.text().isEmpty()
|
|
||||||
|| style.textFontSize() == Style::None)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (Style::isContourLine(poly.type))
|
|
||||||
poly.label.setText(convertUnits(poly.label.text()));
|
|
||||||
|
|
||||||
const QFont *fnt = font(style.textFontSize(), Style::Small);
|
|
||||||
const QColor *color = style.textColor().isValid()
|
|
||||||
? &style.textColor() : 0;
|
|
||||||
|
|
||||||
TextPathItem *item = new TextPathItem(poly.points,
|
|
||||||
&poly.label.text(), tileRect, fnt, color);
|
|
||||||
if (item->isValid() && !item->collides(textItems))
|
|
||||||
textItems.append(item);
|
|
||||||
else
|
|
||||||
delete item;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::processShields(QList<MapData::Poly> &lines, const QRect &tileRect,
|
|
||||||
QList<TextItem*> &textItems)
|
|
||||||
{
|
|
||||||
for (int type = FIRST_SHIELD; type <= LAST_SHIELD; type++) {
|
|
||||||
if (minShieldZoom(static_cast<Label::Shield::Type>(type)) > _zoom)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
QHash<Label::Shield, QPolygonF> shields;
|
|
||||||
QHash<Label::Shield, const Label::Shield*> sp;
|
|
||||||
|
|
||||||
for (int i = 0; i < lines.size(); i++) {
|
|
||||||
const MapData::Poly &poly = lines.at(i);
|
|
||||||
const Label::Shield &shield = poly.label.shield();
|
|
||||||
if (!shield.isValid() || shield.type() != type
|
|
||||||
|| !Style::isMajorRoad(poly.type))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
QPolygonF &p = shields[shield];
|
|
||||||
for (int j = 0; j < poly.points.size(); j++)
|
|
||||||
p.append(poly.points.at(j));
|
|
||||||
|
|
||||||
sp.insert(shield, &shield);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (QHash<Label::Shield, QPolygonF>::const_iterator it
|
|
||||||
= shields.constBegin(); it != shields.constEnd(); ++it) {
|
|
||||||
const QPolygonF &p = it.value();
|
|
||||||
QRectF rect(p.boundingRect() & tileRect);
|
|
||||||
if (qSqrt(AREA(rect)) < TILE_SIZE/4)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
QMap<qreal, int> map;
|
|
||||||
QPointF center = rect.center();
|
|
||||||
for (int j = 0; j < p.size(); j++) {
|
|
||||||
QLineF l(p.at(j), center);
|
|
||||||
map.insert(l.length(), j);
|
|
||||||
}
|
|
||||||
|
|
||||||
QMap<qreal, int>::const_iterator jt = map.constBegin();
|
|
||||||
|
|
||||||
TextPointItem *item = new TextPointItem(
|
|
||||||
p.at(jt.value()).toPoint(), &(sp.value(it.key())->text()),
|
|
||||||
poiFont(), 0, &shieldColor, shieldBgColor(it.key().type()));
|
|
||||||
|
|
||||||
bool valid = false;
|
|
||||||
while (true) {
|
|
||||||
if (!item->collides(textItems)
|
|
||||||
&& tileRect.contains(item->boundingRect().toRect())) {
|
|
||||||
valid = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (++jt == map.constEnd())
|
|
||||||
break;
|
|
||||||
item->setPos(p.at(jt.value()).toPoint());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (valid)
|
|
||||||
textItems.append(item);
|
|
||||||
else
|
|
||||||
delete item;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void IMGMap::processPoints(QList<MapData::Point> &points,
|
|
||||||
QList<TextItem*> &textItems)
|
|
||||||
{
|
|
||||||
qSort(points);
|
|
||||||
|
|
||||||
for (int i = 0; i < points.size(); i++) {
|
for (int i = 0; i < points.size(); i++) {
|
||||||
MapData::Point &point = points[i];
|
QPointF p(ll2xy(points.at(i).coordinates));
|
||||||
const Style::Point &style = _data->style()->point(point.type);
|
points[i].coordinates = Coordinates(p.x(), p.y());
|
||||||
|
|
||||||
if (point.poi && _zoom < minPOIZoom(Style::poiClass(point.type)))
|
|
||||||
continue;
|
|
||||||
|
|
||||||
const QString *label = point.label.text().isEmpty()
|
|
||||||
? 0 : &(point.label.text());
|
|
||||||
const QImage *img = style.img().isNull() ? 0 : &style.img();
|
|
||||||
const QFont *fnt = point.poi
|
|
||||||
? poiFont(style.textFontSize()) : font(style.textFontSize());
|
|
||||||
const QColor *color = style.textColor().isValid()
|
|
||||||
? &style.textColor() : 0;
|
|
||||||
|
|
||||||
if ((!label || !fnt) && !img)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
if (Style::isSpot(point.type))
|
|
||||||
point.label.setText(convertUnits(point.label.text()));
|
|
||||||
if (Style::isSummit(point.type) && !point.label.text().isEmpty()) {
|
|
||||||
QStringList list = point.label.text().split(" ");
|
|
||||||
list.last() = convertUnits(list.last());
|
|
||||||
point.label = list.join(" ");
|
|
||||||
}
|
|
||||||
|
|
||||||
TextPointItem *item = new TextPointItem(
|
|
||||||
ll2xy(point.coordinates).toPoint(), label, fnt, img, color);
|
|
||||||
if (item->isValid() && !item->collides(textItems))
|
|
||||||
textItems.append(item);
|
|
||||||
else
|
|
||||||
delete item;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -587,8 +165,8 @@ void IMGMap::draw(QPainter *painter, const QRectF &rect, Flags flags)
|
|||||||
if (QPixmapCache::find(key, pm))
|
if (QPixmapCache::find(key, pm))
|
||||||
painter->drawPixmap(ttl, pm);
|
painter->drawPixmap(ttl, pm);
|
||||||
else {
|
else {
|
||||||
tiles.append(RasterTile(this, ttl, key));
|
QList<MapData::Poly> polygons, lines;
|
||||||
RasterTile &tile = tiles.last();
|
QList<MapData::Point> points;
|
||||||
|
|
||||||
QRectF polyRect(ttl, QPointF(ttl.x() + TILE_SIZE,
|
QRectF polyRect(ttl, QPointF(ttl.x() + TILE_SIZE,
|
||||||
ttl.y() + TILE_SIZE));
|
ttl.y() + TILE_SIZE));
|
||||||
@ -596,7 +174,8 @@ void IMGMap::draw(QPainter *painter, const QRectF &rect, Flags flags)
|
|||||||
RectD polyRectD(_transform.img2proj(polyRect.topLeft()),
|
RectD polyRectD(_transform.img2proj(polyRect.topLeft()),
|
||||||
_transform.img2proj(polyRect.bottomRight()));
|
_transform.img2proj(polyRect.bottomRight()));
|
||||||
_data->polys(polyRectD.toRectC(_projection, 4), _zoom,
|
_data->polys(polyRectD.toRectC(_projection, 4), _zoom,
|
||||||
&(tile.polygons()), &(tile.lines()));
|
&polygons, &lines);
|
||||||
|
ll2xy(polygons); ll2xy(lines);
|
||||||
|
|
||||||
QRectF pointRect(QPointF(ttl.x() - TEXT_EXTENT,
|
QRectF pointRect(QPointF(ttl.x() - TEXT_EXTENT,
|
||||||
ttl.y() - TEXT_EXTENT), QPointF(ttl.x() + TILE_SIZE
|
ttl.y() - TEXT_EXTENT), QPointF(ttl.x() + TILE_SIZE
|
||||||
@ -605,7 +184,12 @@ void IMGMap::draw(QPainter *painter, const QRectF &rect, Flags flags)
|
|||||||
RectD pointRectD(_transform.img2proj(pointRect.topLeft()),
|
RectD pointRectD(_transform.img2proj(pointRect.topLeft()),
|
||||||
_transform.img2proj(pointRect.bottomRight()));
|
_transform.img2proj(pointRect.bottomRight()));
|
||||||
_data->points(pointRectD.toRectC(_projection, 4), _zoom,
|
_data->points(pointRectD.toRectC(_projection, 4), _zoom,
|
||||||
&(tile.points()));
|
&points);
|
||||||
|
ll2xy(points);
|
||||||
|
|
||||||
|
tiles.append(RasterTile(_data->style(), _zoom,
|
||||||
|
QRect(ttl, QSize(TILE_SIZE, TILE_SIZE)), key, polygons, lines,
|
||||||
|
points));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,6 @@
|
|||||||
#include "transform.h"
|
#include "transform.h"
|
||||||
#include "IMG/mapdata.h"
|
#include "IMG/mapdata.h"
|
||||||
|
|
||||||
class TextItem;
|
|
||||||
|
|
||||||
class IMGMap : public Map
|
class IMGMap : public Map
|
||||||
{
|
{
|
||||||
@ -40,23 +39,10 @@ public:
|
|||||||
QString errorString() const {return _errorString;}
|
QString errorString() const {return _errorString;}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend class RasterTile;
|
void ll2xy(QList<MapData::Poly> &polys);
|
||||||
|
void ll2xy(QList<MapData::Point> &points);
|
||||||
Transform transform(int zoom) const;
|
Transform transform(int zoom) const;
|
||||||
void updateTransform();
|
void updateTransform();
|
||||||
void drawPolygons(QPainter *painter, const QList<MapData::Poly> &polygons);
|
|
||||||
void drawLines(QPainter *painter, const QList<MapData::Poly> &lines);
|
|
||||||
void drawTextItems(QPainter *painter, const QList<TextItem*> &textItems);
|
|
||||||
|
|
||||||
void processPolygons(QList<MapData::Poly> &polygons,
|
|
||||||
QList<TextItem *> &textItems);
|
|
||||||
void processLines(QList<MapData::Poly> &lines, const QRect &tileRect,
|
|
||||||
QList<TextItem*> &textItems);
|
|
||||||
void processPoints(QList<MapData::Point> &points, QList<TextItem*> &textItems);
|
|
||||||
void processShields(QList<MapData::Poly> &lines, const QRect &tileRect,
|
|
||||||
QList<TextItem*> &textItems);
|
|
||||||
void processStreetNames(QList<MapData::Poly> &lines, const QRect &tileRect,
|
|
||||||
QList<TextItem*> &textItems);
|
|
||||||
|
|
||||||
MapData *_data;
|
MapData *_data;
|
||||||
int _zoom;
|
int _zoom;
|
||||||
|
Loading…
Reference in New Issue
Block a user