Функции Lock() и Unlock()
Одна из важнейших особенностей DirectDraw — возможность прямого доступа к графическим данным. Прямой доступ обеспечивает максимум быстродействия и гибкости, поскольку он не замедляется использованием промежуточных API, а разработчик может делать с графическими данными все, что считает нужным. Для прямого доступа к памяти поверхности существуют две функции:
• Unlock()
• Lock()
Функция Lock()возвращает указатель на область памяти, занятую поверхностью, независимо от того, где поверхность находится — в системной памяти или в видеопамяти. Память поверхности всегда организована линейно, что позволяет максимально упростить обращение к графическим данным. Функция Unlock()сообщает DirectDraw о том, что прямой доступ к памяти поверхности завершен.
Для заблокированных поверхностей не выполняются операции блиттинга и переключения, так что хранение поверхности в заблокированном состоянии не даст вам никаких преимуществ. Указатель, полученный функцией Lock(), после разблокирования поверхности становится недействительным.
Заблокированную поверхность невозможно заблокировать снова. Попытка вызова функции Lock()для уже заблокированной поверхности закончится неудачей.
Функции GetDC() и ReleaseDC()
Прямой доступ к памяти поверхности — замечательная возможность, но иногда бывает удобнее рассматривать поверхность как обычное графическое устройство Windows. Для этой цели в интерфейсе DirectDrawSurfaceпредусмотрены две функции:
• GetDC()
• ReleaseDC()
Функция GetDC()предоставляет в ваше распоряжение DC (контекст устройства, Device Context), через который можно осуществлять вывод на поверхность стандартными функциями Win32. Например, передавая его функции Win32 TextOut(), можно вывести на поверхность текст. Функция ReleaseDC()должна быть вызвана сразу же после завершения работы с DC.
Как и в случае с Lock()и Unlock(), функцию ReleaseDC()необходимо вызывать после GetDC()как можно быстрее. Это связано с тем, что внутри функции GetDC()вызывается Lock(), а внутри ReleaseDC() - Unlock().
Функции PageLock() и PageUnlock()
Перейдем к двум функциям, внешне похожим на Lock()и Unlock():
• PageLock()
• PageUnlock()
Вероятно, имена этих функций были выбраны неудачно, потому что они предназначены совсем для других целей. С помощью PageLock()и PageUnlock()можно управлять тем, как Windows обходится с поверхностями в системной памяти. Для работы с ними используется интерфейс DirectDrawSurface2, в DirectDrawSurfaceони отсутствуют.
Обычно система Windows переносит содержимое памяти на диск, когда по ее мнению другое приложение или процесс в данный момент смогут лучше распорядиться памятью. Это относится ко всей системной памяти, поэтому поверхности DirectDraw, хранящиеся в ней, также могут переноситься на диск. Когда в такой поверхности возникнет необходимость, получение данных с диска будет сопровождаться ощутимой паузой.
Функция PageLock()сообщает Windows о том, что данную поверхность нельзя переносить на диск. В этом случае поверхность всегда остается доступной и не требует долгих обращений к жесткому диску. Функция PageUnlock()разрешает Windows переносить поверхность на диск.
Следует помнить, что частое использование PageLock()приведет к замедлению работы Windows из-за сокращения общего объема переносимой памяти. Когда именно это произойдет, зависит от объема памяти, для которой запрещен перенос на диск, и общего объема системной памяти.
Функции PageLock()и PageUnlock()используются в первую очередь самой библиотекой DirectDraw, а не приложениями. Например, DirectDraw автоматически вызывает PageLock()и PageUnlock(), чтобы поверхности, находящиеся в системной памяти, не переносились на диск в ходе блиттинга.
Функцию PageLock()можно вызывать для одной поверхности многократно. DirectDraw следит за количеством вызовов PageLock(), используя механизм подсчета ссылок, поэтому для отмены многократных вызовов PageLock()потребуется несколько вызовов PageUnlock().
Функции PageLock()и PageUnlock()не влияют на поверхности, находящиеся в видеопамяти.
Функции IsLost() и Restore()
Две следующие функции предназначены для работы с поверхностями в видеопамяти:
• IsLost()
• Restore()
Читать дальше