diff --git a/spark-webapp-runtime/globaldefine.h b/spark-webapp-runtime/globaldefine.h
index 9223d85..b831290 100644
--- a/spark-webapp-runtime/globaldefine.h
+++ b/spark-webapp-runtime/globaldefine.h
@@ -4,8 +4,9 @@
 #include <QObject>
 
 #define DEFAULT_TITLE QObject::tr("SparkWebAppRuntime")
-//#define DEFAULT_URL     QString("qrc:/help/help.html")
-#define DEFAULT_URL QString("https://www.baidu.com")
+#define APPLICATION_NAME QString("SparkWebAppRuntime")
+#define ORGANIZATION_NAME QString("spark-union")
+#define DEFAULT_URL QString("qrc:/help/help.html")
 #define DEFAULT_WIDTH (1024)
 #define DEFAULT_HEIGHT (768)
 
diff --git a/spark-webapp-runtime/main.cpp b/spark-webapp-runtime/main.cpp
index da9078a..11378a5 100644
--- a/spark-webapp-runtime/main.cpp
+++ b/spark-webapp-runtime/main.cpp
@@ -5,6 +5,7 @@
 #include "mainwindow.h"
 
 #include <DApplication>
+#include <DPlatformWindowHandle>
 
 #include <QCommandLineParser>
 #include <QCommandLineOption>
@@ -15,18 +16,40 @@
 #include "httpd.h"
 
 DWIDGET_USE_NAMESPACE
+
 int main(int argc, char *argv[])
 {
+    if (!QString(qgetenv("XDG_CURRENT_DESKTOP")).toLower().startsWith("deepin")) {
+        setenv("XDG_CURRENT_DESKTOP", "Deepin", 1);
+    }
+
+    // 龙芯机器配置,使得DApplication能正确加载QTWEBENGINE
+    qputenv("DTK_FORCE_RASTER_WIDGETS", "FALSE");
+//    qputenv("QTWEBENGINE_CHROMIUM_FLAGS", "--disable-features=UseModernMediaControls");
+//    qputenv("QTWEBENGINE_CHROMIUM_FLAGS", "--disable-web-security");
+#ifdef __sw_64__
+    qputenv("QTWEBENGINE_CHROMIUM_FLAGS", "--no-sandbox");
+#endif
+
+#ifndef DSTORE_NO_DXCBs
+    Dtk::Widget::DApplication::loadDXcbPlugin();
+#endif
+
     DApplication a(argc, argv);
-	
+
     a.loadTranslator();
     a.setAttribute(Qt::AA_UseHighDpiPixmaps);
+    if (!Dtk::Widget::DPlatformWindowHandle::pluginVersion().isEmpty()) {
+        a.setAttribute(Qt::AA_DontCreateNativeWidgetSiblings, true);
+    }
 
     a.setApplicationVersion(QString::number(CURRENT_VER));
-    a.setOrganizationName("spark-union"); // 添加组织名称,和商店主体的文件夹同在 ~/.local/share/spark-union 文件夹下
-    a.setApplicationName("SparkWebAppRuntime"); // 这里不要翻译,否则 ~/.local/share 中文件夹名也会被翻译
-QDialog *dialog ;
-/* Customized DAboutDialog (Can't work on other distro like Ubuntu...)
+    a.setOrganizationName(ORGANIZATION_NAME); // 添加组织名称,和商店主体的文件夹同在 ~/.local/share/spark-union 文件夹下
+    a.setApplicationName(APPLICATION_NAME); // 这里不要翻译,否则 ~/.local/share 中文件夹名也会被翻译
+    a.setProductName(DEFAULT_TITLE);
+    a.setApplicationDisplayName(DEFAULT_TITLE);
+
+    // Customized DAboutDialog (Can't work on other distro like Ubuntu...)
     DAboutDialog *dialog = new DAboutDialog;
     a.setAboutDialog(dialog);
 
@@ -41,21 +64,19 @@ QDialog *dialog ;
     // CompanyLogo
     dialog->setCompanyLogo(QPixmap(":/images/Logo-Spark.png"));
     // Description
-*/
+
     QString szDefaultDesc = QString("<a href='https://gitee.com/deepin-community-store/spark-web-app-runtime'><span style='font-size:12pt;font-weight:500;'>%1</span></a><br/>"
                                     "<span style='font-size:12pt;'>%2</span>")
                                 .arg(DEFAULT_TITLE)
                                 .arg(QObject::tr("Presented By Spark developers # HadesStudio"));
-/*    
-dialog->setDescription(szDefaultDesc);
+
+    dialog->setDescription(szDefaultDesc);
     // WebsiteName
     dialog->setWebsiteName("Spark Project");
     // WebsiteLink
-    dialog->setWebsiteLink("https://git
-ee.com/deepin-community-store/");
+    dialog->setWebsiteLink("https://gitee.com/deepin-community-store/");
     // License
-    dialog->setLicense(QObject::tr("This program is open source under GPLv3")); // 本程序按GPL第三版开源
-*/
+    dialog->setLicense(QObject::tr("Published under GPLv3"));
 
     QCommandLineParser parser;
 
@@ -183,8 +204,8 @@ ee.com/deepin-community-store/");
                 QSettings settings(szCfgFile, QSettings::IniFormat);
                 szTitle = settings.value("SparkWebAppRuntime/Title", DEFAULT_TITLE).toString();
                 szUrl = settings.value("SparkWebAppRuntime/URL", DEFAULT_TITLE).toString();
-                width = settings.value("SparkWebAppRuntime/Width", DEFAULT_WIDTH).toUInt();
-                height = settings.value("SparkWebAppRuntime/Height", DEFAULT_HEIGHT).toUInt();
+                width = settings.value("SparkWebAppRuntime/Width", DEFAULT_WIDTH).toInt();
+                height = settings.value("SparkWebAppRuntime/Height", DEFAULT_HEIGHT).toInt();
                 tray = settings.value("SparkWebAppRunTime/Tray", false).toBool();
                 fullScreen = settings.value("SparkWebAppRunTime/FullScreen", false).toBool();
                 fixSize = settings.value("SparkWebAppRunTime/FixSize", false).toBool();
@@ -301,8 +322,7 @@ ee.com/deepin-community-store/");
 
     a.setQuitOnLastWindowClosed(!tray); // 启用托盘时,退出程序后服务不终止
 
-    MainWindow w(szTitle, szUrl, width, height, tray, fullScreen, fixSize, hideButtons,dialog);
-    // qputenv("QTWEBENGINE_CHROMIUM_FLAGS", "--disable-features=UseModernMediaControls");
+    MainWindow w(szTitle, szUrl, width, height, tray, fullScreen, fixSize, hideButtons, dialog);
 
 #if SSL_SERVER
     if (!szRootPath.isEmpty() && u16Port > 0 && u16sslPort > 0) {
@@ -321,7 +341,7 @@ ee.com/deepin-community-store/");
         szIcon = parser.value(optIcon);
     }
 
-/*    if (!szIcon.isEmpty()) {
+    if (!szIcon.isEmpty()) {
         dialog->setWindowIcon(QIcon(szIcon));
         dialog->setProductIcon(QIcon(szIcon));
         w.setIcon(szIcon);
@@ -329,7 +349,7 @@ ee.com/deepin-community-store/");
     if (!szDesc.isEmpty()) {
         dialog->setDescription(szDesc);
     }
-*/
+
     w.show();
     return a.exec();
 }
