mirror of
				https://github.com/ciphervance/supercell-wx.git
				synced 2025-10-31 09:30:05 +00:00 
			
		
		
		
	Add custom marker icons, and rework how marker icons are handled.
This commit is contained in:
		
							parent
							
								
									3685599693
								
							
						
					
					
						commit
						5bb4a7f95a
					
				
					 10 changed files with 368 additions and 204 deletions
				
			
		|  | @ -239,7 +239,6 @@ set(SRC_TYPES source/scwx/qt/types/alert_types.cpp | ||||||
|               source/scwx/qt/types/layer_types.cpp |               source/scwx/qt/types/layer_types.cpp | ||||||
|               source/scwx/qt/types/location_types.cpp |               source/scwx/qt/types/location_types.cpp | ||||||
|               source/scwx/qt/types/map_types.cpp |               source/scwx/qt/types/map_types.cpp | ||||||
|               source/scwx/qt/types/marker_types.cpp |  | ||||||
|               source/scwx/qt/types/media_types.cpp |               source/scwx/qt/types/media_types.cpp | ||||||
|               source/scwx/qt/types/qt_types.cpp |               source/scwx/qt/types/qt_types.cpp | ||||||
|               source/scwx/qt/types/radar_product_record.cpp |               source/scwx/qt/types/radar_product_record.cpp | ||||||
|  |  | ||||||
|  | @ -2,13 +2,16 @@ | ||||||
| #include <scwx/qt/types/marker_types.hpp> | #include <scwx/qt/types/marker_types.hpp> | ||||||
| #include <scwx/qt/util/color.hpp> | #include <scwx/qt/util/color.hpp> | ||||||
| #include <scwx/qt/util/json.hpp> | #include <scwx/qt/util/json.hpp> | ||||||
|  | #include <scwx/qt/util/texture_atlas.hpp> | ||||||
| #include <scwx/qt/main/application.hpp> | #include <scwx/qt/main/application.hpp> | ||||||
|  | #include <scwx/qt/manager/resource_manager.hpp> | ||||||
| #include <scwx/util/logger.hpp> | #include <scwx/util/logger.hpp> | ||||||
| 
 | 
 | ||||||
| #include <filesystem> | #include <filesystem> | ||||||
| #include <shared_mutex> | #include <shared_mutex> | ||||||
| #include <vector> | #include <vector> | ||||||
| #include <string> | #include <string> | ||||||
|  | #include <unordered_map> | ||||||
| 
 | 
 | ||||||
| #include <QStandardPaths> | #include <QStandardPaths> | ||||||
| #include <boost/json.hpp> | #include <boost/json.hpp> | ||||||
|  | @ -31,6 +34,7 @@ static const std::string kLongitudeName_ = "longitude"; | ||||||
| static const std::string kIconName_       = "icon"; | static const std::string kIconName_       = "icon"; | ||||||
| static const std::string kIconColorName_  = "icon-color"; | static const std::string kIconColorName_  = "icon-color"; | ||||||
| 
 | 
 | ||||||
|  | static const std::string defaultIconName = "images/location-marker"; | ||||||
| 
 | 
 | ||||||
| class MarkerManager::Impl | class MarkerManager::Impl | ||||||
| { | { | ||||||
|  | @ -43,12 +47,13 @@ public: | ||||||
|    std::string                                 markerSettingsPath_ {""}; |    std::string                                 markerSettingsPath_ {""}; | ||||||
|    std::vector<std::shared_ptr<MarkerRecord>>  markerRecords_ {}; |    std::vector<std::shared_ptr<MarkerRecord>>  markerRecords_ {}; | ||||||
|    std::unordered_map<types::MarkerId, size_t> idToIndex_ {}; |    std::unordered_map<types::MarkerId, size_t> idToIndex_ {}; | ||||||
| 
 |    std::unordered_map<std::string, types::MarkerIconInfo> markerIcons_ {}; | ||||||
| 
 | 
 | ||||||
|    MarkerManager* self_; |    MarkerManager* self_; | ||||||
| 
 | 
 | ||||||
|    boost::asio::thread_pool threadPool_ {1u}; |    boost::asio::thread_pool threadPool_ {1u}; | ||||||
|    std::shared_mutex        markerRecordLock_ {}; |    std::shared_mutex        markerRecordLock_ {}; | ||||||
|  |    std::shared_mutex        markerIconsLock_ {}; | ||||||
| 
 | 
 | ||||||
|    void                          InitializeMarkerSettings(); |    void                          InitializeMarkerSettings(); | ||||||
|    void                          ReadMarkerSettings(); |    void                          ReadMarkerSettings(); | ||||||
|  | @ -57,7 +62,7 @@ public: | ||||||
| 
 | 
 | ||||||
|    void InitalizeIds(); |    void InitalizeIds(); | ||||||
|    types::MarkerId NewId(); |    types::MarkerId NewId(); | ||||||
|    types::MarkerId lastId_; |    types::MarkerId lastId_ {0}; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
| class MarkerManager::Impl::MarkerRecord | class MarkerManager::Impl::MarkerRecord | ||||||
|  | @ -84,14 +89,14 @@ public: | ||||||
|             {kLatitudeName_, record->markerInfo_.latitude}, |             {kLatitudeName_, record->markerInfo_.latitude}, | ||||||
|             {kLongitudeName_, record->markerInfo_.longitude}, |             {kLongitudeName_, record->markerInfo_.longitude}, | ||||||
|             {kIconName_, record->markerInfo_.iconName}, |             {kIconName_, record->markerInfo_.iconName}, | ||||||
|             {kIconColorName_, util::color::ToArgbString(record->markerInfo_.iconColor)}}; |             {kIconColorName_, | ||||||
|  |              util::color::ToArgbString(record->markerInfo_.iconColor)}}; | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
|    friend MarkerRecord tag_invoke(boost::json::value_to_tag<MarkerRecord>, |    friend MarkerRecord tag_invoke(boost::json::value_to_tag<MarkerRecord>, | ||||||
|                                   const boost::json::value& jv) |                                   const boost::json::value& jv) | ||||||
|    { |    { | ||||||
|       static const std::string defaultIconName = types::getMarkerIcons()[0].name; |  | ||||||
|       static const boost::gil::rgba8_pixel_t defaultIconColor = |       static const boost::gil::rgba8_pixel_t defaultIconColor = | ||||||
|          util::color::ToRgba8PixelT("#ffff0000"); |          util::color::ToRgba8PixelT("#ffff0000"); | ||||||
| 
 | 
 | ||||||
|  | @ -120,12 +125,12 @@ public: | ||||||
|          } |          } | ||||||
|       } |       } | ||||||
| 
 | 
 | ||||||
|       return MarkerRecord(types::MarkerInfo( |       return {types::MarkerInfo( | ||||||
|          boost::json::value_to<std::string>(jv.at(kNameName_)), |          boost::json::value_to<std::string>(jv.at(kNameName_)), | ||||||
|          boost::json::value_to<double>(jv.at(kLatitudeName_)), |          boost::json::value_to<double>(jv.at(kLatitudeName_)), | ||||||
|          boost::json::value_to<double>(jv.at(kLongitudeName_)), |          boost::json::value_to<double>(jv.at(kLongitudeName_)), | ||||||
|          iconName, |          iconName, | ||||||
|          iconColor)); |          iconColor)}; | ||||||
|    } |    } | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
|  | @ -176,14 +181,14 @@ void MarkerManager::Impl::ReadMarkerSettings() | ||||||
|       { |       { | ||||||
|          // For each marker entry
 |          // For each marker entry
 | ||||||
|          auto& markerArray = markerJson.as_array(); |          auto& markerArray = markerJson.as_array(); | ||||||
|  |          //std::vector<std::string> fileNames {};
 | ||||||
|          markerRecords_.reserve(markerArray.size()); |          markerRecords_.reserve(markerArray.size()); | ||||||
|          idToIndex_.reserve(markerArray.size()); |          idToIndex_.reserve(markerArray.size()); | ||||||
|          for (auto& markerEntry : markerArray) |          for (auto& markerEntry : markerArray) | ||||||
|          { |          { | ||||||
|             try |             try | ||||||
|             { |             { | ||||||
|                MarkerRecord record = |                auto record = boost::json::value_to<MarkerRecord>(markerEntry); | ||||||
|                   boost::json::value_to<MarkerRecord>(markerEntry); |  | ||||||
| 
 | 
 | ||||||
|                if (!record.markerInfo_.name.empty()) |                if (!record.markerInfo_.name.empty()) | ||||||
|                { |                { | ||||||
|  | @ -193,6 +198,8 @@ void MarkerManager::Impl::ReadMarkerSettings() | ||||||
|                   markerRecords_.emplace_back( |                   markerRecords_.emplace_back( | ||||||
|                      std::make_shared<MarkerRecord>(record.markerInfo_)); |                      std::make_shared<MarkerRecord>(record.markerInfo_)); | ||||||
|                   idToIndex_.emplace(id, index); |                   idToIndex_.emplace(id, index); | ||||||
|  | 
 | ||||||
|  |                   self_->add_icon(record.markerInfo_.iconName, true); | ||||||
|                } |                } | ||||||
|             } |             } | ||||||
|             catch (const std::exception& ex) |             catch (const std::exception& ex) | ||||||
|  | @ -201,10 +208,14 @@ void MarkerManager::Impl::ReadMarkerSettings() | ||||||
|             } |             } | ||||||
|          } |          } | ||||||
| 
 | 
 | ||||||
|  |          util::TextureAtlas& textureAtlas = util::TextureAtlas::Instance(); | ||||||
|  |          textureAtlas.BuildAtlas(2048, 2048); // TODO should code be moved to ResourceManager (probrably)
 | ||||||
|  | 
 | ||||||
|          logger_->debug("{} location marker entries", markerRecords_.size()); |          logger_->debug("{} location marker entries", markerRecords_.size()); | ||||||
|       } |       } | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
|  | 
 | ||||||
|    Q_EMIT self_->MarkersUpdated(); |    Q_EMIT self_->MarkersUpdated(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | @ -233,17 +244,41 @@ MarkerManager::Impl::GetMarkerByName(const std::string& name) | ||||||
| 
 | 
 | ||||||
| MarkerManager::MarkerManager() : p(std::make_unique<Impl>(this)) | MarkerManager::MarkerManager() : p(std::make_unique<Impl>(this)) | ||||||
| { | { | ||||||
|  |    const std::vector<types::MarkerIconInfo> defaultMarkerIcons_ { | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationMarker, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationPin, 6, 16), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationCrosshair, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationStar, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationBriefcase, -1, -1), | ||||||
|  |       types::MarkerIconInfo( | ||||||
|  |          types::ImageTexture::LocationBuildingColumns, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationBuilding, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationCaravan, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationHouse, -1, -1), | ||||||
|  |       types::MarkerIconInfo(types::ImageTexture::LocationTent, -1, -1), | ||||||
|  |    }; | ||||||
|  | 
 | ||||||
|    p->InitializeMarkerSettings(); |    p->InitializeMarkerSettings(); | ||||||
| 
 | 
 | ||||||
|    boost::asio::post(p->threadPool_, |    boost::asio::post(p->threadPool_, | ||||||
|                      [this]() |                      [this, defaultMarkerIcons_]() | ||||||
|                      { |                      { | ||||||
|                         try |                         try | ||||||
|                         { |                         { | ||||||
|                            // Read Marker settings on startup
 |                            // Read Marker settings on startup
 | ||||||
|                            main::Application::WaitForInitialization(); |                            main::Application::WaitForInitialization(); | ||||||
|  |                            { | ||||||
|  |                               std::unique_lock lock(p->markerIconsLock_); | ||||||
|  |                               p->markerIcons_.reserve( | ||||||
|  |                                  defaultMarkerIcons_.size()); | ||||||
|  |                               for (auto& icon : defaultMarkerIcons_) | ||||||
|  |                               { | ||||||
|  |                                  p->markerIcons_.emplace(icon.name, icon); | ||||||
|  |                               } | ||||||
|  |                            } | ||||||
|                            p->ReadMarkerSettings(); |                            p->ReadMarkerSettings(); | ||||||
| 
 | 
 | ||||||
|  |                            Q_EMIT IconsReady(); | ||||||
|                            Q_EMIT MarkersInitialized(p->markerRecords_.size()); |                            Q_EMIT MarkersInitialized(p->markerRecords_.size()); | ||||||
|                         } |                         } | ||||||
|                         catch (const std::exception& ex) |                         catch (const std::exception& ex) | ||||||
|  | @ -310,6 +345,8 @@ void MarkerManager::set_marker(types::MarkerId          id, | ||||||
|          p->markerRecords_[index]; |          p->markerRecords_[index]; | ||||||
|       markerRecord->markerInfo_ = marker; |       markerRecord->markerInfo_ = marker; | ||||||
|       markerRecord->markerInfo_.id = id; |       markerRecord->markerInfo_.id = id; | ||||||
|  | 
 | ||||||
|  |       add_icon(marker.iconName); | ||||||
|    } |    } | ||||||
|    Q_EMIT MarkerChanged(id); |    Q_EMIT MarkerChanged(id); | ||||||
|    Q_EMIT MarkersUpdated(); |    Q_EMIT MarkersUpdated(); | ||||||
|  | @ -325,6 +362,8 @@ types::MarkerId MarkerManager::add_marker(const types::MarkerInfo& marker) | ||||||
|       p->idToIndex_.emplace(id, index); |       p->idToIndex_.emplace(id, index); | ||||||
|       p->markerRecords_.emplace_back(std::make_shared<Impl::MarkerRecord>(marker)); |       p->markerRecords_.emplace_back(std::make_shared<Impl::MarkerRecord>(marker)); | ||||||
|       p->markerRecords_[index]->markerInfo_.id = id; |       p->markerRecords_[index]->markerInfo_.id = id; | ||||||
|  | 
 | ||||||
|  |       add_icon(marker.iconName); | ||||||
|    } |    } | ||||||
|    Q_EMIT MarkerAdded(id); |    Q_EMIT MarkerAdded(id); | ||||||
|    Q_EMIT MarkersUpdated(); |    Q_EMIT MarkersUpdated(); | ||||||
|  | @ -403,6 +442,48 @@ void MarkerManager::for_each(std::function<MarkerForEachFunc> func) | ||||||
|    } |    } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | void MarkerManager::add_icon(const std::string& name, bool startup) | ||||||
|  | { | ||||||
|  |    { | ||||||
|  |       std::unique_lock lock(p->markerIconsLock_); | ||||||
|  |       if (p->markerIcons_.contains(name)) | ||||||
|  |       { | ||||||
|  |          return; | ||||||
|  |       } | ||||||
|  |       std::shared_ptr<boost::gil::rgba8_image_t> image = | ||||||
|  |          ResourceManager::LoadImageResource(name); | ||||||
|  | 
 | ||||||
|  |       auto icon = types::MarkerIconInfo(name, -1, -1, image); | ||||||
|  |       p->markerIcons_.emplace(name, icon); | ||||||
|  |    } | ||||||
|  | 
 | ||||||
|  |    if (!startup) | ||||||
|  |    { | ||||||
|  |       util::TextureAtlas& textureAtlas = util::TextureAtlas::Instance(); | ||||||
|  |       textureAtlas.BuildAtlas(2048, 2048); // TODO should code be moved to ResourceManager (probrably)
 | ||||||
|  |       Q_EMIT IconAdded(name); | ||||||
|  |    } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | std::optional<types::MarkerIconInfo> | ||||||
|  | MarkerManager::get_icon(const std::string& name) | ||||||
|  | { | ||||||
|  |    std::shared_lock lock(p->markerIconsLock_); | ||||||
|  |    if (p->markerIcons_.contains(name)) | ||||||
|  |    { | ||||||
|  |       return p->markerIcons_.at(name); | ||||||
|  |    } | ||||||
|  | 
 | ||||||
|  |    return {}; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | const std::unordered_map<std::string, types::MarkerIconInfo> | ||||||
|  | MarkerManager::get_icons() | ||||||
|  | { | ||||||
|  |    std::shared_lock lock(p->markerIconsLock_); | ||||||
|  |    return p->markerIcons_; | ||||||
|  | } | ||||||
|  | 
 | ||||||
| // Only use for testing
 | // Only use for testing
 | ||||||
| void MarkerManager::set_marker_settings_path(const std::string& path) | void MarkerManager::set_marker_settings_path(const std::string& path) | ||||||
| { | { | ||||||
|  | @ -429,6 +510,11 @@ std::shared_ptr<MarkerManager> MarkerManager::Instance() | ||||||
|    return markerManager; |    return markerManager; | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | const std::string& MarkerManager::getDefaultIconName() | ||||||
|  | { | ||||||
|  |    return defaultIconName; | ||||||
|  | } | ||||||
|  | 
 | ||||||
| } // namespace manager
 | } // namespace manager
 | ||||||
| } // namespace qt
 | } // namespace qt
 | ||||||
