diff options
-rw-r--r-- | addons/resource.language.en_gb/resources/strings.po | 14 | ||||
-rw-r--r-- | system/settings/settings.xml | 5 | ||||
-rw-r--r-- | xbmc/guilib/D3DResource.cpp | 33 | ||||
-rw-r--r-- | xbmc/guilib/D3DResource.h | 1 | ||||
-rw-r--r-- | xbmc/guilib/Texture.cpp | 15 | ||||
-rw-r--r-- | xbmc/guilib/Texture.h | 4 | ||||
-rw-r--r-- | xbmc/guilib/TextureDX.cpp | 8 | ||||
-rw-r--r-- | xbmc/guilib/TextureGL.cpp | 23 | ||||
-rw-r--r-- | xbmc/guilib/TexturePi.cpp | 4 | ||||
-rw-r--r-- | xbmc/pictures/SlideShowPicture.cpp | 4 | ||||
-rw-r--r-- | xbmc/rendering/dx/RenderSystemDX.cpp | 10 | ||||
-rw-r--r-- | xbmc/settings/Settings.cpp | 1 | ||||
-rw-r--r-- | xbmc/settings/Settings.h | 1 |
13 files changed, 109 insertions, 14 deletions
diff --git a/addons/resource.language.en_gb/resources/strings.po b/addons/resource.language.en_gb/resources/strings.po index a14d1b272d..8ff492a890 100644 --- a/addons/resource.language.en_gb/resources/strings.po +++ b/addons/resource.language.en_gb/resources/strings.po @@ -18880,7 +18880,19 @@ msgctxt "#36618" msgid "Add-ons will be given access to personal data stored on this device. By allowing, you agree that you are solely responsible for any loss of data, unwanted behaviour, or damage to your device. Proceed?" msgstr "" -#empty strings from id 36619 to 36899 +#. Label of a setting, allow the user to specifiy high quality downscaling of pictures +#: system/settings/settings.xml +msgctxt "#36619" +msgid "High quality downscaling" +msgstr "" + +#. Description of setting "Pictures -> Slideshow -> High Quality Downscaling" with label #36619 +#: system/settings/settings.xml +msgctxt "#36620" +msgid "Enable high quality downscaling of pictures (uses more memory and has moderate performance impact)." +msgstr "" + +#empty strings from id 36621 to 36899 #: xbmc/media/MediaType.cpp msgctxt "#36900" diff --git a/system/settings/settings.xml b/system/settings/settings.xml index 21d4439d50..96091ec7ef 100644 --- a/system/settings/settings.xml +++ b/system/settings/settings.xml @@ -611,6 +611,11 @@ <default>false</default> <control type="toggle" /> </setting> + <setting id="slideshow.highqualitydownscaling" type="boolean" label="36619" help="36620"> + <level>1</level> + <default>false</default> + <control type="toggle" /> + </setting> </group> </category> <category id="language" label="14218" help="38106"> diff --git a/xbmc/guilib/D3DResource.cpp b/xbmc/guilib/D3DResource.cpp index 88b4721cc8..66207aea82 100644 --- a/xbmc/guilib/D3DResource.cpp +++ b/xbmc/guilib/D3DResource.cpp @@ -225,16 +225,35 @@ bool CD3DTexture::Create(UINT width, UINT height, UINT mipLevels, D3D11_USAGE us bool CD3DTexture::CreateInternal(const void* pixels /* nullptr */, unsigned int srcPitch /* 0 */) { ID3D11Device* pD3DDevice = g_Windowing.Get3D11Device(); + ID3D11DeviceContext* pD3D11Context = g_Windowing.Get3D11Context(); - CD3D11_TEXTURE2D_DESC textureDesc(m_format, m_width, m_height, 1, m_mipLevels, m_bindFlags, m_usage, m_cpuFlags, 1, 0, - (m_mipLevels > 1) ? D3D11_RESOURCE_MISC_GENERATE_MIPS : 0); + UINT miscFlags = 0; + bool autogenmm = false; + if (m_mipLevels == 0 && g_Windowing.IsFormatSupport(m_format, D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + autogenmm = pixels != nullptr; + miscFlags |= D3D11_RESOURCE_MISC_GENERATE_MIPS; + } + else + m_mipLevels = 1; + CD3D11_TEXTURE2D_DESC textureDesc(m_format, m_width, m_height, 1, m_mipLevels, m_bindFlags, m_usage, m_cpuFlags, 1, 0, miscFlags); D3D11_SUBRESOURCE_DATA initData = { 0 }; initData.pSysMem = pixels; initData.SysMemPitch = srcPitch ? srcPitch : CD3DHelper::BitsPerPixel(m_format) * m_width / 8; initData.SysMemSlicePitch = 0; - return SUCCEEDED(pD3DDevice->CreateTexture2D(&textureDesc, (pixels ? &initData : NULL), &m_texture)); + HRESULT hr = pD3DDevice->CreateTexture2D(&textureDesc, (!autogenmm && pixels) ? &initData : nullptr, &m_texture); + if (SUCCEEDED(hr) && autogenmm) + { + pD3D11Context->UpdateSubresource(m_texture, 0, nullptr, pixels, + (srcPitch ? srcPitch : CD3DHelper::BitsPerPixel(m_format) * m_width / 8), 0); + } + + if (autogenmm) + GenerateMipmaps(); + + return SUCCEEDED(hr); } ID3D11ShaderResourceView* CD3DTexture::GetShaderResource() @@ -244,7 +263,7 @@ ID3D11ShaderResourceView* CD3DTexture::GetShaderResource() if (!m_textureView) { - CD3D11_SHADER_RESOURCE_VIEW_DESC cSRVDesc(D3D11_SRV_DIMENSION_TEXTURE2D); + CD3D11_SHADER_RESOURCE_VIEW_DESC cSRVDesc(D3D11_SRV_DIMENSION_TEXTURE2D, m_format, 0, -1); HRESULT hr = g_Windowing.Get3D11Device()->CreateShaderResourceView(m_texture, &cSRVDesc, &m_textureView); if (FAILED(hr)) @@ -414,6 +433,12 @@ unsigned int CD3DTexture::GetMemoryUsage(unsigned int pitch) const } } +void CD3DTexture::GenerateMipmaps() +{ + if (m_mipLevels == 0) + g_Windowing.Get3D11Context()->GenerateMips(GetShaderResource()); +} + // static methods void CD3DTexture::DrawQuad(const CPoint points[4], color_t color, CD3DTexture *texture, const CRect *texCoords, SHADER_METHOD options) { diff --git a/xbmc/guilib/D3DResource.h b/xbmc/guilib/D3DResource.h index dc2b2ba33a..cf0a0b98bf 100644 --- a/xbmc/guilib/D3DResource.h +++ b/xbmc/guilib/D3DResource.h @@ -122,6 +122,7 @@ public: UINT GetWidth() const { return m_width; } UINT GetHeight() const { return m_height; } DXGI_FORMAT GetFormat() const { return m_format; } + void GenerateMipmaps(); // static methods static void DrawQuad(const CPoint points[4], color_t color, CD3DTexture *texture, const CRect *texCoords, diff --git a/xbmc/guilib/Texture.cpp b/xbmc/guilib/Texture.cpp index 419148d66c..b0ed2220c0 100644 --- a/xbmc/guilib/Texture.cpp +++ b/xbmc/guilib/Texture.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2005-2013 Team XBMC + * Copyright (C) 2005-2015 Team XBMC * http://xbmc.org * * This Program is free software; you can redistribute it and/or modify @@ -43,7 +43,8 @@ /* */ /************************************************************************/ CBaseTexture::CBaseTexture(unsigned int width, unsigned int height, unsigned int format) - : m_hasAlpha( true ) + : m_hasAlpha( true ), + m_mipmapping( false ) { m_pixels = NULL; m_loadedToGPU = false; @@ -433,3 +434,13 @@ bool CBaseTexture::HasAlpha() const { return m_hasAlpha; } + +void CBaseTexture::SetMipmapping() +{ + m_mipmapping = true; +} + +bool CBaseTexture::IsMipmapped() const +{ + return m_mipmapping; +} diff --git a/xbmc/guilib/Texture.h b/xbmc/guilib/Texture.h index 9506ebf790..7d92cd5ba8 100644 --- a/xbmc/guilib/Texture.h +++ b/xbmc/guilib/Texture.h @@ -78,6 +78,9 @@ public: bool HasAlpha() const; + void SetMipmapping(); + bool IsMipmapped() const; + virtual void CreateTextureObject() = 0; virtual void DestroyTextureObject() = 0; virtual void LoadToGPU() = 0; @@ -131,6 +134,7 @@ protected: unsigned int m_format; int m_orientation; bool m_hasAlpha; + bool m_mipmapping; }; #if defined(HAS_OMXPLAYER) diff --git a/xbmc/guilib/TextureDX.cpp b/xbmc/guilib/TextureDX.cpp index ec25f469c3..ba6eecde94 100644 --- a/xbmc/guilib/TextureDX.cpp +++ b/xbmc/guilib/TextureDX.cpp @@ -94,12 +94,12 @@ void CDXTexture::LoadToGPU() if (m_format != XB_FMT_RGB8) { // this is faster way to create texture with initial data instead of create empty and then copy to it - m_texture.Create(m_textureWidth, m_textureHeight, 1, usage, GetFormat(), m_pixels, GetPitch()); + m_texture.Create(m_textureWidth, m_textureHeight, IsMipmapped() ? 0 : 1, usage, GetFormat(), m_pixels, GetPitch()); if (m_texture.Get() != nullptr) needUpdate = false; } else - m_texture.Create(m_textureWidth, m_textureHeight, 1, usage, GetFormat()); + m_texture.Create(m_textureWidth, m_textureHeight, IsMipmapped() ? 0 : 1, usage, GetFormat()); if (m_texture.Get() == nullptr) { @@ -120,7 +120,7 @@ void CDXTexture::LoadToGPU() m_texture.Release(); usage = D3D11_USAGE_DYNAMIC; - m_texture.Create(m_textureWidth, m_textureHeight, 1, usage, GetFormat(), m_pixels, GetPitch()); + m_texture.Create(m_textureWidth, m_textureHeight, IsMipmapped() ? 0 : 1, usage, GetFormat(), m_pixels, GetPitch()); if (m_texture.Get() == nullptr) { CLog::Log(LOGDEBUG, "CDXTexture::CDXTexture: Error creating new texture for size %d x %d.", m_textureWidth, m_textureHeight); @@ -180,6 +180,8 @@ void CDXTexture::LoadToGPU() CLog::Log(LOGERROR, __FUNCTION__" - failed to lock texture."); } m_texture.UnlockRect(0); + if (usage != D3D11_USAGE_STAGING && IsMipmapped()) + m_texture.GenerateMipmaps(); } _aligned_free(m_pixels); m_pixels = nullptr; diff --git a/xbmc/guilib/TextureGL.cpp b/xbmc/guilib/TextureGL.cpp index a18bda068c..5fdda27ca3 100644 --- a/xbmc/guilib/TextureGL.cpp +++ b/xbmc/guilib/TextureGL.cpp @@ -1,5 +1,5 @@ /* - * Copyright (C) 2005-2013 Team XBMC + * Copyright (C) 2005-2015 Team XBMC * http://xbmc.org * * This Program is free software; you can redistribute it and/or modify @@ -24,6 +24,7 @@ #include "utils/log.h" #include "utils/GLUtils.h" #include "guilib/TextureManager.h" +#include "settings/AdvancedSettings.h" #ifdef TARGET_POSIX #include "linux/XMemUtils.h" #endif @@ -73,7 +74,20 @@ void CGLTexture::LoadToGPU() glBindTexture(GL_TEXTURE_2D, m_texture); // Set the texture's stretching properties - glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + if (IsMipmapped()) + { + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); +#ifndef HAS_GLES + // Lower LOD bias equals more sharpness, but less smooth animation + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_LOD_BIAS, -0.5f); + glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP, GL_TRUE); +#endif + } + else + { + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); + } + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); @@ -176,6 +190,11 @@ void CGLTexture::LoadToGPU() glTexImage2D(GL_TEXTURE_2D, 0, internalformat, m_textureWidth, m_textureHeight, 0, pixelformat, GL_UNSIGNED_BYTE, m_pixels); + if (IsMipmapped()) + { + glGenerateMipmap(GL_TEXTURE_2D); + } + #endif VerifyGLState(); diff --git a/xbmc/guilib/TexturePi.cpp b/xbmc/guilib/TexturePi.cpp index 19ce2a2b12..bac4a00eb8 100644 --- a/xbmc/guilib/TexturePi.cpp +++ b/xbmc/guilib/TexturePi.cpp @@ -93,6 +93,10 @@ void CPiTexture::LoadToGPU() // Bind the texture object glBindTexture(GL_TEXTURE_2D, m_texture); + if (IsMipmapped()) { + glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR); + glGenerateMipmap(GL_TEXTURE_2D); + } m_loadedToGPU = true; return; } diff --git a/xbmc/pictures/SlideShowPicture.cpp b/xbmc/pictures/SlideShowPicture.cpp index f571d0472d..ebd3050968 100644 --- a/xbmc/pictures/SlideShowPicture.cpp +++ b/xbmc/pictures/SlideShowPicture.cpp @@ -118,6 +118,10 @@ void CSlideShowPic::SetTexture_Internal(int iSlideNumber, CBaseTexture* pTexture m_pImage = pTexture; m_fWidth = (float)pTexture->GetWidth(); m_fHeight = (float)pTexture->GetHeight(); + if (CSettings::GetInstance().GetBool(CSettings::SETTING_SLIDESHOW_HIGHQUALITYDOWNSCALING)) + { // activate mipmapping when high quality downscaling is 'on' + pTexture->SetMipmapping(); + } // reset our counter m_iCounter = 0; // initialize our transistion effect diff --git a/xbmc/rendering/dx/RenderSystemDX.cpp b/xbmc/rendering/dx/RenderSystemDX.cpp index 52634c0fea..fa9e8bdd92 100644 --- a/xbmc/rendering/dx/RenderSystemDX.cpp +++ b/xbmc/rendering/dx/RenderSystemDX.cpp @@ -675,9 +675,15 @@ bool CRenderSystemDX::CreateDevice() // Second, no wrap sampler modes for textures are allowed - we are using clamp everywhere // At feature levels 10_0, 10_1 and 11_0, the display device unconditionally supports the use of 2D textures with dimensions that are not powers of two. // so, setup caps NPOT - m_renderCaps |= RENDER_CAPS_NPOT; + m_renderCaps |= m_featureLevel > D3D_FEATURE_LEVEL_9_3 ? RENDER_CAPS_NPOT : 0; if ((m_renderCaps & RENDER_CAPS_DXT) != 0) - m_renderCaps |= RENDER_CAPS_DXT_NPOT; + { + if (m_featureLevel > D3D_FEATURE_LEVEL_9_3 || + (!IsFormatSupport(DXGI_FORMAT_BC1_UNORM, D3D11_FORMAT_SUPPORT_MIP_AUTOGEN) + && !IsFormatSupport(DXGI_FORMAT_BC2_UNORM, D3D11_FORMAT_SUPPORT_MIP_AUTOGEN) + && !IsFormatSupport(DXGI_FORMAT_BC3_UNORM, D3D11_FORMAT_SUPPORT_MIP_AUTOGEN))) + m_renderCaps |= RENDER_CAPS_DXT_NPOT; + } // Temporary - allow limiting the caps to debug a texture problem if (g_advancedSettings.m_RestrictCapsMask != 0) diff --git a/xbmc/settings/Settings.cpp b/xbmc/settings/Settings.cpp index 0e429f3924..fb143fe2f6 100644 --- a/xbmc/settings/Settings.cpp +++ b/xbmc/settings/Settings.cpp @@ -303,6 +303,7 @@ const std::string CSettings::SETTING_PICTURES_DISPLAYRESOLUTION = "pictures.disp const std::string CSettings::SETTING_SLIDESHOW_STAYTIME = "slideshow.staytime"; const std::string CSettings::SETTING_SLIDESHOW_DISPLAYEFFECTS = "slideshow.displayeffects"; const std::string CSettings::SETTING_SLIDESHOW_SHUFFLE = "slideshow.shuffle"; +const std::string CSettings::SETTING_SLIDESHOW_HIGHQUALITYDOWNSCALING = "slideshow.highqualitydownscaling"; const std::string CSettings::SETTING_WEATHER_CURRENTLOCATION = "weather.currentlocation"; const std::string CSettings::SETTING_WEATHER_ADDON = "weather.addon"; const std::string CSettings::SETTING_WEATHER_ADDONSETTINGS = "weather.addonsettings"; diff --git a/xbmc/settings/Settings.h b/xbmc/settings/Settings.h index 105099ddc1..e6432087dc 100644 --- a/xbmc/settings/Settings.h +++ b/xbmc/settings/Settings.h @@ -260,6 +260,7 @@ public: static const std::string SETTING_SLIDESHOW_STAYTIME; static const std::string SETTING_SLIDESHOW_DISPLAYEFFECTS; static const std::string SETTING_SLIDESHOW_SHUFFLE; + static const std::string SETTING_SLIDESHOW_HIGHQUALITYDOWNSCALING; static const std::string SETTING_WEATHER_CURRENTLOCATION; static const std::string SETTING_WEATHER_ADDON; static const std::string SETTING_WEATHER_ADDONSETTINGS; |