diff --git a/spark-webapp-runtime/mainwindow.cpp b/spark-webapp-runtime/mainwindow.cpp
index af0cb6d..c46d810 100644
--- a/spark-webapp-runtime/mainwindow.cpp
+++ b/spark-webapp-runtime/mainwindow.cpp
@@ -16,157 +16,54 @@ MainWindow::MainWindow(QString szTitle,
                        QString szUrl,
                        int nWidth,
                        int nHeight,
-                       bool tray,
+                       bool nTray,
                        bool nFullScreen,
                        bool nFixSize,
                        bool nHideButtons,
                        QDialog *dialog,
                        QWidget *parent)
     : DMainWindow(parent)
-    , m_widget(new Widget(szUrl))
-//    , m_dialog(dialog)
-    , m_tray(new QSystemTrayIcon)
+    , m_title(szTitle)
+    , m_url(szUrl)
+    , m_width(nWidth)
+    , m_height(nHeight)
+    , m_isTrayEnabled(nTray)
+    , m_isFullScreen(nFullScreen)
+    , m_isFixedSize(nFixSize)
+    , m_isHideButton(nHideButtons)
+    , m_widget(new Widget(m_url, this))
+    , m_dialog(dynamic_cast<DAboutDialog *>(dialog))
+    , m_tray(new QSystemTrayIcon(this))
     , btnBack(new DToolButton(titlebar()))
     , btnForward(new DToolButton(titlebar()))
     , btnRefresh(new DToolButton(titlebar()))
-    , m_menu(new QMenu)
-    , m_fullScreen(new QAction(tr("Full Screen")))
-    , m_fixSize(new QAction(tr("Fix Size")))
-    , m_hideButtons(new QAction(tr("Hide Buttons")))
-    , t_menu(new QMenu)
-    , t_show(new QAction(tr("Show MainWindow")))
-    , t_about(new QAction(tr("About")))
-    , t_exit(new QAction(tr("Exit")))
-    , downloadProgressBar(new QWidget)
-    , bar(new DProgressBar)
-    , pause(new DPushButton(tr("Pause")))
-    , resume(new DPushButton(tr("Resume")))
-    , cancel(new DPushButton(tr("Cancel")))
-    , progress(new QHBoxLayout)
-    , message(new DFloatingMessage(DFloatingMessage::ResidentType))
+    , m_menu(new QMenu(titlebar()))
+    , m_fullScreen(new QAction(tr("Full Screen"), this))
+    , m_fixSize(new QAction(tr("Fix Size"), this))
+    , m_hideButtons(new QAction(tr("Hide Buttons"), this))
+    , m_clearCache(new QAction(tr("Clear Cache"), this))
+    , t_menu(new QMenu(this))
+    , t_show(new QAction(tr("Show MainWindow"), this))
+    , t_about(new QAction(tr("About"), this))
+    , t_exit(new QAction(tr("Exit"), this))
+    , downloadMessage(new DFloatingMessage(DFloatingMessage::ResidentType, this))
+    , downloadProgressWidget(new QWidget(downloadMessage))
+    , progressBarLayout(new QHBoxLayout(downloadProgressWidget))
+    , downloadProgressBar(new DProgressBar(downloadProgressWidget))
+    , btnPause(new DPushButton(tr("Pause"), downloadProgressWidget))
+    , btnResume(new DPushButton(tr("Resume"), downloadProgressWidget))
+    , btnCancel(new DPushButton(tr("Cancel"), downloadProgressWidget))
     , isCanceled(false)