| } // namespace scwx
 | } // namespace scwx
 | ||||||
|  |  | ||||||
|  | @ -29,12 +29,17 @@ public: | ||||||
|    void remove_marker(types::MarkerId id); |    void remove_marker(types::MarkerId id); | ||||||
|    void move_marker(size_t from, size_t to); |    void move_marker(size_t from, size_t to); | ||||||
| 
 | 
 | ||||||
|  |    void add_icon(const std::string& name, bool startup = false); | ||||||
|  |    std::optional<types::MarkerIconInfo> get_icon(const std::string& name); | ||||||
|  |    const std::unordered_map<std::string, types::MarkerIconInfo> get_icons(); | ||||||
|  | 
 | ||||||
|    void for_each(std::function<MarkerForEachFunc> func); |    void for_each(std::function<MarkerForEachFunc> func); | ||||||
| 
 | 
 | ||||||
|    // Only use for testing
 |    // Only use for testing
 | ||||||
|    void set_marker_settings_path(const std::string& path); |    void set_marker_settings_path(const std::string& path); | ||||||
| 
 | 
 | ||||||
|    static std::shared_ptr<MarkerManager> Instance(); |    static std::shared_ptr<MarkerManager> Instance(); | ||||||
|  |    static const std::string& getDefaultIconName(); | ||||||
| 
 | 
 | ||||||
| signals: | signals: | ||||||
|    void MarkersInitialized(size_t count); |    void MarkersInitialized(size_t count); | ||||||
|  | @ -43,6 +48,10 @@ signals: | ||||||
|    void MarkerAdded(types::MarkerId id); |    void MarkerAdded(types::MarkerId id); | ||||||
|    void MarkerRemoved(types::MarkerId id); |    void MarkerRemoved(types::MarkerId id); | ||||||
| 
 | 
 | ||||||
|  |    void IconsReady(); | ||||||
|  |    void IconAdded(std::string name); | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
| private: | private: | ||||||
|    class Impl; |    class Impl; | ||||||
|    std::unique_ptr<Impl> p; |    std::unique_ptr<Impl> p; | ||||||
|  |  | ||||||
|  | @ -30,11 +30,16 @@ public: | ||||||
|    { |    { | ||||||
|       ConnectSignals(); |       ConnectSignals(); | ||||||
|    } |    } | ||||||
|    ~Impl() {} |    ~Impl() = default; | ||||||
| 
 | 
 | ||||||
|    void ReloadMarkers(); |    void ReloadMarkers(); | ||||||
|    void ConnectSignals(); |    void ConnectSignals(); | ||||||
| 
 | 
 | ||||||
|  |    std::shared_ptr<manager::MarkerManager> markerManager_ { | ||||||
|  |       manager::MarkerManager::Instance()}; | ||||||
|  | 
 | ||||||
|  |    void set_icon_sheets(); | ||||||
|  | 
 | ||||||
|    MarkerLayer* self_; |    MarkerLayer* self_; | ||||||
| 
 | 
 | ||||||
|    std::shared_ptr<gl::draw::GeoIcons> geoIcons_; |    std::shared_ptr<gl::draw::GeoIcons> geoIcons_; | ||||||
|  | @ -43,25 +48,26 @@ public: | ||||||
| 
 | 
 | ||||||
