Windows API Tutorials

Здесь есть возможность читать онлайн «Windows API Tutorials» весь текст электронной книги совершенно бесплатно (целиком полную версию без сокращений). В некоторых случаях можно слушать аудио, скачать через торрент в формате fb2 и присутствует краткое содержание. Жанр: Программирование, на английском языке. Описание произведения, (предисловие) а так же отзывы посетителей доступны на портале библиотеки ЛибКат.

Windows API Tutorials: краткое содержание, описание и аннотация

Предлагаем к чтению аннотацию, описание, краткое содержание или предисловие (зависит от того, что написал сам автор книги «Windows API Tutorials»). Если вы не нашли необходимую информацию о книге — напишите в комментариях, мы постараемся отыскать её.

Windows API Tutorials — читать онлайн бесплатно полную книгу (весь текст) целиком

Ниже представлен текст книги, разбитый по страницам. Система сохранения места последней прочитанной страницы, позволяет с удобством читать онлайн бесплатно книгу «Windows API Tutorials», без необходимости каждый раз заново искать на чём Вы остановились. Поставьте закладку, и сможете в любой момент перейти на страницу, на которой закончили чтение.

Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать

}

void Release () {

LeaveCriticalSection(& _critSection);

}

CRITICAL_SECTION _critSection;

};

class Lock{

public:

// Acquire the state of the semaphore

Lock ( Mutex & mutex ) : _mutex(mutex) {

_mutex.Acquire();

}

// Release the state of the semaphore

~Lock () {

_mutex.Release();

}

private:

Mutex & _mutex;

};

An Event is a signalling device that threads use to communicate with each other. You embed an Event in your active object. Then you make the captive thread wait on it until some other thread releases it. Remember however that if your captive thread waits on a event it can't be terminated. That's why you should call Release from the Flush method.

class Event{

public:

Event () {

// start in non-signaled state (red light)

// auto reset after every Wait

_handle = CreateEvent(0, FALSE, FALSE, 0);

}

~Event () {

CloseHandle(_handle);

}

// put into signaled state

void Release () { SetEvent(_handle); }

void Wait () {

// Wait until event is in signaled (green) state

WaitForSingleObject(_handle, INFINITE);

}

operator HANDLE () { return _handle; }

private:

HANDLE _handle;

};

To see how these classes can be put to use, I suggest a little side trip. You can jump to the page that explains how the Frequency Analyzer uses the activeobject class to update the display asynchronously. Or, you can study a somehow simpler example of a Folder Watcherthat waits quietly watching a folder and wakes up only when a change happens.

I wish I could say programming with threads was simple. It is, however, simpler if you use the right kind of primitives. The primitives I advertised here are ActiveObject, Thread, Mutex, Lock and Event . Some of them are actually available in MFC. For instance, they have a Lock object (or is it CLock?) whose destructor releases the critical section (theirs is slightly less convenient because of the "two-step" construction — you have to create it and then take it in two separate steps — as if you'd want to create it and then not take it). Other than that, MFC only offers some thin veneer over the API, nothing exciting.

You might also recognize some of the mechanisms I presented here in the Javaprogramming language. Of course, when you have the liberty of designing multitasking into the language, you can afford to be elegant. Their version of ActiveObject is called Runnable and it has the run method. Every Java object potentially has a built-in mutex and all you have to do to take a lock is to declare a method (or a scope) synchronized . Similarly, the events are implemented with the wait and notify calls inside any synchronized method. So, if you know how to program in Java, you know how to program in C++ (as if there were people fluent in Java, but ignorant of C++).

When Folders Change

Have you ever wonderedhow the Explorer knows that it should update its display because a file has been added or removed from a folder by some external application? Wonder no more because, with the use of our Active Object, we can do the same and more. There are a few simple API calls that you can make to ask the file system to selectively notify you about changes to files and folders. Once you set up such a watch, your thread can go to sleep waiting on an event. The file system will set the event as soon as it detects the kind of change that you're watching for.

Without further ado, let's derive a FolderWatcher from ActiveObject. We'll give it a notification source — an event, and a notification sink — a handle to a window that will respond to the notification. The source event is set up in the constructor of FolderWatcher. It is also important to start the captive thread at the end of the constructor.

class FolderWatcher: public ActiveObject{

public:

FolderWatcher (char const * folder, HWND hwnd) : _notifySource (folder), _hwndNotifySink (hwnd) {

strcpy (_folder, folder);

_thread.Resume ();

}

~FolderWatcher () {

Kill ();

}

private:

void InitThread () {}

void Loop ();

void FlushThread () {}

FolderChangeEvent _notifySource;

HWND _hwndNotifySink;

char _folder [MAX_PATH];

};

The action in the ActiveObject happens inside the Loop method. Here we set up an "infinite" loop in which we let the thread wait for the event. When the event happens, we check for the _isDying flag (as usual) and post a special message WM_FOLDER_CHANGE to the window that deals with notifications. This is not one of the predefined Windows messages, it's a message defined by us for the special purpose of passing folder notification information from one thread to another.

Two thing happen now: the captive thread makes another API call to let the file system know that it wants more notifications. It then goes back to watchful sleep. Concurrently, Windows retrieves our WM_FOLDER_CHANGE message from the message queue and sends it to the Windows Procedure of the sink window. More about that in a moment.

UINT const WM_FOLDER_CHANGE = WM_USER;

void FolderWatcher::Loop() {

for (;;) {

// Wait for change notification

DWORD waitStatus = WaitForSingleObject(_notifySource, INFINITE);

if (WAIT_OBJECT_0 == waitStatus) {

// If folder changed

if (_isDying) return;

PostMessage(_hwndNotifySink, WM_FOLDER_CHANGE, 0, (LPARAM) _folder);

// Continue change notification

if (!_notifySource.ContinueNotification ()) {

// Error: Continuation failed

return;

}

} else {

// Error: Wait failed

return;

}

}

}

So here what happens in the Windows Procedure in response to our special message: we call the Controller's method OnFolderChange. This method can do anything we want. In the Explorer it refreshes the display of the folder we are watching. In our example it just pops up a simple message box. Notice how we are passing the name of the changed folder as LPARAM. It is totally up to us to define what goes into WPARAM and LPARAM of a user-defined message.

By the way, the Folder Watcher is just a part of the Controller.

case WM_FOLDER_CHANGE:

pCtrl->OnFolderChange (hwnd, (char const *) lParam);

return 0;

void Controller::OnFolderChange(HWND hwnd, char const * folder) {

MessageBox(hwnd, "Change Detected", "Folder Watcher", MB_SETFOREGROUND | MB_ICONEXCLAMATION | MB_OK);

Читать дальше
Тёмная тема
Сбросить

Интервал:

Закладка:

Сделать

Похожие книги на «Windows API Tutorials»

Представляем Вашему вниманию похожие книги на «Windows API Tutorials» списком для выбора. Мы отобрали схожую по названию и смыслу литературу в надежде предоставить читателям больше вариантов отыскать новые, интересные, ещё непрочитанные произведения.


Отзывы о книге «Windows API Tutorials»

Обсуждение, отзывы о книге «Windows API Tutorials» и просто собственные мнения читателей. Оставьте ваши комментарии, напишите, что Вы думаете о произведении, его смысле или главных героях. Укажите что конкретно понравилось, а что нет, и почему Вы так считаете.

x