-    , mtray(tray)
-    , mFixSize(nFixSize)
-   , m_width(nWidth)
-   , m_height(nHeight)
 {
-    /* 初始化 MainWindow */
-    setCentralWidget(m_widget);
-    centralWidget()->layout()->setContentsMargins(0, 0, 0, 0);
-
-    resize(m_width, m_height);
-
-    moveToCenter(this);
-
-    setWindowIcon(QIcon(":/images/spark-webapp-runtime.svg"));
-
-    titlebar()->setTitle(szTitle);
-    titlebar()->setIcon(QIcon(":/images/spark-webapp-runtime.svg"));
-
-    btnBack->setIcon(QIcon(":/images/go-previous-24.svg"));
-    btnBack->setIconSize(QSize(36, 36));
-    btnForward->setIcon(QIcon(":/images/go-next-24.svg"));
-    btnForward->setIconSize(QSize(36, 36));
-    btnRefresh->setIcon(QIcon(":/images/view-refresh.svg"));
-    btnRefresh->setIconSize(QSize(36, 36));
-
-    titlebar()->addWidget(btnBack, Qt::AlignLeft);
-    titlebar()->addWidget(btnForward, Qt::AlignLeft);
-    titlebar()->addWidget(btnRefresh, Qt::AlignLeft);
-
-    m_fullScreen->setCheckable(true);
-    m_fullScreen->setChecked(nFullScreen);
-    m_fullScreen->setDisabled(nFixSize); //  固定窗口大小时禁用全屏模式,避免标题栏按钮 BUG
-    m_fixSize->setCheckable(true);
-    m_fixSize->setChecked(nFixSize);
-    m_fixSize->setDisabled(nFixSize);
-    m_hideButtons->setCheckable(true);
-    m_hideButtons->setChecked(nHideButtons);
-    m_hideButtons->setDisabled(nHideButtons);
-    /* 命令行设置参数后 GUI 中隐藏对应选项 */
-    if (!nFixSize) {
-        m_menu->addAction(m_fullScreen);
-        m_menu->addAction(m_fixSize);
-    }
-    if (!nHideButtons) {
-        m_menu->addAction(m_hideButtons);
-    }
-    titlebar()->setMenu(m_menu);
-
-    titlebar()->setAutoHideOnFullscreen(true);
-
-    fixSize();
-    hideButtons();
-
-    /* 初始化 TrayIcon */
-    t_menu->addAction(t_show);
-    t_menu->addAction(t_about);
-    t_menu->addAction(t_exit);
-    m_tray->setContextMenu(t_menu);
-    m_tray->setToolTip(szTitle);
-    m_tray->setIcon(QIcon(":/images/spark-webapp-runtime.svg"));
-
-    if (tray) {
-        m_tray->show(); // 启用托盘时显示
-    }
-
-    /* 初始化 DownloadProgressBar */
-    bar->setFixedSize(250, 8);
-    progress->addWidget(bar);
-    progress->addSpacing(5);
-    progress->addWidget(pause);
-    progress->addWidget(resume);
-    progress->addWidget(cancel);
-    downloadProgressBar->setLayout(progress);
-    message->setIcon(QIcon::fromTheme("deepin-download").pixmap(64, 64));
-    message->setWidget(downloadProgressBar);
-
-    connect(btnBack, &DToolButton::clicked, this, [&]() {
-        m_widget->goBack();
-    });
-    connect(btnForward, &DToolButton::clicked, this, [&]() {
-        m_widget->goForward();
-    });
-    connect(btnRefresh, &DToolButton::clicked, this, [&]() {
-        m_widget->refresh();
-    });
-
-    connect(m_fullScreen, &QAction::triggered, this, [=]() {
-        fullScreen();
-    });
-    connect(m_fixSize, &QAction::triggered, this, [=]() {
-        fixSize();
-    });
-    connect(m_hideButtons, &QAction::triggered, this, [=]() {
-        hideButtons();
-    });
-
-    connect(t_show, &QAction::triggered, this, [=]() {
-        this->activateWindow();
-        fixSize();
-    });
-    connect(t_about, &QAction::triggered, this, [=]() {
-        m_dialog->activateWindow();
-        m_dialog->show();
-    });
-    connect(t_exit, &QAction::triggered, this, [=]() {
-        exit(0);
-    });
-    connect(m_tray, &QSystemTrayIcon::activated, this, &MainWindow::trayIconActivated);
-
-    connect(m_widget->getPage()->profile(), &QWebEngineProfile::downloadRequested, this, &MainWindow::on_downloadStart);
-
-    connect(m_widget->getPage(), &QWebEnginePage::windowCloseRequested, this, [=]() {
-        this->close();
-    });
+    initUI();
+    initTrayIcon();
+    initConnections();
 }
 
 MainWindow::~MainWindow()
 {
     emit sigQuit();
-    delete m_widget;
     delete m_dialog;
-    delete m_tray;
 }
 
 void MainWindow::setIcon(QString szIconPath)
@@ -197,7 +94,7 @@ void MainWindow::resizeEvent(QResizeEvent *event)
         m_fullScreen->setChecked(true);
     } else {
         m_fullScreen->setChecked(false);
-        if (!mFixSize) {
+        if (!m_isFixedSize) {
             m_fixSize->setEnabled(true); // 命令行参数没有固定窗口大小时,窗口模式下允许手动选择固定窗口大小
         }
     }
@@ -205,15 +102,159 @@ void MainWindow::resizeEvent(QResizeEvent *event)
 }
 
 void MainWindow::closeEvent(QCloseEvent *event)
