Как определить, была ли загрузка текстуры успешной в OpenGL ES 2?

В старые добрые времена обычного OpenGL было довольно легко определить успешность загрузки текстуры — после вызова glTexImage2D можно было использовать glGetTexLevelParameteriv с параметрами GL_TEXTURE_WIDTH и GL_TEXTURE_HEIGHT. GLES, однако, похоже, не позволяет этого, и, насколько я могу судить, не имеет механизма для определения того, действительно ли текстура была успешно предоставлена ​​карте (например, glGetError устанавливается только для вещей, которые будут не удалось, в отличие от того, что не удалось).

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


person fluffy    schedule 28.04.2011    source источник


Ответы (1)


Боюсь, что в данный момент это невозможно. Все состояние OpenGL, содержащее размер текстуры, теперь удалено (согласно спецификациям GLES 2.0.25). Как вы правильно заметили, при неправильной загрузке текстуры не возникает ошибок (это, к сожалению, по дизайну). Прокси-текстуры были удалены, и люди сообщали, что они часто не поддерживаются/не работают на графических процессорах класса ПК. И что теперь?

Вы можете попытаться прочитать содержимое текстуры обратно через объект кадрового буфера (возможно, не всю текстуру, а только угловые точки/каждый 32-й пиксель/...). Это будет не очень быстро, но должно сработать. Возможно, вы также могли бы использовать тест полноты кадрового буфера с прикрепленной текстурой (но, похоже, это ограничивается только внутренним форматом изображения, который может быть установлен или не установлен в случае сбоя загрузки текстуры из-за нехватки памяти - вам придется это проверить) .

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

Было бы довольно легко проверить наличие свободного места перед выделением текстуры, затем удалить буфер рендеринга (в случае успеха) и затем выделить саму текстуру. Имейте в виду, что с MIP-картами текстура будет занимать чуть больше 1,33x памяти для базового уровня.

Еще лучше было бы определить доступную память при запуске приложения (возможно, после компиляции шейдеров и выделения других объектов, где непросто оценить занимаемую память) и отслеживать распределение объектов, чтобы увидеть, сколько памяти осталось. Это кажется сложным, но если объекты OpenGL заключены в классы, это должно быть довольно просто.

person the swine    schedule 11.01.2012
comment
Even better would be to determine available memory and to keep track of object allocations to see how much memory is left Это было бы ненадежно из-за фрагментации памяти. - person Tara; 10.11.2020