diff --git a/src/modules/welcome/Config.cpp b/src/modules/welcome/Config.cpp index 9f7c031d1..1df4e1cab 100644 --- a/src/modules/welcome/Config.cpp +++ b/src/modules/welcome/Config.cpp @@ -187,7 +187,7 @@ Config::setCountryCode( const QString& countryCode ) } void -Config::setLanguageIcon( const QString languageIcon ) +Config::setLanguageIcon(const QString &languageIcon ) { m_languageIcon = languageIcon; } diff --git a/src/modules/welcome/Config.h b/src/modules/welcome/Config.h index 392ca8206..71f2120f9 100644 --- a/src/modules/welcome/Config.h +++ b/src/modules/welcome/Config.h @@ -101,13 +101,15 @@ class Config : public QObject Q_PROPERTY( QString genericWelcomeMessage MEMBER m_genericWelcomeMessage NOTIFY genericWelcomeMessageChanged FINAL ) Q_PROPERTY( QString warningMessage MEMBER m_warningMessage CONSTANT FINAL ) - Q_PROPERTY( bool isNextEnabled MEMBER m_isNextEnabled NOTIFY isNextEnabledChanged FINAL ) - + Q_PROPERTY(QString supportUrl MEMBER m_supportUrl CONSTANT FINAL) + Q_PROPERTY(QString knownIssuesUrl MEMBER m_knownIssuesUrl CONSTANT FINAL) + Q_PROPERTY(QString releaseNotesUrl MEMBER m_releaseNotesUrl CONSTANT FINAL) + Q_PROPERTY(QString donateUrl MEMBER m_donateUrl CONSTANT FINAL) public: Config( QObject* parent = nullptr ); void setCountryCode( const QString &countryCode ); - void setLanguageIcon( const QString languageIcon ); + void setLanguageIcon( const QString &languageIcon ); RequirementsModel& requirementsModel () const; void setIsNextEnabled( const bool& isNextEnabled ); @@ -151,7 +153,6 @@ private: QString m_releaseNotesUrl; QString m_donateUrl; - signals: void countryCodeChanged( QString countryCode ); void localeIndexChanged( int localeIndex ); diff --git a/src/modules/welcomeq/CMakeLists.txt b/src/modules/welcomeq/CMakeLists.txt index 1febf6792..9cb89c3d9 100644 --- a/src/modules/welcomeq/CMakeLists.txt +++ b/src/modules/welcomeq/CMakeLists.txt @@ -1,44 +1,51 @@ # This is a re-write of the welcome module using QML view steps # instead of widgets. -#set( _welcome ${CMAKE_CURRENT_SOURCE_DIR}/../welcome ) +set( _welcome ${CMAKE_CURRENT_SOURCE_DIR}/../welcome ) -#include_directories( ${PROJECT_BINARY_DIR}/src/libcalamaresui ${_welcome} ) +include_directories( ${PROJECT_BINARY_DIR}/src/libcalamaresui ${CMAKE_CURRENT_SOURCE_DIR}/../../libcalamares ${_welcome} ) -## DUPLICATED WITH WELCOME MODULE -#find_package( Qt5 ${QT_VERSION} CONFIG REQUIRED DBus Network ) +# DUPLICATED WITH WELCOME MODULE +find_package( Qt5 ${QT_VERSION} CONFIG REQUIRED DBus Network ) -#find_package( LIBPARTED ) -#if ( LIBPARTED_FOUND ) -# set( PARTMAN_SRC ${_welcome}/checker/partman_devices.c ) -# set( CHECKER_LINK_LIBRARIES ${LIBPARTED_LIBRARY} ) -#else() -# set( PARTMAN_SRC ) -# set( CHECKER_LINK_LIBRARIES ) -# add_definitions( -DWITHOUT_LIBPARTED ) -#endif() +find_package( LIBPARTED ) +if ( LIBPARTED_FOUND ) + set( PARTMAN_SRC ${_welcome}/checker/partman_devices.c ) + set( CHECKER_LINK_LIBRARIES ${LIBPARTED_LIBRARY} ) +else() + set( PARTMAN_SRC ) + set( CHECKER_LINK_LIBRARIES ) + add_definitions( -DWITHOUT_LIBPARTED ) +endif() -#set( CHECKER_SOURCES -# ${_welcome}/checker/CheckerContainer.cpp -# ${_welcome}/checker/GeneralRequirements.cpp -# ${_welcome}/checker/ResultWidget.cpp -# ${_welcome}/checker/ResultsListWidget.cpp -# ${PARTMAN_SRC} -#) +set( CHECKER_SOURCES + ${_welcome}/checker/GeneralRequirements.cpp + ${PARTMAN_SRC} +) -#calamares_add_plugin( welcomeq -# TYPE viewmodule -# EXPORT_MACRO PLUGINDLLEXPORT_PRO -# SOURCES -# ${CHECKER_SOURCES} -# WelcomeQmlViewStep.cpp -# Config.cpp -# RESOURCES -# welcomeq.qrc -# LINK_PRIVATE_LIBRARIES -# calamaresui -# ${CHECKER_LINK_LIBRARIES} -# Qt5::DBus -# Qt5::Network -# SHARED_LIB -#) +calamares_add_plugin( welcomeq + TYPE viewmodule + EXPORT_MACRO PLUGINDLLEXPORT_PRO + SOURCES + ${CHECKER_SOURCES} + WelcomeQmlViewStep.cpp + ${_welcome}/Config.cpp + RESOURCES + welcomeq.qrc + LINK_PRIVATE_LIBRARIES + calamaresui + ${CHECKER_LINK_LIBRARIES} + Qt5::DBus + Qt5::Network + SHARED_LIB +) + +# add_executable( welcomeqmltest qmlmain.cpp Config.cpp WelcomeQmlViewStep.cpp ${CHECKER_SOURCES} ) +# target_link_libraries( welcomeqmltest PRIVATE calamaresui Qt5::Core Qt5::Network Qt5::DBus ${CHECKER_LINK_LIBRARIES}) +# set_target_properties( welcomeqmltest +# PROPERTIES +# ENABLE_EXPORTS TRUE +# RUNTIME_OUTPUT_NAME welcomeqmltest +# ) +# calamares_automoc( welcomeqmltest ) +# calamares_autouic( welcomeqmltest ) diff --git a/src/modules/welcomeq/Config.cpp b/src/modules/welcomeq/Config.cpp deleted file mode 100644 index cfa6336e2..000000000 --- a/src/modules/welcomeq/Config.cpp +++ /dev/null @@ -1,23 +0,0 @@ -/* === This file is part of Calamares - === - * - * Copyright 2019-2020, Adriaan de Groot - * - * Calamares is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * Calamares is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with Calamares. If not, see . - */ - -#include "Config.h" - -Config::Config() {} - -Config::~Config() {} diff --git a/src/modules/welcomeq/Config.h b/src/modules/welcomeq/Config.h deleted file mode 100644 index 50c3e387b..000000000 --- a/src/modules/welcomeq/Config.h +++ /dev/null @@ -1,51 +0,0 @@ -/* === This file is part of Calamares - === - * - * Copyright 2019-2020, Adriaan de Groot - * - * Calamares is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * Calamares is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with Calamares. If not, see . - */ - -#ifndef WELCOMEQ_CONFIG_H -#define WELCOMEQ_CONFIG_H - -#include -#include - -class Config : public QObject -{ - Q_OBJECT - Q_PROPERTY( QUrl helpUrl READ helpUrl CONSTANT FINAL ) - Q_PROPERTY( QUrl issuesUrl READ issuesUrl CONSTANT FINAL ) - Q_PROPERTY( QUrl notesUrl READ notesUrl CONSTANT FINAL ) - Q_PROPERTY( QUrl donateUrl READ donateUrl CONSTANT FINAL ) -public: - Config(); - virtual ~Config(); - - void setHelpUrl( const QUrl& url ) { m_helpUrl = url; } - void setIssuesUrl( const QUrl& url ) { m_issuesUrl = url; } - void setNotesUrl( const QUrl& url ) { m_notesUrl = url; } - void setDonateUrl( const QUrl& url ) { m_donateUrl = url; } - -public slots: - QUrl helpUrl() const { return m_helpUrl; } - QUrl issuesUrl() const { return m_issuesUrl; } - QUrl notesUrl() const { return m_notesUrl; } - QUrl donateUrl() const { return m_donateUrl; } - -private: - QUrl m_helpUrl, m_issuesUrl, m_notesUrl, m_donateUrl; -}; - -#endif diff --git a/src/modules/welcomeq/WelcomeQmlViewStep.cpp b/src/modules/welcomeq/WelcomeQmlViewStep.cpp index 382e0b4d1..571da8150 100644 --- a/src/modules/welcomeq/WelcomeQmlViewStep.cpp +++ b/src/modules/welcomeq/WelcomeQmlViewStep.cpp @@ -26,9 +26,12 @@ #include "locale/Lookup.h" #include "utils/Logger.h" #include "utils/Variant.h" +#include "utils/Dirs.h" #include "Branding.h" #include "modulesystem/ModuleManager.h" +#include +#include "utils/Yaml.h" #include #include @@ -37,167 +40,177 @@ CALAMARES_PLUGIN_FACTORY_DEFINITION( WelcomeQmlViewStepFactory, registerPlugin< WelcomeQmlViewStep >(); ) WelcomeQmlViewStep::WelcomeQmlViewStep( QObject* parent ) - : Calamares::QmlViewStep( QStringLiteral( "welcomeq" ), parent ) +: Calamares::QmlViewStep("welcome", parent ) + , m_config( new Config( ) ) // the qml singleton takes ownership and deletes it +// , m_nextEnabled( false ) , m_requirementsChecker( new GeneralRequirements( this ) ) + { - connect( Calamares::ModuleManager::instance(), - &Calamares::ModuleManager::requirementsComplete, - this, - &WelcomeQmlViewStep::nextStatusChanged ); +// connect( m_config, +// &Config::isNextEnabledChanged, +// this, +// &WelcomeQmlViewStep::nextStatusChanged ); +// emit nextStatusChanged(true); + qmlRegisterSingletonType< Config >( "io.calamares.module", 1, 0, "Welcome", [&](QQmlEngine*, QJSEngine*) -> QObject* { return m_config; } ); + qmlRegisterSingletonType< Calamares::Branding >( "io.calamares.ui", 1, 0, "Branding", [](QQmlEngine*, QJSEngine*) -> QObject* { return Calamares::Branding::instance(); } ); } -WelcomeQmlViewStep::~WelcomeQmlViewStep() {} - QString WelcomeQmlViewStep::prettyName() const { - return tr( "Welcome" ); + return tr( "Welcome" ); } -/** @brief Look up a URL for a button - * - * Looks up @p key in @p map; if it is a *boolean* value, then - * assume an old-style configuration, and fetch the string from - * the branding settings @p e. If it is a string, not a boolean, - * use it as-is. If not found, or a weird type, returns empty. - * - * This allows switching the showKnownIssuesUrl and similar settings - * in welcome.conf from a boolean (deferring to branding) to an - * actual string for immediate use. Empty strings, as well as - * "false" as a setting, will hide the buttons as before. - */ -static QString -jobOrBrandingSetting( Calamares::Branding::StringEntry e, const QVariantMap& map, const QString& key ) +bool +WelcomeQmlViewStep::isNextEnabled() const { - if ( !map.contains( key ) ) - { - return QString(); - } - auto v = map.value( key ); - if ( v.type() == QVariant::Bool ) - { - return v.toBool() ? ( *e ) : QString(); - } - if ( v.type() == QVariant::String ) - { - return v.toString(); - } + // TODO: should return true +// return m_config->property("isNextEnabled").toBool(); + return true; +} - return QString(); +bool +WelcomeQmlViewStep::isBackEnabled() const +{ + // TODO: should return true (it's weird that you are not allowed to have welcome *after* anything + return false; +} + + +bool +WelcomeQmlViewStep::isAtBeginning() const +{ + // TODO: adjust to "pages" in the QML + return true; +} + + +bool +WelcomeQmlViewStep::isAtEnd() const +{ + // TODO: adjust to "pages" in the QML + return true; +} + + +Calamares::JobList +WelcomeQmlViewStep::jobs() const +{ + return Calamares::JobList(); } void WelcomeQmlViewStep::setConfigurationMap( const QVariantMap& configurationMap ) { - using Calamares::Branding; + using Calamares::Branding; - m_config.setHelpUrl( jobOrBrandingSetting( Branding::SupportUrl, configurationMap, "showSupportUrl" ) ); - m_config.setIssuesUrl( jobOrBrandingSetting( Branding::KnownIssuesUrl, configurationMap, "showKnownIssuesUrl" ) ); - m_config.setNotesUrl( jobOrBrandingSetting( Branding::ReleaseNotesUrl, configurationMap, "showReleaseNotesUrl" ) ); - m_config.setDonateUrl( CalamaresUtils::getString( configurationMap, "showDonateUrl" ) ); + // TODO: expand Config class and set the remaining fields // with the configurationMap all those properties can be accesed withouth having to declare a property, get and setter for each - // TODO: figure out how the requirements (held by ModuleManager) should be accessible - // to QML as a odel. - if ( configurationMap.contains( "requirements" ) - && configurationMap.value( "requirements" ).type() == QVariant::Map ) - { - m_requirementsChecker->setConfigurationMap( configurationMap.value( "requirements" ).toMap() ); - } - else - cWarning() << "no valid requirements map found in welcome " - "module configuration."; + // TODO: figure out how the requirements (held by ModuleManager) should be accessible + // to QML as a odel. //will be model as a qvariantmap containing a alert level and the message string + if ( configurationMap.contains( "requirements" ) + && configurationMap.value( "requirements" ).type() == QVariant::Map ) + { + m_requirementsChecker->setConfigurationMap( configurationMap.value( "requirements" ).toMap() ); - bool ok = false; - QVariantMap geoip = CalamaresUtils::getSubMap( configurationMap, "geoip", ok ); - if ( ok ) - { - using FWString = QFutureWatcher< QString >; + m_config->requirementsModel().setRequirementsList( checkRequirements() ); + } + else + cWarning() << "no valid requirements map found in welcome " + "module configuration."; - auto* handler = new CalamaresUtils::GeoIP::Handler( CalamaresUtils::getString( geoip, "style" ), - CalamaresUtils::getString( geoip, "url" ), - CalamaresUtils::getString( geoip, "selector" ) ); - if ( handler->type() != CalamaresUtils::GeoIP::Handler::Type::None ) - { - auto* future = new FWString(); - connect( future, &FWString::finished, [view = this, f = future, h = handler]() { - QString countryResult = f->future().result(); - cDebug() << "GeoIP result for welcome=" << countryResult; - view->setCountry( countryResult, h ); - f->deleteLater(); - delete h; - } ); - future->setFuture( handler->queryRaw() ); - } - else - { - // Would not produce useful country code anyway. - delete handler; - } - } + bool ok = false; + QVariantMap geoip = CalamaresUtils::getSubMap( configurationMap, "geoip", ok ); + if ( ok ) + { + using FWString = QFutureWatcher< QString >; - QString language = CalamaresUtils::getString( configurationMap, "languageIcon" ); - if ( !language.isEmpty() ) - { - auto icon = Calamares::Branding::instance()->image( language, QSize( 48, 48 ) ); - if ( !icon.isNull() ) - { - // TODO: figure out where to set this: Config? - } - } + auto* handler = new CalamaresUtils::GeoIP::Handler( CalamaresUtils::getString( geoip, "style" ), + CalamaresUtils::getString( geoip, "url" ), + CalamaresUtils::getString( geoip, "selector" ) ); + if ( handler->type() != CalamaresUtils::GeoIP::Handler::Type::None ) + { + auto* future = new FWString(); + connect( future, &FWString::finished, [view = this, f = future, h = handler]() { + QString countryResult = f->future().result(); + cDebug() << "GeoIP result for welcome=" << countryResult; + view->setCountry( countryResult, h ); + f->deleteLater(); + delete h; + } ); + future->setFuture( handler->queryRaw() ); + } + else + { + // Would not produce useful country code anyway. + delete handler; + } + } - QmlViewStep::setConfigurationMap( configurationMap ); // call parent implementation last + QString language = CalamaresUtils::getString( configurationMap, "languageIcon" ); + if ( !language.isEmpty() ) + { + auto icon = Calamares::Branding::instance()->image( language, QSize( 48, 48 ) ); + if ( !icon.isNull() ) + { + m_config->setLanguageIcon(language); + } + } + + Calamares::QmlViewStep::setConfigurationMap( configurationMap ); // call parent implementation last } Calamares::RequirementsList WelcomeQmlViewStep::checkRequirements() { - return m_requirementsChecker->checkRequirements(); + return m_requirementsChecker->checkRequirements(); +} + +Config* +WelcomeQmlViewStep::config() const +{ + return m_config; } static inline void logGeoIPHandler( CalamaresUtils::GeoIP::Handler* handler ) { - if ( handler ) - { - cDebug() << Logger::SubEntry << "Obtained from" << handler->url() << " (" - << static_cast< int >( handler->type() ) << handler->selector() << ')'; - } + if ( handler ) + { + cDebug() << Logger::SubEntry << "Obtained from" << handler->url() << " (" + << static_cast< int >( handler->type() ) << handler->selector() << ')'; + } } void WelcomeQmlViewStep::setCountry( const QString& countryCode, CalamaresUtils::GeoIP::Handler* handler ) { - if ( countryCode.length() != 2 ) - { - cDebug() << "Unusable country code" << countryCode; - logGeoIPHandler( handler ); - return; - } + if ( countryCode.length() != 2 ) + { + cDebug() << "Unusable country code" << countryCode; + logGeoIPHandler( handler ); + return; + } - auto c_l = CalamaresUtils::Locale::countryData( countryCode ); - if ( c_l.first == QLocale::Country::AnyCountry ) - { - cDebug() << "Unusable country code" << countryCode; - logGeoIPHandler( handler ); - return; - } - else - { - int r = CalamaresUtils::Locale::availableTranslations()->find( countryCode ); - if ( r < 0 ) - { - cDebug() << "Unusable country code" << countryCode << "(no suitable translation)"; - } - if ( ( r >= 0 ) ) - { - // TODO: update Config to point to selected language - } - } -} - -QObject* -WelcomeQmlViewStep::getConfig() -{ - return &m_config; + auto c_l = CalamaresUtils::Locale::countryData( countryCode ); + if ( c_l.first == QLocale::Country::AnyCountry ) + { + cDebug() << "Unusable country code" << countryCode; + logGeoIPHandler( handler ); + return; + } + else + { + int r = CalamaresUtils::Locale::availableTranslations()->find( countryCode ); + if ( r < 0 ) + { + cDebug() << "Unusable country code" << countryCode << "(no suitable translation)"; + } + if ( ( r >= 0 ) ) + { + // TODO: update Config to point to selected language + m_config->setCountryCode( countryCode ); + } + } } diff --git a/src/modules/welcomeq/WelcomeQmlViewStep.h b/src/modules/welcomeq/WelcomeQmlViewStep.h index 064be0455..fd9faf9ff 100644 --- a/src/modules/welcomeq/WelcomeQmlViewStep.h +++ b/src/modules/welcomeq/WelcomeQmlViewStep.h @@ -21,11 +21,12 @@ #include "Config.h" -#include "DllMacro.h" #include "modulesystem/Requirement.h" #include "utils/PluginFactory.h" #include "viewpages/QmlViewStep.h" +#include + #include #include @@ -39,16 +40,26 @@ class Handler; class GeneralRequirements; +// TODO: Needs a generic Calamares::QmlViewStep as base class +// TODO: refactor and move what makes sense to base class class PLUGINDLLEXPORT WelcomeQmlViewStep : public Calamares::QmlViewStep { Q_OBJECT public: + explicit WelcomeQmlViewStep( QObject* parent = nullptr ); - virtual ~WelcomeQmlViewStep() override; QString prettyName() const override; + bool isNextEnabled() const override; + bool isBackEnabled() const override; + + bool isAtBeginning() const override; + bool isAtEnd() const override; + + Calamares::JobList jobs() const override; + void setConfigurationMap( const QVariantMap& configurationMap ) override; /** @brief Sets the country that Calamares is running in. @@ -60,13 +71,11 @@ public: void setCountry( const QString&, CalamaresUtils::GeoIP::Handler* handler ); Calamares::RequirementsList checkRequirements() override; - -protected: - QObject* getConfig() override; + Config* config() const; private: // TODO: a generic QML viewstep should return a config object from a method - Config m_config; + Config *m_config; GeneralRequirements* m_requirementsChecker; };