-{}
-/*
 {
-    if (!mtray) {
+    if (!m_isTrayEnabled) {
         m_dialog->close(); // 不启用托盘时,关闭主窗口则关闭关于窗口
     }
     event->accept();
 }
-*/
+
+void MainWindow::initUI()
+{
+    // 初始化 MainWindow
+    setCentralWidget(m_widget);
+    centralWidget()->layout()->setContentsMargins(0, 0, 0, 0);
+
+    resize(m_width, m_height);
+
+    moveToCenter(this);
+
+    setWindowIcon(QIcon(":/images/spark-webapp-runtime.svg"));
+
+    initTitleBar();
+    initDownloadProgressBar();
+
+    fixSize();
+    fullScreen();
+}
+
+void MainWindow::initTitleBar()
+{
+    titlebar()->setTitle(m_title);
+    titlebar()->setIcon(QIcon(":/images/spark-webapp-runtime.svg"));
+
+    btnBack->setIcon(QIcon(":/images/go-previous-24.svg"));
+    btnBack->setIconSize(QSize(36, 36));
+    btnForward->setIcon(QIcon(":/images/go-next-24.svg"));
+    btnForward->setIconSize(QSize(36, 36));
+    btnRefresh->setIcon(QIcon(":/images/view-refresh.svg"));
+    btnRefresh->setIconSize(QSize(36, 36));
+
+    titlebar()->addWidget(btnBack, Qt::AlignLeft);
+    titlebar()->addWidget(btnForward, Qt::AlignLeft);
+    titlebar()->addWidget(btnRefresh, Qt::AlignLeft);
+
+    m_fullScreen->setCheckable(true);
+    m_fullScreen->setChecked(m_isFullScreen);
+    m_fullScreen->setDisabled(m_isFixedSize); // NOTE: 固定窗口大小时禁用全屏模式,避免标题栏按钮显示问题
+    m_fixSize->setCheckable(true);
+    m_fixSize->setChecked(m_isFixedSize);
+    m_fixSize->setDisabled(m_isFixedSize);
+    m_hideButtons->setCheckable(true);
+    m_hideButtons->setChecked(m_isHideButton);
+    m_hideButtons->setDisabled(m_isHideButton);
+
+    // 命令行设置参数后 GUI 中隐藏对应选项
+    if (!m_isFixedSize) {
+        m_menu->addAction(m_fullScreen);
+        m_menu->addAction(m_fixSize);
+    }
+
+    if (!m_isHideButton) {
+        m_menu->addAction(m_hideButtons);
+    }
+
+    if (m_menu->actions().size() > 0) {
+        m_menu->addSeparator();
+        m_menu->addAction(m_clearCache);
+    }
+
+    titlebar()->setMenu(m_menu);
+    titlebar()->setAutoHideOnFullscreen(true);
+}
+
+void MainWindow::initDownloadProgressBar()
+{
+    // 初始化 DownloadProgressBar
+    downloadProgressBar->setFixedSize(250, 8);
+    btnPause->setFixedSize(80, 32);
+    btnResume->setFixedSize(80, 32);
+    btnCancel->setFixedSize(80, 32);
+
+    progressBarLayout->setMargin(0);
+    progressBarLayout->setSpacing(0);
+    progressBarLayout->setAlignment(Qt::AlignCenter);
+    progressBarLayout->addWidget(downloadProgressBar);
+    progressBarLayout->addSpacing(10);
+    progressBarLayout->addWidget(btnPause);
+    progressBarLayout->addWidget(btnResume);
+    progressBarLayout->addWidget(btnCancel);
+
+    downloadMessage->setIcon(QIcon::fromTheme("deepin-download").pixmap(64, 64));
+    downloadMessage->setWidget(downloadProgressWidget);
+    downloadMessage->hide();
+}
+
+void MainWindow::initTrayIcon()
+{
+    // 初始化 TrayIcon
+    t_menu->addAction(t_show);
+    t_menu->addAction(t_about);
+    t_menu->addAction(t_exit);
+    m_tray->setContextMenu(t_menu);
+    m_tray->setToolTip(m_title);
+    m_tray->setIcon(QIcon(":/images/spark-webapp-runtime.svg"));
+
+    if (m_isTrayEnabled) {
+        m_tray->show(); // 启用托盘时显示
+    }
+}
+
+void MainWindow::initConnections()
+{
+    connect(btnBack, &DToolButton::clicked, this, [&]() {
+        m_widget->goBack();
+    });
+    connect(btnForward, &DToolButton::clicked, this, [&]() {
+        m_widget->goForward();
+    });
+    connect(btnRefresh, &DToolButton::clicked, this, [&]() {
+        m_widget->refresh();
+    });
+
+    connect(m_fullScreen, &QAction::triggered, this, [=]() {
+        fullScreen();
+    });
+    connect(m_fixSize, &QAction::triggered, this, [=]() {
+        fixSize();
+    });
+    connect(m_hideButtons, &QAction::triggered, this, [=]() {
+        hideButtons();
+    });
+    connect(m_clearCache, &QAction::triggered, this, [=]() {
+        clearCache();
+    });
+
+    connect(t_show, &QAction::triggered, this, [=]() {
+        this->activateWindow();
+        fixSize();
+    });
+    connect(t_about, &QAction::triggered, this, [=]() {
+        m_dialog->activateWindow();
+        m_dialog->show();
+    });
+    connect(t_exit, &QAction::triggered, this, [=]() {
+        exit(0);
+    });
+    connect(m_tray, &QSystemTrayIcon::activated, this, &MainWindow::on_trayIconActivated);
+
+    connect(m_widget->getPage()->profile(), &QWebEngineProfile::downloadRequested, this, &MainWindow::on_downloadStart);
+
+    connect(m_widget->getPage(), &QWebEnginePage::windowCloseRequested, this, [=]() {
+        this->close();
+    });
+}
+
 void MainWindow::fullScreen()
 {
     if (m_fullScreen->isChecked()) {
@@ -223,7 +264,7 @@ void MainWindow::fullScreen()
         showFullScreen();
         // DMessageManager::instance()->sendMessage(this, QIcon::fromTheme("dialog-information").pixmap(64, 64), QString(tr("%1Fullscreen Mode")).arg("    "));
     } else {
-        if (!mFixSize) {
+        if (!m_isFixedSize) {
             m_fixSize->setDisabled(false); // 命令行参数没有固定窗口大小时,窗口模式下允许手动选择固定窗口大小
         }
         m_menu->update();
@@ -239,13 +280,14 @@ void MainWindow::fixSize()
         m_fullScreen->setDisabled(true);
         m_menu->update();
         setFixedSize(this->size());
-        /* 存在 BUG: 启用托盘图标后,若手动选择固定窗口大小,并且关闭窗口,再次打开时会丢失最大化按钮,且无法恢复。 */
+        // BUG: 启用托盘图标后,若手动选择固定窗口大小,并且关闭窗口,再次打开时会丢失最大化按钮,且无法恢复。
     } else {
         m_fullScreen->setDisabled(false);
         m_menu->update();
         setMinimumSize(m_width, m_height);
         setMaximumSize(QSize(QWIDGETSIZE_MAX, QWIDGETSIZE_MAX));
     }
+
     fullScreen();
 }
 
@@ -262,12 +304,23 @@ void MainWindow::hideButtons()
     }
 }
 
