[Назад] Содержание [Дальше]

Применение Simple DirectMedia Layer

Использование Видео

  • Выбор и установка разрешения и глубины цвета (очень просто!)

    SDL позволяет установить разрешение экрана и глубину цвета на ваш выбор.
    Для этого используется функция
    SDL_SetVideoMode ({Width}, {Height}, {Depth}, SDL_SWSURFACE)
    Где Width и Height - разрешение экрана,
    Depth - глубина цвета
    В качетсве последнего параметра следует передать SDL_SWSURFACE.

Совет #1:
Вы можете узнать оптимальную глубину, поддерживаемую аппаратурой, используя функцию SDL_GetVideoInfo().

Совет #2:
Вы можете получить список всех поддерживаемых разрешений и соответствующих им глубин цвета, используя функцию SDL_ListModes().

Пример:
{ SDL_Surface *screen;

    screen = SDL_SetVideoMode(640, 480, 16, SDL_SWSURFACE);
    if ( screen == NULL ) {// Если установить разрешение не удалось
        fprintf(stderr, "Невозможно установить разрешение 640x480: %s\n", SDL_GetError());
        exit(1);
    }
}
  • Рисование точек (пикселей) на экране

    Рисование точек сводится к прямому обращению к видеобуфферу и вызову функции обновления содержимого экрана.
    Для установки цвета точки необходимо создать указатель на буфер, затем поместить в буфер указатель на нужную точку, после чего просто присвоить буферу цвет.

Совет:
Если вам предстоит рисовать много объектов, то мы рекомендуем заблокировать (Lock) экран единожды перед рисованием, вывести все объекты на экран, и разблокировать (unlock) экран вновь по завершении рисования.
Пример:

Рисование точки на экране необходимым цветом

void DrawPixel(SDL_Surface *screen, Uint8 R, Uint8 G, Uint8 B)
{
    Uint32 color = SDL_MapRGB(screen->format, R, G, B);

    if ( SDL_MUSTLOCK(screen) ) {
        if ( SDL_LockSurface(screen) < 0 ) {
            return;
        }
    }
    // Смотрим, сколькими байтами кодируется каждый пиксель (bytes per pixel, bpp)
    switch (screen->format->BytesPerPixel) {
        case 1: { /* Если 8-bpp */
            Uint8 *bufp;

            bufp = (Uint8 *)screen->pixels + y*screen->pitch + x;
            *bufp = color;
        }
        break;

        case 2: { /* Если 15-bpp или 16-bpp */
            Uint16 *bufp;

            bufp = (Uint16 *)screen->pixels + y*screen->pitch/2 + x;
            *bufp = color;
        }
        break;

        case 3: { /* Медленный 24-bpp режим, обычно не используется */
            Uint8 *bufp;

            bufp = (Uint8 *)screen->pixels + y*screen->pitch + x;
            *(bufp+screen->format->Rshift/8) = R;
            *(bufp+screen->format->Gshift/8) = G;
            *(bufp+screen->format->Bshift/8) = B;
        }
        break;

        case 4: { /* Наверное, 32-bpp */
            Uint32 *bufp;

            bufp = (Uint32 *)screen->pixels + y*screen->pitch/4 + x;
            *bufp = color;
        }
        break;
    }
    if ( SDL_MUSTLOCK(screen) ) {
        SDL_UnlockSurface(screen);
    }
    SDL_UpdateRect(screen, x, y, 1, 1);
}
  • Загрузка и отображение рисунков

    SDL предлагает довольно простой способ загрузки изображений. Для того, чтобы загрузить картинку, используется функция
    SDL_Surface SDL_LoadBMP ({FName});
    Где FName - это имя файла, из которого следует произвести загрузку;
    Возвращает функция указатель на изображение.

    Вы можете отобразить загруженную картинку, используя функцию SDL_BlitSurface(), которая блитирует (пересылает) загруженное изображение на видеобуфер. В последствии необходимо вызвать функцию SDL_UpdateRects() для обновления частей экрана, подвергшихся изменению.

Совет #1:
Если вам необходимо показывать некоторую картинку много раз, вы можете ускорить блитинг, конвертровав ее в формат дисплея. Для этого используется функция SDL_DisplayFormat()

Совет #2:
Поскольку почти всегда необходимо переместить не прямоугольную картинку, а картинку определенной формы (иначе говоря, прозрачную картинку), вы можете воспользоваться функцией SDL_SetColorKey() для установки прозрачного цвета.

Пример:
void ShowBMP(char *file, SDL_Surface *screen, int x, int y)
{
    SDL_Surface *image;
    SDL_Rect dest;

    /* Загрузим BMP файл на поверхность */
    image = SDL_LoadBMP(file);
    if ( image == NULL ) {
        fprintf(stderr, "Couldn't load %s: %s\n", file, SDL_GetError());
        return;
    }

    /* Блитируем (копируем) на экранную поверхность.
       Поверхность не должна быть заблокирована (load).
     */
    dest.x = x;
    dest.y = y;
    dest.w = image->w;
    dest.h = image->h;
    SDL_BlitSurface(image, NULL, screen, &dest);

    /* Обновим измененную часть экрана */
    SDL_UpdateRects(screen, 1, &dest);
}

[Назад] Содержание [Дальше]