Revert "experimenting with not clearing the framebuffer during emulation"

This reverts commit bd778e3c2b.
This commit is contained in:
thrust26 2023-08-27 22:37:55 +02:00
parent 647f3d48a5
commit 0367923a77
7 changed files with 40 additions and 101 deletions

View File

@ -63,19 +63,6 @@ const string Bezel::getName(int& index) const
return ""; return "";
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
bool Bezel::checkPixel(uInt32 x, uInt32 y) const
{
uInt32 *pixels{nullptr}, pitch;
uInt8 r, g, b, a;
mySurface->basePtr(pixels, pitch);
pixels += x + y * pitch;
myFB.getRGBA(*pixels, &r, &g, &b, &a);
return a != 0; // pixel is not fully transparent
}
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
uInt32 Bezel::borderSize(uInt32 x, uInt32 y, uInt32 size, Int32 step) const uInt32 Bezel::borderSize(uInt32 x, uInt32 y, uInt32 size, Int32 step) const
{ {
@ -102,17 +89,15 @@ bool Bezel::load()
bool isValid = false; bool isValid = false;
#ifdef IMAGE_SUPPORT #ifdef IMAGE_SUPPORT
const bool isShown = myOSystem.eventHandler().inTIAMode() && const bool show = myOSystem.eventHandler().inTIAMode() &&
myOSystem.settings().getBool("bezel.show") && myOSystem.settings().getBool("bezel.show") &&
(myFB.fullScreen() || myOSystem.settings().getBool("bezel.windowed")); (myOSystem.settings().getBool("fullscreen") ||
myOSystem.settings().getBool("bezel.windowed"));
if(mySurface) if(show)
myFB.deallocateSurface(mySurface);
mySurface = nullptr;
if(isShown)
{ {
mySurface = myFB.allocateSurface(1, 1); // dummy size if(!mySurface)
mySurface = myFB.allocateSurface(1, 1); // dummy size
try try
{ {
const string& path = myOSystem.bezelDir().getPath(); const string& path = myOSystem.bezelDir().getPath();
@ -149,7 +134,6 @@ bool Bezel::load()
const Int32 w = mySurface->width(); const Int32 w = mySurface->width();
const Int32 h = mySurface->height(); const Int32 h = mySurface->height();
uInt32 top, bottom, left, right; uInt32 top, bottom, left, right;
bool isRounded;
if(settings.getBool("bezel.win.auto")) if(settings.getBool("bezel.win.auto"))
{ {
@ -162,12 +146,6 @@ bool Bezel::load()
yCenter = (bottom + top) >> 1; yCenter = (bottom + top) >> 1;
left = borderSize(0, yCenter, w, 1); left = borderSize(0, yCenter, w, 1);
right = w - 1 - borderSize(w - 1, yCenter, w, -1); right = w - 1 - borderSize(w - 1, yCenter, w, -1);
// Check if pixels close to the borders are not fully transparent
isRounded = checkPixel(left + w / 100, top + h / 100)
|| checkPixel(right - w / 100, top + h / 100)
|| checkPixel(left + w / 100, bottom - h / 100)
|| checkPixel(right - w / 100, bottom - h / 100);
} }
else else
{ {
@ -179,15 +157,14 @@ bool Bezel::load()
right = w - 1 - std::min(w - 1, static_cast<Int32>(w * settings.getInt("bezel.win.right") / 100. + .5)); right = w - 1 - std::min(w - 1, static_cast<Int32>(w * settings.getInt("bezel.win.right") / 100. + .5));
top = std::min(h - 1, static_cast<Int32>(h * settings.getInt("bezel.win.top") / 100. + .5)); top = std::min(h - 1, static_cast<Int32>(h * settings.getInt("bezel.win.top") / 100. + .5));
bottom = h - 1 - std::min(h - 1, static_cast<Int32>(h * settings.getInt("bezel.win.bottom") / 100. + .5)); bottom = h - 1 - std::min(h - 1, static_cast<Int32>(h * settings.getInt("bezel.win.bottom") / 100. + .5));
isRounded = settings.getBool("bezel.win.rounded");
} }
//cerr << (int)(right - left + 1) << " x " << (int)(bottom - top + 1) << " = " //cerr << (int)(right - left + 1) << " x " << (int)(bottom - top + 1) << " = "
// << double((int)(right - left + 1)) / double((int)(bottom - top + 1)) << endl; // << double((int)(right - left + 1)) / double((int)(bottom - top + 1));
// Disable bezel is no transparent window was found // Disable bezel is no transparent window was found
if (left < right && top < bottom) if (left < right && top < bottom)
myInfo = Info(Common::Size(w, h), Common::Rect(left, top, right + 1, bottom + 1), isRounded); myInfo = Info(Common::Size(w, h), Common::Rect(left, top, right, bottom));
else else
myInfo = Info(); myInfo = Info();
} }
@ -209,11 +186,6 @@ void Bezel::apply()
std::min(myFB.screenSize().h, std::min(myFB.screenSize().h,
static_cast<uInt32>(std::round(myFB.imageRect().h() * myInfo.ratioH()))); static_cast<uInt32>(std::round(myFB.imageRect().h() * myInfo.ratioH())));
//cerr << myInfo.ratioW() << ", " << myInfo.ratioH() << endl;
//cerr << myInfo.size() << "; " << myInfo.window() << endl;
//cerr << myFB.imageRect().size() << "; " << std::round(imageW * myInfo.ratioW()) << endl;
//cerr << "dbl: " << bezelW << " x " << bezelH << endl;
// Position and scale bezel // Position and scale bezel
mySurface->setDstSize(bezelW, bezelH); mySurface->setDstSize(bezelW, bezelH);
mySurface->setDstPos((myFB.screenSize().w - bezelW) / 2, // center mySurface->setDstPos((myFB.screenSize().w - bezelW) / 2, // center
@ -227,12 +199,14 @@ void Bezel::apply()
mySurface->applyAttributes(); mySurface->applyAttributes();
mySurface->setVisible(true); mySurface->setVisible(true);
} }
else
if(mySurface)
mySurface->setVisible(false);
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
void Bezel::render(bool force) void Bezel::render()
{ {
// Only bezels with rounded windows have to be rendered each frame if(mySurface)
if(mySurface && (myInfo.isRounded() || force))
mySurface->render(); mySurface->render();
} }

View File

@ -65,17 +65,15 @@ class Bezel
bool _isShown{false}; // Is bezel shown? bool _isShown{false}; // Is bezel shown?
Common::Size _size{1, 1}; // Bezel size Common::Size _size{1, 1}; // Bezel size
Common::Rect _window{1, 1}; // Area of transparent TIA window inside bezel Common::Rect _window{1, 1}; // Area of transparent TIA window inside bezel
bool _isRounded{false}; // true, if the bezel window has rounded corners
public: public:
explicit Info() = default; explicit Info() = default;
explicit Info(const Common::Size& size, const Common::Rect& window, bool isRounded) explicit Info(Common::Size size, Common::Rect window)
: _isShown{true}, _size{size}, _window{window}, _isRounded{isRounded} { } : _isShown{true}, _size{size}, _window{window} { }
bool isShown() const { return _isShown; } bool isShown() const { return _isShown; }
const Common::Size& size() const { return _size; } Common::Size size() const { return _size; }
const Common::Rect& window() const { return _window; } Common::Rect window() const { return _window; }
bool isRounded() const { return _isRounded; }
// Ratios between bezel sizes and TIA window sizes // Ratios between bezel sizes and TIA window sizes
double ratioW() const { return static_cast<double>(size().w) / window().w(); } double ratioW() const { return static_cast<double>(size().w) / window().w(); }
@ -85,20 +83,12 @@ class Bezel
// Structure access methods // Structure access methods
const Info& info() const { return myInfo; } const Info& info() const { return myInfo; }
bool isShown() const { return myInfo.isShown(); } bool isShown() const { return myInfo.isShown(); }
const Common::Size& size() const { return myInfo.size(); } Common::Size size() const { return myInfo.size(); }
const Common::Rect& window() const { return myInfo.window(); } Common::Rect window() const { return myInfo.window(); }
bool isRounded() const { return myInfo.isRounded(); }
// Ratio between bezel size and TIA window size // Ratio between bezel size and TIA window size
double ratioW() const { return myInfo.ratioW(); } double ratioW() const { return myInfo.ratioW(); }
double ratioH() const { return myInfo.ratioH(); } double ratioH() const { return myInfo.ratioH(); }
/*
Check if a pixel is not fully transparent.
@return true, if pixel is not fully transparent
*/
bool checkPixel(uInt32 x, uInt32 y) const;
/* /*
Calculate size of a bezel border. Calculate size of a bezel border.
*/ */
@ -117,7 +107,7 @@ class Bezel
/* /*
Render bezel surface Render bezel surface
*/ */
void render(bool force); void render();
private: private:
/* /*

View File

@ -63,8 +63,6 @@ const VideoModeHandler::Mode&
// First calculate maximum zoom that keeps aspect ratio // First calculate maximum zoom that keeps aspect ratio
const double scaleX = static_cast<double>(myImage.w) / (myDisplay.w / bezelInfo.ratioW()), const double scaleX = static_cast<double>(myImage.w) / (myDisplay.w / bezelInfo.ratioW()),
scaleY = static_cast<double>(myImage.h) / (myDisplay.h / bezelInfo.ratioH()); scaleY = static_cast<double>(myImage.h) / (myDisplay.h / bezelInfo.ratioH());
// Note: Since the scale value may differ, the bezel may not be scaled to fully size.
// One value might be tiny bit smaller.
double zoom = 1. / std::max(scaleX, scaleY); double zoom = 1. / std::max(scaleX, scaleY);
// When aspect ratio correction is off, we want pixel-exact images, // When aspect ratio correction is off, we want pixel-exact images,
@ -116,7 +114,7 @@ VideoModeHandler::Mode::Mode(uInt32 iw, uInt32 ih, uInt32 sw, uInt32 sh,
: screenS{sw, sh}, : screenS{sw, sh},
stretch{smode}, stretch{smode},
description{desc}, description{desc},
zoom{zoomLevel}, zoom{zoomLevel}, //hZoom{zoomLevel}, vZoom{zoomLevel},
fsIndex{fsindex} fsIndex{fsindex}
{ {
// Now resize based on windowed/fullscreen mode and stretch factor // Now resize based on windowed/fullscreen mode and stretch factor

View File

@ -281,7 +281,7 @@ FBInitStatus FrameBuffer::createDisplay(string_view title, BufferType type,
if(myBufferType == BufferType::Emulator) if(myBufferType == BufferType::Emulator)
{ {
myBezel->load(); // myBezel->load();
// Determine possible TIA windowed zoom levels // Determine possible TIA windowed zoom levels
const double currentTIAZoom = const double currentTIAZoom =
@ -588,7 +588,7 @@ void FrameBuffer::updateInEmulationMode(float framesPerSecond)
// We don't worry about selective rendering here; the rendering // We don't worry about selective rendering here; the rendering
// always happens at the full framerate // always happens at the full framerate
renderTIA(false); // do not clear screen in emulation mode renderTIA();
// Show frame statistics // Show frame statistics
if(myStatsMsg.enabled) if(myStatsMsg.enabled)
@ -967,7 +967,7 @@ void FrameBuffer::renderTIA(bool doClear, bool shade)
myTIASurface->render(shade); myTIASurface->render(shade);
if(myBezel) if(myBezel)
myBezel->render(doClear); // force rendering if framebuffer was cleared myBezel->render();
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
@ -1309,11 +1309,6 @@ FBInitStatus FrameBuffer::applyVideoMode()
const Settings& s = myOSystem.settings(); const Settings& s = myOSystem.settings();
const int display = displayId(); const int display = displayId();
// Get rid of the previous output
myBackend->clear();
myBackend->renderToScreen();
myBackend->clear();
if(s.getBool("fullscreen")) if(s.getBool("fullscreen"))
myVidModeHandler.setDisplaySize(myFullscreenDisplays[display], display); myVidModeHandler.setDisplaySize(myFullscreenDisplays[display], display);
else else
@ -1321,6 +1316,11 @@ FBInitStatus FrameBuffer::applyVideoMode()
const bool inTIAMode = myOSystem.eventHandler().inTIAMode(); const bool inTIAMode = myOSystem.eventHandler().inTIAMode();
#ifdef IMAGE_SUPPORT
if(inTIAMode)
myBezel->load();
#endif
// Build the new mode based on current settings // Build the new mode based on current settings
const VideoModeHandler::Mode& mode const VideoModeHandler::Mode& mode
= myVidModeHandler.buildMode(s, inTIAMode, myBezel->info()); = myVidModeHandler.buildMode(s, inTIAMode, myBezel->info());
@ -1347,23 +1347,14 @@ FBInitStatus FrameBuffer::applyVideoMode()
// Inform TIA surface about new mode, and update TIA settings // Inform TIA surface about new mode, and update TIA settings
if(inTIAMode) if(inTIAMode)
{ {
#ifdef IMAGE_SUPPORT myTIASurface->initialize(myOSystem.console(), myActiveVidMode);
myBezel->apply();
if(!myBezel->info().isRounded())
{
// If the bezel window is not rounded, it has to be rendered only once for each buffer
myBezel->render(true);
myBackend->renderToScreen();
myBezel->render(true);
}
#endif
myTIASurface->initialize(myOSystem.console(), myActiveVidMode);
if(fullScreen()) if(fullScreen())
myOSystem.settings().setValue("tia.fs_stretch", myOSystem.settings().setValue("tia.fs_stretch",
myActiveVidMode.stretch == VideoModeHandler::Mode::Stretch::Fill); myActiveVidMode.stretch == VideoModeHandler::Mode::Stretch::Fill);
else else
myOSystem.settings().setValue("tia.zoom", myActiveVidMode.zoom); myOSystem.settings().setValue("tia.zoom", myActiveVidMode.zoom);
myBezel->apply();
} }
resetSurfaces(); resetSurfaces();

View File

@ -69,7 +69,6 @@ Settings::Settings()
setPermanent("bezel.win.right", "12"); setPermanent("bezel.win.right", "12");
setPermanent("bezel.win.top", "0"); setPermanent("bezel.win.top", "0");
setPermanent("bezel.win.bottom", "0"); setPermanent("bezel.win.bottom", "0");
setPermanent("bezel.win.rounded", "false");
// TIA specific options // TIA specific options
setPermanent("tia.inter", "false"); setPermanent("tia.inter", "false");
setPermanent("tia.zoom", "3"); setPermanent("tia.zoom", "3");
@ -548,14 +547,13 @@ void Settings::usage()
<< " -uimessages <1|0> Show onscreen UI messages for different events\n" << " -uimessages <1|0> Show onscreen UI messages for different events\n"
<< " -pausedim <1|0> Enable emulation dimming in pause mode\n" << " -pausedim <1|0> Enable emulation dimming in pause mode\n"
<< endl << endl
<< " -bezel.show <1|0> Show bezel around emulation window\n" << " -bezel.show <1|0> Show bezel around emulation window\n"
<< " -bezel.windowed <1|0> Show bezel in windowed modes\n" << " -bezel.windowed <1|0> Show bezel in windowed modes\n"
<< " -bezel.win.auto <1|0> Automatically set bezel window position\n" << " -bezel.win.auto <1|0> Automatically set bezel window position\n"
<< " -bezel.win.left <0-40> Set left bezel window position [%]\n" << " -bezel.win.left <0-40> Set left bezel window position [%]\n"
<< " -bezel.win.right <0-40> Set right bezel window position [%]\n" << " -bezel.win.right <0-40> Set right bezel window position [%]\n"
<< " -bezel.win.top <0-40> Set top bezel window position [%]\n" << " -bezel.win.top <0-40> Set top bezel window position [%]\n"
<< " -bezel.win.bottom <0-40> Set bottom bezel window position [%]\n" << " -bezel.win.bottom <0-40> Set bottom bezel window position [%]\n"
<< " -bezel.win.rounded <1|0> Set if the bezel window has rounded borders\n"
<< endl << endl
#ifdef SOUND_SUPPORT #ifdef SOUND_SUPPORT
<< " -audio.enabled <1|0> Enable audio\n" << " -audio.enabled <1|0> Enable audio\n"

View File

@ -519,15 +519,7 @@ void VideoAudioDialog::addBezelTab()
myWinBottomSlider->setTickmarkIntervals(4); myWinBottomSlider->setTickmarkIntervals(4);
wid.push_back(myWinBottomSlider); wid.push_back(myWinBottomSlider);
// Mark bezel windows as rounded (requires rendering each frame)
ypos += lineHeight + VGAP;
myBezelWinRounded = new CheckboxWidget(myTab, _font, xpos, ypos,
"Rounded borders");
myBezelWinRounded->setToolTip("Enable if the bezel window has rounded borders");
wid.push_back(myBezelWinRounded);
// Add items for tab 3 // Add items for tab 3
addToFocusList(wid, myTab, tabID);
myTab->parentWidget(tabID)->setHelpAnchor("VideoAudioBezels"); myTab->parentWidget(tabID)->setHelpAnchor("VideoAudioBezels");
} }
@ -782,7 +774,6 @@ void VideoAudioDialog::loadConfig()
myWinRightSlider->setValue(settings.getInt("bezel.win.right")); myWinRightSlider->setValue(settings.getInt("bezel.win.right"));
myWinTopSlider->setValue(settings.getInt("bezel.win.top")); myWinTopSlider->setValue(settings.getInt("bezel.win.top"));
myWinBottomSlider->setValue(settings.getInt("bezel.win.bottom")); myWinBottomSlider->setValue(settings.getInt("bezel.win.bottom"));
myBezelWinRounded->setState(settings.getBool("bezel.win.rounded"));
handleBezelChange(); handleBezelChange();
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
@ -918,7 +909,6 @@ void VideoAudioDialog::saveConfig()
settings.setValue("bezel.win.right", myWinRightSlider->getValueLabel()); settings.setValue("bezel.win.right", myWinRightSlider->getValueLabel());
settings.setValue("bezel.win.top", myWinTopSlider->getValueLabel()); settings.setValue("bezel.win.top", myWinTopSlider->getValueLabel());
settings.setValue("bezel.win.bottom", myWinBottomSlider->getValueLabel()); settings.setValue("bezel.win.bottom", myWinBottomSlider->getValueLabel());
settings.setValue("bezel.win.rounded", myBezelWinRounded->getState());
// Note: The following has to happen after all video related setting have been saved // Note: The following has to happen after all video related setting have been saved
if(instance().hasConsole()) if(instance().hasConsole())
@ -1237,7 +1227,6 @@ void VideoAudioDialog::handleBezelChange()
myWinRightSlider->setEnabled(enable && nonAuto); myWinRightSlider->setEnabled(enable && nonAuto);
myWinTopSlider->setEnabled(enable && nonAuto); myWinTopSlider->setEnabled(enable && nonAuto);
myWinBottomSlider->setEnabled(enable && nonAuto); myWinBottomSlider->setEnabled(enable && nonAuto);
myBezelWinRounded->setEnabled(enable && nonAuto);
} }
// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

View File

@ -140,7 +140,6 @@ class VideoAudioDialog : public Dialog
SliderWidget* myWinRightSlider{nullptr}; SliderWidget* myWinRightSlider{nullptr};
SliderWidget* myWinTopSlider{nullptr}; SliderWidget* myWinTopSlider{nullptr};
SliderWidget* myWinBottomSlider{nullptr}; SliderWidget* myWinBottomSlider{nullptr};
CheckboxWidget* myBezelWinRounded{nullptr};
// Audio // Audio
CheckboxWidget* mySoundEnableCheckbox{nullptr}; CheckboxWidget* mySoundEnableCheckbox{nullptr};