+void MainWindow::clearCache()
+{
+    // 清除缓存文件夹并刷新页面
+    QDir dir(QDir::homePath() + "/.local/share/" + ORGANIZATION_NAME + "/" + APPLICATION_NAME);
+    if (dir.exists()) {
+        dir.removeRecursively();
+    }
+
+    emit btnRefresh->clicked();
+}
+
 QString MainWindow::saveAs(QString fileName)
 {
     QString saveFile = QFileDialog::getSaveFileName(this, tr("Save As"), QDir::homePath() + "/Downloads/" + fileName);
     if (!saveFile.isEmpty()) {
-        if (QFileInfo(QFileInfo(saveFile).absolutePath()).permissions().testFlag(QFile::WriteUser)) // 判断上层目录是否可写入
-        {
+        // 判断上层目录是否可写入
+        if (QFileInfo(QFileInfo(saveFile).absolutePath()).isWritable()) {
             return saveFile;
         } else {
             return saveAs(fileName);
@@ -276,7 +329,7 @@ QString MainWindow::saveAs(QString fileName)
     return nullptr;
 }
 
-void MainWindow::trayIconActivated(QSystemTrayIcon::ActivationReason reason)
+void MainWindow::on_trayIconActivated(QSystemTrayIcon::ActivationReason reason)
 {
     switch (reason) {
     /* 响应托盘点击事件 */
@@ -291,7 +344,7 @@ void MainWindow::trayIconActivated(QSystemTrayIcon::ActivationReason reason)
 
 void MainWindow::on_downloadStart(QWebEngineDownloadItem *item)
 {
-    /* 尝试加锁互斥量,禁止同时下载多个文件 */
+    // 尝试加锁互斥量,禁止同时下载多个文件
     if (mutex.tryLock()) {
         QString fileName = QFileInfo(item->path()).fileName();
         QString filePath = saveAs(fileName);
@@ -307,13 +360,13 @@ void MainWindow::on_downloadStart(QWebEngineDownloadItem *item)
             on_downloadFinish(filePath);
         });
 
-        connect(pause, &DPushButton::clicked, this, [=]() {
+        connect(btnPause, &DPushButton::clicked, this, [=]() {
             on_downloadPause(item);
         });
-        connect(resume, &DPushButton::clicked, this, [=]() {
+        connect(btnResume, &DPushButton::clicked, this, [=]() {
             on_downloadResume(item);
         });
-        connect(cancel, &DPushButton::clicked, this, [=]() {
+        connect(btnCancel, &DPushButton::clicked, this, [=]() {
             on_downloadCancel(item);
         });
 
@@ -324,11 +377,11 @@ void MainWindow::on_downloadStart(QWebEngineDownloadItem *item)
 
         item->accept();
 
-        /* 重置 DownloadProgressBar 状态 */
+        // 重置 DownloadProgressBar 状态
         isCanceled = false;
-        resume->hide();
-        pause->show();
-        this->message->show(); // 上一次下载完成后隐藏了进度条,这里要重新显示
+        btnResume->hide();
+        btnPause->show();
+        this->downloadMessage->show(); // 上一次下载完成后隐藏了进度条,这里要重新显示
     } else {
         DMessageManager::instance()->sendMessage(this, QIcon::fromTheme("dialog-cancel").pixmap(64, 64), QString(tr("%1Wait for previous download to complete!")).arg("    "));
     }
@@ -337,21 +390,21 @@ void MainWindow::on_downloadStart(QWebEngineDownloadItem *item)
 void MainWindow::on_downloadProgress(qint64 bytesReceived, qint64 bytesTotal)
 {
     int value = int(double(bytesReceived) / double(bytesTotal) * 100.0);
-    bar->setValue(value);
+    downloadProgressBar->setValue(value);
 
-    message->setMessage("    " + QString::number(value) + "%");
+    downloadMessage->setMessage("    " + QString::number(value) + "%");
 
-    DMessageManager::instance()->sendMessage(this, message);
+    DMessageManager::instance()->sendMessage(this, downloadMessage);
 }
 
 void MainWindow::on_downloadFinish(QString filePath)
 {
     mutex.unlock(); // 解锁互斥量,允许下载新文件
 
-    message->hide();
+    downloadMessage->hide();
 
-    if (!isCanceled) // 下载完成显示提示信息
-    {
+    // 下载完成显示提示信息
+    if (!isCanceled) {
         DPushButton *button = new DPushButton(tr("Open"));
 
         DFloatingMessage *message = new DFloatingMessage(DFloatingMessage::ResidentType);
@@ -371,18 +424,18 @@ void MainWindow::on_downloadPause(QWebEngineDownloadItem *item)
 {
     item->pause();
 
-    message->setIcon(QIcon::fromTheme("package-download-failed").pixmap(64, 64));
-    resume->show();
-    pause->hide();
+    downloadMessage->setIcon(QIcon::fromTheme("package-download-failed").pixmap(64, 64));
+    btnResume->show();
+    btnPause->hide();
 }
 
 void MainWindow::on_downloadResume(QWebEngineDownloadItem *item)
 {
     item->resume();
 
-    message->setIcon(QIcon::fromTheme("deepin-download").pixmap(64, 64));
-    resume->hide();
-    pause->show();
+    downloadMessage->setIcon(QIcon::fromTheme("deepin-download").pixmap(64, 64));
+    btnResume->hide();
+    btnPause->show();
 }
 
 void MainWindow::on_downloadCancel(QWebEngineDownloadItem *item)
@@ -392,6 +445,6 @@ void MainWindow::on_downloadCancel(QWebEngineDownloadItem *item)
 
     mutex.unlock();
 
-    message->hide();
+    downloadMessage->hide();
     DMessageManager::instance()->sendMessage(this, QIcon::fromTheme("dialog-error").pixmap(64, 64), QString(tr("%1Download canceled!")).arg("    "));
 }
diff --git a/spark-webapp-runtime/mainwindow.h b/spark-webapp-runtime/mainwindow.h
index a585a09..c060638 100644
--- a/spark-webapp-runtime/mainwindow.h
+++ b/spark-webapp-runtime/mainwindow.h
@@ -26,11 +26,11 @@ public:
                QString szUrl = DEFAULT_URL,
                int nWidth = DEFAULT_WIDTH,
                int nHeight = DEFAULT_HEIGHT,
-               bool tray = false,
+               bool nTray = false,
                bool nFullScreen = false,
                bool nFixSize = false,
                bool nHideButtons = false,
-              QDialog *dialog = nullptr,
+               QDialog *dialog = nullptr,
                QWidget *parent = nullptr);
     ~MainWindow();
 
@@ -42,6 +42,37 @@ protected:
     void closeEvent(QCloseEvent *event);
 
 private:
+    void initUI();
+    void initTitleBar();
+    void initDownloadProgressBar();
+    void initTrayIcon();
+    void initConnections();
+
+    void fullScreen();
+    void fixSize();
+    void hideButtons();
+    void clearCache();
+
+    QString saveAs(QString fileName);
+
+signals:
+    void sigQuit();
+
+private slots:
+    void on_trayIconActivated(QSystemTrayIcon::ActivationReason reason);
+
+    void on_downloadStart(QWebEngineDownloadItem *item);
+    void on_downloadProgress(qint64 bytesReceived, qint64 bytesTotal);
+    void on_downloadFinish(QString filePath);
+    void on_downloadPause(QWebEngineDownloadItem *item);
+    void on_downloadResume(QWebEngineDownloadItem *item);
+    void on_downloadCancel(QWebEngineDownloadItem *item);
+
+private:
+    QString m_title, m_url;
+    int m_width, m_height;
+    bool m_isTrayEnabled, m_isFullScreen, m_isFixedSize, m_isHideButton;
+
     Widget *m_widget;
     DAboutDialog *m_dialog;
     QSystemTrayIcon *m_tray;
@@ -54,44 +85,23 @@ private:
     QAction *m_fullScreen;
     QAction *m_fixSize;
     QAction *m_hideButtons;
+    QAction *m_clearCache;
 
     QMenu *t_menu;
     QAction *t_show;
     QAction *t_about;
     QAction *t_exit;
 
-    QWidget *downloadProgressBar;
-    DProgressBar *bar;
-    DPushButton *pause;
-    DPushButton *resume;
-    DPushButton *cancel;
-    QHBoxLayout *progress;
-    DFloatingMessage *message;
+    DFloatingMessage *downloadMessage;
+    QWidget *downloadProgressWidget;
+    QHBoxLayout *progressBarLayout;
+    DProgressBar *downloadProgressBar;
+    DPushButton *btnPause;
+    DPushButton *btnResume;
+    DPushButton *btnCancel;
 
     QMutex mutex; // 通过 Mutex 互斥量禁止同时下载多个文件(使用简单的 bool 变量应该也可以实现该功能?)
     bool isCanceled; // 判断是否为取消下载
-
-    bool mtray, mFixSize;
-    int m_width, m_height;
-
-    void fullScreen();
-    void fixSize();
-    void hideButtons();
-
-    QString saveAs(QString fileName);
-
-private slots:
-    void trayIconActivated(QSystemTrayIcon::ActivationReason reason);
-
-    void on_downloadStart(QWebEngineDownloadItem *item);
-    void on_downloadProgress(qint64 bytesReceived, qint64 bytesTotal);
-    void on_downloadFinish(QString filePath);
-    void on_downloadPause(QWebEngineDownloadItem *item);
-    void on_downloadResume(QWebEngineDownloadItem *item);
-    void on_downloadCancel(QWebEngineDownloadItem *item);
-
-signals:
-    void sigQuit();
 };
 
 #endif // MAINWINDOW_H
diff --git a/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.qm b/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.qm
index 7da2e32..e8b5034 100644
Binary files a/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.qm and b/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.qm differ
diff --git a/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.ts b/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.ts
index d3bc26e..58840cc 100644
--- a/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.ts
+++ b/spark-webapp-runtime/translations/spark-webapp-runtime_zh_CN.ts
@@ -4,47 +4,52 @@
 <context>
     <name>MainWindow</name>
     <message>
-        <location filename="../mainwindow.cpp" line="33"/>
+        <location filename="../mainwindow.cpp" line="41"/>
         <source>Full Screen</source>
         <translation>全屏显示</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="34"/>
+        <location filename="../mainwindow.cpp" line="42"/>
         <source>Fix Size</source>
         <translation>固定大小</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="35"/>
+        <location filename="../mainwindow.cpp" line="43"/>
         <source>Hide Buttons</source>
         <translation>隐藏按钮</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="37"/>
+        <location filename="../mainwindow.cpp" line="44"/>
+        <source>Clear Cache</source>
+        <translation>清理缓存</translation>
+    </message>
+    <message>
+        <location filename="../mainwindow.cpp" line="46"/>
         <source>Show MainWindow</source>
         <translation>显示主界面</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="38"/>
+        <location filename="../mainwindow.cpp" line="47"/>
         <source>About</source>
         <translation>关于</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="39"/>
+        <location filename="../mainwindow.cpp" line="48"/>
         <source>Exit</source>
         <translation>退出</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="42"/>
+        <location filename="../mainwindow.cpp" line="53"/>
         <source>Pause</source>
         <translation>暂停</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="43"/>
+        <location filename="../mainwindow.cpp" line="54"/>
         <source>Resume</source>
         <translation>继续</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="44"/>
+        <location filename="../mainwindow.cpp" line="55"/>
         <source>Cancel</source>
         <translation>取消</translation>
     </message>
@@ -57,37 +62,37 @@
         <translation type="vanished">%1窗口模式</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="265"/>
+        <location filename="../mainwindow.cpp" line="321"/>
         <source>Save As</source>
         <translation>另存为</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="320"/>
+        <location filename="../mainwindow.cpp" line="376"/>
         <source>%1Start downloading %2</source>
         <translation>%1开始下载 %2</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="331"/>
+        <location filename="../mainwindow.cpp" line="387"/>
         <source>%1Wait for previous download to complete!</source>
         <translation>%1请等待上一个下载任务完成!</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="353"/>
+        <location filename="../mainwindow.cpp" line="409"/>
         <source>Open</source>
         <translation>打开</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="357"/>
+        <location filename="../mainwindow.cpp" line="413"/>
         <source>download finished.</source>
         <translation>下载完成。</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="357"/>
+        <location filename="../mainwindow.cpp" line="413"/>
         <source>Show in file manager?</source>
         <translation>是否在文件管理器中显示?</translation>
     </message>
     <message>
-        <location filename="../mainwindow.cpp" line="394"/>
+        <location filename="../mainwindow.cpp" line="450"/>
         <source>%1Download canceled!</source>
         <translation>%1下载取消!</translation>
     </message>
@@ -95,97 +100,97 @@
 <context>
     <name>QObject</name>
     <message>
-        <location filename="../main.cpp" line="45"/>
+        <location filename="../main.cpp" line="71"/>
         <source>Presented By Spark developers # HadesStudio</source>
         <translation>由 星火开发者联盟 @ 花心胡萝卜 提供</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="52"/>
-        <source>This program is open source under GPLv3</source>
-        <translation>本程序按GPL第三版开源</translation>
-    </message>
-    <message>
-        <location filename="../main.cpp" line="38"/>
+        <location filename="../main.cpp" line="63"/>
         <source>Version:</source>
         <translation>版本:</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="56"/>
+        <location filename="../main.cpp" line="79"/>
+        <source>Published under GPLv3</source>
+        <translation>遵循 GPLv3 协议发布</translation>
+    </message>
+    <message>
+        <location filename="../main.cpp" line="83"/>
         <source>Description: %1</source>
         <translation>描述:%1</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="62"/>
+        <location filename="../main.cpp" line="89"/>
         <source>Enable CommandLineParser. Default is false.</source>
         <translation>启用参数解析方式。默认顺序解析方式。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="67"/>
+        <location filename="../main.cpp" line="94"/>
         <source>The Title of Application. Default is %1.</source>
         <translation>设置程序的运行标题。默认是 %1。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="74"/>
+        <location filename="../main.cpp" line="101"/>
         <source>The target URL. Default is Blank.</source>
         <translation>设置要打开的目标 URL。默认是空。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="81"/>
+        <location filename="../main.cpp" line="108"/>
         <source>The Width of Application. Default is %1.</source>
         <translation>设置应用的窗口宽度。默认是 %1。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="88"/>
+        <location filename="../main.cpp" line="115"/>
         <source>The Height of Application. Default is %1.</source>
         <translation>设置应用的窗口高度。默认是 %1。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="95"/>
+        <location filename="../main.cpp" line="122"/>
         <source>Enable Tray Icon. Default is false.</source>
         <translation>启用托盘图标。默认不启用。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="99"/>
+        <location filename="../main.cpp" line="126"/>
         <source>Run in Fullscreen Mode. Default is false.</source>
         <translation>以全屏模式运行。默认关闭该功能。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="103"/>
+        <location filename="../main.cpp" line="130"/>
         <source>Fix Window Size. Default is false.</source>
         <translation>固定窗口大小。默认关闭该功能。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="107"/>
+        <location filename="../main.cpp" line="134"/>
         <source>Hide Control Buttons. Default is false.</source>
         <translation>隐藏控制按钮。默认关闭该此功能。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="112"/>
+        <location filename="../main.cpp" line="139"/>
         <source>The ICON of Application.</source>
         <translation>设置应用的图标。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="119"/>
+        <location filename="../main.cpp" line="146"/>
         <source>The Description of Application.</source>
         <translation>设置应用的描述信息。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="126"/>
+        <location filename="../main.cpp" line="153"/>
         <source>The Configuration file of Application.</source>
         <translation>设置应用的配置文件。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="133"/>
+        <location filename="../main.cpp" line="160"/>
         <source>The root path of the program web service.</source>
         <translation>设置内置 WebServer 的根路径。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="140"/>
+        <location filename="../main.cpp" line="167"/>
         <source>The port number of the program web service.</source>
         <translation>设置内置 WebServer 的监听端口号。</translation>
     </message>
     <message>
-        <location filename="../main.cpp" line="148"/>
+        <location filename="../main.cpp" line="175"/>
         <source>The ssl port number of the program web service.</source>
         <translation>设置内置 WebServer 的 SSL 协议的监听端口号。</translation>
     </message>
diff --git a/spark-webapp-runtime/webengineview.cpp b/spark-webapp-runtime/webengineview.cpp
index b1e8cd5..acae105 100644
--- a/spark-webapp-runtime/webengineview.cpp
+++ b/spark-webapp-runtime/webengineview.cpp
@@ -3,7 +3,6 @@
 WebEngineView::WebEngineView(QWidget *parent)
     : QWebEngineView(parent)
 {
-
 }
 
 QWebEngineView *WebEngineView::createWindow(QWebEnginePage::WebWindowType type)
diff --git a/spark-webapp-runtime/widget.cpp b/spark-webapp-runtime/widget.cpp
index 784a219..b6e1dd8 100644
--- a/spark-webapp-runtime/widget.cpp
+++ b/spark-webapp-runtime/widget.cpp
@@ -2,21 +2,19 @@
 
 Widget::Widget(QString szUrl, QWidget *parent)
     : QWidget(parent)
-    , m_webEngineView(new WebEngineView)
+    , m_webEngineView(new WebEngineView(this))
+    , m_spinner(new DSpinner(this))
+    , mainLayout(new QStackedLayout(this))
     , m_szUrl(szUrl)
-    , m_spinner(new DSpinner)
-    , main(new QHBoxLayout)
 {
     m_spinner->setFixedSize(96, 96);
 
-    setLayout(main);
-
     m_webEngineView->setObjectName(QStringLiteral("webEngineView"));
     m_webEngineView->setEnabled(true);
     m_webEngineView->setAutoFillBackground(false);
     m_webEngineView->setZoomFactor(1.0);
 
-    QWebEnginePage *page = new QWebEnginePage;
+    QWebEnginePage *page = new QWebEnginePage(m_webEngineView);
     m_webEngineView->setPage(page);
 
     m_webEngineView->setUrl(QUrl(nullptr));
@@ -24,12 +22,26 @@ Widget::Widget(QString szUrl, QWidget *parent)
         m_webEngineView->setUrl(QUrl(m_szUrl));
     }
 
+    QWidget *spinnerWidget = new QWidget(this);
+    QHBoxLayout *spinnerLayout = new QHBoxLayout(spinnerWidget);
+    spinnerLayout->setMargin(0);
+    spinnerLayout->setSpacing(0);
+    spinnerLayout->setAlignment(Qt::AlignCenter);
+    spinnerLayout->addStretch();
+    spinnerLayout->addWidget(m_spinner);
+    spinnerLayout->addStretch();
+
+    mainLayout->addWidget(spinnerWidget);
+    mainLayout->addWidget(m_webEngineView);
+
     connect(m_webEngineView, &QWebEngineView::loadStarted, this, &Widget::on_loadStarted);
     connect(m_webEngineView, &QWebEngineView::loadFinished, this, &Widget::on_loadFinished);
 }
 
 Widget::~Widget()
 {
+    delete m_webEngineView;
+    delete m_spinner;
 }
 
 QWebEnginePage *Widget::getPage()
@@ -52,29 +64,14 @@ void Widget::refresh()
     m_webEngineView->reload();
 }
 
-void Widget::clearLayout(QLayout *layout)
-{
-    QLayoutItem *item;
-    while ((item = layout->takeAt(0)) != nullptr) {
-        delete item;
-    }
-}
-
 void Widget::on_loadStarted()
 {
-    clearLayout(main);
-
-    main->addStretch();
-    main->addWidget(m_spinner);
-    main->addStretch();
-
+    mainLayout->setCurrentIndex(0);
     m_spinner->start();
 }
 
 void Widget::on_loadFinished()
 {
     m_spinner->stop();
-    clearLayout(main);
-
-    main->addWidget(m_webEngineView);
+    mainLayout->setCurrentIndex(1);
 }
diff --git a/spark-webapp-runtime/widget.h b/spark-webapp-runtime/widget.h
index f50223e..ec2c2f9 100644
--- a/spark-webapp-runtime/widget.h
+++ b/spark-webapp-runtime/widget.h
@@ -5,6 +5,7 @@
 #include <QWebEngineProfile>
 #include <QWebEngineView>
 #include <QLayout>
+#include <QStackedLayout>
 
 #include <DSpinner>
 
@@ -27,12 +28,10 @@ public:
 
 private:
     WebEngineView *m_webEngineView;
-    QString m_szUrl;
     DSpinner *m_spinner;
+    QStackedLayout *mainLayout;
 
-    QHBoxLayout *main;
-
-    void clearLayout(QLayout *layout);
+    QString m_szUrl;
 
 private slots:
     void on_loadStarted();