screenwall_simple.cpp 50 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654
  1. // #include "screenwall_simple.h"
  2. // #include <QApplication>
  3. // #include <QDesktopWidget>
  4. // #include <QScreen>
  5. // #include <QMouseEvent>
  6. // #include <QResizeEvent>
  7. // #include <QShowEvent>
  8. // #include <QHideEvent>
  9. // #include <QCloseEvent>
  10. // #include <QPainter>
  11. // #include <QDebug>
  12. // #include <QMessageBox>
  13. // #include <QToolTip>
  14. // #include <QStyle>
  15. // #include <QStyleOption>
  16. // #include <QFileInfo>
  17. // #include <QDir>
  18. // #include <QStandardPaths>
  19. // #include <QSettings>
  20. // #include <QJsonDocument>
  21. // #include <QJsonObject>
  22. // #include <QPushButton>
  23. // #include <QVBoxLayout>
  24. // #include <QHBoxLayout>
  25. // #include <QLabel>
  26. // #include <string>
  27. // // ============================================================================
  28. // // SimpleWindowFinder Implementation
  29. // // ============================================================================
  30. // struct EnumWindowsData {
  31. // QVector<SimpleWindowInfo>* windows;
  32. // bool includeMinimized;
  33. // };
  34. // BOOL CALLBACK SimpleWindowFinder::enumWindowsProc(HWND hwnd, LPARAM lParam)
  35. // {
  36. // auto* data = reinterpret_cast<EnumWindowsData*>(lParam);
  37. // if (!isValidWindow(hwnd)) {
  38. // return TRUE;
  39. // }
  40. // bool isMinimized = IsIconic(hwnd);
  41. // if (!data->includeMinimized && isMinimized) {
  42. // return TRUE;
  43. // }
  44. // SimpleWindowInfo info;
  45. // info.hwnd = hwnd;
  46. // info.title = getWindowTitle(hwnd);
  47. // info.processName = getProcessName(hwnd);
  48. // info.isMinimized = isMinimized;
  49. // info.isVisible = IsWindowVisible(hwnd);
  50. // RECT rect;
  51. // GetWindowRect(hwnd, &rect);
  52. // info.geometry = QRect(rect.left, rect.top, rect.right - rect.left, rect.bottom - rect.top);
  53. // GetWindowThreadProcessId(hwnd, &info.processId);
  54. // // 获取图标
  55. // info.icon = SimpleCacheManager::instance().getCachedIcon(hwnd);
  56. // if (info.icon.isNull()) {
  57. // info.icon = getWindowIcon(hwnd);
  58. // if (!info.icon.isNull()) {
  59. // SimpleCacheManager::instance().cacheIcon(hwnd, info.icon);
  60. // }
  61. // }
  62. // data->windows->append(info);
  63. // return TRUE;
  64. // }
  65. // QVector<SimpleWindowInfo> SimpleWindowFinder::getWindowList(bool includeMinimized)
  66. // {
  67. // QVector<SimpleWindowInfo> windows;
  68. // EnumWindowsData data;
  69. // data.windows = &windows;
  70. // data.includeMinimized = includeMinimized;
  71. // EnumWindows(enumWindowsProc, reinterpret_cast<LPARAM>(&data));
  72. // return windows;
  73. // }
  74. // QPixmap SimpleWindowFinder::captureWindow(HWND hwnd, const QSize& size)
  75. // {
  76. // if (!IsWindow(hwnd)) {
  77. // return QPixmap();
  78. // }
  79. // // 检查缓存
  80. // QPixmap cached = SimpleCacheManager::instance().getCachedThumbnail(hwnd);
  81. // if (!cached.isNull() && (size.isEmpty() || cached.size() == size)) {
  82. // return cached;
  83. // }
  84. // RECT rect;
  85. // GetWindowRect(hwnd, &rect);
  86. // int width = rect.right - rect.left;
  87. // int height = rect.bottom - rect.top;
  88. // if (width <= 0 || height <= 0) {
  89. // return QPixmap();
  90. // }
  91. // QPixmap pixmap;
  92. // // 简化的窗口捕获:直接使用屏幕截图方法
  93. // pixmap = captureScreenshot(hwnd, rect);
  94. // if (!pixmap.isNull()) {
  95. // qDebug() << "Captured window:" << hwnd << "size:" << width << "x" << height;
  96. // } else {
  97. // qDebug() << "Failed to capture window:" << hwnd;
  98. // // 如果截图失败,创建一个占位图像
  99. // pixmap = QPixmap(width > 0 ? width : 200, height > 0 ? height : 150);
  100. // pixmap.fill(QColor(64, 64, 64)); // 深灰色背景
  101. // QPainter painter(&pixmap);
  102. // painter.setPen(Qt::white);
  103. // painter.drawText(pixmap.rect(), Qt::AlignCenter, "无法捕获窗口");
  104. // }
  105. // // 缩放到指定尺寸
  106. // if (!pixmap.isNull()) {
  107. // if (!size.isEmpty() && pixmap.size() != size) {
  108. // pixmap = pixmap.scaled(size, Qt::KeepAspectRatio, Qt::SmoothTransformation);
  109. // }
  110. // // 缓存结果
  111. // SimpleCacheManager::instance().cacheThumbnail(hwnd, pixmap);
  112. // }
  113. // return pixmap;
  114. // }
  115. // // DWM缩略图捕获方法
  116. // QPixmap SimpleWindowFinder::captureDWMThumbnail(HWND hwnd, int width, int height)
  117. // {
  118. // // 检查是否支持DWM
  119. // BOOL dwmEnabled = FALSE;
  120. // if (FAILED(DwmIsCompositionEnabled(&dwmEnabled)) || !dwmEnabled) {
  121. // return QPixmap();
  122. // }
  123. // // 创建临时窗口用于DWM缩略图
  124. // HWND tempWindow = CreateWindowEx(WS_EX_TOOLWINDOW | WS_EX_LAYERED,
  125. // L"STATIC", L"TempThumbnail",
  126. // WS_POPUP,
  127. // -32000, -32000, width, height,
  128. // NULL, NULL, GetModuleHandle(NULL), NULL);
  129. // if (!tempWindow) {
  130. // return QPixmap();
  131. // }
  132. // HTHUMBNAIL thumbnail = NULL;
  133. // HRESULT hr = DwmRegisterThumbnail(tempWindow, hwnd, &thumbnail);
  134. // QPixmap result;
  135. // if (SUCCEEDED(hr) && thumbnail) {
  136. // // 设置缩略图属性
  137. // DWM_THUMBNAIL_PROPERTIES props = {0};
  138. // props.dwFlags = DWM_TNP_RECTDESTINATION | DWM_TNP_RECTSOURCE | DWM_TNP_OPACITY | DWM_TNP_VISIBLE;
  139. // props.rcDestination = {0, 0, width, height};
  140. // // 获取源窗口大小
  141. // RECT sourceRect;
  142. // GetWindowRect(hwnd, &sourceRect);
  143. // props.rcSource = {0, 0, sourceRect.right - sourceRect.left, sourceRect.bottom - sourceRect.top};
  144. // props.opacity = 255;
  145. // props.fVisible = TRUE;
  146. // hr = DwmUpdateThumbnailProperties(thumbnail, &props);
  147. // if (SUCCEEDED(hr)) {
  148. // // 显示临时窗口并截图
  149. // ShowWindow(tempWindow, SW_SHOW);
  150. // UpdateWindow(tempWindow);
  151. // // 等待一小段时间让缩略图渲染
  152. // Sleep(50);
  153. // // 截取临时窗口
  154. // HDC hdcWindow = GetDC(tempWindow);
  155. // HDC hdcMemDC = CreateCompatibleDC(hdcWindow);
  156. // HBITMAP hbmScreen = CreateCompatibleBitmap(hdcWindow, width, height);
  157. // HGDIOBJ oldBitmap = SelectObject(hdcMemDC, hbmScreen);
  158. // BitBlt(hdcMemDC, 0, 0, width, height, hdcWindow, 0, 0, SRCCOPY);
  159. // result = convertBitmapToPixmap(hbmScreen, width, height);
  160. // // 清理资源
  161. // SelectObject(hdcMemDC, oldBitmap);
  162. // DeleteObject(hbmScreen);
  163. // DeleteDC(hdcMemDC);
  164. // ReleaseDC(tempWindow, hdcWindow);
  165. // }
  166. // DwmUnregisterThumbnail(thumbnail);
  167. // }
  168. // DestroyWindow(tempWindow);
  169. // return result;
  170. // }
  171. // // PrintWindow捕获方法
  172. // QPixmap SimpleWindowFinder::capturePrintWindow(HWND hwnd, int width, int height)
  173. // {
  174. // HDC hdcWindow = GetDC(hwnd);
  175. // HDC hdcMemDC = CreateCompatibleDC(hdcWindow);
  176. // HBITMAP hbmScreen = CreateCompatibleBitmap(hdcWindow, width, height);
  177. // HGDIOBJ oldBitmap = SelectObject(hdcMemDC, hbmScreen);
  178. // QPixmap result;
  179. // // 尝试不同的PrintWindow标志
  180. // UINT flags[] = {
  181. // PW_RENDERFULLCONTENT,
  182. // PW_CLIENTONLY,
  183. // 0 // 默认标志
  184. // };
  185. // for (int i = 0; i < 3; i++) {
  186. // if (PrintWindow(hwnd, hdcMemDC, flags[i])) {
  187. // result = convertBitmapToPixmap(hbmScreen, width, height);
  188. // if (!result.isNull()) {
  189. // break;
  190. // }
  191. // }
  192. // }
  193. // // 清理资源
  194. // SelectObject(hdcMemDC, oldBitmap);
  195. // DeleteObject(hbmScreen);
  196. // DeleteDC(hdcMemDC);
  197. // ReleaseDC(hwnd, hdcWindow);
  198. // return result;
  199. // }
  200. // // 屏幕截图方法
  201. // QPixmap SimpleWindowFinder::captureScreenshot(HWND hwnd, const RECT& rect)
  202. // {
  203. // int width = rect.right - rect.left;
  204. // int height = rect.bottom - rect.top;
  205. // HDC hdcScreen = GetDC(NULL);
  206. // HDC hdcMemDC = CreateCompatibleDC(hdcScreen);
  207. // HBITMAP hbmScreen = CreateCompatibleBitmap(hdcScreen, width, height);
  208. // HGDIOBJ oldBitmap = SelectObject(hdcMemDC, hbmScreen);
  209. // // 使用BitBlt从屏幕复制
  210. // BOOL result = BitBlt(hdcMemDC, 0, 0, width, height, hdcScreen, rect.left, rect.top, SRCCOPY);
  211. // QPixmap pixmap;
  212. // if (result) {
  213. // pixmap = convertBitmapToPixmap(hbmScreen, width, height);
  214. // }
  215. // // 清理资源
  216. // SelectObject(hdcMemDC, oldBitmap);
  217. // DeleteObject(hbmScreen);
  218. // DeleteDC(hdcMemDC);
  219. // ReleaseDC(NULL, hdcScreen);
  220. // return pixmap;
  221. // }
  222. // // 位图转换为QPixmap的辅助方法
  223. // QPixmap SimpleWindowFinder::convertBitmapToPixmap(HBITMAP hBitmap, int width, int height)
  224. // {
  225. // if (!hBitmap || width <= 0 || height <= 0) {
  226. // return QPixmap();
  227. // }
  228. // // 手动转换HBITMAP到QPixmap (Qt5兼容)
  229. // HDC hdc = CreateCompatibleDC(NULL);
  230. // if (!hdc) {
  231. // return QPixmap();
  232. // }
  233. // BITMAPINFO bmi = {0};
  234. // bmi.bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
  235. // bmi.bmiHeader.biWidth = width;
  236. // bmi.bmiHeader.biHeight = -height; // 负值表示自上而下
  237. // bmi.bmiHeader.biPlanes = 1;
  238. // bmi.bmiHeader.biBitCount = 32;
  239. // bmi.bmiHeader.biCompression = BI_RGB;
  240. // // 分配内存
  241. // int dataSize = width * height * 4;
  242. // uchar* data = new uchar[dataSize];
  243. // QPixmap pixmap;
  244. // if (GetDIBits(hdc, hBitmap, 0, height, data, &bmi, DIB_RGB_COLORS)) {
  245. // // 创建QImage并转换为QPixmap
  246. // QImage image(data, width, height, QImage::Format_RGB32);
  247. // pixmap = QPixmap::fromImage(image);
  248. // qDebug() << "Successfully converted HBITMAP to QPixmap, size:" << width << "x" << height;
  249. // } else {
  250. // qDebug() << "Failed to get DIB bits from HBITMAP";
  251. // }
  252. // delete[] data;
  253. // DeleteDC(hdc);
  254. // return pixmap;
  255. // }
  256. // QPixmap SimpleWindowFinder::captureDesktop(const QSize& size)
  257. // {
  258. // // 获取主屏幕
  259. // QScreen* screen = QApplication::primaryScreen();
  260. // if (!screen) {
  261. // return QPixmap();
  262. // }
  263. // QPixmap pixmap = screen->grabWindow(0);
  264. // if (!pixmap.isNull() && !size.isEmpty()) {
  265. // pixmap = pixmap.scaled(size, Qt::KeepAspectRatio, Qt::SmoothTransformation);
  266. // }
  267. // return pixmap;
  268. // }
  269. // QIcon SimpleWindowFinder::getWindowIcon(HWND hwnd)
  270. // {
  271. // // 尝试多种方式获取图标
  272. // HICON hIcon = nullptr;
  273. // // 方法1: 发送消息获取大图标
  274. // hIcon = reinterpret_cast<HICON>(SendMessage(hwnd, WM_GETICON, ICON_BIG, 0));
  275. // if (!hIcon) {
  276. // // 方法2: 发送消息获取小图标
  277. // hIcon = reinterpret_cast<HICON>(SendMessage(hwnd, WM_GETICON, ICON_SMALL, 0));
  278. // }
  279. // if (!hIcon) {
  280. // // 方法3: 从窗口类获取图标
  281. // hIcon = reinterpret_cast<HICON>(GetClassLongPtr(hwnd, GCLP_HICON));
  282. // }
  283. // if (!hIcon) {
  284. // // 方法4: 从窗口类获取小图标
  285. // hIcon = reinterpret_cast<HICON>(GetClassLongPtr(hwnd, GCLP_HICONSM));
  286. // }
  287. // if (hIcon) {
  288. // // Qt5兼容的HICON转换
  289. // QPixmap pixmap;
  290. // ICONINFO iconInfo;
  291. // if (GetIconInfo(hIcon, &iconInfo)) {
  292. // // 获取位图信息
  293. // BITMAP bmp;
  294. // if (GetObject(iconInfo.hbmColor, sizeof(BITMAP), &bmp)) {
  295. // // 创建设备上下文
  296. // HDC hdc = CreateCompatibleDC(NULL);
  297. // if (hdc) {
  298. // // 准备位图信息头
  299. // BITMAPINFOHEADER bih = {0};
  300. // bih.biSize = sizeof(BITMAPINFOHEADER);
  301. // bih.biWidth = bmp.bmWidth;
  302. // bih.biHeight = -bmp.bmHeight;
  303. // bih.biPlanes = 1;
  304. // bih.biBitCount = 32;
  305. // bih.biCompression = BI_RGB;
  306. // // 分配内存
  307. // int dataSize = bmp.bmWidth * bmp.bmHeight * 4;
  308. // uchar* data = new uchar[dataSize];
  309. // // 获取位图数据
  310. // BITMAPINFO bi = {0};
  311. // bi.bmiHeader = bih;
  312. // if (GetDIBits(hdc, iconInfo.hbmColor, 0, bmp.bmHeight, data, &bi, DIB_RGB_COLORS)) {
  313. // // 创建QImage
  314. // QImage image(data, bmp.bmWidth, bmp.bmHeight, QImage::Format_ARGB32);
  315. // pixmap = QPixmap::fromImage(image.rgbSwapped());
  316. // }
  317. // delete[] data;
  318. // DeleteDC(hdc);
  319. // }
  320. // }
  321. // // 清理资源
  322. // if (iconInfo.hbmColor) DeleteObject(iconInfo.hbmColor);
  323. // if (iconInfo.hbmMask) DeleteObject(iconInfo.hbmMask);
  324. // }
  325. // if (!pixmap.isNull()) {
  326. // return QIcon(pixmap);
  327. // }
  328. // }
  329. // // 使用默认图标
  330. // return QApplication::style()->standardIcon(QStyle::SP_ComputerIcon);
  331. // }
  332. // QString SimpleWindowFinder::getWindowTitle(HWND hwnd)
  333. // {
  334. // wchar_t title[256];
  335. // int length = GetWindowTextW(hwnd, title, 256);
  336. // if (length > 0) {
  337. // return QString::fromWCharArray(title, length);
  338. // }
  339. // return QString();
  340. // }
  341. // QString SimpleWindowFinder::getProcessName(HWND hwnd)
  342. // {
  343. // DWORD processId;
  344. // GetWindowThreadProcessId(hwnd, &processId);
  345. // HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, processId);
  346. // if (!hProcess) {
  347. // return QString();
  348. // }
  349. // wchar_t processName[MAX_PATH];
  350. // DWORD size = MAX_PATH;
  351. // if (QueryFullProcessImageNameW(hProcess, 0, processName, &size)) {
  352. // CloseHandle(hProcess);
  353. // QString fullPath = QString::fromWCharArray(processName);
  354. // return QFileInfo(fullPath).baseName();
  355. // }
  356. // CloseHandle(hProcess);
  357. // return QString();
  358. // }
  359. // bool SimpleWindowFinder::isValidWindow(HWND hwnd)
  360. // {
  361. // if (!IsWindow(hwnd) || !IsWindowVisible(hwnd)) {
  362. // return false;
  363. // }
  364. // // 过滤掉没有标题的窗口
  365. // wchar_t title[256];
  366. // if (GetWindowTextW(hwnd, title, 256) == 0) {
  367. // return false;
  368. // }
  369. // // 过滤掉工具窗口
  370. // LONG exStyle = GetWindowLong(hwnd, GWL_EXSTYLE);
  371. // if (exStyle & WS_EX_TOOLWINDOW) {
  372. // return false;
  373. // }
  374. // // 检查窗口是否有父窗口(排除子窗口)
  375. // if (GetParent(hwnd) != NULL) {
  376. // return false;
  377. // }
  378. // // 更严格的顶层窗口检查:必须是应用程序主窗口
  379. // LONG style = GetWindowLong(hwnd, GWL_STYLE);
  380. // // 检查是否是顶层窗口(必须有标题栏或是弹出窗口)
  381. // if (!(style & WS_CAPTION) && !(style & WS_POPUP)) {
  382. // return false;
  383. // }
  384. // // 排除子窗口:检查WS_CHILD样式
  385. // if (style & WS_CHILD) {
  386. // return false;
  387. // }
  388. // // 检查窗口是否在Alt+Tab列表中(更严格的检查)
  389. // HWND owner = GetWindow(hwnd, GW_OWNER);
  390. // if (owner != NULL) {
  391. // // 如果有所有者窗口且所有者可见,则不显示
  392. // if (IsWindowVisible(owner)) {
  393. // return false;
  394. // }
  395. // // 检查所有者是否是桌面窗口
  396. // HWND desktop = GetDesktopWindow();
  397. // if (owner != desktop) {
  398. // return false;
  399. // }
  400. // }
  401. // // 确保是应用程序窗口:检查窗口是否有应用程序图标
  402. // HICON icon = (HICON)SendMessage(hwnd, WM_GETICON, ICON_BIG, 0);
  403. // if (!icon) {
  404. // icon = (HICON)SendMessage(hwnd, WM_GETICON, ICON_SMALL, 0);
  405. // }
  406. // if (!icon) {
  407. // icon = (HICON)GetClassLongPtr(hwnd, GCLP_HICON);
  408. // }
  409. // // 如果没有图标,可能不是应用程序主窗口
  410. // if (!icon) {
  411. // return false;
  412. // }
  413. // // 过滤掉一些系统窗口类名
  414. // wchar_t className[256];
  415. // if (GetClassNameW(hwnd, className, 256) > 0) {
  416. // std::wstring classStr(className);
  417. // if (classStr == L"Shell_TrayWnd" || // 任务栏
  418. // classStr == L"DV2ControlHost" || // 桌面窗口
  419. // classStr == L"MsgrIMEWindowClass" || // 输入法窗口
  420. // classStr == L"SysShadow" || // 阴影窗口
  421. // classStr.find(L"IME") != std::wstring::npos) { // 输入法相关窗口
  422. // return false;
  423. // }
  424. // }
  425. // return true;
  426. // }
  427. // // ============================================================================
  428. // // SimpleDesktopPreview Implementation
  429. // // ============================================================================
  430. // SimpleDesktopPreview::SimpleDesktopPreview(QWidget* parent)
  431. // : QLabel(parent)
  432. // , m_updateTimer(new QTimer(this))
  433. // , m_previewSize(240, 180) // 程序预览的2倍 (120x90 * 2)
  434. // , m_isActive(false)
  435. // {
  436. // setMinimumSize(m_previewSize);
  437. // setScaledContents(false); // 不拉伸内容,保持1:1比例
  438. // setAlignment(Qt::AlignCenter); // 居中显示
  439. // setStyleSheet(
  440. // "QLabel { "
  441. // " border: 2px solid #3498db; "
  442. // " border-radius: 5px; "
  443. // " background-color: #ecf0f1; "
  444. // "}"
  445. // );
  446. // setCursor(Qt::PointingHandCursor);
  447. // connect(m_updateTimer, &QTimer::timeout, this, &SimpleDesktopPreview::updateDesktop);
  448. // setText("点击开始桌面预览");
  449. // setAlignment(Qt::AlignCenter);
  450. // }
  451. // SimpleDesktopPreview::~SimpleDesktopPreview()
  452. // {
  453. // stopPreview();
  454. // }
  455. // void SimpleDesktopPreview::startPreview()
  456. // {
  457. // if (m_isActive) {
  458. // return;
  459. // }
  460. // qDebug() << "Starting desktop preview";
  461. // m_isActive = true;
  462. // m_updateTimer->start(1000); // 1秒更新一次
  463. // updateDesktop();
  464. // }
  465. // void SimpleDesktopPreview::stopPreview()
  466. // {
  467. // if (!m_isActive) {
  468. // return;
  469. // }
  470. // qDebug() << "Stopping desktop preview";
  471. // m_isActive = false;
  472. // m_updateTimer->stop();
  473. // setText("桌面预览已停止");
  474. // setAlignment(Qt::AlignCenter);
  475. // }
  476. // void SimpleDesktopPreview::setUpdateInterval(int ms)
  477. // {
  478. // if (m_updateTimer->isActive()) {
  479. // m_updateTimer->setInterval(ms);
  480. // }
  481. // }
  482. // void SimpleDesktopPreview::updateDesktop()
  483. // {
  484. // if (!m_isActive) {
  485. // return;
  486. // }
  487. // QPixmap desktop = SimpleWindowFinder::captureDesktop(m_previewSize);
  488. // if (!desktop.isNull()) {
  489. // setPixmap(desktop);
  490. // }
  491. // }
  492. // void SimpleDesktopPreview::mousePressEvent(QMouseEvent* event)
  493. // {
  494. // if (event->button() == Qt::LeftButton) {
  495. // emit clicked();
  496. // }
  497. // QLabel::mousePressEvent(event);
  498. // }
  499. // void SimpleDesktopPreview::paintEvent(QPaintEvent* event)
  500. // {
  501. // QLabel::paintEvent(event);
  502. // if (m_isActive) {
  503. // QPainter painter(this);
  504. // painter.setRenderHint(QPainter::Antialiasing);
  505. // // 绘制录制指示器
  506. // painter.setPen(QPen(Qt::red, 2));
  507. // painter.setBrush(Qt::red);
  508. // painter.drawEllipse(width() - 20, 10, 10, 10);
  509. // painter.setPen(Qt::white);
  510. // painter.drawText(width() - 60, 25, "LIVE");
  511. // }
  512. // }
  513. // // ============================================================================
  514. // // SimpleWindowList Implementation
  515. // // ============================================================================
  516. // SimpleWindowList::SimpleWindowList(QWidget* parent)
  517. // : QScrollArea(parent)
  518. // , m_contentWidget(new QWidget)
  519. // , m_layout(new QGridLayout(m_contentWidget))
  520. // , m_thumbnailSize(120, 90)
  521. // , m_showMinimized(true)
  522. // , m_columnsCount(6)
  523. // {
  524. // setWidget(m_contentWidget);
  525. // setWidgetResizable(true);
  526. // setHorizontalScrollBarPolicy(Qt::ScrollBarAsNeeded);
  527. // setVerticalScrollBarPolicy(Qt::ScrollBarAsNeeded);
  528. // m_layout->setSpacing(5);
  529. // m_layout->setContentsMargins(5, 5, 5, 5);
  530. // setStyleSheet(
  531. // "QScrollArea { "
  532. // " background-color: #f8f9fa; "
  533. // " border: 1px solid #bdc3c7; "
  534. // " border-radius: 3px; "
  535. // "}"
  536. // "QWidget { background-color: transparent; }"
  537. // );
  538. // }
  539. // SimpleWindowList::~SimpleWindowList()
  540. // {
  541. // clearLayout();
  542. // }
  543. // void SimpleWindowList::setThumbnailSize(const QSize& size)
  544. // {
  545. // if (m_thumbnailSize != size) {
  546. // m_thumbnailSize = size;
  547. // refreshWindowList();
  548. // }
  549. // }
  550. // void SimpleWindowList::setShowMinimized(bool show)
  551. // {
  552. // if (m_showMinimized != show) {
  553. // m_showMinimized = show;
  554. // refreshWindowList();
  555. // }
  556. // }
  557. // QWidget* SimpleWindowList::createDesktopPreviewItem()
  558. // {
  559. // auto* widget = new QWidget;
  560. // widget->setFixedSize(m_thumbnailSize + QSize(10, 30));
  561. // widget->setCursor(Qt::PointingHandCursor);
  562. // auto* layout = new QVBoxLayout(widget);
  563. // layout->setContentsMargins(2, 2, 2, 2);
  564. // layout->setSpacing(2);
  565. // // 桌面缩略图
  566. // auto* thumbnailLabel = new QLabel;
  567. // thumbnailLabel->setFixedSize(m_thumbnailSize);
  568. // thumbnailLabel->setScaledContents(false);
  569. // thumbnailLabel->setAlignment(Qt::AlignCenter);
  570. // thumbnailLabel->setStyleSheet(
  571. // "QLabel { "
  572. // " border: 2px solid #3498db; "
  573. // " border-radius: 3px; "
  574. // " background-color: #ecf0f1; "
  575. // "}"
  576. // );
  577. // // 获取桌面缩略图
  578. // QPixmap desktop = SimpleWindowFinder::captureDesktop(m_thumbnailSize);
  579. // if (!desktop.isNull()) {
  580. // thumbnailLabel->setPixmap(desktop);
  581. // } else {
  582. // thumbnailLabel->setText("桌面");
  583. // thumbnailLabel->setAlignment(Qt::AlignCenter);
  584. // }
  585. // layout->addWidget(thumbnailLabel);
  586. // // 标题
  587. // auto* titleLabel = new QLabel("桌面预览");
  588. // titleLabel->setAlignment(Qt::AlignCenter);
  589. // titleLabel->setWordWrap(true);
  590. // titleLabel->setMaximumHeight(20);
  591. // titleLabel->setStyleSheet("font-size: 10px; color: #2c3e50; font-weight: bold;");
  592. // layout->addWidget(titleLabel);
  593. // // 标记为桌面预览项
  594. // widget->setProperty("isDesktop", true);
  595. // // 连接点击事件
  596. // widget->installEventFilter(this);
  597. // return widget;
  598. // }
  599. // void SimpleWindowList::refreshWindowList()
  600. // {
  601. // qDebug() << "Refreshing window list...";
  602. // auto newWindows = SimpleWindowFinder::getWindowList(m_showMinimized);
  603. // // 检查是否有变化
  604. // bool hasChanges = (newWindows.size() != m_windows.size());
  605. // if (!hasChanges) {
  606. // for (int i = 0; i < newWindows.size(); ++i) {
  607. // if (newWindows[i].hwnd != m_windows[i].hwnd) {
  608. // hasChanges = true;
  609. // break;
  610. // }
  611. // }
  612. // }
  613. // if (hasChanges) {
  614. // m_windows = newWindows;
  615. // updateLayout();
  616. // qDebug() << "Window list updated:" << m_windows.size() << "windows";
  617. // }
  618. // }
  619. // void SimpleWindowList::updateLayout()
  620. // {
  621. // clearLayout();
  622. // // 计算列数
  623. // int availableWidth = viewport()->width() - 20;
  624. // m_columnsCount = qMax(1, availableWidth / (m_thumbnailSize.width() + 10));
  625. // int row = 0, col = 0;
  626. // // 首先添加桌面预览项
  627. // auto* desktopItem = createDesktopPreviewItem();
  628. // if (desktopItem) {
  629. // m_layout->addWidget(desktopItem, row, col);
  630. // col++;
  631. // if (col >= m_columnsCount) {
  632. // col = 0;
  633. // row++;
  634. // }
  635. // }
  636. // // 然后添加窗口项
  637. // for (const auto& window : m_windows) {
  638. // auto* item = createWindowItem(window);
  639. // if (item) {
  640. // m_layout->addWidget(item, row, col);
  641. // col++;
  642. // if (col >= m_columnsCount) {
  643. // col = 0;
  644. // row++;
  645. // }
  646. // }
  647. // }
  648. // // 添加弹性空间
  649. // m_layout->setRowStretch(row + 1, 1);
  650. // m_layout->setColumnStretch(m_columnsCount, 1);
  651. // }
  652. // QWidget* SimpleWindowList::createWindowItem(const SimpleWindowInfo& info)
  653. // {
  654. // auto* widget = new QWidget;
  655. // widget->setFixedSize(m_thumbnailSize + QSize(10, 30));
  656. // widget->setCursor(Qt::PointingHandCursor);
  657. // auto* layout = new QVBoxLayout(widget);
  658. // layout->setContentsMargins(2, 2, 2, 2);
  659. // layout->setSpacing(2);
  660. // // 缩略图
  661. // auto* thumbnailLabel = new QLabel;
  662. // thumbnailLabel->setFixedSize(m_thumbnailSize);
  663. // thumbnailLabel->setScaledContents(false); // 不拉伸内容,保持原比例
  664. // thumbnailLabel->setAlignment(Qt::AlignCenter); // 居中显示
  665. // thumbnailLabel->setStyleSheet(
  666. // "QLabel { "
  667. // " border: 1px solid #bdc3c7; "
  668. // " border-radius: 3px; "
  669. // " background-color: #ecf0f1; "
  670. // "}"
  671. // );
  672. // // 获取缩略图
  673. // QPixmap thumbnail = SimpleWindowFinder::captureWindow(info.hwnd, m_thumbnailSize);
  674. // if (!thumbnail.isNull()) {
  675. // thumbnailLabel->setPixmap(thumbnail);
  676. // } else {
  677. // // 使用图标作为占位符
  678. // QPixmap iconPixmap = info.icon.pixmap(64, 64);
  679. // thumbnailLabel->setPixmap(iconPixmap);
  680. // }
  681. // layout->addWidget(thumbnailLabel);
  682. // // 标题
  683. // auto* titleLabel = new QLabel(info.title);
  684. // titleLabel->setAlignment(Qt::AlignCenter);
  685. // titleLabel->setWordWrap(true);
  686. // titleLabel->setMaximumHeight(20);
  687. // titleLabel->setStyleSheet("font-size: 10px; color: #2c3e50;");
  688. // // 截断过长的标题
  689. // QString displayTitle = info.title;
  690. // if (displayTitle.length() > 20) {
  691. // displayTitle = displayTitle.left(17) + "...";
  692. // }
  693. // titleLabel->setText(displayTitle);
  694. // titleLabel->setToolTip(info.title);
  695. // layout->addWidget(titleLabel);
  696. // // 存储窗口句柄
  697. // widget->setProperty("hwnd", reinterpret_cast<qintptr>(info.hwnd));
  698. // // 连接点击事件
  699. // widget->installEventFilter(this);
  700. // // 最小化窗口的视觉提示
  701. // if (info.isMinimized) {
  702. // widget->setStyleSheet("QWidget { opacity: 0.7; }");
  703. // }
  704. // return widget;
  705. // }
  706. // void SimpleWindowList::clearLayout()
  707. // {
  708. // while (QLayoutItem* item = m_layout->takeAt(0)) {
  709. // if (QWidget* widget = item->widget()) {
  710. // widget->deleteLater();
  711. // }
  712. // delete item;
  713. // }
  714. // }
  715. // void SimpleWindowList::resizeEvent(QResizeEvent* event)
  716. // {
  717. // QScrollArea::resizeEvent(event);
  718. // QTimer::singleShot(100, this, &SimpleWindowList::updateLayout);
  719. // }
  720. // bool SimpleWindowList::eventFilter(QObject* obj, QEvent* event)
  721. // {
  722. // if (auto* widget = qobject_cast<QWidget*>(obj)) {
  723. // // 检查是否是桌面预览项
  724. // bool isDesktop = widget->property("isDesktop").toBool();
  725. // if (event->type() == QEvent::MouseButtonPress) {
  726. // auto* mouseEvent = static_cast<QMouseEvent*>(event);
  727. // if (mouseEvent->button() == Qt::LeftButton) {
  728. // if (isDesktop) {
  729. // emit desktopClicked();
  730. // return true;
  731. // } else {
  732. // QVariant hwndVariant = widget->property("hwnd");
  733. // if (hwndVariant.isValid()) {
  734. // HWND hwnd = reinterpret_cast<HWND>(hwndVariant.value<qintptr>());
  735. // if (hwnd) {
  736. // // 查找窗口标题
  737. // QString title;
  738. // for (const auto& window : m_windows) {
  739. // if (window.hwnd == hwnd) {
  740. // title = window.title;
  741. // break;
  742. // }
  743. // }
  744. // emit windowSelected(hwnd, title);
  745. // return true;
  746. // } else {
  747. // qDebug() << "Invalid hwnd in click event";
  748. // }
  749. // } else {
  750. // qDebug() << "No hwnd property found in click event";
  751. // }
  752. // }
  753. // }
  754. // } else if (event->type() == QEvent::MouseButtonDblClick) {
  755. // if (!isDesktop) {
  756. // QVariant hwndVariant = widget->property("hwnd");
  757. // if (hwndVariant.isValid()) {
  758. // HWND hwnd = reinterpret_cast<HWND>(hwndVariant.value<qintptr>());
  759. // if (hwnd) {
  760. // emit windowDoubleClicked(hwnd);
  761. // return true;
  762. // } else {
  763. // qDebug() << "Invalid hwnd in double click event";
  764. // }
  765. // } else {
  766. // qDebug() << "No hwnd property found in double click event";
  767. // }
  768. // }
  769. // }
  770. // }
  771. // return QScrollArea::eventFilter(obj, event);
  772. // }
  773. // // ============================================================================
  774. // // SimpleWindowPreview Implementation
  775. // // ============================================================================
  776. // SimpleWindowPreview::SimpleWindowPreview(QWidget* parent)
  777. // : QLabel(parent)
  778. // , m_updateTimer(new QTimer(this))
  779. // , m_stateTimer(new QTimer(this))
  780. // , m_targetHwnd(nullptr)
  781. // , m_isActive(false)
  782. // , m_isWindowMinimized(false)
  783. // {
  784. // setMinimumSize(400, 300);
  785. // setScaledContents(true);
  786. // setStyleSheet(
  787. // "QLabel { "
  788. // " border: 2px solid #e74c3c; "
  789. // " border-radius: 5px; "
  790. // " background-color: #ecf0f1; "
  791. // "}"
  792. // );
  793. // connect(m_updateTimer, &QTimer::timeout, this, &SimpleWindowPreview::updatePreview);
  794. // connect(m_stateTimer, &QTimer::timeout, this, &SimpleWindowPreview::checkWindowState);
  795. // setText("请选择要预览的窗口");
  796. // setAlignment(Qt::AlignCenter);
  797. // }
  798. // SimpleWindowPreview::~SimpleWindowPreview()
  799. // {
  800. // stopPreview();
  801. // }
  802. // void SimpleWindowPreview::setTargetWindow(HWND hwnd, const QString& title)
  803. // {
  804. // if (m_targetHwnd == hwnd) {
  805. // return;
  806. // }
  807. // stopPreview();
  808. // m_targetHwnd = hwnd;
  809. // m_windowTitle = title;
  810. // if (hwnd && IsWindow(hwnd)) {
  811. // setText(QString("准备预览: %1").arg(m_windowTitle));
  812. // } else {
  813. // setText("请选择要预览的窗口");
  814. // }
  815. // setAlignment(Qt::AlignCenter);
  816. // }
  817. // void SimpleWindowPreview::startPreview()
  818. // {
  819. // if (!m_targetHwnd || !IsWindow(m_targetHwnd) || m_isActive) {
  820. // return;
  821. // }
  822. // qDebug() << "Starting window preview for" << m_windowTitle;
  823. // m_isActive = true;
  824. // m_isWindowMinimized = IsIconic(m_targetHwnd);
  825. // m_updateTimer->start(500); // 0.5秒更新一次
  826. // m_stateTimer->start(1000); // 每秒检查窗口状态
  827. // updatePreview();
  828. // }
  829. // void SimpleWindowPreview::stopPreview()
  830. // {
  831. // if (!m_isActive) {
  832. // return;
  833. // }
  834. // qDebug() << "Stopping window preview";
  835. // m_updateTimer->stop();
  836. // m_stateTimer->stop();
  837. // m_isActive = false;
  838. // if (!m_windowTitle.isEmpty()) {
  839. // setText(QString("预览已停止: %1").arg(m_windowTitle));
  840. // } else {
  841. // setText("请选择要预览的窗口");
  842. // }
  843. // setAlignment(Qt::AlignCenter);
  844. // }
  845. // void SimpleWindowPreview::setUpdateInterval(int ms)
  846. // {
  847. // if (m_updateTimer->isActive()) {
  848. // m_updateTimer->setInterval(ms);
  849. // }
  850. // }
  851. // void SimpleWindowPreview::updatePreview()
  852. // {
  853. // if (!m_isActive || !m_targetHwnd || !IsWindow(m_targetHwnd)) {
  854. // return;
  855. // }
  856. // QPixmap frame = SimpleWindowFinder::captureWindow(m_targetHwnd, size());
  857. // if (!frame.isNull()) {
  858. // // 如果窗口未最小化,保存最后一帧
  859. // if (!m_isWindowMinimized) {
  860. // m_lastFrame = frame;
  861. // }
  862. // setPixmap(frame);
  863. // } else if (m_isWindowMinimized && !m_lastFrame.isNull()) {
  864. // // 显示最后一帧
  865. // setPixmap(m_lastFrame);
  866. // }
  867. // }
  868. // void SimpleWindowPreview::checkWindowState()
  869. // {
  870. // if (!m_targetHwnd || !IsWindow(m_targetHwnd)) {
  871. // stopPreview();
  872. // return;
  873. // }
  874. // bool isMinimized = IsIconic(m_targetHwnd);
  875. // if (isMinimized != m_isWindowMinimized) {
  876. // m_isWindowMinimized = isMinimized;
  877. // if (isMinimized) {
  878. // qDebug() << "Window minimized:" << m_windowTitle;
  879. // } else {
  880. // qDebug() << "Window restored:" << m_windowTitle;
  881. // }
  882. // }
  883. // }
  884. // void SimpleWindowPreview::paintEvent(QPaintEvent* event)
  885. // {
  886. // QLabel::paintEvent(event);
  887. // if (!m_windowTitle.isEmpty()) {
  888. // QPainter painter(this);
  889. // painter.setRenderHint(QPainter::Antialiasing);
  890. // // 绘制窗口标题
  891. // painter.setPen(Qt::white);
  892. // painter.drawText(10, height() - 10, m_windowTitle);
  893. // // 绘制状态指示器
  894. // if (m_isActive) {
  895. // painter.setPen(QPen(Qt::green, 2));
  896. // painter.setBrush(Qt::green);
  897. // painter.drawEllipse(width() - 20, 10, 10, 10);
  898. // }
  899. // if (m_isWindowMinimized) {
  900. // painter.setPen(Qt::yellow);
  901. // painter.drawText(width() - 100, 25, "MINIMIZED");
  902. // }
  903. // }
  904. // }
  905. // // ============================================================================
  906. // // SimpleScreenWall Implementation
  907. // // ============================================================================
  908. // SimpleScreenWall::SimpleScreenWall(QWidget* parent)
  909. // : QWidget(parent)
  910. // , m_mainLayout(nullptr)
  911. // , m_desktopPreview(nullptr)
  912. // , m_windowList(nullptr)
  913. // , m_isRunning(false)
  914. // , m_selectedWindow(nullptr)
  915. // , m_refreshTimer(new QTimer(this))
  916. // {
  917. // setupUI();
  918. // setupConnections();
  919. // setMinimumSize(800, 600);
  920. // resize(1200, 900);
  921. // }
  922. // SimpleScreenWall::~SimpleScreenWall()
  923. // {
  924. // stopScreenWall();
  925. // }
  926. // void SimpleScreenWall::setupUI()
  927. // {
  928. // m_mainLayout = new QVBoxLayout(this);
  929. // m_mainLayout->setContentsMargins(5, 5, 5, 5);
  930. // m_mainLayout->setSpacing(5);
  931. // // 统一的预览区域,包含桌面和程序预览
  932. // m_windowList = new SimpleWindowList(this);
  933. // m_mainLayout->addWidget(m_windowList, 1);
  934. // // 移除单独的桌面预览和窗口预览组件
  935. // m_desktopPreview = nullptr;
  936. // }
  937. // void SimpleScreenWall::setupConnections()
  938. // {
  939. // connect(m_windowList, &SimpleWindowList::desktopClicked,
  940. // this, &SimpleScreenWall::onDesktopClicked);
  941. // connect(m_windowList, &SimpleWindowList::windowSelected,
  942. // this, &SimpleScreenWall::onWindowSelected);
  943. // connect(m_windowList, &SimpleWindowList::windowDoubleClicked,
  944. // this, &SimpleScreenWall::onWindowDoubleClicked);
  945. // connect(m_refreshTimer, &QTimer::timeout,
  946. // this, &SimpleScreenWall::refreshWindowList);
  947. // }
  948. // void SimpleScreenWall::setConfig(const SimpleScreenWallConfig& config)
  949. // {
  950. // m_config = config;
  951. // if (m_windowList) {
  952. // m_windowList->setThumbnailSize(config.thumbnailSize);
  953. // m_windowList->setShowMinimized(config.showMinimizedWindows);
  954. // }
  955. // // 桌面预览现在集成在窗口列表中,不需要单独设置
  956. // SimpleCacheManager::instance().setMaxCacheSize(config.maxCachedThumbnails);
  957. // }
  958. // void SimpleScreenWall::startScreenWall()
  959. // {
  960. // if (m_isRunning) {
  961. // return;
  962. // }
  963. // qDebug() << "Starting SimpleScreenWall...";
  964. // m_isRunning = true;
  965. // // 桌面预览现在集成在窗口列表中
  966. // // 刷新窗口列表
  967. // refreshWindowList();
  968. // // 启动定时刷新
  969. // m_refreshTimer->start(m_config.windowUpdateInterval);
  970. // emit started();
  971. // qDebug() << "SimpleScreenWall started successfully";
  972. // }
  973. // void SimpleScreenWall::stopScreenWall()
  974. // {
  975. // if (!m_isRunning) {
  976. // return;
  977. // }
  978. // qDebug() << "Stopping SimpleScreenWall...";
  979. // m_isRunning = false;
  980. // // 停止定时器
  981. // m_refreshTimer->stop();
  982. // // 窗口预览功能已集成到窗口列表中
  983. // // 清理缓存
  984. // SimpleCacheManager::instance().clearCache();
  985. // m_selectedWindow = nullptr;
  986. // emit stopped();
  987. // qDebug() << "SimpleScreenWall stopped";
  988. // }
  989. // void SimpleScreenWall::refreshWindowList()
  990. // {
  991. // if (m_windowList) {
  992. // m_windowList->refreshWindowList();
  993. // }
  994. // }
  995. // void SimpleScreenWall::onWindowSelected(HWND hwnd, const QString& title)
  996. // {
  997. // if (m_selectedWindow == hwnd) {
  998. // return;
  999. // }
  1000. // m_selectedWindow = hwnd;
  1001. // if (hwnd && IsWindow(hwnd)) {
  1002. // emit windowSelected(hwnd, title);
  1003. // }
  1004. // }
  1005. // void SimpleScreenWall::onDesktopClicked()
  1006. // {
  1007. // // 取消窗口选择
  1008. // if (m_selectedWindow) {
  1009. // m_selectedWindow = nullptr;
  1010. // }
  1011. // emit desktopSelected();
  1012. // }
  1013. // void SimpleScreenWall::onWindowDoubleClicked(HWND hwnd)
  1014. // {
  1015. // // 检查窗口句柄是否有效
  1016. // if (!hwnd || !IsWindow(hwnd)) {
  1017. // qDebug() << "Invalid window handle in double click event";
  1018. // return;
  1019. // }
  1020. // // 激活窗口
  1021. // if (!SimpleScreenWallUtils::activateWindow(hwnd)) {
  1022. // qDebug() << "Failed to activate window:" << hwnd;
  1023. // }
  1024. // }
  1025. // void SimpleScreenWall::showEvent(QShowEvent* event)
  1026. // {
  1027. // QWidget::showEvent(event);
  1028. // if (!m_isRunning) {
  1029. // QTimer::singleShot(500, this, &SimpleScreenWall::startScreenWall);
  1030. // }
  1031. // }
  1032. // void SimpleScreenWall::hideEvent(QHideEvent* event)
  1033. // {
  1034. // QWidget::hideEvent(event);
  1035. // if (m_isRunning) {
  1036. // stopScreenWall();
  1037. // }
  1038. // }
  1039. // void SimpleScreenWall::resizeEvent(QResizeEvent* event)
  1040. // {
  1041. // QWidget::resizeEvent(event);
  1042. // if (m_windowList) {
  1043. // QTimer::singleShot(100, m_windowList, &SimpleWindowList::refreshWindowList);
  1044. // }
  1045. // }
  1046. // void SimpleScreenWall::updateLayout()
  1047. // {
  1048. // // 根据窗口大小调整布局比例
  1049. // int totalHeight = height();
  1050. // int desktopHeight = totalHeight * 0.3;
  1051. // int listHeight = totalHeight * 0.2;
  1052. // int previewHeight = totalHeight * 0.5;
  1053. // // 现在只有窗口列表,不需要复杂的布局分配
  1054. // // m_windowList 会自动调整大小
  1055. // }
  1056. // // ============================================================================
  1057. // // SimpleCacheManager Implementation
  1058. // // ============================================================================
  1059. // SimpleCacheManager& SimpleCacheManager::instance()
  1060. // {
  1061. // static SimpleCacheManager instance;
  1062. // return instance;
  1063. // }
  1064. // void SimpleCacheManager::cacheThumbnail(HWND hwnd, const QPixmap& thumbnail)
  1065. // {
  1066. // m_thumbnailCache.insert(hwnd, new QPixmap(thumbnail));
  1067. // }
  1068. // QPixmap SimpleCacheManager::getCachedThumbnail(HWND hwnd) const
  1069. // {
  1070. // QPixmap* cached = m_thumbnailCache.object(hwnd);
  1071. // return cached ? *cached : QPixmap();
  1072. // }
  1073. // void SimpleCacheManager::cacheIcon(HWND hwnd, const QIcon& icon)
  1074. // {
  1075. // m_iconCache.insert(hwnd, new QIcon(icon));
  1076. // }
  1077. // QIcon SimpleCacheManager::getCachedIcon(HWND hwnd) const
  1078. // {
  1079. // QIcon* cached = m_iconCache.object(hwnd);
  1080. // return cached ? *cached : QIcon();
  1081. // }
  1082. // void SimpleCacheManager::clearCache()
  1083. // {
  1084. // m_thumbnailCache.clear();
  1085. // m_iconCache.clear();
  1086. // }
  1087. // void SimpleCacheManager::setMaxCacheSize(int size)
  1088. // {
  1089. // m_thumbnailCache.setMaxCost(size);
  1090. // m_iconCache.setMaxCost(size);
  1091. // }
  1092. // // ============================================================================
  1093. // // SimpleScreenWallUtils Implementation
  1094. // // ============================================================================
  1095. // QPixmap SimpleScreenWallUtils::scalePixmap(const QPixmap& pixmap, const QSize& size, Qt::AspectRatioMode mode)
  1096. // {
  1097. // if (pixmap.isNull() || size.isEmpty()) {
  1098. // return pixmap;
  1099. // }
  1100. // return pixmap.scaled(size, mode, Qt::SmoothTransformation);
  1101. // }
  1102. // QPixmap SimpleScreenWallUtils::addBorder(const QPixmap& pixmap, int borderWidth, const QColor& color)
  1103. // {
  1104. // if (pixmap.isNull() || borderWidth <= 0) {
  1105. // return pixmap;
  1106. // }
  1107. // QPixmap result(pixmap.size() + QSize(borderWidth * 2, borderWidth * 2));
  1108. // result.fill(color);
  1109. // QPainter painter(&result);
  1110. // painter.drawPixmap(borderWidth, borderWidth, pixmap);
  1111. // return result;
  1112. // }
  1113. // QPixmap SimpleScreenWallUtils::addShadow(const QPixmap& pixmap, int shadowSize, const QColor& color)
  1114. // {
  1115. // if (pixmap.isNull() || shadowSize <= 0) {
  1116. // return pixmap;
  1117. // }
  1118. // QPixmap result(pixmap.size() + QSize(shadowSize * 2, shadowSize * 2));
  1119. // result.fill(Qt::transparent);
  1120. // QPainter painter(&result);
  1121. // painter.setRenderHint(QPainter::Antialiasing);
  1122. // // 绘制阴影
  1123. // painter.setBrush(color);
  1124. // painter.setPen(Qt::NoPen);
  1125. // painter.drawRoundedRect(shadowSize, shadowSize, pixmap.width(), pixmap.height(), 5, 5);
  1126. // // 绘制原图
  1127. // painter.drawPixmap(0, 0, pixmap);
  1128. // return result;
  1129. // }
  1130. // QString SimpleScreenWallUtils::getSystemInfo()
  1131. // {
  1132. // QString info;
  1133. // info += QString("OS: Windows\n");
  1134. // info += QString("Qt Version: %1\n").arg(QT_VERSION_STR);
  1135. // info += QString("Screen Count: %1\n").arg(QApplication::screens().count());
  1136. // return info;
  1137. // }
  1138. // QStringList SimpleScreenWallUtils::getRunningProcesses()
  1139. // {
  1140. // QStringList processes;
  1141. // DWORD processIds[1024], bytesReturned;
  1142. // if (EnumProcesses(processIds, sizeof(processIds), &bytesReturned)) {
  1143. // DWORD processCount = bytesReturned / sizeof(DWORD);
  1144. // for (DWORD i = 0; i < processCount; i++) {
  1145. // HANDLE hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, processIds[i]);
  1146. // if (hProcess) {
  1147. // wchar_t processName[MAX_PATH];
  1148. // DWORD size = MAX_PATH;
  1149. // if (QueryFullProcessImageNameW(hProcess, 0, processName, &size)) {
  1150. // QString fullPath = QString::fromWCharArray(processName);
  1151. // processes.append(QFileInfo(fullPath).baseName());
  1152. // }
  1153. // CloseHandle(hProcess);
  1154. // }
  1155. // }
  1156. // }
  1157. // return processes;
  1158. // }
  1159. // int SimpleScreenWallUtils::getSystemMemoryUsage()
  1160. // {
  1161. // MEMORYSTATUSEX memInfo;
  1162. // memInfo.dwLength = sizeof(MEMORYSTATUSEX);
  1163. // GlobalMemoryStatusEx(&memInfo);
  1164. // return static_cast<int>(memInfo.dwMemoryLoad);
  1165. // }
  1166. // int SimpleScreenWallUtils::getCpuUsage()
  1167. // {
  1168. // // 简化实现,返回固定值
  1169. // // 实际实现需要使用性能计数器
  1170. // return 0;
  1171. // }
  1172. // void SimpleScreenWallUtils::saveConfig(const SimpleScreenWallConfig& config, const QString& filePath)
  1173. // {
  1174. // QString path = filePath;
  1175. // if (path.isEmpty()) {
  1176. // path = QStandardPaths::writableLocation(QStandardPaths::AppConfigLocation) + "/screenwall_config.json";
  1177. // }
  1178. // QJsonObject json;
  1179. // json["desktopUpdateInterval"] = config.desktopUpdateInterval;
  1180. // json["windowUpdateInterval"] = config.windowUpdateInterval;
  1181. // json["previewUpdateInterval"] = config.previewUpdateInterval;
  1182. // json["thumbnailWidth"] = config.thumbnailSize.width();
  1183. // json["thumbnailHeight"] = config.thumbnailSize.height();
  1184. // json["desktopPreviewWidth"] = config.desktopPreviewSize.width();
  1185. // json["desktopPreviewHeight"] = config.desktopPreviewSize.height();
  1186. // json["maxCachedThumbnails"] = config.maxCachedThumbnails;
  1187. // json["enableDesktopPreview"] = config.enableDesktopPreview;
  1188. // json["enableWindowPreview"] = config.enableWindowPreview;
  1189. // json["showMinimizedWindows"] = config.showMinimizedWindows;
  1190. // QJsonDocument doc(json);
  1191. // QDir().mkpath(QFileInfo(path).absolutePath());
  1192. // QFile file(path);
  1193. // if (file.open(QIODevice::WriteOnly)) {
  1194. // file.write(doc.toJson());
  1195. // }
  1196. // }
  1197. // SimpleScreenWallConfig SimpleScreenWallUtils::loadConfig(const QString& filePath)
  1198. // {
  1199. // QString path = filePath;
  1200. // if (path.isEmpty()) {
  1201. // path = QStandardPaths::writableLocation(QStandardPaths::AppConfigLocation) + "/screenwall_config.json";
  1202. // }
  1203. // SimpleScreenWallConfig config; // 使用默认值
  1204. // QFile file(path);
  1205. // if (file.open(QIODevice::ReadOnly)) {
  1206. // QJsonDocument doc = QJsonDocument::fromJson(file.readAll());
  1207. // QJsonObject json = doc.object();
  1208. // if (json.contains("desktopUpdateInterval")) {
  1209. // config.desktopUpdateInterval = json["desktopUpdateInterval"].toInt();
  1210. // }
  1211. // if (json.contains("windowUpdateInterval")) {
  1212. // config.windowUpdateInterval = json["windowUpdateInterval"].toInt();
  1213. // }
  1214. // if (json.contains("previewUpdateInterval")) {
  1215. // config.previewUpdateInterval = json["previewUpdateInterval"].toInt();
  1216. // }
  1217. // if (json.contains("thumbnailWidth") && json.contains("thumbnailHeight")) {
  1218. // config.thumbnailSize = QSize(json["thumbnailWidth"].toInt(), json["thumbnailHeight"].toInt());
  1219. // }
  1220. // if (json.contains("desktopPreviewWidth") && json.contains("desktopPreviewHeight")) {
  1221. // config.desktopPreviewSize = QSize(json["desktopPreviewWidth"].toInt(), json["desktopPreviewHeight"].toInt());
  1222. // }
  1223. // if (json.contains("maxCachedThumbnails")) {
  1224. // config.maxCachedThumbnails = json["maxCachedThumbnails"].toInt();
  1225. // }
  1226. // if (json.contains("enableDesktopPreview")) {
  1227. // config.enableDesktopPreview = json["enableDesktopPreview"].toBool();
  1228. // }
  1229. // if (json.contains("enableWindowPreview")) {
  1230. // config.enableWindowPreview = json["enableWindowPreview"].toBool();
  1231. // }
  1232. // if (json.contains("showMinimizedWindows")) {
  1233. // config.showMinimizedWindows = json["showMinimizedWindows"].toBool();
  1234. // }
  1235. // }
  1236. // return config;
  1237. // }
  1238. // // ============================================================================
  1239. // // SimpleScreenWallWindow Implementation
  1240. // // ============================================================================
  1241. // SimpleScreenWallWindow::SimpleScreenWallWindow(QWidget* parent)
  1242. // : QWidget(parent)
  1243. // , m_mainLayout(nullptr)
  1244. // , m_controlPanel(nullptr)
  1245. // , m_controlLayout(nullptr)
  1246. // , m_startButton(nullptr)
  1247. // , m_stopButton(nullptr)
  1248. // , m_refreshButton(nullptr)
  1249. // , m_settingsButton(nullptr)
  1250. // , m_statusLabel(nullptr)
  1251. // , m_screenWall(nullptr)
  1252. // {
  1253. // setupUI();
  1254. // setupConnections();
  1255. // setWindowTitle("简化版屏幕墙");
  1256. // setMinimumSize(1000, 700);
  1257. // resize(1200, 900);
  1258. // }
  1259. // SimpleScreenWallWindow::~SimpleScreenWallWindow()
  1260. // {
  1261. // if (m_screenWall && m_screenWall->isRunning()) {
  1262. // m_screenWall->stopScreenWall();
  1263. // }
  1264. // }
  1265. // void SimpleScreenWallWindow::setupUI()
  1266. // {
  1267. // m_mainLayout = new QVBoxLayout(this);
  1268. // m_mainLayout->setContentsMargins(5, 5, 5, 5);
  1269. // m_mainLayout->setSpacing(5);
  1270. // // 控制面板
  1271. // m_controlPanel = new QWidget(this);
  1272. // m_controlLayout = new QHBoxLayout(m_controlPanel);
  1273. // m_controlLayout->setContentsMargins(0, 0, 0, 0);
  1274. // m_startButton = new QPushButton("启动屏幕墙", this);
  1275. // m_stopButton = new QPushButton("停止屏幕墙", this);
  1276. // m_refreshButton = new QPushButton("刷新窗口", this);
  1277. // m_settingsButton = new QPushButton("设置", this);
  1278. // m_statusLabel = new QLabel("状态: 已停止", this);
  1279. // m_controlLayout->addWidget(m_startButton);
  1280. // m_controlLayout->addWidget(m_stopButton);
  1281. // m_controlLayout->addWidget(m_refreshButton);
  1282. // m_controlLayout->addWidget(m_settingsButton);
  1283. // m_controlLayout->addStretch();
  1284. // m_controlLayout->addWidget(m_statusLabel);
  1285. // m_mainLayout->addWidget(m_controlPanel);
  1286. // // 屏幕墙组件
  1287. // m_screenWall = new SimpleScreenWall(this);
  1288. // m_mainLayout->addWidget(m_screenWall, 1);
  1289. // updateControlButtons();
  1290. // }
  1291. // void SimpleScreenWallWindow::setupConnections()
  1292. // {
  1293. // connect(m_startButton, &QPushButton::clicked, this, &SimpleScreenWallWindow::startScreenWall);
  1294. // connect(m_stopButton, &QPushButton::clicked, this, &SimpleScreenWallWindow::stopScreenWall);
  1295. // connect(m_refreshButton, &QPushButton::clicked, this, &SimpleScreenWallWindow::refreshWindows);
  1296. // connect(m_settingsButton, &QPushButton::clicked, this, &SimpleScreenWallWindow::showSettings);
  1297. // if (m_screenWall) {
  1298. // connect(m_screenWall, &SimpleScreenWall::windowSelected, this, &SimpleScreenWallWindow::onWindowSelected);
  1299. // connect(m_screenWall, &SimpleScreenWall::desktopSelected, this, &SimpleScreenWallWindow::onDesktopSelected);
  1300. // connect(m_screenWall, &SimpleScreenWall::started, this, &SimpleScreenWallWindow::onScreenWallStarted);
  1301. // connect(m_screenWall, &SimpleScreenWall::stopped, this, &SimpleScreenWallWindow::onScreenWallStopped);
  1302. // }
  1303. // }
  1304. // void SimpleScreenWallWindow::updateControlButtons()
  1305. // {
  1306. // bool isRunning = m_screenWall && m_screenWall->isRunning();
  1307. // m_startButton->setEnabled(!isRunning);
  1308. // m_stopButton->setEnabled(isRunning);
  1309. // m_refreshButton->setEnabled(isRunning);
  1310. // m_statusLabel->setText(isRunning ? "状态: 运行中" : "状态: 已停止");
  1311. // }
  1312. // void SimpleScreenWallWindow::closeEvent(QCloseEvent* event)
  1313. // {
  1314. // if (m_screenWall && m_screenWall->isRunning()) {
  1315. // m_screenWall->stopScreenWall();
  1316. // }
  1317. // QWidget::closeEvent(event);
  1318. // }
  1319. // void SimpleScreenWallWindow::startScreenWall()
  1320. // {
  1321. // if (m_screenWall) {
  1322. // m_screenWall->startScreenWall();
  1323. // }
  1324. // }
  1325. // void SimpleScreenWallWindow::stopScreenWall()
  1326. // {
  1327. // if (m_screenWall) {
  1328. // m_screenWall->stopScreenWall();
  1329. // }
  1330. // }
  1331. // void SimpleScreenWallWindow::refreshWindows()
  1332. // {
  1333. // if (m_screenWall) {
  1334. // m_screenWall->refreshWindowList();
  1335. // }
  1336. // }
  1337. // void SimpleScreenWallWindow::showSettings()
  1338. // {
  1339. // QMessageBox::information(this, "设置", "设置功能尚未实现");
  1340. // }
  1341. // void SimpleScreenWallWindow::showAbout()
  1342. // {
  1343. // QMessageBox::about(this, "关于", "简化版屏幕墙\n版本: 1.0\n\n实时窗口预览系统");
  1344. // }
  1345. // void SimpleScreenWallWindow::onWindowSelected(HWND hwnd, const QString& title)
  1346. // {
  1347. // Q_UNUSED(hwnd)
  1348. // m_statusLabel->setText(QString("已选择窗口: %1").arg(title));
  1349. // }
  1350. // void SimpleScreenWallWindow::onDesktopSelected()
  1351. // {
  1352. // m_statusLabel->setText("已选择桌面预览");
  1353. // }
  1354. // void SimpleScreenWallWindow::onScreenWallStarted()
  1355. // {
  1356. // updateControlButtons();
  1357. // m_statusLabel->setText("状态: 运行中");
  1358. // }
  1359. // void SimpleScreenWallWindow::onScreenWallStopped()
  1360. // {
  1361. // updateControlButtons();
  1362. // m_statusLabel->setText("状态: 已停止");
  1363. // }