| void MarkerLayer::Impl::ConnectSignals() | void MarkerLayer::Impl::ConnectSignals() | ||||||
| { | { | ||||||
|    auto markerManager = manager::MarkerManager::Instance(); |    QObject::connect(markerManager_.get(), | ||||||
| 
 |  | ||||||
|    QObject::connect(markerManager.get(), |  | ||||||
|                     &manager::MarkerManager::MarkersUpdated, |                     &manager::MarkerManager::MarkersUpdated, | ||||||
|                     self_, |                     self_, | ||||||
|          [this]() |                     [this]() { ReloadMarkers(); }); | ||||||
|          { |    QObject::connect(markerManager_.get(), | ||||||
|             this->ReloadMarkers(); |                     &manager::MarkerManager::IconsReady, | ||||||
|          }); |                     self_, | ||||||
|  |                     [this]() { set_icon_sheets(); }); | ||||||
|  |    QObject::connect(markerManager_.get(), | ||||||
|  |                     &manager::MarkerManager::IconAdded, | ||||||
|  |                     self_, | ||||||
|  |                     [this]() { set_icon_sheets(); }); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void MarkerLayer::Impl::ReloadMarkers() | void MarkerLayer::Impl::ReloadMarkers() | ||||||
| { | { | ||||||
|    logger_->debug("ReloadMarkers()"); |    logger_->debug("ReloadMarkers()"); | ||||||
|    auto markerManager = manager::MarkerManager::Instance(); |  | ||||||
| 
 | 
 | ||||||
|    geoIcons_->StartIcons(); |    geoIcons_->StartIcons(); | ||||||
| 
 |    markerManager_->for_each( | ||||||
|    markerManager->for_each( |  | ||||||
|       [this](const types::MarkerInfo& marker) |       [this](const types::MarkerInfo& marker) | ||||||
|       { |       { | ||||||
|          // must use local ID, instead of reference to marker in event handler
 |          // must use local ID, instead of reference to marker in event handler
 | ||||||
|  | @ -69,6 +75,7 @@ void MarkerLayer::Impl::ReloadMarkers() | ||||||
|          types::MarkerId id = marker.id; |          types::MarkerId id = marker.id; | ||||||
| 
 | 
 | ||||||
|          std::shared_ptr<gl::draw::GeoIconDrawItem> icon = geoIcons_->AddIcon(); |          std::shared_ptr<gl::draw::GeoIconDrawItem> icon = geoIcons_->AddIcon(); | ||||||
|  | 
 | ||||||
|          geoIcons_->SetIconTexture(icon, marker.iconName, 0); |          geoIcons_->SetIconTexture(icon, marker.iconName, 0); | ||||||
|          geoIcons_->SetIconLocation(icon, marker.latitude, marker.longitude); |          geoIcons_->SetIconLocation(icon, marker.latitude, marker.longitude); | ||||||
|          geoIcons_->SetIconHoverText(icon, marker.name); |          geoIcons_->SetIconHoverText(icon, marker.name); | ||||||
|  | @ -81,7 +88,7 @@ void MarkerLayer::Impl::ReloadMarkers() | ||||||
|                { |                { | ||||||
|                case QEvent::Type::MouseButtonPress: |                case QEvent::Type::MouseButtonPress: | ||||||
|                { |                { | ||||||
|                   QMouseEvent* mouseEvent = reinterpret_cast<QMouseEvent*>(ev); |                   auto* mouseEvent = reinterpret_cast<QMouseEvent*>(ev); | ||||||
|                   if (mouseEvent->buttons() == Qt::MouseButton::RightButton) |                   if (mouseEvent->buttons() == Qt::MouseButton::RightButton) | ||||||
|                   { |                   { | ||||||
|                      editMarkerDialog_->setup(id); |                      editMarkerDialog_->setup(id); | ||||||
|  | @ -113,17 +120,24 @@ void MarkerLayer::Initialize() | ||||||
|    logger_->debug("Initialize()"); |    logger_->debug("Initialize()"); | ||||||
|    DrawLayer::Initialize(); |    DrawLayer::Initialize(); | ||||||
| 
 | 
 | ||||||
|    p->geoIcons_->StartIconSheets(); |    p->set_icon_sheets(); | ||||||
|    for (auto& markerIcon : types::getMarkerIcons()) |  | ||||||
|    { |  | ||||||
|       p->geoIcons_->AddIconSheet( |  | ||||||
|          markerIcon.name, 0, 0, markerIcon.hotX, markerIcon.hotY); |  | ||||||
|    } |  | ||||||
|    p->geoIcons_->FinishIconSheets(); |  | ||||||
| 
 |  | ||||||
|    p->ReloadMarkers(); |    p->ReloadMarkers(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | void MarkerLayer::Impl::set_icon_sheets() | ||||||
|  | { | ||||||
|  |    geoIcons_->StartIconSheets(); | ||||||
|  |    for (auto& markerIcon : markerManager_->get_icons()) | ||||||
|  |    { | ||||||
|  |       geoIcons_->AddIconSheet(markerIcon.second.name, | ||||||
|  |                               0, | ||||||
|  |                               0, | ||||||
|  |                               markerIcon.second.hotX, | ||||||
|  |                               markerIcon.second.hotY); | ||||||
|  |    } | ||||||
|  |    geoIcons_->FinishIconSheets(); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| void MarkerLayer::Render(const QMapLibre::CustomLayerRenderParameters& params) | void MarkerLayer::Render(const QMapLibre::CustomLayerRenderParameters& params) | ||||||
| { | { | ||||||
|    gl::OpenGLFunctions& gl = context()->gl(); |    gl::OpenGLFunctions& gl = context()->gl(); | ||||||
|  |  | ||||||
|  | @ -19,6 +19,7 @@ namespace model | ||||||
| 
 | 
 | ||||||
| static const std::string logPrefix_ = "scwx::qt::model::marker_model"; | static const std::string logPrefix_ = "scwx::qt::model::marker_model"; | ||||||
| static const auto        logger_    = scwx::util::Logger::Create(logPrefix_); | static const auto        logger_    = scwx::util::Logger::Create(logPrefix_); | ||||||
|  | static const int         iconSize_  = 30; | ||||||
| 
 | 
 | ||||||
| static constexpr int kFirstColumn = | static constexpr int kFirstColumn = | ||||||
|    static_cast<int>(MarkerModel::Column::Latitude); |    static_cast<int>(MarkerModel::Column::Latitude); | ||||||
|  | @ -130,17 +131,19 @@ QVariant MarkerModel::data(const QModelIndex& index, int role) const | ||||||
|    case static_cast<int>(Column::Icon): |    case static_cast<int>(Column::Icon): | ||||||
|       if (role == Qt::ItemDataRole::DecorationRole) |       if (role == Qt::ItemDataRole::DecorationRole) | ||||||
|       { |       { | ||||||
|          for (auto& icon : types::getMarkerIcons()) |          std::optional<types::MarkerIconInfo> icon = | ||||||
|          { |             p->markerManager_->get_icon(markerInfo->iconName); | ||||||
|             if (icon.name == markerInfo->iconName) |          if (icon) { | ||||||
|             { |             return util::modulateColors(icon->qIcon, | ||||||
|                return util::modulateColors(icon.qIcon, |                                         QSize(iconSize_, iconSize_), | ||||||
|                                            QSize(30, 30), |  | ||||||
|                                         QColor(markerInfo->iconColor[0], |                                         QColor(markerInfo->iconColor[0], | ||||||
|                                                markerInfo->iconColor[1], |                                                markerInfo->iconColor[1], | ||||||
|                                                markerInfo->iconColor[2], |                                                markerInfo->iconColor[2], | ||||||
|                                                markerInfo->iconColor[3])); |                                                markerInfo->iconColor[3])); | ||||||
|          } |          } | ||||||
|  |          else | ||||||
|  |          { | ||||||
|  |             return {}; | ||||||
|          } |          } | ||||||
|       } |       } | ||||||
|       break; |       break; | ||||||
|  |  | ||||||
|  | @ -1,34 +0,0 @@ | ||||||
| #include <scwx/qt/types/marker_types.hpp> |  | ||||||
| 
 |  | ||||||
| namespace scwx |  | ||||||
| { |  | ||||||
| namespace qt |  | ||||||
| { |  | ||||||
| namespace types |  | ||||||
| { |  | ||||||
| 
 |  | ||||||
| const std::vector<MarkerIconInfo>& getMarkerIcons() |  | ||||||
| { |  | ||||||
|    static std::vector<MarkerIconInfo> markerIcons = {}; |  | ||||||
|    if (markerIcons.size() == 0) |  | ||||||
|    { |  | ||||||
|       markerIcons = { |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationMarker, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationPin, 6, 16), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationCrosshair, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationStar, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationBriefcase, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationBuildingColumns, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationBuilding, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationCaravan, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationHouse, -1, -1), |  | ||||||
|          MarkerIconInfo(types::ImageTexture::LocationTent, -1, -1), |  | ||||||
|       }; |  | ||||||
|    } |  | ||||||
| 
 |  | ||||||
|    return markerIcons; |  | ||||||
| } |  | ||||||
| 
 |  | ||||||
| } // namespace types
 |  | ||||||
| } // namespace qt
 |  | ||||||
| } // namespace scwx
 |  | ||||||
|  | @ -14,15 +14,15 @@ namespace qt | ||||||
| { | { | ||||||
| namespace types | namespace types | ||||||
| { | { | ||||||
| typedef std::uint64_t MarkerId; | using MarkerId = std::uint64_t; | ||||||
| 
 | 
 | ||||||
| struct MarkerInfo | struct MarkerInfo | ||||||
| { | { | ||||||
|    MarkerInfo(const std::string&               name, |    MarkerInfo(const std::string&               name, | ||||||
|               double                           latitude, |               double                           latitude, | ||||||
|               double                           longitude, |               double                           longitude, | ||||||
|               const std::string         iconName, |               const std::string&               iconName, | ||||||
|               boost::gil::rgba8_pixel_t iconColor) : |               const boost::gil::rgba8_pixel_t& iconColor) : | ||||||
|        name {name}, |        name {name}, | ||||||
|        latitude {latitude}, |        latitude {latitude}, | ||||||
|        longitude {longitude}, |        longitude {longitude}, | ||||||
|  | @ -31,7 +31,7 @@ struct MarkerInfo | ||||||
|    { |    { | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
|    MarkerId                  id; |    MarkerId                  id{0}; | ||||||
|    std::string               name; |    std::string               name; | ||||||
|    double                    latitude; |    double                    latitude; | ||||||
|    double                    longitude; |    double                    longitude; | ||||||
|  | @ -47,7 +47,21 @@ struct MarkerIconInfo { | ||||||
|       path{types::GetTexturePath(texture)}, |       path{types::GetTexturePath(texture)}, | ||||||
|       hotX{hotX}, |       hotX{hotX}, | ||||||
|       hotY{hotY}, |       hotY{hotY}, | ||||||
|       qIcon{QIcon(QString::fromStdString(path))} |       qIcon{QIcon(QString::fromStdString(path))}, | ||||||
|  |       image{} | ||||||
|  |    { | ||||||
|  |    } | ||||||
|  | 
 | ||||||
|  |    explicit MarkerIconInfo(const std::string& path, | ||||||
|  |                            std::int32_t       hotX, | ||||||
|  |                            std::int32_t       hotY, | ||||||
|  |                            std::shared_ptr<boost::gil::rgba8_image_t> image) : | ||||||
|  |       name{path}, | ||||||
|  |       path{path}, | ||||||
|  |       hotX{hotX}, | ||||||
|  |       hotY{hotY}, | ||||||
|  |       qIcon{QIcon(QString::fromStdString(path))}, | ||||||
|  |       image{image} | ||||||
|    { |    { | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
|  | @ -56,10 +70,9 @@ struct MarkerIconInfo { | ||||||
|    std::int32_t hotX; |    std::int32_t hotX; | ||||||
|    std::int32_t hotY; |    std::int32_t hotY; | ||||||
|    QIcon qIcon; |    QIcon qIcon; | ||||||
|  |    std::optional<std::shared_ptr<boost::gil::rgba8_image_t>> image; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
| const std::vector<MarkerIconInfo>& getMarkerIcons(); |  | ||||||
| 
 |  | ||||||
| } // namespace types
 | } // namespace types
 | ||||||
| } // namespace qt
 | } // namespace qt
 | ||||||
| } // namespace scwx
 | } // namespace scwx
 | ||||||
|  |  | ||||||
|  | @ -8,7 +8,6 @@ | ||||||
| #include <scwx/util/logger.hpp> | #include <scwx/util/logger.hpp> | ||||||
| 
 | 
 | ||||||
| #include <string> | #include <string> | ||||||
| #include <vector> |  | ||||||
| 
 | 
 | ||||||
| #include <QObject> | #include <QObject> | ||||||
| #include <QString> | #include <QString> | ||||||
|  | @ -16,6 +15,7 @@ | ||||||
| #include <QPixmap> | #include <QPixmap> | ||||||
| #include <QColorDialog> | #include <QColorDialog> | ||||||
| #include <QPushButton> | #include <QPushButton> | ||||||
|  | #include <QFileDialog> | ||||||
| 
 | 
 | ||||||
| namespace scwx | namespace scwx | ||||||
| { | { | ||||||
|  | @ -36,6 +36,8 @@ public: | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
|    void show_color_dialog(); |    void show_color_dialog(); | ||||||
|  |    void show_icon_file_dialog(); | ||||||
|  | 
 | ||||||
|    void set_icon_color(const std::string& color); |    void set_icon_color(const std::string& color); | ||||||
| 
 | 
 | ||||||
|    void connect_signals(); |    void connect_signals(); | ||||||
|  | @ -45,24 +47,20 @@ public: | ||||||
| 
 | 
 | ||||||
|    EditMarkerDialog* self_; |    EditMarkerDialog* self_; | ||||||
|    QPushButton* deleteButton_; |    QPushButton* deleteButton_; | ||||||
|    QIcon get_colored_icon(size_t index, const std::string& color); |    QIcon             get_colored_icon(const types::MarkerIconInfo& marker, | ||||||
|  |                                       const std::string&           color); | ||||||
| 
 | 
 | ||||||
|    std::shared_ptr<manager::MarkerManager> markerManager_ = |    std::shared_ptr<manager::MarkerManager> markerManager_ = | ||||||
|       manager::MarkerManager::Instance(); |       manager::MarkerManager::Instance(); | ||||||
|    const std::vector<types::MarkerIconInfo>* icons_; |  | ||||||
|    types::MarkerId editId_; |    types::MarkerId editId_; | ||||||
|    bool adding_; |    bool adding_; | ||||||
|  |    std::string setIconOnAdded_{""}; | ||||||
| }; | }; | ||||||
| 
 | 
 | ||||||
| QIcon EditMarkerDialog::Impl::get_colored_icon(size_t             index, | QIcon EditMarkerDialog::Impl::get_colored_icon( | ||||||
|                                                const std::string& color) |    const types::MarkerIconInfo& marker, const std::string& color) | ||||||
| { | { | ||||||
|    if (index >= icons_->size()) |    return util::modulateColors(marker.qIcon, | ||||||
|    { |  | ||||||
|       return QIcon(); |  | ||||||
|    } |  | ||||||
| 
 |  | ||||||
|    return util::modulateColors((*icons_)[index].qIcon, |  | ||||||
|                                self_->ui->iconComboBox->iconSize(), |                                self_->ui->iconComboBox->iconSize(), | ||||||
|                                QColor(QString::fromStdString(color))); |                                QColor(QString::fromStdString(color))); | ||||||
| } | } | ||||||
|  | @ -74,12 +72,11 @@ EditMarkerDialog::EditMarkerDialog(QWidget* parent) : | ||||||
| { | { | ||||||
|    ui->setupUi(this); |    ui->setupUi(this); | ||||||
| 
 | 
 | ||||||
|    p->icons_ = &types::getMarkerIcons(); |    for (auto& markerIcon : p->markerManager_->get_icons()) | ||||||
|    for (auto& markerIcon : (*p->icons_)) |  | ||||||
|    { |    { | ||||||
|       ui->iconComboBox->addItem(markerIcon.qIcon, |       ui->iconComboBox->addItem(markerIcon.second.qIcon, | ||||||
|                                 QString(""), |                                 QString(""), | ||||||
|                                 QString::fromStdString(markerIcon.name)); |                                 QString::fromStdString(markerIcon.second.name)); | ||||||
|    } |    } | ||||||
|    p->deleteButton_ = |    p->deleteButton_ = | ||||||
|       ui->buttonBox->addButton("Delete", QDialogButtonBox::DestructiveRole); |       ui->buttonBox->addButton("Delete", QDialogButtonBox::DestructiveRole); | ||||||
|  | @ -98,7 +95,6 @@ void EditMarkerDialog::setup() | ||||||
| 
 | 
 | ||||||
| void EditMarkerDialog::setup(double latitude, double longitude) | void EditMarkerDialog::setup(double latitude, double longitude) | ||||||
| { | { | ||||||
|    ui->iconComboBox->setCurrentIndex(0); |  | ||||||
|    // By default use foreground color as marker color, mainly so the icons
 |    // By default use foreground color as marker color, mainly so the icons
 | ||||||
|    // are vissable in the dropdown menu.
 |    // are vissable in the dropdown menu.
 | ||||||
|    QColor color = QWidget::palette().color(QWidget::foregroundRole()); |    QColor color = QWidget::palette().color(QWidget::foregroundRole()); | ||||||
|  | @ -106,7 +102,7 @@ void EditMarkerDialog::setup(double latitude, double longitude) | ||||||
|       "", |       "", | ||||||
|       latitude, |       latitude, | ||||||
|       longitude, |       longitude, | ||||||
|       ui->iconComboBox->currentData().toString().toStdString(), |       manager::MarkerManager::getDefaultIconName(), | ||||||
|       boost::gil::rgba8_pixel_t {static_cast<uint8_t>(color.red()), |       boost::gil::rgba8_pixel_t {static_cast<uint8_t>(color.red()), | ||||||
|                                  static_cast<uint8_t>(color.green()), |                                  static_cast<uint8_t>(color.green()), | ||||||
|                                  static_cast<uint8_t>(color.blue()), |                                  static_cast<uint8_t>(color.blue()), | ||||||
|  | @ -128,6 +124,9 @@ void EditMarkerDialog::setup(types::MarkerId id) | ||||||
|    p->editId_ = id; |    p->editId_ = id; | ||||||
|    p->adding_ = false; |    p->adding_ = false; | ||||||
| 
 | 
 | ||||||
|  |    std::string iconColorStr = util::color::ToArgbString(marker->iconColor); | ||||||
|  |    p->set_icon_color(iconColorStr); | ||||||
|  | 
 | ||||||
|    int iconIndex = |    int iconIndex = | ||||||
|       ui->iconComboBox->findData(QString::fromStdString(marker->iconName)); |       ui->iconComboBox->findData(QString::fromStdString(marker->iconName)); | ||||||
|    if (iconIndex < 0 || marker->iconName == "") |    if (iconIndex < 0 || marker->iconName == "") | ||||||
|  | @ -135,15 +134,11 @@ void EditMarkerDialog::setup(types::MarkerId id) | ||||||
|       iconIndex = 0; |       iconIndex = 0; | ||||||
|    } |    } | ||||||
| 
 | 
 | ||||||
|    std::string iconColorStr = util::color::ToArgbString(marker->iconColor); |  | ||||||
| 
 |  | ||||||
|    ui->nameLineEdit->setText(QString::fromStdString(marker->name)); |    ui->nameLineEdit->setText(QString::fromStdString(marker->name)); | ||||||
|    ui->iconComboBox->setCurrentIndex(iconIndex); |    ui->iconComboBox->setCurrentIndex(iconIndex); | ||||||
|    ui->latitudeDoubleSpinBox->setValue(marker->latitude); |    ui->latitudeDoubleSpinBox->setValue(marker->latitude); | ||||||
|    ui->longitudeDoubleSpinBox->setValue(marker->longitude); |    ui->longitudeDoubleSpinBox->setValue(marker->longitude); | ||||||
|    ui->iconColorLineEdit->setText(QString::fromStdString(iconColorStr)); |    ui->iconColorLineEdit->setText(QString::fromStdString(iconColorStr)); | ||||||
| 
 |  | ||||||
|    p->set_icon_color(iconColorStr); |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| types::MarkerInfo EditMarkerDialog::get_marker_info() const | types::MarkerInfo EditMarkerDialog::get_marker_info() const | ||||||
|  | @ -163,7 +158,7 @@ types::MarkerInfo EditMarkerDialog::get_marker_info() const | ||||||
| void EditMarkerDialog::Impl::show_color_dialog() | void EditMarkerDialog::Impl::show_color_dialog() | ||||||
| { | { | ||||||
| 
 | 
 | ||||||
|    QColorDialog* dialog = new QColorDialog(self_); |    auto* dialog = new QColorDialog(self_); | ||||||
| 
 | 
 | ||||||
|    dialog->setAttribute(Qt::WA_DeleteOnClose); |    dialog->setAttribute(Qt::WA_DeleteOnClose); | ||||||
|    dialog->setOption(QColorDialog::ColorDialogOption::ShowAlphaChannel); |    dialog->setOption(QColorDialog::ColorDialogOption::ShowAlphaChannel); | ||||||
|  | @ -187,6 +182,28 @@ void EditMarkerDialog::Impl::show_color_dialog() | ||||||
|    dialog->open(); |    dialog->open(); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | void EditMarkerDialog::Impl::show_icon_file_dialog() | ||||||
|  | { | ||||||
|  | 
 | ||||||
|  |    auto* dialog = new QFileDialog(self_); | ||||||
|  | 
 | ||||||
|  |    dialog->setFileMode(QFileDialog::ExistingFile); | ||||||
|  |    dialog->setNameFilters({"Icon (*.png *.svg)", "All (*)"}); | ||||||
|  |    dialog->setAttribute(Qt::WA_DeleteOnClose); | ||||||
|  | 
 | ||||||
|  |    QObject::connect(dialog, | ||||||
|  |                     &QFileDialog::fileSelected, | ||||||
|  |                     self_, | ||||||
|  |                     [this](const QString& file) | ||||||
|  |                     { | ||||||
|  |                        std::string path = | ||||||
|  |                           QDir::toNativeSeparators(file).toStdString(); | ||||||
|  |                        setIconOnAdded_ = path; | ||||||
|  |                        markerManager_->add_icon(path); | ||||||
|  |                     }); | ||||||
|  |    dialog->open(); | ||||||
|  | } | ||||||
|  | 
 | ||||||
| void EditMarkerDialog::Impl::connect_signals() | void EditMarkerDialog::Impl::connect_signals() | ||||||
| { | { | ||||||
|    connect(self_, |    connect(self_, | ||||||
|  | @ -217,7 +234,33 @@ void EditMarkerDialog::Impl::connect_signals() | ||||||
|    connect(self_->ui->iconColorButton, |    connect(self_->ui->iconColorButton, | ||||||
|            &QAbstractButton::clicked, |            &QAbstractButton::clicked, | ||||||
|            self_, |            self_, | ||||||
|            [=, this]() { self_->p->show_color_dialog(); }); |            [=, this]() { show_color_dialog(); }); | ||||||
|  | 
 | ||||||
|  |    connect(self_->ui->iconFileOpenButton, | ||||||
|  |            &QPushButton::clicked, | ||||||
|  |            self_, | ||||||
|  |            [this]() { show_icon_file_dialog(); }); | ||||||
|  | 
 | ||||||
|  |    connect(markerManager_.get(), | ||||||
|  |            &manager::MarkerManager::IconAdded, | ||||||
|  |            self_, | ||||||
|  |            [this]() | ||||||
|  |            { | ||||||
|  |               std::string color = | ||||||
|  |                  self_->ui->iconColorLineEdit->text().toStdString(); | ||||||
|  |               set_icon_color(color); | ||||||
|  | 
 | ||||||
|  |               if (setIconOnAdded_ != "") | ||||||
|  |               { | ||||||
|  |                  int i = self_->ui->iconComboBox->findData( | ||||||
|  |                     QString::fromStdString(setIconOnAdded_)); | ||||||
|  |                  if (i >= 0) | ||||||
|  |                  { | ||||||
|  |                     self_->ui->iconComboBox->setCurrentIndex(i); | ||||||
|  |                     setIconOnAdded_ = ""; | ||||||
|  |                  } | ||||||
|  |               } | ||||||
|  |            }); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| void EditMarkerDialog::Impl::set_icon_color(const std::string& color) | void EditMarkerDialog::Impl::set_icon_color(const std::string& color) | ||||||
|  | @ -225,10 +268,25 @@ void EditMarkerDialog::Impl::set_icon_color(const std::string& color) | ||||||
|    self_->ui->iconColorFrame->setStyleSheet( |    self_->ui->iconColorFrame->setStyleSheet( | ||||||
|       QString::fromStdString(fmt::format("background-color: {}", color))); |       QString::fromStdString(fmt::format("background-color: {}", color))); | ||||||
| 
 | 
 | ||||||
|    for (size_t i = 0; i < icons_->size(); i++) |    auto* iconComboBox = self_->ui->iconComboBox; | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  |    QVariant data = self_->ui->iconComboBox->currentData(); | ||||||
|  |    self_->ui->iconComboBox->clear(); | ||||||
|  |    for (auto& markerIcon : markerManager_->get_icons()) | ||||||
|    { |    { | ||||||
|       self_->ui->iconComboBox->setItemIcon(static_cast<int>(i), |       int i = | ||||||
|                                            get_colored_icon(i, color)); |          iconComboBox->findData(QString::fromStdString(markerIcon.second.name)); | ||||||
|  |       QIcon icon = get_colored_icon(markerIcon.second, color); | ||||||
|  |       if (i < 0) | ||||||
|  |       { | ||||||
|  |          iconComboBox->addItem( | ||||||
|  |             icon, QString(""), QString::fromStdString(markerIcon.second.name)); | ||||||
|  |       } | ||||||
|  |       else | ||||||
|  |       { | ||||||
|  |          self_->ui->iconComboBox->setItemIcon(i, icon); | ||||||
|  |       } | ||||||
|    } |    } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  |  | ||||||
|  | @ -21,7 +21,7 @@ class EditMarkerDialog : public QDialog | ||||||
| 
 | 
 | ||||||
| public: | public: | ||||||
|    explicit EditMarkerDialog(QWidget* parent = nullptr); |    explicit EditMarkerDialog(QWidget* parent = nullptr); | ||||||
|    ~EditMarkerDialog(); |    ~EditMarkerDialog() override; | ||||||
| 
 | 
 | ||||||
|    void setup(); |    void setup(); | ||||||
|    void setup(double latitude, double longitude); |    void setup(double latitude, double longitude); | ||||||
|  |  | ||||||
|  | @ -7,88 +7,14 @@ | ||||||
|     <x>0</x> |     <x>0</x> | ||||||
|     <y>0</y> |     <y>0</y> | ||||||
|     <width>400</width> |     <width>400</width> | ||||||
|     <height>211</height> |     <height>249</height> | ||||||
|    </rect> |    </rect> | ||||||
|   </property> |   </property> | ||||||
|   <property name="windowTitle"> |   <property name="windowTitle"> | ||||||
|    <string>Edit Location Marker</string> |    <string>Edit Location Marker</string> | ||||||
|   </property> |   </property> | ||||||
|   <layout class="QGridLayout" name="gridLayout"> |   <layout class="QGridLayout" name="gridLayout"> | ||||||
|    <item row="2" column="0"> |    <item row="9" column="0"> | ||||||
|     <widget class="QLabel" name="label_4"> |  | ||||||
|      <property name="text"> |  | ||||||
|       <string>Icon</string> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="6" column="0" colspan="2"> |  | ||||||
|     <widget class="QDialogButtonBox" name="buttonBox"> |  | ||||||
|      <property name="orientation"> |  | ||||||
|       <enum>Qt::Orientation::Horizontal</enum> |  | ||||||
|      </property> |  | ||||||
|      <property name="standardButtons"> |  | ||||||
|       <set>QDialogButtonBox::StandardButton::Cancel|QDialogButtonBox::StandardButton::Ok</set> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="2" column="1"> |  | ||||||
|     <widget class="QComboBox" name="iconComboBox"> |  | ||||||
|      <property name="autoFillBackground"> |  | ||||||
|       <bool>true</bool> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="0" column="0"> |  | ||||||
|     <widget class="QLabel" name="label_2"> |  | ||||||
|      <property name="text"> |  | ||||||
|       <string>Latitude</string> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="1" column="1"> |  | ||||||
|     <widget class="QDoubleSpinBox" name="longitudeDoubleSpinBox"> |  | ||||||
|      <property name="decimals"> |  | ||||||
|       <number>4</number> |  | ||||||
|      </property> |  | ||||||
|      <property name="minimum"> |  | ||||||
|       <double>-180.000000000000000</double> |  | ||||||
|      </property> |  | ||||||
|      <property name="maximum"> |  | ||||||
|       <double>180.000000000000000</double> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="4" column="1"> |  | ||||||
|     <widget class="QLineEdit" name="nameLineEdit"/> |  | ||||||
|    </item> |  | ||||||
|    <item row="4" column="0"> |  | ||||||
|     <widget class="QLabel" name="label"> |  | ||||||
|      <property name="text"> |  | ||||||
|       <string>Name</string> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="0" column="1"> |  | ||||||
|     <widget class="QDoubleSpinBox" name="latitudeDoubleSpinBox"> |  | ||||||
|      <property name="decimals"> |  | ||||||
|       <number>4</number> |  | ||||||
|      </property> |  | ||||||
|      <property name="minimum"> |  | ||||||
|       <double>-90.000000000000000</double> |  | ||||||
|      </property> |  | ||||||
|      <property name="maximum"> |  | ||||||
|       <double>90.000000000000000</double> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="1" column="0"> |  | ||||||
|     <widget class="QLabel" name="label_3"> |  | ||||||
|      <property name="text"> |  | ||||||
|       <string>Longitude</string> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="5" column="0"> |  | ||||||
|     <spacer name="verticalSpacer"> |     <spacer name="verticalSpacer"> | ||||||
|      <property name="orientation"> |      <property name="orientation"> | ||||||
|       <enum>Qt::Orientation::Vertical</enum> |       <enum>Qt::Orientation::Vertical</enum> | ||||||
|  | @ -101,14 +27,7 @@ | ||||||
|      </property> |      </property> | ||||||
|     </spacer> |     </spacer> | ||||||
|    </item> |    </item> | ||||||
|    <item row="3" column="0"> |    <item row="4" column="2"> | ||||||
|     <widget class="QLabel" name="label_5"> |  | ||||||
|      <property name="text"> |  | ||||||
|       <string>Icon Color</string> |  | ||||||
|      </property> |  | ||||||
|     </widget> |  | ||||||
|    </item> |  | ||||||
|    <item row="3" column="1"> |  | ||||||
|     <layout class="QHBoxLayout" name="horizontalLayout"> |     <layout class="QHBoxLayout" name="horizontalLayout"> | ||||||
|      <item> |      <item> | ||||||
|       <widget class="QFrame" name="iconColorFrame"> |       <widget class="QFrame" name="iconColorFrame"> | ||||||
|  | @ -146,6 +65,103 @@ | ||||||
|      </item> |      </item> | ||||||
|     </layout> |     </layout> | ||||||
|    </item> |    </item> | ||||||
|  |    <item row="0" column="2"> | ||||||
|  |     <widget class="QDoubleSpinBox" name="latitudeDoubleSpinBox"> | ||||||
|  |      <property name="decimals"> | ||||||
|  |       <number>4</number> | ||||||
|  |      </property> | ||||||
|  |      <property name="minimum"> | ||||||
|  |       <double>-90.000000000000000</double> | ||||||
|  |      </property> | ||||||
|  |      <property name="maximum"> | ||||||
|  |       <double>90.000000000000000</double> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="5" column="0"> | ||||||
|  |     <widget class="QLabel" name="label"> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>Name</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="3" column="0"> | ||||||
|  |     <widget class="QLabel" name="label_4"> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>Icon</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="10" column="0" colspan="3"> | ||||||
|  |     <widget class="QDialogButtonBox" name="buttonBox"> | ||||||
|  |      <property name="orientation"> | ||||||
|  |       <enum>Qt::Orientation::Horizontal</enum> | ||||||
|  |      </property> | ||||||
|  |      <property name="standardButtons"> | ||||||
|  |       <set>QDialogButtonBox::StandardButton::Cancel|QDialogButtonBox::StandardButton::Ok</set> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="1" column="0"> | ||||||
|  |     <widget class="QLabel" name="label_3"> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>Longitude</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="4" column="0"> | ||||||
|  |     <widget class="QLabel" name="label_5"> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>Icon Color</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="0" column="0"> | ||||||
|  |     <widget class="QLabel" name="label_2"> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>Latitude</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="3" column="3"> | ||||||
|  |     <widget class="QToolButton" name="iconFileOpenButton"> | ||||||
|  |      <property name="toolTip"> | ||||||
|  |       <string>Add Custom Icon</string> | ||||||
|  |      </property> | ||||||
|  |      <property name="text"> | ||||||
|  |       <string>...</string> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="1" column="2"> | ||||||
|  |     <widget class="QDoubleSpinBox" name="longitudeDoubleSpinBox"> | ||||||
|  |      <property name="decimals"> | ||||||
|  |       <number>4</number> | ||||||
|  |      </property> | ||||||
|  |      <property name="minimum"> | ||||||
|  |       <double>-180.000000000000000</double> | ||||||
|  |      </property> | ||||||
|  |      <property name="maximum"> | ||||||
|  |       <double>180.000000000000000</double> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|  |    <item row="5" column="2"> | ||||||
|  |     <widget class="QLineEdit" name="nameLineEdit"/> | ||||||
|  |    </item> | ||||||
|  |    <item row="3" column="2"> | ||||||
|  |     <widget class="QComboBox" name="iconComboBox"> | ||||||
|  |      <property name="sizePolicy"> | ||||||
|  |       <sizepolicy hsizetype="Preferred" vsizetype="Fixed"> | ||||||
|  |        <horstretch>0</horstretch> | ||||||
|  |        <verstretch>0</verstretch> | ||||||
|  |       </sizepolicy> | ||||||
|  |      </property> | ||||||
|  |      <property name="autoFillBackground"> | ||||||
|  |       <bool>true</bool> | ||||||
|  |      </property> | ||||||
|  |     </widget> | ||||||
|  |    </item> | ||||||
|   </layout> |   </layout> | ||||||
|  </widget> |  </widget> | ||||||
|  <resources> |  <resources> | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 AdenKoperczak
						AdenKoperczak