From b9acb26c073e18da3057df45057553605e04b54b Mon Sep 17 00:00:00 2001 From: James Turner Date: Thu, 12 Nov 2015 00:10:06 +0000 Subject: [PATCH] Work on launcher diagrams. --- src/GUI/AirportDiagram.cxx | 8 +++-- src/GUI/BaseDiagram.cxx | 62 ++++++++++++++++++++++++++++++------ src/GUI/BaseDiagram.hxx | 9 +++++- src/GUI/NavaidDiagram.cxx | 11 +++++++ src/GUI/airplane-icon.png | Bin 0 -> 2064 bytes src/GUI/ndb-large-icon.png | Bin 0 -> 8872 bytes src/GUI/ndb-small-icon .png | Bin 0 -> 1863 bytes src/GUI/resources.qrc | 3 ++ src/Navaids/CacheSchema.h | 2 +- src/Navaids/navdb.cxx | 13 ++++++-- src/Navaids/navrecord.cxx | 10 ++++++ src/Navaids/navrecord.hxx | 44 +++++++++++++------------ 12 files changed, 125 insertions(+), 37 deletions(-) create mode 100644 src/GUI/airplane-icon.png create mode 100644 src/GUI/ndb-large-icon.png create mode 100644 src/GUI/ndb-small-icon .png diff --git a/src/GUI/AirportDiagram.cxx b/src/GUI/AirportDiagram.cxx index a800bf1e2..449957dfd 100644 --- a/src/GUI/AirportDiagram.cxx +++ b/src/GUI/AirportDiagram.cxx @@ -103,6 +103,9 @@ void AirportDiagram::setAirport(FGAirportRef apt) buildPavements(); } + clearIgnoredNavaids(); + addIgnoredNavaid(apt); + recomputeBounds(true); update(); } @@ -204,8 +207,9 @@ void AirportDiagram::paintContents(QPainter* p) p->setFont(f); // draw ILS first so underneath all runways - QPen pen(Qt::magenta); - pen.setWidth(1.0 / m_scale); + QPen pen(QColor(0x5f, 0x5f, 0x5f)); + pen.setWidth(1); + pen.setCosmetic(true); p->setPen(pen); Q_FOREACH(const RunwayData& r, m_runways) { diff --git a/src/GUI/BaseDiagram.cxx b/src/GUI/BaseDiagram.cxx index 1c938a0a0..bced50f42 100644 --- a/src/GUI/BaseDiagram.cxx +++ b/src/GUI/BaseDiagram.cxx @@ -66,6 +66,18 @@ QTransform BaseDiagram::transform() const return t; } +void BaseDiagram::clearIgnoredNavaids() +{ + m_ignored.clear(); +} + +void BaseDiagram::addIgnoredNavaid(FGPositionedRef pos) +{ + if (isNavaidIgnored(pos)) + return; + m_ignored.push_back(pos); +} + void BaseDiagram::extendRect(QRectF &r, const QPointF &p) { if (p.x() < r.left()) { @@ -148,10 +160,14 @@ void BaseDiagram::paintNavaids(QPainter* painter) FGPositionedList::const_iterator it; for (it = items.begin(); it != items.end(); ++it) { + FGPositionedRef pos(*it); bool drawAsIcon = true; + if (isNavaidIgnored(pos)) + continue; - if ((*it)->type() == FGPositioned::AIRPORT) { - FGAirport* apt = static_cast(it->ptr()); + FGPositioned::Type ty(pos->type()); + if (ty == FGPositioned::AIRPORT) { + FGAirport* apt = static_cast(pos.ptr()); if (apt->hasHardRunwayOfLengthFt(minRunwayLengthFt)) { drawAsIcon = false; @@ -173,10 +189,32 @@ void BaseDiagram::paintNavaids(QPainter* painter) } if (drawAsIcon) { - QPixmap pm = iconForPositioned(*it); - QPointF loc = xf.map(project((*it)->geod())); - loc -= QPointF(pm.width() >> 1, pm.height() >> 1); - painter->drawPixmap(loc, pm); + QPixmap pm = iconForPositioned(pos, false); + QPointF loc = xf.map(project(pos->geod())); + + QPointF iconLoc = loc - QPointF(pm.width() >> 1, pm.height() >> 1); + painter->drawPixmap(iconLoc, pm); + + painter->setPen(QColor(0x03, 0x83, 0xbf)); + + QString label; + if (FGAirport::isAirportType(pos.ptr())) { + label = QString::fromStdString((*it)->name()); + } else { + label = QString::fromStdString((*it)->ident()); + } + + if (ty == FGPositioned::NDB) { + FGNavRecord* nav = static_cast(pos.ptr()); + label.append("\n").append(QString::number(nav->get_freq() / 100)); + } else if (ty == FGPositioned::VOR) { + FGNavRecord* nav = static_cast(pos.ptr()); + label.append("\n").append(QString::number(nav->get_freq() / 100.0, 'f', 1)); + } + + QRect labelBox(loc.x() + (pm.width()/2) + 4, loc.y() - 50, 100, 100); + painter->drawText(labelBox, Qt::AlignVCenter | Qt::AlignLeft | Qt::TextWordWrap, + label); } } @@ -184,6 +222,11 @@ void BaseDiagram::paintNavaids(QPainter* painter) painter->setTransform(xf); } +bool BaseDiagram::isNavaidIgnored(const FGPositionedRef &pos) const +{ + return m_ignored.contains(pos); +} + void BaseDiagram::mousePressEvent(QMouseEvent *me) { m_lastMousePos = me->pos(); @@ -336,7 +379,7 @@ QPointF BaseDiagram::project(const SGGeod& geod) const return project(geod, m_projectionCenter); } -QPixmap BaseDiagram::iconForPositioned(const FGPositionedRef& pos) +QPixmap BaseDiagram::iconForPositioned(const FGPositionedRef& pos, bool small) { // if airport type, check towered or untowered @@ -348,7 +391,8 @@ QPixmap BaseDiagram::iconForPositioned(const FGPositionedRef& pos) switch (pos->type()) { case FGPositioned::VOR: - // check for VORTAC + if (static_cast(pos.ptr())->isVORTAC()) + return QPixmap(":/vortac-icon"); if (static_cast(pos.ptr())->hasDME()) return QPixmap(":/vor-dme-icon"); @@ -363,7 +407,7 @@ QPixmap BaseDiagram::iconForPositioned(const FGPositionedRef& pos) case FGPositioned::SEAPORT: return QPixmap(isTowered ? ":/seaport-tower-icon" : ":/seaport-icon"); case FGPositioned::NDB: - return QPixmap(":/ndb-icon"); + return QPixmap(small ? ":/ndb-small-icon" : ":/ndb-icon"); case FGPositioned::FIX: return QPixmap(":/waypoint-icon"); diff --git a/src/GUI/BaseDiagram.hxx b/src/GUI/BaseDiagram.hxx index 9ad65eb84..9c82d21ab 100644 --- a/src/GUI/BaseDiagram.hxx +++ b/src/GUI/BaseDiagram.hxx @@ -35,7 +35,7 @@ class BaseDiagram : public QWidget public: BaseDiagram(QWidget* pr); - static QPixmap iconForPositioned(const FGPositionedRef &pos); + static QPixmap iconForPositioned(const FGPositionedRef &pos, bool small); static QPixmap iconForAirport(FGAirport *apt); static QVector projectAirportRuwaysIntoRect(FGAirportRef apt, const QRectF& bounds); @@ -50,6 +50,7 @@ protected: virtual void paintContents(QPainter*); + protected: void recomputeBounds(bool resetZoom); @@ -59,6 +60,9 @@ protected: QPointF project(const SGGeod& geod) const; QTransform transform() const; + void clearIgnoredNavaids(); + void addIgnoredNavaid(FGPositionedRef pos); + SGGeod m_projectionCenter; double m_scale; QRectF m_bounds; @@ -75,6 +79,9 @@ protected: private: void paintNavaids(QPainter *p); + bool isNavaidIgnored(const FGPositionedRef& pos) const; + + QVector m_ignored; }; #endif // of GUI_BASEDIAGRAM_HXX diff --git a/src/GUI/NavaidDiagram.cxx b/src/GUI/NavaidDiagram.cxx index fa6b78c2c..c2b139ef6 100644 --- a/src/GUI/NavaidDiagram.cxx +++ b/src/GUI/NavaidDiagram.cxx @@ -77,6 +77,8 @@ void NavaidDiagram::paintContents(QPainter *painter) { QPointF base = project(m_geod); + QPointF airplaneIconPos = base; + if (m_offsetEnabled) { double d = m_offsetDistanceNm * SG_NM_TO_METER; SGGeod offsetGeod = SGGeodesy::direct(m_geod, m_offsetBearingDeg, d); @@ -86,7 +88,16 @@ void NavaidDiagram::paintContents(QPainter *painter) pen.setCosmetic(true); painter->setPen(pen); painter->drawLine(base, offset); + + airplaneIconPos = offset; } + + QPixmap pix(":/airplane-icon"); + airplaneIconPos = painter->transform().map(airplaneIconPos); + painter->resetTransform(); + QRect airplaneIconRect = pix.rect(); + airplaneIconRect.moveCenter(airplaneIconPos.toPoint()); + painter->drawPixmap(airplaneIconRect, pix); } void NavaidDiagram::doComputeBounds() diff --git a/src/GUI/airplane-icon.png b/src/GUI/airplane-icon.png new file mode 100644 index 0000000000000000000000000000000000000000..b688e513f065e465cc7fe60d8edf3d330c810881 GIT binary patch literal 2064 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 literal 0 HcmV?d00001 diff --git a/src/GUI/resources.qrc b/src/GUI/resources.qrc index c48a7d40f..6eb011e58 100644 --- a/src/GUI/resources.qrc +++ b/src/GUI/resources.qrc @@ -15,5 +15,8 @@ airport-tower-icon.png vor-dme-icon.png seaport-tower-icon.png + ndb-small-icon .png + ndb-large-icon.png + airplane-icon.png diff --git a/src/Navaids/CacheSchema.h b/src/Navaids/CacheSchema.h index 297ab3e11..b3665beb2 100644 --- a/src/Navaids/CacheSchema.h +++ b/src/Navaids/CacheSchema.h @@ -1,7 +1,7 @@ #ifndef FG_NAVCACHE_SCHEMA_HXX #define FG_NAVCACHE_SCHEMA_HXX -const int SCHEMA_VERSION = 10; +const int SCHEMA_VERSION = 14; #define SCHEMA_SQL \ "CREATE TABLE properties (key VARCHAR, value VARCHAR);" \ diff --git a/src/Navaids/navdb.cxx b/src/Navaids/navdb.cxx index 486a27d97..ac0cd6e31 100644 --- a/src/Navaids/navdb.cxx +++ b/src/Navaids/navdb.cxx @@ -184,6 +184,10 @@ static PositionedID readNavFromStream(std::istream& aStream, PositionedID navaid_dme = 0; if (type == FGPositioned::DME) { + // complication here: the database doesn't record TACAN sites at all, + // we simply infer their existence from DMEs whose name includes 'VORTAC' + // or 'TACAN' (since all TACAN stations include DME) + // hence the cache never actually includes entries of type TACAN FGPositioned::TypeFilter f(FGPositioned::INVALID); if ( name.find("VOR-DME") != std::string::npos ) { f.addType(FGPositioned::VOR); @@ -194,8 +198,6 @@ static PositionedID readNavFromStream(std::istream& aStream, f.addType(FGPositioned::VOR); } else if ( name.find("NDB-DME") != std::string::npos ) { f.addType(FGPositioned::NDB); - } else if ( name.find("TACAN") != std::string::npos ) { - f.addType(FGPositioned::VOR); } if (f.maxType() > 0) { @@ -206,9 +208,14 @@ static PositionedID readNavFromStream(std::istream& aStream, if ( simgear::strutils::uppercase(navaid_part[0]) == simgear::strutils::uppercase(dme_part[0]) ) { navaid_dme = ref.get()->guid(); + } else { + SG_LOG(SG_NAVAID, SG_WARN, "DME " << ident << " (" << name << "), closest match has wrong name:" + << ref->ident() << " (" << ref->name() << ")"); } + } else { + SG_LOG(SG_NAVAID, SG_WARN, "Couldn't find navaid for DME:" << ident << " (" << name << ")"); } - } + } // of have a co-located navaid to locate } if ((type >= FGPositioned::ILS) && (type <= FGPositioned::GS)) { diff --git a/src/Navaids/navrecord.cxx b/src/Navaids/navrecord.cxx index fabc9a0d0..c65e9491b 100644 --- a/src/Navaids/navrecord.cxx +++ b/src/Navaids/navrecord.cxx @@ -98,6 +98,16 @@ bool FGNavRecord::hasDME() return (mColocated > 0); } + + +bool FGNavRecord::isVORTAC() const +{ + if (mType != VOR) + return false; + + return mName.find(" VORTAC") != std::string::npos; +} + void FGNavRecord::setColocatedDME(PositionedID other) { mColocated = other; diff --git a/src/Navaids/navrecord.hxx b/src/Navaids/navrecord.hxx index 0091ac651..f2178fcf9 100644 --- a/src/Navaids/navrecord.hxx +++ b/src/Navaids/navrecord.hxx @@ -79,27 +79,29 @@ class FGNavRecord : public FGPositioned inline bool get_serviceable() const { return serviceable; } inline const char *get_trans_ident() const { return get_ident(); } - virtual const std::string& name() const - { return mName; } - - /** - * Retrieve the runway this navaid is associated with (for ILS/LOC/GS) - */ - FGRunwayRef runway() const; - - /** - * return the localizer width, in degrees - * computation is based up ICAO stdandard width at the runway threshold - * see implementation for further details. - */ - double localizerWidth() const; - - void bindToNode(SGPropertyNode* nd) const; - void unbindFromNode(SGPropertyNode* nd) const; - - void setColocatedDME(PositionedID other); - bool hasDME(); - + virtual const std::string& name() const + { return mName; } + + /** + * Retrieve the runway this navaid is associated with (for ILS/LOC/GS) + */ + FGRunwayRef runway() const; + + /** + * return the localizer width, in degrees + * computation is based up ICAO stdandard width at the runway threshold + * see implementation for further details. + */ + double localizerWidth() const; + + void bindToNode(SGPropertyNode* nd) const; + void unbindFromNode(SGPropertyNode* nd) const; + + void setColocatedDME(PositionedID other); + bool hasDME(); + + bool isVORTAC() const; + void updateFromXML(const SGGeod& geod, double heading); }; -- 2.39.5