Алекс Jenter - Программирование на Visual C++. Архив рассылки
- Название:Программирование на Visual C++. Архив рассылки
- Автор:
- Жанр:
- Издательство:неизвестно
- Год:неизвестен
- ISBN:нет данных
- Рейтинг:
- Избранное:Добавить в избранное
-
Отзывы:
-
Ваша оценка:
Алекс Jenter - Программирование на Visual C++. Архив рассылки краткое содержание
РАССЫЛКА ЯВЛЯЕТСЯ ЧАСТЬЮ ПРОЕКТА RSDN, НА САЙТЕ КОТОРОГО ВСЕГДА МОЖНО НАЙТИ ВСЮ НЕОБХОДИМУЮ РАЗРАБОТЧИКУ ИНФОРМАЦИЮ, СТАТЬИ, ФОРУМЫ, РЕСУРСЫ, ПОЛНЫЙ АРХИВ ПРЕДЫДУЩИХ ВЫПУСКОВ РАССЫЛКИ И МНОГОЕ ДРУГОЕ.
Программирование на Visual C++. Архив рассылки - читать онлайн бесплатно полную версию (весь текст целиком)
Интервал:
Закладка:
Будем также считать, что библиотека импорта находится в файле MyLib.lib.
Неявное подключение
Первое, что нам нужно сделать – это передать линкеру имя библиотеки импорта нашей DLL. Для этого необходимо открыть окно настройки проекта (Project->Settings) и на вкладке Link дописать "MyLib.lib" в конец списка Object/Library modules. Альтернативный подход заключается в использовании директивы #pragma. В нашем случае необходимо вставить в код программы следующую строку:
#pragma comment(lib,"MyLib")
Второе, что нужно проделать – это добавить объявление функции в код программы (обычно объявления функций, экспортируемых DLL, сводятся в заголовочный файл – тогда требуется просто подключить его). Для нашей функции X объявление выглядит так:
__declspec(dllimport) void X(void);
Вот и всё. Теперь к функции X можно обращаться, как и к любой другой функции, статически прилинкованной к нашей программе:
X();
Явное подключение
Как уже говорилось ранее, при явном подключении к DLL программист должен сам позаботиться о загрузке библиотеки, получении адреса функций и выгрузке библиотеки. Таким образом последовательность шагов может быть следующей.
Загружаем библиотеку:
HINSTANCE hLib = LoadLibrary("MyLib.dll");
Получаем указатель на функцию и вызываем её:
void (*X)();
(FARPROC &)X = GetProcAddress(hLib, "X");
X();
Выгружаем библиотеку из памяти:
FreeLibrary(hLib);
Отложенная загрузка
Сначала необходимо повторить шаги, которые мы проделывали при неявном подключении: передать линкеру имя библиотеки импорта и добавить в программу объявление функции X. Теперь, чтобы отложенная загрузка заработала, нужно добавить ключ линкера /DELAYLOAD:MyLib.dll и прилинковать к приложению библиотеку Delayimp.lib, реализующую вспомогательные функции механизма отложенной загрузки. Хотя эти опции можно добавить в настройки проекта, я предпочитаю использовать директивы #pragma:
#pragma comment(lib, "Delayimp")
#pragma comment(linker, "/DelayLoad:MyLib.dll")
Если после вызова функции X нам требуется выгрузить библиотеку MyLib.dll из памяти, можно воспользоваться функцией FUnloadDelayLoadedDLL. Чтобы эта функция работала корректно, необходимо добавить ещё один ключ линкера /DELAY:unload. Кроме того, нужно подключить заголовочный файл , в котором эта функция объявлена. Выглядеть это может примерно так:
#include
#pragma comment(linker, "/Delay:unload")
.
.
X();
__FUnloadDelayLoadedDLL("MyLib.dll");
Имя, передаваемое функции FUnloadDelayLoadedDLL, должно в точности совпадать с именем, указанным в ключе /DELAYLOAD. Так, если передать ей имя "MYLIB.DLL", библиотека останется в памяти.
В заключение хочется отметить ещё один интересный момент. Когда я попытался воспользоваться отложенной загрузкой в своей программе, линкер отказался подключать библиотеку Delayimp.lib, выдавая сообщение о внутренней ошибке и подробную отладочную информацию. Чтобы решить эту проблему, я просто взял файлы Delayhlp.cpp и Delayimp.h из каталога Vc98\Include, добавил в файл Delayhlp.cpp строки:
PfnDliHook __pfnDliNotifyHook = NULL;
PfnDliHook __pfnDliFailureHook = NULL;
и перестроил эту библиотеку заново. После этого отложенная загрузка заработала нормально.
Ссылки
Поскольку я рассказал об отложенной загрузке далеко не все, рекомендую обратиться за дополнительной информацией к следующим статьям в MSDN:
– December 1998, Microsoft systems journal, Win32 Q&A
– December 1998, Microsoft systems journal, Under the hood
– Linker support for delay-loaded DLLs
Alexander Shargin ( rudankort@mail.ru)Q. Все, наверное, знают программы, называемые Viewbar, которые показывают рекламные баннеры. Но вот как они ограничивают часть экрана, не позволяя другим окнам находиться поверх них? Например, если разрешение экрана 800×600, как они выделяют полосу сверху, в которой находятся, т.ч. программы, развернутые на полный экран, имеют высоту где-то на 60 пикселей меньше. Причем и немаксимизированные окна не могут "влезть" в эту полосу.
Alexander PopovДля рассылки пока уникальный случай: на вопрос ответил сам автор.
A 1 Спасибо за опубликование вопроса. Теперь я сам же могу на него ответить. Для создания приложения, похожего на панель задач или панель MS Office, используется AppBar. Последний достаточно хорошо описан в MSDN (см. Extend the Windows 95 Shell with Application Desktop Toolbars, Application Desktop Toolbars) А вообще, достаточно много интересного содержится в Windows Shell API, в частности: работа с панелью задач, как написать ScreenSaver, работа с панелью управления, Band Objects в Internet Explorer.
Alexander PopovA 2Этого можно добиться, используя функцию SystemParametersInfo. У этой исключительно полезной функции существуют параметры SPI_GETWORKAREA и SPI_SETWORKAREA, позволяющие получить размер рабочей области экрана или установить для неё собственный размер (перед завершением работы программы его рекомендуется восстановить). Напрмер, следующий фрагмент "резервирует" полосу шириной в 100 пикселей в верхней части экрана:
CRect rcOld, rcNew;
SystemParametersInfo(SPI_GETWORKAREA, 0, (PVOID)&rcOld, 0);
rcNew = rcOld;
rcNew.top = 100;
SystemParametersInfo(SPI_SETWORKAREA, 0, (PVOID)&rcNew, 0);
Чтобы восстановить исходный размер, достаточно вызвать:
SystemParametersInfo(SPI_SETWORKAREA, 0, (PVOID)&rcOld, 0);
После того как нужная область зарезервирована, можно, например, поместить туда своё окно (вызовом CWnd::MoveWindow) и лишить пользователя возможности убрать его оттуда (так как в противном случае оно туда не вернётся), после чего рисовать в нём баннеры.
В заключение отмечу, что именно этой функцией пользуются программы типа Magnify.exe из комплекта Windows.
Alexander Shargin ( rudankort@mail.ru)Фактически, ответы, конечно, одинаковые (в статье из MSDN как раз и используется SystemsParametersInfo), просто первый в отличие от самого ответа содержит ссылку на него.
Эти два ответа – все, что я получил. Два из восьми тысяч. Действительно, не очень-то сильно читатели хотят отвечать на вопросы. Так что я по всей видимости был прав по поводу поощрений… Господа! Прошу поактивнее! Или я могу решить что рубрика вам неинтересна и закрою ее…
Многие спрашивают, почему я лично не отвечаю на вопросы. Это неправда, иногда все-таки отвечаю ;)
Ну а главное: посмотрите Microsoft Systems Journal. Там человек В МЕСЯЦ отвечает на ДВА вопроса, причем это – его работа, т.е. он получает за это деньги. Потом, далеко не на всякий вопрос можно сходу дать однозначный ответ. Как правило, те вопросы, для которых можно это сделать – неинтересны. Так что наверное гораздо эффективнее разделять эту задачу с читателями.
Alexander Shargin по поводу ответа A 1(Sergey Emantayev) из №21 пишет:
Справедливости ради следует отметить, что всплывающие меню не обновляются в Idle loop'е. В нём обновляются тулбары, статус бар и т.п., но всплывающие меню обновляются только в ответ на WM_INITMENUPOPUP. Этой практики следует придерживаться и в собственных приложениях.
Читать дальшеИнтервал:
Закладка: