Воспоминание программирование под Windows 9x 24.09.2024
Всем привет! Сначало немного болтавни (оффтоп), а потом будет по теме. Я долго пропадал, потому-что лежал долог в больнице. Короче вчера смотрел чутку голливудский фильм "Ловушка" реж. М. Найт Шьямалан. Как появится настроение, пересмотрю его см.
Недавно смотрел новый документальный фильм примерно снятый в 2023-2024 гг., на немецком про немецкую тюрьму:
Если не хотите весь документальный фильм смотреть, вот тайм-коды. Вот заключёный в немецкой тюрьме учиться электриком, он будет учиться 2 года см. https://youtu.be/A3kiq9HY7hU?t=344. Эта тюрьма расположена недалеко от жилых домов, т.е. рукой подать до свободы см. отсюда https://youtu.be/A3kiq9HY7hU?t=577 и отсюда см. https://youtu.be/A3kiq9HY7hU?t=2291. Это то что едят заключенные в немецкой тюрьме см. отсюда https://youtu.be/A3kiq9HY7hU?t=1097. Так-же заключённые в немецкой тюрьме смотрят DVD фильмы см. отсюда https://youtu.be/A3kiq9HY7hU?t=1710. Вот такую еду покупают заключёные в немецкой тюрьме см. https://youtu.be/A3kiq9HY7hU?t=1512.
В Алматы когда был маленьким ребёнком примерно в 5-10 лет, изучал и программировал на Turbo C 1.0, т.к. моему oтцу дали с работы компьютер, т.е. мой oтeц работал дома (удалёнка) ну или как сейчас это называют хоумофис. А в университете мы изучали язык программирования паскаль. Короче Когда приехал в Германию 01.04.2004 г., мы взяли компьютеры свои, мне мaть дала свой ноутбук Toshiba Satellite 100CS на ноутбуке был установлен Windows 95 и Microsoft Office 95 Professional, и я этим ноутбуком пользовался 1-е 6 месяцев в Германии, а один poдcтвенник программист дал мне в Германии свой диск, и на том диске было записано Turbo Pascal for Windows, и я учился программировать под Windows именно на Turbo Pascal for Windows. Среда разработки выглядела
вот так:
Тут я уже обсуждал про современный Dev-C++ см. https://foren.germany.ru/1299414/f/40661211.html?Cat=&page..., тут я обсуждал про Си/Си++ см. https://programming.mybb.ru/viewforum.php?id=11. Мы будем играться в Dev-C++ его можно скачать тут см. https://www.bloodshed.net/ и программировать на Си, а не на Си++. Я поставил на Windows 2000 Dev-C++ 4.9.9.2. Вот так создавать новый проект в Dev-C++:
Простой пример:
#include <windows.h> LRESULT CALLBACK WindowProcedure(HWND, UINT, WPARAM, LPARAM); char szClassName[] = "WindowsApp"; int WINAPI WinMain(HINSTANCE hThisInstance, HINSTANCE hPrevInstance, LPSTR lpszArgument, int nFunsterStil) { HWND hwnd; MSG messages; WNDCLASSEX wincl; wincl.hInstance = hThisInstance; wincl.lpszClassName = szClassName; wincl.lpfnWndProc = WindowProcedure; wincl.style = CS_DBLCLKS; wincl.cbSize = sizeof(WNDCLASSEX); wincl.hIcon = LoadIcon(NULL, IDI_APPLICATION); wincl.hIconSm = LoadIcon(NULL, IDI_APPLICATION); wincl.hCursor = LoadCursor(NULL, IDC_ARROW); wincl.lpszMenuName = NULL; wincl.cbClsExtra = 0; wincl.cbWndExtra = 0; wincl.hbrBackground = (HBRUSH)COLOR_BACKGROUND; if(!RegisterClassEx(&wincl)) return 0; hwnd = CreateWindowEx( 0, szClassName, "Windows App", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, 544, 375, HWND_DESKTOP, NULL, hThisInstance, NULL ); ShowWindow(hwnd, nFunsterStil); while(GetMessage(&messages, NULL, 0, 0)) { TranslateMessage(&messages); DispatchMessage(&messages); } return messages.wParam; } LRESULT CALLBACK WindowProcedure(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { switch(message) { case WM_DESTROY: PostQuitMessage(0); break; default: return DefWindowProc(hwnd, message, wParam, lParam); } return 0; }
Результат работы программы:
Давайте напишим простую программу, выглядеть будет так:
Прежде чем начать будем использовать следующие Win32 API функции:
https://learn.microsoft.com/ru-ru/windows/win32/api/winuse...
https://learn.microsoft.com/ru-ru/windows/win32/api/winuse...
https://learn.microsoft.com/ru-ru/windows/win32/api/winuse...
А так-же константы:
https://learn.microsoft.com/ru-ru/windows/win32/winmsg/ext...
https://learn.microsoft.com/ru-ru/windows/win32/winmsg/ext...
Вот код main.c:
#include <windows.h> #define ID_SAY 100 /* ID кнопки HWND hwndButton; HWND hwndField; LRESULT CALLBACK WindowProcedure(HWND, UINT, WPARAM, LPARAM); char szClassName[ ] = "WindowsApp"; int WINAPI WinMain(HINSTANCE hThisInstance, HINSTANCE hPrevInstance, LPSTR lpszArgument, int nFunsterStil) { HWND hwnd; MSG messages; WNDCLASSEX wincl; wincl.hInstance = hThisInstance; wincl.lpszClassName = szClassName; wincl.lpfnWndProc = WindowProcedure; wincl.style = CS_DBLCLKS; wincl.cbSize = sizeof(WNDCLASSEX); wincl.hIcon = LoadIcon(NULL, IDI_APPLICATION); wincl.hIconSm = LoadIcon(NULL, IDI_APPLICATION); wincl.hCursor = LoadCursor(NULL, IDC_ARROW); wincl.lpszMenuName = NULL; wincl.cbClsExtra = 0; wincl.cbWndExtra = 0; wincl.hbrBackground = (HBRUSH)COLOR_BACKGROUND; if(!RegisterClassEx(&wincl)) return 0; hwnd = CreateWindowEx( 0, szClassName, "Моя первая Windows программа", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, 290, 115, HWND_DESKTOP, NULL, hThisInstance, NULL ); ShowWindow(hwnd, nFunsterStil); while(GetMessage(&messages, NULL, 0, 0)) { TranslateMessage(&messages); DispatchMessage(&messages); } return messages.wParam; } LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) { char *buf, *buf2; /* Переменные будут содержать тексты */ int sz; /* Переменная для размера текста в поле */ switch(message) { /* Событие срабатывает, если нажимать на кнопки */ case WM_COMMAND: /* Если нажали на кнопку "Нажми на меня!" */ if(wParam == ID_SAY) { sz = GetWindowTextLength(hwndField) + 1; /* Получаем количество букв в поле */ buf = (char *) malloc(sz); /* Резервируем память */ buf2 = (char *) malloc(sz + 100); /* Резервируем память */ GetWindowText(hwndField, buf, sz); /* Получем текст из поле */ sprintf(buf2, "Привет \"%s!\'", buf); /* Вставляем текст Привет "Антон Попов"! */ MessageBox(hwnd, buf2, "Ваше имя", MB_OK); /* Выводим окно с сообщением */ free(buf); /* Освобождаем зарезервированную память, чтобы не было утечки памяти */ free(buf2); /* Освобождаем зарезервированную память, чтобы не было утечки памяти */ } break; /* Событие срабатывает сразу как появляется окно, чтобы добавить элементы. Там в окне будут лейбл с надписью "Ваше имя:", поле для ввода имени, и кнопка с надписью "Намжи на меня!" */ case WM_CREATE: CreateWindow("STATIC", "Ваше имя:", WS_CHILD | WS_VISIBLE, 10, 10, 120, 20, hwnd, (HMENU)ID_SAY, NULL, NULL); /* Лейбл с надписью "Ваше имя:" */ hwndField = CreateWindowEx(WS_EX_CLIENTEDGE, "EDIT", "", WS_CHILD | WS_VISIBLE | WS_BORDER, 90, 10, 120, 20, hwnd, (HMENU)ID_SAY, NULL, NULL); /* Поле, куда нужно вводить имя */ hwndButton = CreateWindow("BUTTON", "Нажми на меня!", WS_CHILD | WS_VISIBLE, 10, 40, 120, 30, hwnd, (HMENU)ID_SAY, NULL, NULL); /* Кнопка с надписью "Нажми на меня!" */ break; case WM_DESTROY: PostQuitMessage(0); break; default: return DefWindowProc (hwnd, message, wParam, lParam); } return 0; }
Вуаля! Результат работы нашей программы:
Прежде чем продолжить, поговорим чуть-чуть не по теме. Вот этот тролль https://otvet.mail.ru/answer/2062434061 меня достал уже, который раз пропагандирует Россию. Ну что тут не понятного, ну если нет спроса на товары, зачем его будут продавать в Москве? Ну включайте же логику, магазин не будет продавать товар себе в убыток! А некоторые вещи под запретом в России, и их нигде не купишь. Допустим у меня есть часы со скрытой камерой, которые мне подарили мои poдители мне на моё ДР. Мне один чел из России жаловался что у них в Россию за покупку скрытой камеры могут посадить в тюрьму, или оштрафовать. Причина, очень простая, чтобы не дискретировать чиновников, т.е. покуда чиновники боятся что их богатства снимут на камеру, и выложат в интернет. А этот чел. хотел купить дрона, чтобы запустить его.
Ладно продолжим кодить. Спомощью функций CreateWindow и CreateWindowEx можно создать окна, или элементы управления (надпись, кнопки, поле, список, listview, combobox, treeview, richttextbox, итд.). CreateWindow используется, если не надо расширенные стили, а если надо, то надо пользоваться функцией CreateWindowEx. У некоторых элементов управления можно отображать текст, допустим у надписи, кнопки, или поле. Чтобы записать текст в элемент управления нужно пользоваться функцией SetWindowText, чтобы получить текст нужно использовать функцию GetWindowText, но чтобы получить текст у элемента управления, нужно сначало узнать количество букв в элементе управления спомощью функции GetWindowTextLength. А чтобы записать в другие или прочитать из других элементов текст, допустим в список или в combobox, нужно использовать функцию SendMessage.
Вообще Windows приложения работают интересно, и напоминает немного работу мозга. Одно Windows приложение может послать другому приложению сообщение, и влиять на другое приложение. Но чтобы послать сообщение другому приложению, нужно узнать HWND приложения, в которое нужно послать сообщение. Ищем окно спомощью функции FindWindow см. https://learn.microsoft.com/ru-ru/windows/win32/api/winuse..., по имени класса окна, или по заголовку окна. Дальше посылается сообщение спомощью SendMessage см. https://learn.microsoft.com/ru-ru/windows/win32/api/winuse.... Если в приложение, которому посылается сообщение, есть обработчик сообщение которое посылается, то оно сработает.