Перейти к содержимому


Свернуть чат Чат Открыть чат во всплывающем окне

Yakim (Watco... : (2 дней назад) :D
Yakim (Watco... : (2 дней назад) nope
Yandersen : (2 дней назад) Айаяй. Поди Якимко заспамил чат стикерами. :)
Yandersen : (2 дней назад) Да лан, тут каждый день кто-нить из админов заглядывает. Как пропустили?
Nextovoy : (3 дней назад) Я писал
Гость : (5 дней назад) Сорьки, что так у нас. Чего три года так и не попытался в чат писнуть? :)
Nextovoy : (неделю назад) Спасибо
lz : (неделю назад) Активировал.
Гость : (неделю назад) Активируйте его.
Гость : (неделю назад) Мой профиль - Nextovoy
Гость : (неделю назад) Написать в чат. Профиль в ручную админы активируют.
Гость : (неделю назад) Ох уж эта дурацкая привычка писать всё раздельно засоряя чат. Это всё классно, конечно, но ребята, одменестраторы, так называемые. Третий год пытаюсь зарегистрироваться (буквально, третий) на этом форуме, но ПИСЬМО С ПОДТВЕРЖДЕНИЕМ НА ПОЧТУ ТАК И НЕ ПРИХОДИТ. Что делать?
Гость : (неделю назад) Перешёл я всё же по ссылке Redoctor'a...
Гость : (неделю назад) Пора уже M4
Гость : (2 недель назад) итак м3
lz : (2 недель назад) Мы тебе и тут передадим.
Гость : (2 недель назад) Зачем в телеграмме делать?!Я вот например не могу зайти,написать в чат,подписаться и не только у меня это.
Redoctor : (3 недель назад) https://vk.com/away....0_23001&cc_key=
Redoctor : (3 недель назад) Тогда в телеграмме в поисковике набери Механоиды 3
Гость : (3 недель назад) Не открывается.
Redoctor : (3 недель назад) https://t.me/mechanoids3 Для тех кто в танке.
Yakim (Watco... : (4 недель назад) КРУЗИИИС!!!11

Изображение
lz : (4 недель назад) КРУЗИС!
lz : (4 недель назад) ЗИС
lz : (4 недель назад) КРУ
Yakim (Watco... : (4 недель назад) Крузис и Королева тоже не в моем вкусе, а проигрывать нечего =D
lz : (4 недель назад) Конечно, полюбить - так королеву, проиграть - так миллион, сделать - так крузис.
smt005 : (4 недель назад) И от третьего лица тоже можно сделать простенькую игру. Простая игра это лучше чем ничего.
smt005 : (4 недель назад) А, ты хочеш что-бы хит был, с "Crysis" графоном и контентом на 100500 часов игры?
Yakim (Watco... : (4 недель назад) Ни топдовншутеры, ни стратежки)
Yakim (Watco... : (4 недель назад) Не, спасибо, не в моем вкусе=)
smt005 : (4 недель назад) Помнится за пару недель от скуки сделал. Делал по вечерам.
smt005 : (4 недель назад)
smt005 : (4 недель назад) Или например такое, только с моделями из игры -> https://youtu.be/RFDdN5dcX8s
smt005 : (4 недель назад) Yakim, да сами себя пните... :) Сделайте что-то, хотя бы уровня "Scrolling TopDown Shooter".
Yakim (Watco... : (4 недель назад) так что, думаю завтра с утреца стартану марафон)
Yakim (Watco... : (4 недель назад) хе-хе, не сомневайся, я в чате по уе уже поинтересовался, сказали обалденный сериал)))
Yandersen : (4 недель назад) Оооооо, поди ща залипнет на пару дней, стопудофф. :)
Yakim (Watco... : (4 недель назад) Окей гляну)
Yandersen : (4 недель назад) Сериал Пространство посмотри. Не по части Мехов, просто шикарен, авось ману доставит.
Yakim (Watco... : (4 недель назад) Дуст и ты уже закаленные и пустые, надож где-то ману доставать)))
Yakim (Watco... : (4 недель назад) Думаю, кого быть пнуть, что-бы тот пнул в ответ да по сильнее.
Yakim (Watco... : (4 недель назад) Давненько и не маленько хе-хе, делать нечего, прокрастинирую =)
Yandersen : (4 недель назад) Якимка, ты там шо, упоролсо маленько? Чиво картинами опспамилсо?
Yakim (Watco... : (09 Июнь 2018 - 22:27) Изображение

Фотография
- - - - -

[GLT.hpp] - поддержка текстур в формате GLT

OpenGL texture image GLTexture

  • Авторизуйтесь для ответа в теме
В этой теме нет ответов

#1 OFFLINE   Yandersen

Yandersen

    Диванный теоретик

  • Админ
  • 454 сообщений
  • Откуда:Canada
  • Настоящее имя:Ян

Отправлено 28 Апрель 2015 - 19:51

Формат файла *.glt (OpenGL Texture) предназначен для сохранения и загрузки текстур (мипмапы и настройки) для OpenGL приложений.

GLT.hpp содержит описание структуры файлов *.glt и класс GLTexture, осуществляющий сохранение и загрузку *.glt файлов и работу с текстурами:

 

GLT.hpp
 

:!: Требуется наличие LoadGL.h.

:!: Некоторые функции используют OpenGL4.5.

 

Для создания файла текстуры нужно создать и настроить текстуру, загрузить мипмапы удобным способом, а затем средствами класса GLTexture сохранить готовую текстуру из контекста OpenGL в указанный *.glt файл. Альтернативно, можно создать *.glt файл из *.bmp с помощью специальной программы - GLT editor.

Пока что для работы с *.glt файлами использовался FileGLT.hpp, поддерживавший формат файла первой версии ('G','L','T',1). Первая версия позволяла хранить любое количество картинок в любом порядке, и в шапке файла размеры базовой картинки не указывались явно, так как загрузка мипмапов шла с помощью функции glTexImage*D. Но эта функция уже устарела - сегодня текстуры имеют immutable формат, т.е. аллоцируются лишь один раз (glTexStorage*D) и для этого необходимо знать размерность самой большой картинки и количество уровней мипмапов. Поэтому шапка второй версии файла ('G','L','T',2) включает размерность базовой картинки. Плюс добавлена поддержка бордеров и свиззл-настроек. Короче, вторая версия просто лучше. Хотя первая всё так же поддерживается - GLT.hpp умеет её грузить, но сохраняет уже в формате второй версии.
 
---
 
Структурно файл *.glt выглядит так:

  • первые 4 байта - это "подпись", определяющая тип файла и версию - 0x02544C47 для GLT второй версии (0x01544C47 было для GLT первой версии);
  • затем идёт заголовок с настройками и параметрами текстуры (у первой и второй версий шапки разные - 40 байт для GLT1 и 80 байт для GLT2);
  • массив картинок; каждая картинка имеет шапку (GLTMipmapHeader) и собсно данные (опционально); эта часть файла одинакова для обоих версий, хотя имеет разный оффсет, т.к. шапки разного размера.

Все структуры (GLT1Header, GLT2Header, GLTMipmapHeader) описаны и обкоменчены в GLT.hpp, хотя юзеру и не требуется с ними знакомиться, т.к. класс GLTexture умеет грузить и сохранять *.glt файлы.

 

Итак, включаем GLT.hpp в проект:

#include "GLT.hpp"

Класс GLTexture содержит лишь одну переменную - имя текстуры, т.к. большая часть интерфейса использует функции из расширения Direct State Access (OpenGL4.5). Если это расширение не поддерживается, доступными будут лишь загрузка и сохранение *.glt файлов. Узнать имя текстуры можно так:

//GLTexture Texture;
GLuint Name = Texture.Name();

Класс GLTexture автоматически кастается в GLuint при его использовании в OpenGL функциях там, где требуется имя текстуры. Например:

//GLTexture Texture;
glBindTexture(GL_TEXTURE_2D, Texture);

Это имеет смысл для работы с текстурами на аппаратуре, не поддерживающей DSA из OpenGL4.5, т.к. большинство функций класса GLTexture используют это расширение.

 

Чтобы создать новую текстуру определённого типа и размерности, пользуемся этими функциями:

void GLTexture::Create1D(GLenum internalFormat, GLsizei width, bool Mipmapped=true);

void GLTexture::Create1DArray(GLenum internalFormat, GLsizei width, GLsizei layers, bool Mipmapped=true);

void GLTexture::CreateRectangle(GLenum internalFormat, GLsizei width, GLsizei height);

void GLTexture::Create2D(GLenum internalFormat, GLsizei width, GLsizei height, bool Mipmapped=true);

void GLTexture::Create2DArray(GLenum internalFormat, GLsizei width, GLsizei height, GLsizei layers, bool Mipmapped=true);
 
void GLTexture::Create3D(GLenum internalFormat, GLsizei width, GLsizei height, GLsizei depth, bool Mipmapped=true);
 
void GLTexture::CreateCubeMap(GLenum internalFormat, GLsizei width, bool Mipmapped=true);

void GLTexture::CreateCubeMapArray(GLenum internalFormat, GLsizei width, GLsizei layers, bool Mipmapped=true);

При создании текстуры требуется указать формат текселя (одна из OpenGLевских констант), размерность базовой картинки (и количество слоёв, если текстура слоёная, т.е. "layered"), а также будут ли у текстуры мипмапы (обычно да, поэтому последний параметр можно не указывать).

 

Сами же картинки загружаются этими функциями:

void GLTexture::SubImage1D(GLint level,
                           GLint xoffset,
                           GLsizei width,
                           GLenum format, GLenum type, const void *pixels);
 
void GLTexture::SubImage1DArray(GLint level,
                                GLint xoffset, GLint layerOffset,
                                GLsizei width, GLsizei layers,
                                GLenum format, GLenum type, const void *pixels);

void GLTexture::SubImageRectangle(GLint xoffset, GLint yoffset,
                                  GLsizei width, GLsizei height,
                                  GLenum format, GLenum type, const void *pixels);
 
void GLTexture::SubImage2D(GLint level,
                           GLint xoffset, GLint yoffset,
                           GLsizei width, GLsizei height,
                           GLenum format, GLenum type, const void *pixels);
 
void GLTexture::SubImage2DArray(GLint level,
                                GLint xoffset, GLint yoffset, GLint layerOffset,
                                GLsizei width, GLsizei height, GLsizei layers,
                                GLenum format, GLenum type, const void *pixels);
 
void GLTexture::SubImage3D(GLint level,
                           GLint xoffset, GLint yoffset, GLint zoffset,
                           GLsizei width, GLsizei height, GLsizei depth,
                           GLenum format, GLenum type, const void *pixels);
 
void GLTexture::SubImageCubeMap(GLint level,
                                GLint xoffset, GLint yoffset, GLint layerFaceOffset,
                                GLsizei width, GLsizei height, GLsizei layerFaces,
                                GLenum format, GLenum type, const void *pixels);

void GLTexture::SubImageCubeMapFace(GLenum targetFace, GLint level,
                                    GLint xoffset, GLint yoffset,
                                    GLsizei width, GLsizei height,
                                    GLenum format, GLenum type, const void *pixels);

void GLTexture::SubImageCubeMapArrayFace(GLenum targetFace, GLint layer, GLint level,
                                         GLint xoffset, GLint yoffset,
                                         GLsizei width, GLsizei height,
                                         GLenum format, GLenum type, const void *pixels);

Параметры следующие:

level - уровень мипмапы, для которой указывается картинка (у текстур типа GL_TEXTURE_RECTANGLE мипмапов нет, лишь базовая картинка).

xoffset, yoffset, zoffset - смещение в пикселах от левого нижнего переднего края картинки; обычно 0, если вся картинка загружается целиком, а не по частям.

layerOffset - для слоёных текстур это номер слоя, с которого начинается перезаписываемый регион картинок.

layerFaceOffset - то же, что и layerOffset, но для текстур типа GL_TEXTURE_CUBE_MAP и GL_TEXTURE_CUBE_MAP_ARRAY, для которых слои играют роль картинок для различных сторон куба. Чтобы не запутаться со сторонами и слоями, особенно для слоёных куб-мапов, где всё вперемежку и абы как, я ввёл несколько функций, позволяющих конкретно указывать сторону и номер слоя отдельно загружаемой картинки (функция SubImageCubeMapFace для обычных кубмапов и SubImageCubeMapArrayFace для слоёных кубмапов).

targetFace - для кубмапов этот параметр указывает на конкретную сторону куба (GL_TEXTURE_CUBE_MAP_POSITIVE_X, GL_TEXTURE_CUBE_MAP_NEGATIVE_X, ...).

width, height, depth, layers (layerFaces) - количество пикселей в передаваемой картинке и слоёв (если сразу несколько слоёв грузятся разом).

format, type, pixels - эти параметры описывают передаваемую картинку: format+type определяют формат пикселя, а pixels - собственно указатель на массив данных. Не забывайте о padding bytes - каждый ряд пикселей должен иметь длину, кратную 4 байтам. К примеру, если формат GL_BGR и тип - GL_UNSIGNED_BYTE (у стандартных bmp-шек так), и ширина картинки - 2 пикселя, то это 6 байт данных - непозволительный размер. Соответственно, каждый ряд должен иметь в конце 2 лишних байта, дотягивающих длину до 8 байт. В битмапах так и есть, так что их можно грузить как есть. Но если Вы создаёте текстуру процедурно, эту мелочь нужно учитывать.

 

Если Вы создали текстуру с мипмапами, но ограничились загрузкой лишь базовой картинки, автоматически мипмапы генерируются этой функцией:

inline void GLTexture::GenerateMipmaps();

Чтобы настроить параметры текстуры, используйте эти функции:

//Setup the minification filtering mode
inline void GLTexture::SetMinFilter(GLenum minFilter);

//Setup the magnification filtering mode
inline void GLTexture::SetMagFilter(GLenum magFilter);

//Set the wrapping parameter for s coordinate
inline void GLTexture::SetWrapS(GLenum wrap_s);

//Set the wrapping parameter for t coordinate
inline void GLTexture::SetWrapT(GLenum wrap_t);

//Set the wrapping parameter for r coordinate
inline void GLTexture::SetWrapR(GLenum wrap_r);

//Set the swizzling parameters
inline void GLTexture::SetSwizzle(GLenum swizzle_r=GL_RED,
                                  GLenum swizzle_g=GL_GREEN,
                                  GLenum swizzle_b=GL_BLUE,
                                  GLenum swizzle_a=GL_ALPHA);

//Set the border color
inline void GLTexture::SetBorderColor(const GLuint *ColorRGBA);

//Set the border color
inline void GLTexture::SetBorderColor(const GLint *ColorRGBA);

//Set the border color
inline void GLTexture::SetBorderColor(const GLfloat *ColorRGBA);

//Set GL_DEPTH_STENCIL_TEXTURE_MODE to GL_STENCIL_INDEX
inline void GLTexture::SelectStencilMode();

//Set GL_DEPTH_STENCIL_TEXTURE_MODE to GL_DEPTH_COMPONENT
inline void GLTexture::SelectDepthMode();

//Set GL_TEXTURE_COMPARE_MODE to GL_COMPARE_REF_TO_TEXTURE and then set a given
//value for GL_TEXTURE_COMPARE_FUNC; permissible values are: GL_LEQUAL,
//GL_GEQUAL, GL_LESS, GL_GREATER, GL_EQUAL, GL_NOTEQUAL, GL_ALWAYS, GL_NEVER
inline void GLTexture::ConfigureShadowmap(GLenum CompareFuncToUse);

//Set GL_TEXTURE_LOD_BIAS parameter
inline void GLTexture::SetLODBias(GLfloat Value);

//Set GL_TEXTURE_MIN_LOD parameter
inline void GLTexture::SetMinLOD(GLint Value);

//Set GL_TEXTURE_MAX_LOD parameter
inline void GLTexture::SetMaxLOD(GLint Value);

Учтите, что в *.glt файл сохраняются лишь filter, wrap, swizzle и border color параметры. Картинку карты тени или трафарета можно сохранить, но настройки в файл не пойдут - при сохранении и последующей загрузке эти параметры вернутся в дефолтное состояние.

 

Узнать параметры текстуры можно в любой момент (без биндинья) этими функциями:

//Return the value of the requested texture parameter
inline GLint GLTexture::GetParameteri(GLenum pname)const;

//Return the value of the requested texture parameter
inline GLfloat GLTexture::GetParameterf(GLenum pname)const;

//Return the value of the requested vector texture parameter
inline void GLTexture::GetParameterv(GLenum pname, GLint *params);

//Return the value of the requested vector texture parameter
inline void GLTexture::GetParameterv(GLenum pname, GLfloat *params)const;

//Return the value of the requested vector texture parameter
inline void GLTexture::GetParameterIv(GLenum pname, GLint *params);

//Return the value of the requested vector texture parameter
inline void GLTexture::GetParameterIv(GLenum pname, GLuint *params)const;

//Return the value of the requested parameter for the specified level
inline GLint GLTexture::GetLevelParameteri(GLint level, GLenum pname)const;

Вариант GetParameterIv отличается от GetParameterv тем, что используется лишь для возвращения цвета бордера текстур integer-формата.

 

Некоторые ширпотребные параметры удостоены чести иметь свои отдельные функции:

//Return the target type of the texture or 0 on failure
inline GLenum GLTexture::Target()const;

//Return internalFormat value for the mipmap of the specified level
inline GLenum GLTexture::InternalFormat(GLint level=0)const;

//Get texture's width
inline GLint GLTexture::Width(GLint level=0)const;

//Get texture's height (or number of layers if type is GL_TEXTURE_1D_ARRAY)
inline GLint GLTexture::Height(GLint level=0)const;

//Get texture's depth (or number of layers if it is one of 2D array textures)
inline GLint GLTexture::Depth(GLint level=0)const;

Тут нужно учесть, что для слоёных текстур Height или Depth будут возвращать количество слоёв, а не высоту или глубину картинки в пикселях, несмотря на название функции. Если не указывать уровень мипмапы, то по-умолчанию будут возвращаться параметры базовой картинки.

 

Привязать текстуру к указанному текстурному юниту можно так:

//GLTexture Texture;
Texture.Bind(GL_TEXTURE0);

Загрузка из файла *.glt:

//GLTexture Texture;
bool Success = Texture.LoadFromFile("Texture.glt");

Возвращённое значение (Success) будет true в случае успеха.

Если файл уже загружен в память (если, например, в один файл запихано несколько текстур, моделей и других данных), то текстуру можно загрузить и оттуда. Нужно лишь указать на то место, где начинается кусок, принадлежащий текстуре (начинается с 4хбайтной сигнатуры GLT1 или GLT2). Например, у нас есть файл, склееный из двух *.glt файлов, т.е. содержащий две текстуры. В таком случае грузим их так:

GLTexture Texture1, Texture2;
  
int Handle=-1; //File handle
_sopen_s(&Handle, "Textures.pak", _O_RDONLY|_O_BINARY,_SH_DENYWR,_S_IREAD);
int FileSize=_filelength(Handle);
char* Buffer=(char*)malloc(FileSize);
_read(Handle,Buffer,FileSize);
_close(Handle);

void* ptr1 = Buffer;
unsigned int BytesLoaded = Texture1.LoadFromBuffer(ptr1);

void* ptr2 = Buffer+BytesLoaded;
Texture2.LoadFromBuffer(ptr2);

free(Buffer);

Логичный вопрос - отчего стримовую загрузку не предоставить? А потому, что при загрузке отдельных мипмапов ОпенГЛ требует указатель на картинку, поэтому при стримовой загрузке пришлось бы лишний раз отводить память (и, возможно, не один раз) и копировать туда части файла с массивом пикселей.

 

А вот сохранение текстур может идти стримом:

//GLTexture Texture1, Texture2;
FILE* Stream = _fsopen("Textures.pak","wb",_SH_DENYWR);

bool Success1 = Texture1.SaveToStream(Stream);

bool Success2 = Texture2.SaveToStream(Stream);

fclose(Stream);

В отдельный файл сохраняется текстура так:

//GLTexture Texture;
bool Success = Texture.SaveToFile("Texture.glt");

Вотъ.  :)







Темы с аналогичным тегами OpenGL, texture, image, GLTexture

Количество пользователей, читающих эту тему: 1

0 пользователей, 1 гостей, 0 анонимных