Advertisement
Old_But_Gold

WINAPI_1

Sep 4th, 2024 (edited)
60
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 12.20 KB | None | 0 0
  1. #ifndef UNICODE
  2. #define UNICODE
  3. #endif
  4.  
  5. #include <Windows.h>
  6. #include <CommCtrl.h>
  7. #include <string>
  8. #include <iostream>
  9. #include <vector>
  10. #include <unordered_map>
  11. #include <fstream>
  12. #include <ctime>
  13.  
  14. #define LoadFilesButtonClicked 0x1
  15. #define SortFilesButtonClicked 0x2
  16.  
  17. #define SCREEN_WIDTH GetSystemMetrics(SM_CXSCREEN)
  18. #define SCREEN_HEIGHT GetSystemMetrics(SM_CYSCREEN)
  19.  
  20. struct FileData {
  21. std::wstring fileName;
  22. std::wstring fileSize;
  23. };
  24.  
  25. //g for global
  26. std::vector<FileData> gFilesVector;
  27.  
  28. HWND hEdit, hListViewLeft, hListViewRight, hLoadButton, hSortButton;
  29.  
  30. LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
  31.  
  32. void AddColumns(HWND hListView)
  33. {
  34. LVCOLUMN lvCol = { };
  35. lvCol.mask = LVCF_TEXT | LVCF_WIDTH | LVCF_SUBITEM;
  36.  
  37. lvCol.cx = 50;
  38. lvCol.pszText = (LPWSTR)L"Index";
  39. ListView_InsertColumn(hListView, 0, &lvCol);
  40.  
  41. RECT rect;
  42. GetWindowRect(hListView, &rect);
  43.  
  44. lvCol.cx = (rect.right - rect.left) / 2;
  45. lvCol.pszText = (LPWSTR)L"File Name";
  46. ListView_InsertColumn(hListView, 1, &lvCol);
  47.  
  48. lvCol.cx = (rect.right - rect.left) / 2 - 50;
  49. lvCol.pszText = (LPWSTR)L"File Size";
  50. ListView_InsertColumn(hListView, 2, &lvCol);
  51. }
  52.  
  53. void AddItemToListView(HWND hListView, FileData* fileData)
  54. {
  55. LVITEM lvItem = { };
  56. lvItem.mask = LVIF_TEXT;
  57.  
  58. int index = ListView_GetItemCount(hListView);
  59. lvItem.iItem = index; //index should start with the next Item
  60.  
  61. std::wstring indexStr = std::to_wstring(index + 1);
  62. lvItem.pszText = (LPWSTR)indexStr.c_str();
  63. ListView_InsertItem(hListView, &lvItem);
  64.  
  65. ListView_SetItemText(hListView, index, 1, (LPWSTR)fileData->fileName.c_str());
  66. ListView_SetItemText(hListView, index, 2, (LPWSTR)fileData->fileSize.c_str());
  67. }
  68.  
  69. std::wstring GenerateUniqueFileName(const std::wstring& baseName,
  70. std::unordered_map<std::wstring, int>& gNameCount)
  71. {
  72. std::wstring uniqueName = baseName;
  73. int count = gNameCount[baseName];
  74.  
  75. if (count > 0) {
  76. uniqueName = baseName + L"[" + std::to_wstring(count) + L"]";
  77. }
  78.  
  79. gNameCount[baseName]++;
  80.  
  81. return uniqueName;
  82. }
  83.  
  84. void LogError(std::wofstream& logFile, const std::wstring& message) {
  85. std::time_t currentTime = std::time(nullptr);
  86. std::tm localTime;
  87. localtime_s(&localTime, &currentTime);
  88.  
  89. wchar_t timeBuffer[80];
  90. wcsftime(timeBuffer, sizeof(timeBuffer) / sizeof(wchar_t), L"%Y-%m-%d %H:%M:%S", &localTime);
  91.  
  92. logFile << L"[" << timeBuffer << L"] " << message << std::endl;
  93. }
  94.  
  95. void LoadFilesData(HWND hListView, const std::wstring directoryPath,
  96. std::vector<FileData>& files, std::unordered_map<std::wstring, int> &gNameCount,
  97. std::wofstream &errorLogFile)
  98. {
  99. WIN32_FIND_DATA data;
  100.  
  101. std::wstring searchPath = directoryPath + L"//*";
  102.  
  103. HANDLE hFind = FindFirstFile(searchPath.c_str(), &data);
  104.  
  105. if (hFind == INVALID_HANDLE_VALUE) {
  106. DWORD errorCode = GetLastError();
  107. std::wstring errorMessage = L"Error when getting files from directory: " + directoryPath +
  108. L". Error Code: " + std::to_wstring(errorCode);
  109. //std::wcout << errorMessage << std::endl;
  110. LogError(errorLogFile, errorMessage);
  111. return;
  112. }
  113.  
  114. do {
  115. if (data.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
  116. if (wcscmp(data.cFileName, L".") != 0 && wcscmp(data.cFileName, L"..") != 0) {
  117. const std::wstring newDirPath = directoryPath + L"//" + data.cFileName;
  118. LoadFilesData(hListView, newDirPath, files, gNameCount, errorLogFile);
  119. }
  120. }
  121. else {
  122. FileData fileData;
  123. std::wstring baseName = data.cFileName;
  124.  
  125. fileData.fileName = GenerateUniqueFileName(baseName, gNameCount);
  126.  
  127. ULONGLONG fileSize = ((ULONGLONG)data.nFileSizeHigh << 32) + data.nFileSizeLow;
  128. fileData.fileSize = std::to_wstring(fileSize) + L" bytes";
  129.  
  130. gFilesVector.push_back(fileData);
  131. }
  132. } while (FindNextFile(hFind, &data) != 0);
  133.  
  134. FindClose(hFind);
  135. }
  136.  
  137. void Swap(int i, int j)
  138. {
  139. auto temp = gFilesVector[i];
  140. gFilesVector[i] = gFilesVector[j];
  141. gFilesVector[j] = temp;
  142. }
  143.  
  144. int Partition(int left, int right)
  145. {
  146. auto pivot = gFilesVector[left].fileSize.c_str();
  147. int j = left;
  148.  
  149. for (int i = left + 1; i <= right; i++)
  150. {
  151. if (wcscmp(gFilesVector[i].fileSize.c_str(), pivot) <= 0)
  152. {
  153. j++;
  154. Swap(i, j);
  155. }
  156. }
  157.  
  158. Swap(left, j);
  159. return j;
  160. }
  161.  
  162. void QSort(int left, int right)
  163. {
  164. while (left < right)
  165. {
  166. int pivotIndex = Partition(left, right);
  167. if (pivotIndex - left <= right - pivotIndex)
  168. {
  169. QSort(left, pivotIndex - 1);
  170. left = pivotIndex + 1;
  171. }
  172. else
  173. {
  174. QSort(pivotIndex + 1, right);
  175. right = pivotIndex - 1;
  176. }
  177. }
  178. }
  179.  
  180. enum class SortDirection { Ascending, Descending };
  181.  
  182. void RadixSortStrings(std::vector<FileData>& array, SortDirection sortDirection)
  183. {
  184. if (array.size() < 2)
  185. return;
  186.  
  187. int maxLength = 0;
  188. for (const auto& item : array) {
  189. int size = static_cast<int>(item.fileSize.length());
  190. maxLength = size > maxLength ? size : maxLength;
  191. }
  192.  
  193. wchar_t maxChar = 0;
  194. for (const auto& item : array) {
  195. for (const auto& ch : item.fileSize) {
  196. maxChar = ch > maxChar ? ch : maxChar;
  197. }
  198. }
  199. maxChar++;
  200.  
  201. std::vector<FileData> output(array.size());
  202. std::vector<int> count(maxChar, 0);
  203.  
  204. for (int digit = maxLength - 1; digit >= 0; digit--)
  205. {
  206. std::fill(count.begin(), count.end(), 0);
  207.  
  208. for (const auto& item : array)
  209. {
  210. int bucketIndex = digit < item.fileSize.length() ? item.fileSize[digit] : 0;
  211. count[bucketIndex]++;
  212. }
  213.  
  214. for (int i = 1; i < maxChar; i++)
  215. {
  216. count[i] += count[i - 1];
  217. }
  218.  
  219. if (sortDirection == SortDirection::Ascending)
  220. {
  221. for (int i = array.size() - 1; i >= 0; i--)
  222. {
  223. int bucketIndex = digit < array[i].fileSize.length() ? array[i].fileSize[digit] : 0;
  224. output[--count[bucketIndex]] = array[i];
  225. }
  226. }
  227. else
  228. {
  229. for (int i = 0; i < array.size(); i++)
  230. {
  231. int bucketIndex = digit < array[i].fileSize.length() ? array[i].fileSize[digit] : 0;
  232. output[--count[bucketIndex]] = array[i];
  233. }
  234. }
  235.  
  236. for (int i = 0; i < array.size(); i++)
  237. {
  238. array[i] = output[i];
  239. }
  240. }
  241. }
  242.  
  243. void RadixSort(std::vector<FileData>& array, SortDirection sortDirection = SortDirection::Ascending)
  244. {
  245. RadixSortStrings(array, sortDirection);
  246. }
  247.  
  248. void SortListView(HWND hListView)
  249. {
  250. if (gFilesVector.size() > 0) {
  251. ListView_DeleteAllItems(hListView);
  252.  
  253. //QSort(0, gFilesVector.size() - 1);
  254. RadixSort(gFilesVector);
  255.  
  256. SendMessage(hListView, WM_SETREDRAW, FALSE, 0);
  257.  
  258. size_t size = gFilesVector.size();
  259.  
  260. for (auto i = 0; i < size; i++) {
  261. AddItemToListView(hListView, &gFilesVector[i]);
  262. }
  263.  
  264. SendMessage(hListView, WM_SETREDRAW, TRUE, 0);
  265. }
  266. else {
  267. MessageBox(hListView, L"Fill your left table!", L"Error", MB_ICONERROR);
  268. }
  269. }
  270.  
  271. void PrepareListView(HWND hListView)
  272. {
  273. wchar_t directoryPath[MAX_PATH] = { 0 };
  274. GetWindowTextW(hEdit, directoryPath, MAX_PATH);
  275.  
  276. WIN32_FIND_DATA data;
  277.  
  278. std::wstring searchPath = std::wstring(directoryPath) + L"\\*";
  279.  
  280. HANDLE hFind = FindFirstFile(searchPath.c_str(), &data);
  281.  
  282. if (hFind == INVALID_HANDLE_VALUE || searchPath == L"\\*") {
  283. MessageBox(hListView, L"Enter existing directory path!", L"Error", MB_ICONERROR);
  284. return;
  285. }
  286.  
  287. ListView_DeleteAllItems(hListView);
  288.  
  289. std::wofstream errorLogFile(L"D://errors.log.txt", std::ios::app);
  290.  
  291. gFilesVector = { };
  292. std::unordered_map<std::wstring, int> gNameCount = { };
  293.  
  294. SendMessage(hListView, WM_SETREDRAW, FALSE, 0);
  295.  
  296. LoadFilesData(hListView, directoryPath, gFilesVector, gNameCount, errorLogFile);
  297.  
  298. int size = static_cast<int>(gFilesVector.size());
  299.  
  300. for (int i = 0; i < size; i++) {
  301. AddItemToListView(hListView, &gFilesVector[i]);
  302. }
  303.  
  304. SendMessage(hListView, WM_SETREDRAW, TRUE, 0);
  305. }
  306.  
  307. int WINAPI wWinMain(_In_ HINSTANCE hInstance, _In_opt_ HINSTANCE hPrevInstance,
  308. _In_ PWSTR pCmdLine, _In_ int nCmdShow)
  309. {
  310. /*if (AllocConsole()) {
  311. FILE* fp;
  312. freopen_s(&fp, "CONOUT$", "w", stdout);
  313. }*/
  314.  
  315. const wchar_t CLASS_NAME[] = L"WINAPI_LAB1";
  316.  
  317. WNDCLASS wc = { };
  318. wc.lpfnWndProc = WindowProc;
  319. wc.hInstance = hInstance;
  320. wc.lpszClassName = CLASS_NAME;
  321.  
  322. RegisterClass(&wc);
  323.  
  324. HWND hwnd = CreateWindowEx(0, CLASS_NAME, L"WINAPI_LAB1", WS_OVERLAPPEDWINDOW,
  325. CW_USEDEFAULT, CW_USEDEFAULT, SCREEN_WIDTH, SCREEN_HEIGHT,
  326. NULL, NULL, hInstance, NULL
  327. );
  328.  
  329. if (hwnd == NULL)
  330. {
  331. return 0;
  332. }
  333.  
  334. ShowWindow(hwnd, SW_SHOWMAXIMIZED);
  335.  
  336. MSG msg;
  337. while (GetMessage(&msg, NULL, 0, 0) > 0)
  338. {
  339. TranslateMessage(&msg);
  340. DispatchMessage(&msg);
  341. }
  342.  
  343. return 0;
  344. }
  345.  
  346. LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
  347. {
  348. switch (uMsg)
  349. {
  350. case WM_PAINT:
  351. {
  352. PAINTSTRUCT ps;
  353. HDC hdc = BeginPaint(hwnd, &ps);
  354.  
  355. FillRect(hdc, &ps.rcPaint, (HBRUSH)(COLOR_WINDOW + 1));
  356. EndPaint(hwnd, &ps);
  357. }
  358. return 0;
  359.  
  360. case WM_CREATE:
  361. {
  362. hListViewLeft = CreateWindowEx(0, WC_LISTVIEW, L"",
  363. WS_CHILD | WS_VISIBLE | WS_BORDER | LVS_REPORT,
  364. 10, 40, SCREEN_WIDTH / 2 - 10, SCREEN_HEIGHT - 120,
  365. hwnd, NULL, NULL, NULL);
  366.  
  367. hListViewRight = CreateWindowEx(0, WC_LISTVIEW, L"",
  368. WS_CHILD | WS_VISIBLE | WS_BORDER | LVS_REPORT,
  369. 10 + SCREEN_WIDTH / 2, 40, SCREEN_WIDTH / 2 - 50, SCREEN_HEIGHT - 120,
  370. hwnd, NULL, NULL, NULL);
  371.  
  372. AddColumns(hListViewLeft);
  373. AddColumns(hListViewRight);
  374.  
  375. hEdit = CreateWindowEx(0, WC_EDIT, L"",
  376. WS_CHILD | WS_VISIBLE | WS_BORDER,
  377. 10, 10, SCREEN_WIDTH - 400, 20,
  378. hwnd, NULL, NULL, NULL);
  379.  
  380. hLoadButton = CreateWindowEx(0, WC_BUTTON, L"Load Files",
  381. WS_CHILD | WS_VISIBLE | BS_DEFPUSHBUTTON | WS_TABSTOP,
  382. SCREEN_WIDTH - 380, 8, 120, 25,
  383. hwnd, (HMENU)LoadFilesButtonClicked, NULL, NULL);
  384.  
  385. hSortButton = CreateWindowEx(0, WC_BUTTON, L"Sort Files",
  386. WS_CHILD | WS_VISIBLE | BS_DEFPUSHBUTTON | WS_TABSTOP,
  387. SCREEN_WIDTH - 160, 8, 120, 25,
  388. hwnd, (HMENU)SortFilesButtonClicked, NULL, NULL);
  389.  
  390. }
  391. break;
  392.  
  393. case WM_COMMAND:
  394. {
  395. int wmId = LOWORD(wParam);
  396. int wmEvent = HIWORD(wParam);
  397.  
  398. switch (wmId)
  399. {
  400. case LoadFilesButtonClicked:
  401. {
  402. if (wmEvent == BN_CLICKED) {
  403. PrepareListView(hListViewLeft);
  404. //GetDlgItem(hwnd, LoadFilesButtonClicked); – GETS HWND OF Window element
  405. }
  406. break;
  407. }
  408.  
  409. case SortFilesButtonClicked:
  410. {
  411. if (wmEvent == BN_CLICKED) {
  412. SortListView(hListViewRight);
  413. }
  414. break;
  415. }
  416. }
  417. }
  418. break;
  419.  
  420. case WM_CLOSE:
  421. /*if (MessageBox(hwnd, L"Really quit?", L"My application", MB_OKCANCEL) == IDOK) {
  422. DestroyWindow(hwnd);
  423. }*/
  424. PostQuitMessage(0);
  425. break;
  426.  
  427. case WM_DESTROY:
  428. return 0;
  429.  
  430. default:
  431. return DefWindowProc(hwnd, uMsg, wParam, lParam);
  432. }
  433. return 0;
  434. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement