diff --git a/FluentUI.pro b/FluentUI.pro index 59eb6a4..982edab 100644 --- a/FluentUI.pro +++ b/FluentUI.pro @@ -3,5 +3,4 @@ TEMPLATE = subdirs SUBDIRS += \ src/FluentUI.pro \ example - example.depends = src/FluentUI.pro diff --git a/README.md b/README.md index 543d6ca..5e9c7fc 100644 Binary files a/README.md and b/README.md differ diff --git a/example/AboutPage.qml b/example/AboutPage.qml index 3039e75..4f14f20 100644 --- a/example/AboutPage.qml +++ b/example/AboutPage.qml @@ -1,4 +1,5 @@ import QtQuick 2.15 +import QtQuick.Layouts 1.15 import FluentUI 1.0 FluWindow { @@ -12,18 +13,60 @@ FluWindow { title:"关于" } - FluText{ - text:"关于" - fontStyle: FluText.Display - anchors.centerIn: parent + ColumnLayout{ + anchors{ + top: appbar.bottom + left: parent.left + right: parent.right + } - MouseArea{ - anchors.fill: parent - onClicked: { + RowLayout{ + Layout.topMargin: 20 + Layout.leftMargin: 15 + spacing: 14 + FluText{ + text:"FluentUI" + fontStyle: FluText.Title + } + FluText{ + text:"v1.0.0.0" + fontStyle: FluText.Body + Layout.alignment: Qt.AlignBottom + } + } + RowLayout{ + spacing: 14 + Layout.topMargin: 20 + Layout.leftMargin: 15 + FluText{ + text:"作者:" + } + FluText{ + text:"朱子楚" + Layout.alignment: Qt.AlignBottom + } + } + + RowLayout{ + spacing: 14 + Layout.topMargin: 20 + Layout.leftMargin: 15 + FluText{ + text:"GitHub:" + } + FluTextButton{ + id:text_hublink + text:"https://github.com/zhuzichu520/FluentUI" + Layout.alignment: Qt.AlignBottom + onClicked: { + Qt.openUrlExternally(text_hublink.text) + } } } } + + } diff --git a/example/App.qml b/example/App.qml index d644703..4ac129c 100644 --- a/example/App.qml +++ b/example/App.qml @@ -9,16 +9,23 @@ Window { id:app color: "#00000000" Component.onCompleted: { - FluApp.isFps = true + + FluApp.setContextProperty("installHelper",installHelper) + FluApp.isDark = false FluApp.setAppWindow(app) FluApp.routes = { "/":"qrc:/MainPage.qml", "/Setting":"qrc:/SettingPage.qml", "/About":"qrc:/AboutPage.qml", - "/Installer":"qrc:/Installer.qml" + "/Installer":"qrc:/Installer.qml", + "/Uninstall":"qrc:/Uninstall.qml" + } + if(installHelper.isNavigateUninstall()){ + FluApp.initialRoute = "/Uninstall" + }else{ + FluApp.initialRoute = "/Installer" } - FluApp.initialRoute = "/Installer" FluApp.run() } diff --git a/example/InstallHelper.cpp b/example/InstallHelper.cpp index 4a92eb6..ef83a0c 100644 --- a/example/InstallHelper.cpp +++ b/example/InstallHelper.cpp @@ -1,5 +1,105 @@ #include "InstallHelper.h" +#include +#include +#include + +#include +#include +#include + +#pragma comment(lib, "User32.lib") +#pragma comment(lib, "Ole32.lib") + + +using CopyProgressCallback = std::function; + + +static void copyDir(const QString& srcPath, const QString& dstPath, CopyProgressCallback callback) +{ + QDir srcDir(srcPath); + QDir dstDir(dstPath); + if (!dstDir.exists()) { + dstDir.mkdir(dstPath); + } + QFileInfoList fileInfos = srcDir.entryInfoList(QDir::Files | QDir::Dirs | QDir::NoDotAndDotDot); + int totalFiles = fileInfos.count(); + int currentFile = 0; + foreach (QFileInfo fileInfo, fileInfos) { + currentFile++; + QString srcFilePath = fileInfo.filePath(); + QString dstFilePath = dstPath + QDir::separator() + fileInfo.fileName(); + if (fileInfo.isDir()) { + copyDir(srcFilePath, dstFilePath, callback); + } else { + QFile dstFile(dstFilePath); + if(dstFile.exists()){ + dstFile.remove(); + } + QFile::copy(srcFilePath, dstFilePath); + } + if (callback != nullptr) { + callback(currentFile, totalFiles); + } + } +} + +static void createHome(const QString& exePath,const QString& linkName){ + //创建桌面快捷方式 + QFile::link(exePath, QStandardPaths::writableLocation(QStandardPaths::DesktopLocation).append("/").append(linkName)); +} + +static void createUninstallLink(QString exePath, QString path, QString uninstallLinkName){ +#ifdef Q_OS_WIN + QString dst = path.append("\\").append(uninstallLinkName); + IShellLink *pShellLink; + QString args = "--uninstall"; + HRESULT hres = CoCreateInstance(CLSID_ShellLink, NULL, CLSCTX_INPROC_SERVER, + IID_IShellLink, (LPVOID *)&pShellLink); + if (SUCCEEDED(hres)) + { + // 设置快捷方式的目标路径和参数 + pShellLink->SetPath(exePath.toStdWString().c_str()); + pShellLink->SetArguments(args.toStdWString().c_str()); + + // 设置快捷方式的描述 + pShellLink->SetDescription(L"Fluent Uninstall"); + + // 获取IPersistFile接口 + IPersistFile *pPersistFile; + hres = pShellLink->QueryInterface(IID_IPersistFile, (LPVOID *)&pPersistFile); + + if (SUCCEEDED(hres)) + { + // 保存快捷方式到文件 + hres = pPersistFile->Save(dst.toStdWString().c_str(), TRUE); + pPersistFile->Release(); + } + pShellLink->Release(); + } + CoUninitialize(); + + // std::string dst = path.append("\\").append(uninstallLinkName).toStdString(); + + // QFile::link(exePath,QString::fromStdString(dst + " --uninstall")); +#endif +} + +static void createStartMenu(const QString& exePath,const QString& fileName,const QString& linkName){ + //创建开始菜单快捷方式 + QString startMenuPath=QStandardPaths::writableLocation(QStandardPaths::ApplicationsLocation).append("/").append(fileName); + QDir dir(startMenuPath); + if(!dir.exists()) + { + dir.mkdir(startMenuPath); + } + if(dir.exists()) + { + QFile::link(exePath, startMenuPath.append("/").append(linkName)); + } +} + + InstallHelper::InstallHelper(QObject *parent) : QObject{parent} { @@ -7,6 +107,32 @@ InstallHelper::InstallHelper(QObject *parent) } void InstallHelper::install(const QString& path,bool isHome,bool isStartMenu){ - installing(true); - qDebug()< future = QtConcurrent::run(copyDir,QCoreApplication::applicationDirPath(),path,[=](int currentFile, int totalFiles){ + if(currentFile==totalFiles){ + QString exePath = path+"\\"+"example.exe"; + QString fileName = "FluentUI"; + QString linkName = "FluentUI.lnk"; + QString uninstallLinkName = "Uninstall FluentUI.lnk"; + if(isHome){ + createHome(exePath,linkName); + } + if(isStartMenu){ + createStartMenu(exePath,fileName,linkName); + } + createUninstallLink(exePath,path,uninstallLinkName); + } + }); + future.waitForFinished(); + qDebug()< +#include #include + #include "stdafx.h" + class InstallHelper : public QObject { + Q_OBJECT Q_PROPERTY_AUTO(bool,installing) public: explicit InstallHelper(QObject *parent = nullptr); Q_INVOKABLE void install(const QString& path,bool isHome,bool isStartMenu); -signals: + + Q_INVOKABLE QString applicationFilePath(){ + return QGuiApplication::arguments().join(" "); + } + + Q_INVOKABLE bool isNavigateUninstall(){ + return true; +// return QGuiApplication::arguments().contains("--uninstall"); + } + + Q_INVOKABLE void uninstall(); }; diff --git a/example/Installer.qml b/example/Installer.qml index 5bd8b55..f9866f8 100644 --- a/example/Installer.qml +++ b/example/Installer.qml @@ -2,7 +2,6 @@ import QtQuick.Layouts 1.15 import QtQuick.Dialogs 1.3 as Dialogs import Qt.labs.platform 1.1 -import UI 1.0 import FluentUI 1.0 FluWindow { @@ -27,9 +26,6 @@ FluWindow { Item{ id:data - InstallHelper{ - id:helper - } Dialogs.FileDialog { id: fileDialog selectFolder: true @@ -72,7 +68,8 @@ FluWindow { text:"更改路径" Layout.rightMargin: 30 onClicked: { - fileDialog.open() + showInfo(installHelper.applicationFilePath()) + // fileDialog.open() } } } @@ -122,7 +119,7 @@ FluWindow { FluFilledButton{ text:"同意并安装" onClicked: { - helper.install(textbox_path.text,checkbox_home.checked,checkbox_startmenu.checked) + installHelper.install(textbox_path.text,checkbox_home.checked,checkbox_startmenu.checked) } } FluButton{ @@ -139,7 +136,7 @@ FluWindow { Rectangle{ anchors.fill: parent - visible: helper.installing + visible: installHelper.installing color: "#80000000" MouseArea{ diff --git a/example/MainPage.qml b/example/MainPage.qml index c68ce18..beb0f2e 100644 --- a/example/MainPage.qml +++ b/example/MainPage.qml @@ -17,6 +17,8 @@ FluWindow { FluAppBar{ id:appbar title: "FluentUI" + showDark: true + showFps: true } Item{ @@ -75,18 +77,24 @@ FluWindow { id:menu x:40 margins:4 + FluMenuItem{ + text:"意见反馈" + onClicked:{ + showInfo("正在建设中...") + } + } FluMenuItem{ text:"关于" onClicked:{ FluApp.navigate("/About") } } - FluMenuItem{ - text:"设置" - onClicked:{ - FluApp.navigate("/Setting") - } - } + // FluMenuItem{ + // text:"设置" + // onClicked:{ + // FluApp.navigate("/Setting") + // } + // } } onClicked:{ menu.open() diff --git a/example/T_Rectangle.qml b/example/T_Rectangle.qml index bd84062..716a41d 100644 --- a/example/T_Rectangle.qml +++ b/example/T_Rectangle.qml @@ -79,9 +79,6 @@ Item { source: "qrc:/res/svg/avatar_1.svg" sourceSize: Qt.size(width,height) } - layer.enabled: true - layer.effect: FluDropShadow {} - } FluRectangle{ width: 50 @@ -93,8 +90,6 @@ Item { sourceSize: Qt.size(width,height) source: "qrc:/res/svg/avatar_2.svg" } - layer.enabled: true - layer.effect: FluDropShadow {} } FluRectangle{ width: 50 @@ -106,12 +101,6 @@ Item { sourceSize: Qt.size(width,height) source: "qrc:/res/svg/avatar_3.svg" } - layer.enabled: true - layer.effect: DropShadow { - radius: 5 - samples: 4 - color: "#80000000" - } } FluRectangle{ width: 50 @@ -123,8 +112,6 @@ Item { sourceSize: Qt.size(width,height) source: "qrc:/res/svg/avatar_4.svg" } - layer.enabled: true - layer.effect: FluDropShadow {} } } @@ -139,12 +126,6 @@ Item { sourceSize: Qt.size(width,height) } Layout.topMargin: 10 - layer.enabled: true - layer.effect: FluDropShadow {} } - - - - } } diff --git a/example/Uninstall.qml b/example/Uninstall.qml new file mode 100644 index 0000000..a53d9b6 --- /dev/null +++ b/example/Uninstall.qml @@ -0,0 +1,68 @@ +import QtQuick 2.15 +import QtQuick.Layouts 1.15 +import QtQuick.Dialogs 1.3 as Dialogs +import Qt.labs.platform 1.1 +import FluentUI 1.0 + +FluWindow { + + id:window + width: 800 + height: 400 + minimumWidth:800 + maximumWidth:800 + minimumHeight:400 + maximumHeight:400 + title:"卸载向导" + + FluAppBar{ + id:appbar + title: "卸载向导" + } + + ColumnLayout{ + + width: parent.width + + anchors{ + top: appbar.bottom + bottom: parent.bottom + topMargin: 20 + } + + Item{ + width: 1 + Layout.fillHeight: true + } + + Rectangle{ + + Layout.fillWidth: true + border.width: 1 + border.color: FluApp.isDark ? Qt.rgba(45/255,45/255,45/255,1) : Qt.rgba(238/255,238/255,238/255,1) + + height: 60 + color: FluApp.isDark ? "#323232" : "#FFFFFF" + RowLayout{ + anchors{ + right: parent.right + rightMargin: 30 + verticalCenter: parent.verticalCenter + } + spacing: 14 + FluButton{ + text:"取消" + onClicked: { + window.close() + } + } + FluButton{ + text:"确定要卸载" + onClicked: { + installHelper.uninstall() + } + } + } + } + } +} diff --git a/example/example.pro b/example/example.pro index 00baeda..280f407 100644 --- a/example/example.pro +++ b/example/example.pro @@ -1,4 +1,4 @@ -QT += quick +QT += quick concurrent CONFIG += c++11 DEFINES += QT_DEPRECATED_WARNINGS QT_NO_WARNING_OUTPUT @@ -13,37 +13,6 @@ qnx: target.path = /tmp/$${TARGET}/bin else: unix:!android: target.path = /opt/$${TARGET}/bin !isEmpty(target.path): INSTALLS += target - - -#### 如果你正在使用静态库.a 那么你还需要将下面的配置注释取消掉。 -#### 其它项目使用方法也是如此。 - -# DEFINES += STATICLIB - -# LIBNAME = FluentUI - -# CONFIG(debug, debug|release) { -# contains(QMAKE_HOST.os,Windows) { -# LIBNAME = FluentUId -# }else{ -# LIBNAME = FluentUI_debug -# } -# } - -# # Additional import path used to resolve QML modules in Qt Creator's code model -# QML_IMPORT_PATH = $$OUT_PWD/../bin/ - -# # Additional import path used to resolve QML modules just for Qt Quick Designer -# QML_DESIGNER_IMPORT_PATH = $$OUT_PWD/../bin/ - -# INCLUDEPATH += $$OUT_PWD/../bin/FluentUI/ -# DEPENDPATH += $$OUT_PWD/../bin/FluentUI/ - -# LIBS += -L$$OUT_PWD/../bin/FluentUI/ -l$${LIBNAME} -# PRE_TARGETDEPS += $$OUT_PWD/../bin/FluentUI/lib$${LIBNAME}.a - -### 注意:静态库 .so .dylib .dll 是自动安装的Qt qml plugin目录中,不需要此步配置 - HEADERS += \ InstallHelper.h \ stdafx.h diff --git a/example/main.cpp b/example/main.cpp index b82a794..96c8c76 100644 --- a/example/main.cpp +++ b/example/main.cpp @@ -1,35 +1,18 @@ #include #include +#include #include "InstallHelper.h" -#if defined(STATICLIB) -#include -#endif - int main(int argc, char *argv[]) { QCoreApplication::setOrganizationName("ZhuZiChu"); QCoreApplication::setOrganizationDomain("https://zhuzichu520.github.io"); QCoreApplication::setApplicationName("FluentUI"); - - qputenv("QSG_RENDER_LOOP","basic"); - QCoreApplication::setAttribute(Qt::AA_DontCreateNativeWidgetSiblings); -#if (QT_VERSION < QT_VERSION_CHECK(6, 0, 0)) - QGuiApplication::setAttribute(Qt::AA_EnableHighDpiScaling); - QGuiApplication::setAttribute(Qt::AA_UseHighDpiPixmaps); -#endif -#if (QT_VERSION >= QT_VERSION_CHECK(5, 14, 0)) - QGuiApplication::setHighDpiScaleFactorRoundingPolicy(Qt::HighDpiScaleFactorRoundingPolicy::Round); -#endif - // QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); + QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); QGuiApplication app(argc, argv); QQmlApplicationEngine engine; - - qmlRegisterType("UI",1,0,"InstallHelper"); - -#if defined(STATICLIB) - FluentUI::create(&engine); -#endif + qDebug()<<"setContextProperty------->1"; + engine.rootContext()->setContextProperty("installHelper",new InstallHelper()); const QUrl url(QStringLiteral("qrc:/App.qml")); QObject::connect(&engine, &QQmlApplicationEngine::objectCreated, &app, [url](QObject *obj, const QUrl &objUrl) { diff --git a/example/qml.qrc b/example/qml.qrc index 2cf0548..fb457d3 100644 --- a/example/qml.qrc +++ b/example/qml.qrc @@ -27,5 +27,6 @@ Installer.qml T_Awesome.qml T_TextBox.qml + Uninstall.qml diff --git a/src/FluApp.cpp b/src/FluApp.cpp index 2a4a800..0bb4450 100644 --- a/src/FluApp.cpp +++ b/src/FluApp.cpp @@ -22,8 +22,7 @@ FluApp *FluApp::getInstance() FluApp::FluApp(QObject *parent) : QObject{parent} { - isDark(true); - isFps(true); + isDark(false); } void FluApp::setAppWindow(QWindow *window){ @@ -39,7 +38,7 @@ void FluApp::navigate(const QString& route){ qErrnoWarning("没有找到当前路由"); return; } - bool isAppWindow = route==initialRoute(); + bool isAppWindow = route == initialRoute(); FramelessView *view = new FramelessView(); view->setColor(QColor(Qt::transparent)); QObject::connect(view, &QQuickView::statusChanged, view, [&](QQuickView::Status status) { diff --git a/src/FluApp.h b/src/FluApp.h index 935bc57..08009e4 100644 --- a/src/FluApp.h +++ b/src/FluApp.h @@ -4,7 +4,9 @@ #include #include #include +#include #include +#include #include "FramelessView.h" #include "stdafx.h" @@ -13,7 +15,6 @@ class FluApp : public QObject Q_OBJECT Q_PROPERTY_AUTO(QString,initialRoute); Q_PROPERTY_AUTO(bool,isDark); - Q_PROPERTY_AUTO(bool,isFps); Q_PROPERTY_AUTO(QJsonObject,routes); public: @@ -36,10 +37,20 @@ public: Q_INVOKABLE void clipText(const QString& text); + Q_INVOKABLE void setContextProperty(const QString &name, QObject *data){ + if(engine){ + engine->rootContext()->setContextProperty(name,data); + } + } + + void setEngine(QQmlEngine *engine){ + this->engine = engine; + } private: static FluApp* m_instance; + QQmlEngine *engine; QWindow *appWindow; }; diff --git a/src/Fluent.cpp b/src/Fluent.cpp index b235c6b..ccb7bc6 100644 --- a/src/Fluent.cpp +++ b/src/Fluent.cpp @@ -32,10 +32,9 @@ void Fluent::registerTypes(const char *uri){ qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluMenu.qml"),uri,major,minor,"FluMenu"); qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluMenuItem.qml"),uri,major,minor,"FluMenuItem"); - qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluScrollBar.qml"),uri,major,minor,"FluScrollBar"); + qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluTextButton.qml"),uri,major,minor,"FluTextButton"); qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluMultiLineTextBox.qml"),uri,major,minor,"FluMultiLineTextBox"); - qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluDropShadow.qml"),uri,major,minor,"FluDropShadow"); qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluTooltip.qml"),uri,major,minor,"FluTooltip"); qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluDivider.qml"),uri,major,minor,"FluDivider"); qmlRegisterType(QUrl("qrc:/com.zhuzichu/controls/FluIcon.qml"),uri,major,minor,"FluIcon"); @@ -72,5 +71,7 @@ void Fluent::initializeEngine(QQmlEngine *engine, const char *uri) font.setFamily("Microsoft YaHei"); QGuiApplication::setFont(font); QFontDatabase::addApplicationFont(":/com.zhuzichu/res/font/fontawesome-webfont.ttf"); - engine->rootContext()->setContextProperty("FluApp",FluApp::getInstance()); + FluApp* app = FluApp::getInstance(); + app->setEngine(engine); + engine->rootContext()->setContextProperty("FluApp",app); } diff --git a/src/FluentUI.cpp b/src/FluentUI.cpp index 2b6f3cd..367cdc0 100644 --- a/src/FluentUI.cpp +++ b/src/FluentUI.cpp @@ -2,14 +2,10 @@ #include "Fluent.h" -void FluentUI::create(QQmlEngine *engine) -{ - engine->addImportPath("/"); - Fluent::getInstance()->initializeEngine(engine,URI_STR); - Fluent::getInstance()->registerTypes(URI_STR); -} -QString FluentUI::version() -{ - return Fluent::getInstance()->version(); +void FluentUI::registerTypes(const char *uri){ + Fluent::getInstance()->registerTypes(uri); +} +void FluentUI::initializeEngine(QQmlEngine *engine, const char *uri){ + Fluent::getInstance()->initializeEngine(engine,uri); } diff --git a/src/FluentUI.h b/src/FluentUI.h index daa8ca9..1636630 100644 --- a/src/FluentUI.h +++ b/src/FluentUI.h @@ -7,8 +7,8 @@ class FluentUI { public: - static void create(QQmlEngine* engine); - static QString version(); + static void registerTypes(const char *uri) ; + static void initializeEngine(QQmlEngine *engine, const char *uri); }; #endif // FLUENTUI_H diff --git a/src/FluentUI.pro b/src/FluentUI.pro index 717ea49..b6869b6 100644 --- a/src/FluentUI.pro +++ b/src/FluentUI.pro @@ -5,24 +5,11 @@ TARGET = FluentUI TARGET = $$qtLibraryTarget($$TARGET) uri = FluentUI -########################################## CONFIG += sharedlib # staticlib or sharedlib -#** 多次切换编译构建模式,建议先清理缓存。项目右键->清理 - -#*[staticlib] 构建静态库.a -#需要修改example.pro,请打开后按说明操作 - -#*[sharedlib] 构建动态库 .dll .so .dylib -#会自动安装到Qt qmlplugin目录中 -#无需其它配置即可运行demo以及其它项目中使用 -#发布目标平台前必须每个平台都要构建一次。 -########################################## RESOURCES += \ res.qrc - -# Input HEADERS += \ Def.h \ FluApp.h \ @@ -33,7 +20,6 @@ HEADERS += \ qml_plugin.h \ stdafx.h - SOURCES += \ Def.cpp \ FluApp.cpp \ @@ -50,7 +36,6 @@ win32 { FramelessView_unix.cpp } - DEFINES += VERSION_IN=\\\"1.0.0\\\" DEFINES += URI_STR=\\\"$$uri\\\" diff --git a/src/controls/FluAppBar.qml b/src/controls/FluAppBar.qml index 95aa647..9f0b01c 100644 --- a/src/controls/FluAppBar.qml +++ b/src/controls/FluAppBar.qml @@ -15,6 +15,9 @@ Rectangle{ property string title: "标题" + property bool showDark: false + property bool showFps: false + property bool resizable: { if(Window.window == null){ return false @@ -63,12 +66,13 @@ Rectangle{ Layout.alignment: Qt.AlignVCenter Layout.rightMargin: 12 Layout.topMargin: 5 - visible: FluApp.isFps + visible: showFps } RowLayout{ Layout.alignment: Qt.AlignVCenter spacing: 5 + visible: showDark FluText{ text:"夜间模式" fontStyle: FluText.Body @@ -112,7 +116,6 @@ Rectangle{ icon : FluentIcons.FA_close Layout.alignment: Qt.AlignVCenter text:"关闭" - iconSize: 15 onClicked: { Window.window.close() } diff --git a/src/controls/FluDropShadow.qml b/src/controls/FluDropShadow.qml deleted file mode 100644 index 4438a97..0000000 --- a/src/controls/FluDropShadow.qml +++ /dev/null @@ -1,8 +0,0 @@ -import QtQuick 2.15 -import QtGraphicalEffects 1.15 - -DropShadow { - radius: 5 - samples: 4 - color: FluApp.isDark ? "#80FFFFFF" : "#40000000" -} diff --git a/src/controls/FluMenu.qml b/src/controls/FluMenu.qml index c6ec568..2dc061d 100644 --- a/src/controls/FluMenu.qml +++ b/src/controls/FluMenu.qml @@ -6,13 +6,14 @@ Popup { id: popup default property alias content: container.children - background: FluRectangle { + background: Rectangle { implicitWidth: 140 implicitHeight: container.height color:FluApp.isDark ? Qt.rgba(45/255,45/255,45/255,1) : Qt.rgba(237/255,237/255,237/255,1) - radius: [5,5,5,5] - layer.effect: FluDropShadow{} - layer.enabled: true + radius: 5 + FluShadow{ + radius: 5 + } Column{ spacing: 5 topPadding: 5 diff --git a/src/controls/FluRectangle.qml b/src/controls/FluRectangle.qml index f373dac..2673d23 100644 --- a/src/controls/FluRectangle.qml +++ b/src/controls/FluRectangle.qml @@ -8,6 +8,7 @@ Item{ property color color : "#FFFFFF" property color borderColor:"red" property int borderWidth: 1 + property bool shadow: true default property alias contentItem: container.children Rectangle{ @@ -18,6 +19,17 @@ Item{ color:root.color } + FluShadow{ + anchors.fill: container + radius: root.radius[0] + visible: { + if(root.radius[0] === root.radius[1] && root.radius[0] === root.radius[2] && root.radius[0] === root.radius[3] && root.shadow){ + return true + } + return false + } + } + Canvas { id: canvas anchors.fill: parent diff --git a/src/controls/FluShadow.qml b/src/controls/FluShadow.qml new file mode 100644 index 0000000..8e88af2 --- /dev/null +++ b/src/controls/FluShadow.qml @@ -0,0 +1,65 @@ +import QtQuick 2.15 + +Item { + id:root + anchors.fill: parent + anchors.margins: -4 + property color color: FluApp.isDark ? "#FFFFFF" : "#000000" + + property var radius: 4 + + Rectangle{ + width: root.width + height: root.height + anchors.centerIn: parent + color: "#00000000" + opacity: 0.02 + border.width: 1 + radius: root.radius + border.color: root.color + } + + Rectangle{ + width: root.width - 2 + height: root.height - 2 + anchors.centerIn: parent + color: "#00000000" + opacity: 0.04 + border.width: 1 + radius: root.radius + border.color: root.color + } + Rectangle{ + width: root.width - 4 + height: root.height - 4 + anchors.centerIn: parent + color: "#00000000" + opacity: 0.06 + border.width: 1 + radius: root.radius + border.color: root.color + } + + Rectangle{ + width: root.width - 6 + height: root.height - 6 + anchors.centerIn: parent + color: "#00000000" + opacity: 0.08 + border.width: 1 + radius: root.radius + border.color: root.color + } + + Rectangle{ + width: root.width - 8 + height: root.height - 8 + anchors.centerIn: parent + opacity: 0.1 + radius: root.radius + color: "#00000000" + border.width: 1 + border.color: root.color + } + +} diff --git a/src/controls/FluSlider.qml b/src/controls/FluSlider.qml index fea3a56..d482001 100644 --- a/src/controls/FluSlider.qml +++ b/src/controls/FluSlider.qml @@ -40,11 +40,12 @@ Item{ id:dot width: dotSize height: dotSize + FluShadow{ + radius: 15 + } radius: 15 anchors.verticalCenter: parent.verticalCenter - layer.enabled: true color:FluApp.isDark ? Qt.rgba(69/255,69/255,69/255,1) :Qt.rgba(1,1,1,1) - layer.effect: FluDropShadow {} Rectangle{ width: dotSize/2 height: dotSize/2 diff --git a/src/controls/FluTextButton.qml b/src/controls/FluTextButton.qml new file mode 100644 index 0000000..3bfeb83 --- /dev/null +++ b/src/controls/FluTextButton.qml @@ -0,0 +1,22 @@ +import QtQuick 2.15 +import FluentUI 1.0 + +FluText { + id:root + color: { + if(FluApp.isDark){ + return mouse_area.containsMouse?Qt.rgba(73/255,148/255,206/255,1):Qt.rgba(76/255,160/255,224/255,1) + } + return mouse_area.containsMouse?Qt.rgba(24/255,116/255,186/255,1):Qt.rgba(0/255,102/255,180/255,1) + } + signal clicked + MouseArea{ + id:mouse_area + anchors.fill: parent + hoverEnabled: true + cursorShape: Qt.PointingHandCursor + onClicked: { + root.clicked() + } + } +} diff --git a/src/controls/FluTooltip.qml b/src/controls/FluTooltip.qml index 4496346..d6965ba 100644 --- a/src/controls/FluTooltip.qml +++ b/src/controls/FluTooltip.qml @@ -18,7 +18,6 @@ ToolTip { anchors.fill: parent color: FluApp.isDark ? Qt.rgba(50/255,49/255,48/255,1) : Qt.rgba(1,1,1,1) radius: 5 - layer.enabled: true - layer.effect: FluDropShadow {} + FluShadow{} } } diff --git a/src/controls/FluWindow.qml b/src/controls/FluWindow.qml index 35dff10..20a21ea 100644 --- a/src/controls/FluWindow.qml +++ b/src/controls/FluWindow.qml @@ -32,25 +32,22 @@ Item { FluWindowResize{} + Behavior on opacity{ NumberAnimation{ duration: 100 } } + FluShadow{ + anchors.fill: container + } + Rectangle{ id:container color:root.color anchors.fill: parent anchors.margins: borderless - layer.enabled: true - layer.effect: DropShadow { - radius: 5 - samples: 5 - horizontalOffset: 0 - verticalOffset: 0 - color: "#40000000" - } } Component.onCompleted: { diff --git a/src/controls/FluWindowResize.qml b/src/controls/FluWindowResize.qml index ea2cad6..3d07f29 100644 --- a/src/controls/FluWindowResize.qml +++ b/src/controls/FluWindowResize.qml @@ -31,68 +31,50 @@ MouseArea { return; } - var rc = Qt.rect(0, 0, 0, 0); let e = 0; - - //top-left - rc = Qt.rect(0, 0, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,0,border,border, mouse.x, mouse.y)) { e = Qt.TopEdge | Qt.LeftEdge; window.startSystemResize(e); return; } - //top - rc = Qt.rect(border, 0, window.width-border*2, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(border,0,window.width-border*2,border, mouse.x, mouse.y)) { e = Qt.TopEdge; window.startSystemResize(e); return; } - //top-right - rc = Qt.rect(window.width-border, 0, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,0,border,border, mouse.x, mouse.y)) { e = Qt.TopEdge | Qt.RightEdge; window.startSystemResize(e); return; } - //right - rc = Qt.rect(window.width-border, border, border, window.height-border*2); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,border,border,window.height-border*2, mouse.x, mouse.y)) { e = Qt.RightEdge; window.startSystemResize(e); return; } - //bottom-right - rc = Qt.rect(window.width-border, window.height-border, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,window.height-border,border,border, mouse.x, mouse.y)) { e = Qt.BottomEdge | Qt.RightEdge; window.startSystemResize(e); return; } - //bottom - rc = Qt.rect(border, window.height-border, window.width-border*2, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(border,window.height-border,window.width-border*2,border, mouse.x, mouse.y)) { e = Qt.BottomEdge; window.startSystemResize(e); return; } - //bottom_left - rc = Qt.rect(0, window.height-border,border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,window.height-border,border,border, mouse.x, mouse.y)) { e = Qt.BottomEdge | Qt.LeftEdge; window.startSystemResize(e); return; } - //left - rc = Qt.rect(0, border,border, window.height-border*2); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,border,border , window.height-border*2, mouse.x, mouse.y)) { e = Qt.LeftEdge; window.startSystemResize(e); return; @@ -105,66 +87,46 @@ MouseArea { cursorShape = Qt.ArrowCursor; return; } - - var rc = Qt.rect(0, 0, 0, 0); - - //top-left - rc = Qt.rect(0, 0, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,0,border,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeFDiagCursor; return; } - //top - rc = Qt.rect(border, 0, window.width-border*2, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(border,0,window.width-border*2,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeVerCursor; return; } - //top-right - rc = Qt.rect(window.width-border, 0, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,0,border,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeBDiagCursor; return; } - //right - rc = Qt.rect(window.width-border, border, border, window.height-border*2); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,border,border,window.height-border*2, mouse.x, mouse.y)) { cursorShape = Qt.SizeHorCursor; return; } - //bottom-right - rc = Qt.rect(window.width-border, window.height-border, border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(window.width-border,window.height-border,border,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeFDiagCursor; return; } - //bottom - rc = Qt.rect(border, window.height-border, window.width-border*2, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(border,window.height-border,window.width-border*2,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeVerCursor; return; } - //bottom_left - rc = Qt.rect(0, window.height-border,border, border); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,window.height-border,border,border, mouse.x, mouse.y)) { cursorShape = Qt.SizeBDiagCursor; return; } - //left - rc = Qt.rect(0, border,border, window.height-border*2); - if (ptInRect(rc, mouse.x, mouse.y)) { + if (ptInRect(0,border,border, window.height-border*2, mouse.x, mouse.y)) { cursorShape = Qt.SizeHorCursor; return; } - //default cursorShape = Qt.ArrowCursor; } @@ -172,13 +134,12 @@ MouseArea { cursorShape = Qt.ArrowCursor; } - function ptInRect(rc, x, y) + function ptInRect(rcx,rcy,rcwidth,rcheight, x, y) { - if ((rc.x <= x && x <= (rc.x + rc.width)) && - (rc.y <= y && y <= (rc.y + rc.height))) { + if ((rcx <= x && x <= (rcx + rcwidth)) && + (rcy <= y && y <= (rcy + rcheight))) { return true; } - return false; } diff --git a/src/qml_plugin.cpp b/src/qml_plugin.cpp index 84cd7a6..31a6ca8 100644 --- a/src/qml_plugin.cpp +++ b/src/qml_plugin.cpp @@ -1,14 +1,12 @@ #include "qml_plugin.h" -#include "Fluent.h" - void FluentUIQmlPlugin::registerTypes(const char *uri) { - Fluent::getInstance()->registerTypes(uri); + FluentUI::registerTypes(uri); } void FluentUIQmlPlugin::initializeEngine(QQmlEngine *engine, const char *uri) { - Fluent::getInstance()->initializeEngine(engine,uri); + FluentUI::initializeEngine(engine,uri); } diff --git a/src/qml_plugin.h b/src/qml_plugin.h index b28d281..6cf5719 100644 --- a/src/qml_plugin.h +++ b/src/qml_plugin.h @@ -1,6 +1,7 @@ #pragma once #include +#include class FluentUIQmlPlugin : public QQmlExtensionPlugin { diff --git a/src/res.qrc b/src/res.qrc index 95c5375..fd39bb5 100644 --- a/src/res.qrc +++ b/src/res.qrc @@ -23,7 +23,6 @@ controls/FluIcon.qml controls/FluDivider.qml controls/FluTooltip.qml - controls/FluDropShadow.qml controls/TFpsMonitor.qml controls/FluTextBoxBackground.qml controls/FluMultiLineTextBox.qml @@ -31,5 +30,7 @@ controls/FluScrollBar.qml controls/FluMenu.qml controls/FluMenuItem.qml + controls/FluShadow.qml + controls/FluTextButton.qml