mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-06-01 16:02:39 +00:00
VideoCommon: add loading cube maps from DDS files and loading it into our custom texture object. Custom texture object now has the concept of slices in addition to levels. Traditional custom textures have a single slice
This commit is contained in:
parent
5e5887a378
commit
62fee2f3b6
8 changed files with 225 additions and 118 deletions
|
@ -15,9 +15,12 @@ namespace
|
|||
std::size_t GetAssetSize(const CustomTextureData& data)
|
||||
{
|
||||
std::size_t total = 0;
|
||||
for (const auto& level : data.m_levels)
|
||||
for (const auto& slice : data.m_slices)
|
||||
{
|
||||
total += level.data.size();
|
||||
for (const auto& level : slice.m_levels)
|
||||
{
|
||||
total += level.data.size();
|
||||
}
|
||||
}
|
||||
return total;
|
||||
}
|
||||
|
@ -30,51 +33,58 @@ CustomAssetLibrary::LoadInfo CustomAssetLibrary::LoadGameTexture(const AssetID&
|
|||
return {};
|
||||
|
||||
// Note: 'LoadTexture()' ensures we have a level loaded
|
||||
const auto& first_mip = data->m_levels[0];
|
||||
|
||||
// Verify that each mip level is the correct size (divide by 2 each time).
|
||||
u32 current_mip_width = first_mip.width;
|
||||
u32 current_mip_height = first_mip.height;
|
||||
for (u32 mip_level = 1; mip_level < static_cast<u32>(data->m_levels.size()); mip_level++)
|
||||
for (std::size_t slice_index = 0; slice_index < data->m_slices.size(); slice_index++)
|
||||
{
|
||||
if (current_mip_width != 1 || current_mip_height != 1)
|
||||
{
|
||||
current_mip_width = std::max(current_mip_width / 2, 1u);
|
||||
current_mip_height = std::max(current_mip_height / 2, 1u);
|
||||
auto& slice = data->m_slices[slice_index];
|
||||
const auto& first_mip = slice.m_levels[0];
|
||||
|
||||
const VideoCommon::CustomTextureData::Level& level = data->m_levels[mip_level];
|
||||
if (current_mip_width == level.width && current_mip_height == level.height)
|
||||
continue;
|
||||
|
||||
ERROR_LOG_FMT(VIDEO,
|
||||
"Invalid custom game texture size {}x{} for texture asset {}. Mipmap level {} "
|
||||
"must be {}x{}.",
|
||||
level.width, level.height, asset_id, mip_level, current_mip_width,
|
||||
current_mip_height);
|
||||
}
|
||||
else
|
||||
// Verify that each mip level is the correct size (divide by 2 each time).
|
||||
u32 current_mip_width = first_mip.width;
|
||||
u32 current_mip_height = first_mip.height;
|
||||
for (u32 mip_level = 1; mip_level < static_cast<u32>(slice.m_levels.size()); mip_level++)
|
||||
{
|
||||
// It is invalid to have more than a single 1x1 mipmap.
|
||||
ERROR_LOG_FMT(VIDEO,
|
||||
"Custom game texture {} has too many 1x1 mipmaps. Skipping extra levels.",
|
||||
asset_id);
|
||||
if (current_mip_width != 1 || current_mip_height != 1)
|
||||
{
|
||||
current_mip_width = std::max(current_mip_width / 2, 1u);
|
||||
current_mip_height = std::max(current_mip_height / 2, 1u);
|
||||
|
||||
const VideoCommon::CustomTextureData::ArraySlice::Level& level = slice.m_levels[mip_level];
|
||||
if (current_mip_width == level.width && current_mip_height == level.height)
|
||||
continue;
|
||||
|
||||
ERROR_LOG_FMT(VIDEO,
|
||||
"Invalid custom game texture size {}x{} for texture asset {}. Slice {} with "
|
||||
"mipmap level {} "
|
||||
"must be {}x{}.",
|
||||
level.width, level.height, asset_id, slice_index, mip_level,
|
||||
current_mip_width, current_mip_height);
|
||||
}
|
||||
else
|
||||
{
|
||||
// It is invalid to have more than a single 1x1 mipmap.
|
||||
ERROR_LOG_FMT(
|
||||
VIDEO,
|
||||
"Custom game texture {} has too many 1x1 mipmaps for slice {}. Skipping extra levels.",
|
||||
asset_id, slice_index);
|
||||
}
|
||||
|
||||
// Drop this mip level and any others after it.
|
||||
while (slice.m_levels.size() > mip_level)
|
||||
slice.m_levels.pop_back();
|
||||
}
|
||||
|
||||
// Drop this mip level and any others after it.
|
||||
while (data->m_levels.size() > mip_level)
|
||||
data->m_levels.pop_back();
|
||||
}
|
||||
// All levels have to have the same format.
|
||||
if (std::any_of(slice.m_levels.begin(), slice.m_levels.end(),
|
||||
[&first_mip](const VideoCommon::CustomTextureData::ArraySlice::Level& l) {
|
||||
return l.format != first_mip.format;
|
||||
}))
|
||||
{
|
||||
ERROR_LOG_FMT(
|
||||
VIDEO, "Custom game texture {} has inconsistent formats across mip levels for slice {}.",
|
||||
asset_id, slice_index);
|
||||
|
||||
// All levels have to have the same format.
|
||||
if (std::any_of(data->m_levels.begin(), data->m_levels.end(),
|
||||
[&first_mip](const VideoCommon::CustomTextureData::Level& l) {
|
||||
return l.format != first_mip.format;
|
||||
}))
|
||||
{
|
||||
ERROR_LOG_FMT(VIDEO, "Custom game texture {} has inconsistent formats across mip levels.",
|
||||
asset_id);
|
||||
|
||||
return {};
|
||||
return {};
|
||||
}
|
||||
}
|
||||
|
||||
return load_info;
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue