aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorfuzzard <fuzzard@users.noreply.github.com>2024-05-09 19:30:34 +1000
committerGitHub <noreply@github.com>2024-05-09 19:30:34 +1000
commit161ccd09dca7980500bccc06e5b6012c11ea9a8b (patch)
treeea0dab33f02d9799cd9c92b80afb1e8267ffff28
parentdad1445ba04d5a3d4709b61af5fdd9dbe5c9db8c (diff)
parentd8c2cc727a4e9830d1346af740f3a36cc58ba247 (diff)
downloadxbmc-161ccd09dca7980500bccc06e5b6012c11ea9a8b.tar.xz
Merge pull request #25120 from neo1973/fix_25100
[picture] Make picture viewer work with enabled smart redraw
-rw-r--r--xbmc/pictures/GUIWindowSlideShow.cpp13
-rw-r--r--xbmc/pictures/SlideShowPicture.cpp129
-rw-r--r--xbmc/pictures/SlideShowPicture.h5
3 files changed, 96 insertions, 51 deletions
diff --git a/xbmc/pictures/GUIWindowSlideShow.cpp b/xbmc/pictures/GUIWindowSlideShow.cpp
index 4a47726dc8..b1fe3d56c5 100644
--- a/xbmc/pictures/GUIWindowSlideShow.cpp
+++ b/xbmc/pictures/GUIWindowSlideShow.cpp
@@ -408,9 +408,12 @@ void CGUIWindowSlideShow::Process(unsigned int currentTime, CDirtyRegionList &re
// if we haven't processed yet, we should mark the whole screen
if (!HasProcessed())
+ {
regions.emplace_back(CRect(
0.0f, 0.0f, static_cast<float>(CServiceBroker::GetWinSystem()->GetGfxContext().GetWidth()),
static_cast<float>(CServiceBroker::GetWinSystem()->GetGfxContext().GetHeight())));
+ MarkDirtyRegion();
+ }
if (m_iCurrentSlide < 0 || m_iCurrentSlide >= static_cast<int>(m_slides.size()))
m_iCurrentSlide = 0;
@@ -496,6 +499,7 @@ void CGUIWindowSlideShow::Process(unsigned int currentTime, CDirtyRegionList &re
regions.emplace_back(CRect(
0.0f, 0.0f, static_cast<float>(CServiceBroker::GetWinSystem()->GetGfxContext().GetWidth()),
static_cast<float>(CServiceBroker::GetWinSystem()->GetGfxContext().GetHeight())));
+ MarkDirtyRegion();
return;
}
@@ -558,6 +562,9 @@ void CGUIWindowSlideShow::Process(unsigned int currentTime, CDirtyRegionList &re
// render the current image
if (m_Image[m_iCurrentPic]->IsLoaded())
{
+ if (m_Image[m_iCurrentPic]->IsAnimating())
+ MarkDirtyRegion();
+
m_Image[m_iCurrentPic]->SetInSlideshow(bSlideShow);
m_Image[m_iCurrentPic]->Pause(!bSlideShow);
m_Image[m_iCurrentPic]->Process(currentTime, regions);
@@ -572,6 +579,7 @@ void CGUIWindowSlideShow::Process(unsigned int currentTime, CDirtyRegionList &re
{
m_Image[m_iCurrentPic]->SetTransitionTime(1, IMMEDIATE_TRANSITION_TIME);
m_bLoadNextPic = false;
+ MarkDirtyRegion();
}
}
@@ -598,6 +606,10 @@ void CGUIWindowSlideShow::Process(unsigned int currentTime, CDirtyRegionList &re
if (m_Image[1 - m_iCurrentPic]->DisplayEffectNeedChange(effect))
m_Image[1 - m_iCurrentPic]->Reset(effect);
}
+
+ if (m_Image[1 - m_iCurrentPic]->IsAnimating())
+ MarkDirtyRegion();
+
// set the appropriate transition time
m_Image[1 - m_iCurrentPic]->SetTransitionTime(0,
m_Image[m_iCurrentPic]->GetTransitionTime(1));
@@ -980,6 +992,7 @@ bool CGUIWindowSlideShow::OnAction(const CAction &action)
default:
return CGUIDialog::OnAction(action);
}
+ MarkDirtyRegion();
return true;
}
diff --git a/xbmc/pictures/SlideShowPicture.cpp b/xbmc/pictures/SlideShowPicture.cpp
index fd0fd2cdd6..b66c27520e 100644
--- a/xbmc/pictures/SlideShowPicture.cpp
+++ b/xbmc/pictures/SlideShowPicture.cpp
@@ -16,6 +16,7 @@
#include "windowing/GraphicContext.h"
#include "windowing/WinSystem.h"
+#include <cassert>
#include <mutex>
#ifndef _USE_MATH_DEFINES
@@ -38,7 +39,6 @@ static float zoomamount[10] = { 1.0f, 1.2f, 1.5f, 2.0f, 2.8f, 4.0f, 6.0f, 9.0f,
CSlideShowPic::CSlideShowPic() : m_pImage(nullptr)
{
m_bIsLoaded = false;
- m_bIsFinished = false;
m_bDrawNextImage = false;
m_bTransitionImmediately = false;
@@ -56,7 +56,6 @@ void CSlideShowPic::Close()
std::unique_lock<CCriticalSection> lock(m_textureAccess);
m_pImage.reset();
m_bIsLoaded = false;
- m_bIsFinished = false;
m_bDrawNextImage = false;
m_bTransitionImmediately = false;
m_bIsDirty = true;
@@ -81,6 +80,21 @@ bool CSlideShowPic::DisplayEffectNeedChange(DISPLAY_EFFECT newDispEffect) const
return true;
}
+bool CSlideShowPic::IsFinished() const
+{
+ return IsLoaded() && m_iCounter >= m_transitionEnd.start + m_transitionEnd.length;
+}
+
+bool CSlideShowPic::IsAnimating() const
+{
+ return !IsFinished() &&
+ (m_displayEffect != EFFECT_NO_TIMEOUT || // Special snowflake, doesn't work without this
+ m_iCounter < m_transitionStart.length || // Inside start transition
+ m_iCounter >= m_transitionEnd.start || // Inside end transition
+ (m_iCounter >= m_transitionTemp.start &&
+ m_iCounter < m_transitionTemp.start + m_transitionTemp.length)); // Inside display effect
+}
+
void CSlideShowPic::SetTexture(int iSlideNumber,
std::unique_ptr<CTexture> pTexture,
DISPLAY_EFFECT dispEffect,
@@ -207,7 +221,6 @@ void CSlideShowPic::SetTexture_Internal(int iSlideNumber,
m_transitionEnd.start = m_transitionStart.length + iFrames;
- m_bIsFinished = false;
m_bDrawNextImage = false;
m_bIsLoaded = true;
}
@@ -272,25 +285,11 @@ void CSlideShowPic::UpdateVertices(float cur_x[4], float cur_y[4], const float n
void CSlideShowPic::Process(unsigned int currentTime, CDirtyRegionList &dirtyregions)
{
- if (!m_pImage || !m_bIsLoaded || m_bIsFinished) return ;
- UTILS::COLOR::Color alpha = m_alpha;
- if (m_iCounter <= m_transitionStart.length)
- { // do start transition
- if (m_transitionStart.type == CROSSFADE)
- { // fade in at 1x speed
- alpha = (UTILS::COLOR::Color)((float)m_iCounter / (float)m_transitionStart.length * 255.0f);
- }
- else if (m_transitionStart.type == FADEIN_FADEOUT)
- { // fade in at 2x speed, then keep solid
- alpha =
- (UTILS::COLOR::Color)((float)m_iCounter / (float)m_transitionStart.length * 255.0f * 2);
- if (alpha > 255) alpha = 255;
- }
- else // m_transitionEffect == TRANSITION_NONE
- {
- alpha = 0xFF; // opaque
- }
- }
+ if (!m_pImage || !m_bIsLoaded || IsFinished())
+ return;
+
+ UpdateAlpha();
+
bool bPaused = m_bPause | (m_fZoomAmount != 1.0f);
// check if we're doing a temporary effect (such as rotate + zoom)
if (m_transitionTemp.type != TRANSITION_NONE)
@@ -378,32 +377,8 @@ void CSlideShowPic::Process(unsigned int currentTime, CDirtyRegionList &dirtyreg
m_transitionEnd.start++;
}
if (m_iCounter >= m_transitionEnd.start)
- { // do end transition
-// CLog::Log(LOGDEBUG,"Transitioning");
m_bDrawNextImage = true;
- if (m_transitionEnd.type == CROSSFADE)
- { // fade out at 1x speed
- alpha = 255 - (UTILS::COLOR::Color)((float)(m_iCounter - m_transitionEnd.start) /
- (float)m_transitionEnd.length * 255.0f);
- }
- else if (m_transitionEnd.type == FADEIN_FADEOUT)
- { // keep solid, then fade out at 2x speed
- alpha = (UTILS::COLOR::Color)(
- (float)(m_transitionEnd.length - m_iCounter + m_transitionEnd.start) /
- (float)m_transitionEnd.length * 255.0f * 2);
- if (alpha > 255) alpha = 255;
- }
- else // m_transitionEffect == TRANSITION_NONE
- {
- alpha = 0xFF; // opaque
- }
- }
- if (alpha != m_alpha)
- {
- m_alpha = alpha;
- m_bIsDirty = true;
- }
- if (m_displayEffect != EFFECT_NO_TIMEOUT || m_iCounter < m_transitionStart.length || m_iCounter >= m_transitionEnd.start || (m_iCounter >= m_transitionTemp.start && m_iCounter < m_transitionTemp.start + m_transitionTemp.length))
+ if (IsAnimating())
{
/* this really annoying. there's non-stop logging when viewing a pic outside of the slideshow
if (m_displayEffect == EFFECT_NO_TIMEOUT)
@@ -411,8 +386,6 @@ void CSlideShowPic::Process(unsigned int currentTime, CDirtyRegionList &dirtyreg
*/
m_iCounter++;
}
- if (m_iCounter > m_transitionEnd.start + m_transitionEnd.length)
- m_bIsFinished = true;
RESOLUTION_INFO info = CServiceBroker::GetWinSystem()->GetGfxContext().GetResInfo();
@@ -717,6 +690,64 @@ void CSlideShowPic::Zoom(float fZoom, bool immediate /* = false */)
m_bNoEffect = true;
}
+void CSlideShowPic::UpdateAlpha()
+{
+ assert(m_iCounter >= 0);
+
+ UTILS::COLOR::Color alpha = m_alpha;
+
+ if (m_iCounter < m_transitionStart.length)
+ { // do start transition
+ switch (m_transitionStart.type)
+ {
+ case CROSSFADE:
+ // fade in at 1x speed
+ alpha =
+ static_cast<UTILS::COLOR::Color>(static_cast<float>(m_iCounter + 1) /
+ static_cast<float>(m_transitionStart.length) * 255.0f);
+ break;
+ case FADEIN_FADEOUT:
+ // fade in at 2x speed, then keep solid
+ alpha = std::min(static_cast<UTILS::COLOR::Color>(
+ static_cast<float>(m_iCounter + 1) /
+ static_cast<float>(m_transitionStart.length) * 255.0f * 2),
+ UTILS::COLOR::Color{255});
+ break;
+ default:
+ alpha = 255; // opaque
+ }
+ }
+
+ if (m_iCounter >= m_transitionEnd.start)
+ { // do end transition
+ switch (m_transitionEnd.type)
+ {
+ case CROSSFADE:
+ // fade in at 1x speed
+ alpha = 255 - static_cast<UTILS::COLOR::Color>(
+ static_cast<float>(m_iCounter - m_transitionEnd.start + 1) /
+ static_cast<float>(m_transitionEnd.length) * 255.0f);
+ break;
+ case FADEIN_FADEOUT:
+ // fade in at 2x speed, then keep solid
+ alpha = std::min(static_cast<UTILS::COLOR::Color>(
+ static_cast<float>(m_transitionEnd.length - m_iCounter +
+ m_transitionEnd.start + 1) /
+ static_cast<float>(m_transitionEnd.length) * 255.0f * 2),
+ UTILS::COLOR::Color{255});
+ break;
+ default:
+ alpha = 255; // opaque
+ }
+ }
+
+ if (alpha != m_alpha)
+ {
+ m_alpha = alpha;
+ m_bIsDirty = true;
+ }
+}
+
void CSlideShowPic::Move(float fDeltaX, float fDeltaY)
{
m_fZoomLeft += fDeltaX;
diff --git a/xbmc/pictures/SlideShowPicture.h b/xbmc/pictures/SlideShowPicture.h
index 9e2a5d9323..6b480fb166 100644
--- a/xbmc/pictures/SlideShowPicture.h
+++ b/xbmc/pictures/SlideShowPicture.h
@@ -50,7 +50,8 @@ public:
DISPLAY_EFFECT DisplayEffect() const { return m_displayEffect; }
bool DisplayEffectNeedChange(DISPLAY_EFFECT newDispEffect) const;
bool IsStarted() const { return m_iCounter > 0; }
- bool IsFinished() const { return m_bIsFinished; }
+ bool IsFinished() const;
+ bool IsAnimating() const;
bool DrawNextImage() const { return m_bDrawNextImage; }
int GetWidth() const { return (int)m_fWidth; }
@@ -65,6 +66,7 @@ public:
void Zoom(float fZoomAmount, bool immediate = false);
void Rotate(float fRotateAngle, bool immediate = false);
+ void UpdateAlpha();
void Pause(bool bPause);
void SetInSlideshow(bool slideshow);
void SetOriginalSize(int iOriginalWidth, int iOriginalHeight, bool bFullSize);
@@ -95,7 +97,6 @@ private:
int m_iOriginalHeight;
int m_iSlideNumber;
bool m_bIsLoaded;
- bool m_bIsFinished;
bool m_bDrawNextImage;
bool m_bIsDirty;
std::string m_strFileName;