#include "sqlitehelper.h" #include #include "globalvariables.h" #include "MyButton.h" #include #include #include #include #include #include #include "navbar.h" #include "netio.h" #include "config.h" #ifdef _DEBUG #pragma comment (lib,"Qt5Xmld.lib") #else #pragma comment (lib,"Qt5Xml.lib") #endif #pragma comment (lib,"Shell32.lib") #if _MSC_VER >=1936 #include namespace fs = std::filesystem; #else #define _SILENCE_EXPERIMENTAL_FILESYSTEM_DEPRECATION_WARNING #include namespace fs = std::experimental::filesystem; #endif SQLiteHelper::SQLiteHelper(QObject *parent) : QObject(parent) { if (QSqlDatabase::contains("qt_sql_default_connection")) { db = QSqlDatabase::database("qt_sql_default_connection"); } else { db = QSqlDatabase::addDatabase("QSQLITE"); db.setDatabaseName("OfficeAssistant.db"); } if (!db.open()) { QMessageBox::critical(nullptr, QString::fromLocal8Bit("提示"), QString::fromLocal8Bit("无法打开数据库")); exit_manager.exit(1); } } SQLiteHelper::~SQLiteHelper() { db.close(); } bool SQLiteHelper::update_software() { HKEY hKeyUninstall = nullptr; QMap records; QList paths; /*QSqlQuery query; QString sql = "select * from kmd_menu;"; query.exec(sql); while(query.next()) { Record record; record.id = query.value("id").toInt(); record.sort = query.value("sort").toInt(); record.app_id = query.value("app_id").toString(); record.locked = query.value("locked").toBool(); record.type = query.value("type").toString(); record.category_id = query.value("category_id").toString(); record.name = query.value("name").toString(); record.orig_name = query.value("orig_name").toString(); record.version = query.value("version").toString(); record.dev = query.value("dev").toString(); record.create_time = query.value("create_time").toLongLong(); record.use_time = query.value("use_time").toLongLong(); record.op = query.value("op").toString(); record.func = query.value("func").toString(); record.path = query.value("path").toString(); record.url = query.value("url").toString(); QStringList path_list = record.path.split("\\"); path_list.removeLast(); QString path; for(auto str : path_list) { path.append(str); path.append("\\"); } path.remove(path.length() - 1, 1); records.insert(path, record); }*/ //开始菜单中已安装软件列表 WCHAR path[MAX_PATH]; HRESULT hr = SHGetFolderPathW(nullptr, CSIDL_COMMON_PROGRAMS, nullptr, 0, path);//获取ProgramData中开始菜单的路径 std::wstring path_str(path); for(auto file : fs::directory_iterator(path_str)) { Record record; if(fs::is_regular_file(file)) { if(file.path().extension().wstring()==L".lnk") { HRESULT hr = CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED | COINIT_DISABLE_OLE1DDE); if (SUCCEEDED(hr)) { IShellItem* pShellItem; hr = SHCreateItemFromParsingName(file.path().wstring().c_str(), nullptr, IID_PPV_ARGS(&pShellItem)); if (SUCCEEDED(hr)) { IPersistFile* pPersistFile; hr = pShellItem->QueryInterface(IID_PPV_ARGS(&pPersistFile)); if (SUCCEEDED(hr)) { WCHAR szTargetPath[MAX_PATH]; LPOLESTR pszTargetPath = szTargetPath; hr = pPersistFile->Load(nullptr, STGM_READ); if (SUCCEEDED(hr)) { hr = pPersistFile->GetCurFile(&pszTargetPath); if (SUCCEEDED(hr)) { paths<Release(); pShellItem->Release(); CoUninitialize(); return false; } }else { pPersistFile->Release(); pShellItem->Release(); CoUninitialize(); return false; } pPersistFile->Release(); }else { pShellItem->Release(); pShellItem->Release(); CoUninitialize(); return false; } pShellItem->Release(); }else { CoUninitialize(); return false; } CoUninitialize(); } } } } for(int i=0;iQueryInterface(IID_PPV_ARGS(&pPersistFile)); if (SUCCEEDED(hr)) { WCHAR szTargetPath[MAX_PATH]; LPOLESTR pszTargetPath = szTargetPath; hr = pPersistFile->Load(nullptr, STGM_READ); if (SUCCEEDED(hr)) { hr = pPersistFile->GetCurFile(&pszTargetPath); if (SUCCEEDED(hr)) { paths << QString::fromWCharArray(szTargetPath); } else { pPersistFile->Release(); pShellItem->Release(); CoUninitialize(); return false; } } else { pPersistFile->Release(); pShellItem->Release(); CoUninitialize(); return false; } pPersistFile->Release(); } else { pShellItem->Release(); pShellItem->Release(); CoUninitialize(); return false; } pShellItem->Release(); } else { CoUninitialize(); return false; } CoUninitialize(); } } } } // 打开注册表中的已安装软件列表 QHash reg_records; HKEY hKey; if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall", 0, KEY_READ, &hKey) == ERROR_SUCCESS) { // 枚举该列表下所有子键 for (DWORD i = 0; ; i++) { WCHAR szSubKey[MAX_PATH] = { 0 }; DWORD dwSize = MAX_PATH; if (RegEnumKeyExW(hKey, i, szSubKey, &dwSize, NULL, NULL, NULL, NULL) == ERROR_SUCCESS) { // 读取软件属性值 HKEY hSubKey; if (RegOpenKeyExW(hKey, szSubKey, 0, KEY_READ, &hSubKey) == ERROR_SUCCESS) { Record record; WCHAR szProductPath[MAX_PATH] = { 0 }; WCHAR buffer[MAX_PATH] = { 0 }; DWORD buffer_num; dwSize = MAX_PATH * sizeof(WCHAR); //安装文件夹 if (RegQueryValueExW(hSubKey, L"InstallLocation", NULL, NULL, (LPBYTE)szProductPath, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } QString path = QString::fromWCharArray(szProductPath); //软件名 if (RegQueryValueExW(hSubKey, L"DisplayName", NULL, NULL, (LPBYTE)buffer, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } record.name = QString::fromWCharArray(buffer); record.orig_name = QString::fromWCharArray(buffer); //图标 if (RegQueryValueExW(hSubKey, L"DisplayIcon", NULL, NULL, (LPBYTE)buffer, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } record.logo = QString::fromWCharArray(buffer); //主版本号 if (RegQueryValueExW(hSubKey, L"VersionMajor", NULL, NULL, (LPBYTE)buffer_num, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } QString versionMajor = QString::number(buffer_num); //次版本号 if (RegQueryValueExW(hSubKey, L"VersionMinor", NULL, NULL, (LPBYTE)buffer_num, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } QString versionMinor = QString::number(buffer_num); //将主版本号和次版本号拼接在一起 QString version = versionMajor + "." + versionMinor; record.version = version; //开发者 if (RegQueryValueExW(hSubKey, L"Publisher", NULL, NULL, (LPBYTE)buffer, &dwSize) != ERROR_SUCCESS) { RegCloseKey(hSubKey); RegCloseKey(hKey); return false; } record.dev = QString::fromWCharArray(buffer); record.type = "app"; record.locked = false; RegCloseKey(hSubKey); reg_records.insert(path, record); } } else { break; } } RegCloseKey(hKey); } //对比两个路径,找出公共部分 QHash public_programs_list; for(auto path:paths) { QStringList path_list = path.split("\\"); path_list.removeLast(); QString path2; for(auto str : path_list) { path2.append(str); path2.append("\\"); } path2.remove(path2.length() - 1, 1); if(reg_records.contains(path2)) { reg_records[path2].path = path; public_programs_list.insert(reg_records[path2].orig_name, reg_records[path2]); } } //进行网络请求,补全字段 SoftwareRequest software_request; if(!software_request.sendRequest(&public_programs_list)) { return false; } QSqlQuery begin("begin;"); if (!begin.exec()) { return false; } for(auto key : public_programs_list.keys()) { QString sql_find = "select sort from kmd_menu where orig_name='"; sql_find += key; sql_find += "';"; QSqlQuery query_find(sql_find); if(!query_find.exec()) { QSqlQuery rollback("rollback;"); rollback.exec(); return false; } QString sql; if(query_find.next()) { sql = "update kmd_menu set"; sql += " path='"; sql += public_programs_list[key].path; sql += "'"; sql += " op="; sql += public_programs_list[key].op; sql += " func="; sql += public_programs_list[key].func; sql += " url="; sql += public_programs_list[key].url; sql += " where orig_name='"; sql += key; sql += "';"; } else { sql = "insert into kmd_menu (sort,app_id,locked,type,category_id,name,orig_name,version,dev,create_time,use_time,op,func,path,url) values ("; sql += "50"; sql += ",'"; sql += public_programs_list[key].app_id; sql += "',"; sql += QString::number(public_programs_list[key].locked); sql += ",'"; sql += public_programs_list[key].type; sql += "','"; sql += public_programs_list[key].category_id; sql += "','"; sql += public_programs_list[key].name; sql += "','"; sql += public_programs_list[key].orig_name; sql += "','"; sql += public_programs_list[key].version; sql += "','"; sql += public_programs_list[key].dev; sql += "',"; sql += QString::number(public_programs_list[key].create_time); sql += ","; sql += QString::number(public_programs_list[key].use_time); sql += ",'"; sql += public_programs_list[key].op; sql += "','"; sql += public_programs_list[key].func; sql += "','"; sql += public_programs_list[key].path; sql += "','"; sql += public_programs_list[key].url; sql += "');"; } QSqlQuery query(sql); if(!query.exec()) { QSqlQuery rollback("rollback;"); rollback.exec(); return false; } } QSqlQuery commit("commit;"); commit.exec(); return true; } void SetSVGBackColor(QDomElement& elem, QString strtagname, QString strattr, QString strattrval) { if (elem.tagName().compare(strtagname) == 0) { QString before_color = elem.attribute(strattr); elem.setAttribute(strattr, strattrval); QString color = elem.attribute(strattr); } for (int i = 0; i < elem.childNodes().count(); i++) { if (!elem.childNodes().at(i).isElement()) { continue; } SetSVGBackColor(elem.childNodes().at(i).toElement(), strtagname, strattr, strattrval); } } bool SQLiteHelper::get_software(QList* buttons) { QSqlQuery query(db); QString sql = "select * from kmd_menu;"; if (!query.exec(sql)) { return false; } QByteArray* buffer = new QByteArray; while (query.next()) { QNetworkAccessManager manager; downloadSuccess = true; ButtonStruct button_struct; button_struct.path = query.value("path").toString(); button_struct.text = query.value("name").toString(); button_struct.orig_name = query.value("orig_name").toString(); QUrl url_image(query.value("logo").toString()); QNetworkRequest* request_image = new QNetworkRequest(url_image); reply = manager.get(*request_image); QTimer timer; timer.setInterval(5000); connect(reply, &QNetworkReply::finished, &eventLoop, &QEventLoop::quit); connect(&timer, &QTimer::timeout, this, &SQLiteHelper::cancelDownload); eventLoop.exec(); timer.stop(); QImage* image = new QImage(200, 200, QImage::Format_ARGB32); if (downloadSuccess) { *buffer = reply->readAll(); QSvgRenderer* render_image = new QSvgRenderer(*buffer); QPainter painter_image(image); painter_image.setCompositionMode(QPainter::CompositionMode_Clear); // 清除画布 painter_image.fillRect(image->rect(), Qt::transparent); // 填充透明色 painter_image.setCompositionMode(QPainter::CompositionMode_SourceOver); // 恢复默认值 render_image->render(&painter_image); buffer->clear(); delete render_image; } else { QString icon = QApplication::applicationDirPath() + "/icon/default.svg"; QFile file(icon); if(!file.open(QIODevice::ReadOnly)) { return false; } QByteArray svg_buffer = file.readAll(); file.close(); QDomDocument doc; doc.setContent(svg_buffer); QColor color; color.setNamedColor(DEFAULT_COLOR); SetSVGBackColor(doc.documentElement(), "path", "fill",QColor() ); } reply->close(); button_struct.image = image; *buttons << button_struct; } return true; } void SQLiteHelper::cancelDownload() { disconnect(reply, &QNetworkReply::finished, &eventLoop, &QEventLoop::quit); eventLoop.quit(); reply->abort(); downloadSuccess = false; } bool SQLiteHelper::update_others() { }