[Scummvm-git-logs] scummvm master -> b8e4fb7380605c06bc55d3d14810637bf97d92c7

bluegr noreply at scummvm.org
Sun Jan 23 18:29:02 UTC 2022


This automated email contains information about 5 new commits which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .

Summary:
30a8d927a1 GUI: tabs with scrollbars
4ef38a9255 GUI: tabs with scrollbars
42a27fda40 GUI: tabs with scrollbars for more pages
626b86fcce GUI: fix removeTab not writing back _firstWidget
b8e4fb7380 GUI: fix RTL clip rect for tabs with scrollbars


Commit: 30a8d927a126a5066748171dd7405cb88dc265a9
    https://github.com/scummvm/scummvm/commit/30a8d927a126a5066748171dd7405cb88dc265a9
Author: Die4Ever (die4ever2005 at gmail.com)
Date: 2022-01-23T20:28:55+02:00

Commit Message:
GUI: tabs with scrollbars

Changed paths:
    engines/dialogs.cpp
    gui/editgamedialog.cpp
    gui/object.cpp
    gui/object.h
    gui/themes/common/highres_layout.stx
    gui/themes/common/lowres_layout.stx
    gui/themes/residualvm.zip
    gui/themes/scummclassic.zip
    gui/themes/scummmodern.zip
    gui/themes/scummremastered.zip
    gui/widget.cpp
    gui/widget.h
    gui/widgets/scrollcontainer.cpp
    gui/widgets/tab.cpp
    gui/widgets/tab.h


diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index 437919e402d..5b18deb367c 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -377,7 +377,7 @@ void ConfigDialog::apply() {
 }
 
 ExtraGuiOptionsWidget::ExtraGuiOptionsWidget(GuiObject *containerBoss, const Common::String &name, const Common::String &domain, const ExtraGuiOptions &options) :
-		OptionsContainerWidget(containerBoss, name, dialogLayout(domain), true, domain),
+		OptionsContainerWidget(containerBoss, name, dialogLayout(domain), false, domain),
 		_options(options) {
 
 	for (uint i = 0; i < _options.size(); i++) {
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 4ae6bc65f29..d7efc0ebaf9 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -183,25 +183,21 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 	}
 
 	//
-	// 2) The engine tab (shown only if the engine implements one or there are custom engine options)
+	// 2) The engine's game settings (shown only if the engine implements one or there are custom engine options)
 	//
 
 	if (metaEnginePlugin) {
-		int tabId = tab->addTab(_("Engine"), "GameOptions_Engine");
-
 		const MetaEngineDetection &metaEngineDetection = metaEnginePlugin->get<MetaEngineDetection>();
 		metaEngineDetection.registerDefaultSettings(_domain);
 		if (enginePlugin) {
 			enginePlugin->get<MetaEngine>().registerDefaultSettings(_domain);
-			_engineOptions = enginePlugin->get<MetaEngine>().buildEngineOptionsWidgetDynamic(tab, "GameOptions_Engine.Container", _domain);
+			_engineOptions = enginePlugin->get<MetaEngine>().buildEngineOptionsWidgetDynamic(tab, "GameOptions_Game.Container", _domain);
 		}
 		if (!_engineOptions)
-			_engineOptions = metaEngineDetection.buildEngineOptionsWidgetStatic(tab, "GameOptions_Engine.Container", _domain);
+			_engineOptions = metaEngineDetection.buildEngineOptionsWidgetStatic(tab, "GameOptions_Game.Container", _domain);
 
 		if (_engineOptions) {
 			_engineOptions->setParentDialog(this);
-		} else {
-			tab->removeTab(tabId);
 		}
 	}
 
diff --git a/gui/object.cpp b/gui/object.cpp
index 0f43c8e81b7..f31495df4c6 100644
--- a/gui/object.cpp
+++ b/gui/object.cpp
@@ -58,6 +58,12 @@ void GuiObject::resize(int x, int y, int w, int h, bool scale) {
 	}
 }
 
+Widget *GuiObject::addChild(Widget *newChild) {
+	Widget *oldFirstWidget = _firstWidget;
+	_firstWidget = newChild;
+	return oldFirstWidget;
+}
+
 void GuiObject::reflowLayout() {
 	if (!_name.empty()) {
 		int16 w, h;
diff --git a/gui/object.h b/gui/object.h
index 23c9ec616f6..1d2fd13c2d1 100644
--- a/gui/object.h
+++ b/gui/object.h
@@ -77,6 +77,7 @@ public:
 	virtual void setTextDrawableArea(const Common::Rect &r) { _textDrawableArea = r; }
 
 	virtual void resize(int x, int y, int w, int h, bool scale = true);
+	virtual Widget *addChild(Widget *newChild);
 
 	virtual int16	getRelX() const		{ return _x; }
 	virtual int16	getRelY() const		{ return _y; }
diff --git a/gui/themes/common/highres_layout.stx b/gui/themes/common/highres_layout.stx
index dcc8b4035bd..92df10491b4 100644
--- a/gui/themes/common/highres_layout.stx
+++ b/gui/themes/common/highres_layout.stx
@@ -1328,6 +1328,7 @@
 						type = 'PopUp'
 				/>
 			</layout>
+			<widget name = 'Container'/>
 		</layout>
 	</dialog>
 
@@ -1368,12 +1369,6 @@
 		</layout>
 	</dialog>
 
-	<dialog name = 'GameOptions_Engine' overlays = 'Dialog.GameOptions.TabWidget'>
-		<layout type = 'vertical' padding = '0, 0, 0, 0'>
-			<widget name = 'Container'/>
-		</layout>
-	</dialog>
-
 	<dialog name = 'GlobalMenu' overlays = 'screen_center'>
 		<layout type = 'vertical' padding = '16, 16, 16, 16' align = 'center'>
 			<widget name = 'Logo'
diff --git a/gui/themes/common/lowres_layout.stx b/gui/themes/common/lowres_layout.stx
index ddbf0ff6229..f2a361d4b7b 100644
--- a/gui/themes/common/lowres_layout.stx
+++ b/gui/themes/common/lowres_layout.stx
@@ -1307,6 +1307,7 @@
 						type = 'PopUp'
 				/>
 			</layout>
+			<widget name = 'Container'/>
 		</layout>
 	</dialog>
 
@@ -1347,12 +1348,6 @@
 		</layout>
 	</dialog>
 
-	<dialog name = 'GameOptions_Engine' overlays = 'Dialog.GameOptions.TabWidget'>
-		<layout type = 'vertical' padding = '0, 0, 0, 0'>
-			<widget name = 'Container'/>
-		</layout>
-	</dialog>
-
 	<dialog name = 'GlobalMenu' overlays = 'screen_center'>
 		<layout type = 'vertical' padding = '4, 4, 4, 4' align = 'center' spacing='2'>
 			<widget name = 'Title'
diff --git a/gui/themes/residualvm.zip b/gui/themes/residualvm.zip
index d99b9afbfe5..d66dfeea770 100644
Binary files a/gui/themes/residualvm.zip and b/gui/themes/residualvm.zip differ
diff --git a/gui/themes/scummclassic.zip b/gui/themes/scummclassic.zip
index a947d9c8406..990cace669a 100644
Binary files a/gui/themes/scummclassic.zip and b/gui/themes/scummclassic.zip differ
diff --git a/gui/themes/scummmodern.zip b/gui/themes/scummmodern.zip
index 21716d9cad9..6d9ca48f06a 100644
Binary files a/gui/themes/scummmodern.zip and b/gui/themes/scummmodern.zip differ
diff --git a/gui/themes/scummremastered.zip b/gui/themes/scummremastered.zip
index 39a88aec914..73deee8f61c 100644
Binary files a/gui/themes/scummremastered.zip and b/gui/themes/scummremastered.zip differ
diff --git a/gui/widget.cpp b/gui/widget.cpp
index ad19265ba9b..79bccccd6a0 100644
--- a/gui/widget.cpp
+++ b/gui/widget.cpp
@@ -50,9 +50,7 @@ Widget::Widget(GuiObject *boss, const Common::String &name, const Common::U32Str
 }
 
 void Widget::init() {
-	// Insert into the widget list of the boss
-	_next = _boss->_firstWidget;
-	_boss->_firstWidget = this;
+	_next = _boss->addChild(this);
 	_needsRedraw = true;
 }
 
@@ -1045,10 +1043,15 @@ void OptionsContainerWidget::reflowLayout() {
 	}
 
 	Widget *w = _firstWidget;
+	int16 minY = getAbsY();
+	int maxY = minY;
 	while (w) {
 		w->reflowLayout();
+		minY = MIN(minY, w->getAbsY());
+		maxY = MAX(maxY, w->getAbsY() + w->getHeight());
 		w = w->next();
 	}
+	_h = maxY - minY;
 }
 
 bool OptionsContainerWidget::containsWidget(Widget *widget) const {
diff --git a/gui/widget.h b/gui/widget.h
index 17f7e4bc0ce..08bbde6f0be 100644
--- a/gui/widget.h
+++ b/gui/widget.h
@@ -121,6 +121,7 @@ public:
 	void init();
 
 	void setNext(Widget *w) { _next = w; }
+	void setBoss(GuiObject *newBoss) { _boss = newBoss; }
 	Widget *next() { return _next; }
 
 	int16	getAbsX() const override	{ return _x + _boss->getChildX(); }
diff --git a/gui/widgets/scrollcontainer.cpp b/gui/widgets/scrollcontainer.cpp
index 31b1937887c..b8b8223930d 100644
--- a/gui/widgets/scrollcontainer.cpp
+++ b/gui/widgets/scrollcontainer.cpp
@@ -59,7 +59,6 @@ void ScrollContainerWidget::recalc() {
 
 	//calculate virtual height
 	const int spacing = g_gui.xmlEval()->getVar("Global.Font.Height", 16); //on the bottom
-	int h = 0;
 	int min = spacing, max = 0;
 	Widget *ptr = _firstWidget;
 	while (ptr) {
@@ -70,7 +69,7 @@ void ScrollContainerWidget::recalc() {
 		}
 		ptr = ptr->next();
 	}
-	h = max - min;
+	int h = max - min;
 
 	if (h <= _limitH) _scrolledY = 0;
 	if (_scrolledY > h - _limitH) _scrolledY = 0;
diff --git a/gui/widgets/tab.cpp b/gui/widgets/tab.cpp
index 3e785b738b3..b84d7e515df 100644
--- a/gui/widgets/tab.cpp
+++ b/gui/widgets/tab.cpp
@@ -22,6 +22,7 @@
 #include "common/util.h"
 #include "gui/widgets/tab.h"
 #include "gui/gui-manager.h"
+#include "gui/widgets/scrollcontainer.h"
 
 #include "gui/ThemeEval.h"
 
@@ -90,12 +91,10 @@ TabWidget::~TabWidget() {
 	// having been switched using setActiveTab() afterward, then the
 	// firstWidget in the _tabs list for the active tab may not be up to
 	// date. So update it now.
-	if (_activeTab != -1)
-		_tabs[_activeTab].firstWidget = _firstWidget;
 	_firstWidget = nullptr;
 	for (uint i = 0; i < _tabs.size(); ++i) {
-		delete _tabs[i].firstWidget;
-		_tabs[i].firstWidget = nullptr;
+		delete _tabs[i].scrollWidget;
+		_tabs[i].scrollWidget = nullptr;
 	}
 	_tabs.clear();
 	delete _navRight;
@@ -121,6 +120,7 @@ int TabWidget::addTab(const Common::U32String &title, const Common::String &dial
 	newTab.title = title;
 	newTab.dialogName = dialogName;
 	newTab.firstWidget = nullptr;
+	newTab.scrollWidget = nullptr;
 
 	// Determine the new tab width
 	int newWidth = g_gui.getStringWidth(title) + _titleSpacing;
@@ -132,24 +132,34 @@ int TabWidget::addTab(const Common::U32String &title, const Common::String &dial
 
 	int numTabs = _tabs.size();
 
-	// Activate the new tab
+	// Activate the new tab, also writes back our _firstWidget
 	setActiveTab(numTabs - 1);
 
+	_tabs.back().scrollWidget = new ScrollContainerWidget(this, "", dialogName);
+
 	return _activeTab;
 }
 
+Widget *TabWidget::addChild(Widget *newChild) {
+	if (_activeTab == -1 || _tabs[_activeTab].scrollWidget == nullptr)
+		return Widget::addChild(newChild);
+
+	newChild->setBoss(_tabs[_activeTab].scrollWidget);
+	_firstWidget = newChild;
+	return _tabs[_activeTab].scrollWidget->addChild(newChild);
+}
+
 void TabWidget::removeTab(int tabID) {
 	assert(0 <= tabID && tabID < (int)_tabs.size());
 
 	// Deactivate the tab if it's currently the active one
 	if (tabID == _activeTab) {
-		_tabs[tabID].firstWidget = _firstWidget;
 		releaseFocus();
 		_firstWidget = nullptr;
 	}
 
 	// Dispose the widgets in that tab and then the tab itself
-	delete _tabs[tabID].firstWidget;
+	delete _tabs[tabID].scrollWidget;
 	_tabs.remove_at(tabID);
 
 	// Adjust _firstVisibleTab if necessary
@@ -333,11 +343,13 @@ void TabWidget::reflowLayout() {
 		_tabs[_activeTab].firstWidget = _firstWidget;
 
 	for (uint i = 0; i < _tabs.size(); ++i) {
+		_tabs[i].scrollWidget->setPos(_x, _y);
+		_tabs[i].scrollWidget->setSize(_w, _h);
 		if (!_tabs[i].dialogName.empty()) {
-			g_gui.xmlEval()->reflowDialogLayout(_tabs[i].dialogName, _tabs[i].firstWidget);
+			g_gui.xmlEval()->reflowDialogLayout(_tabs[i].dialogName, _tabs[i].scrollWidget);
 		}
 
-		Widget *w = _tabs[i].firstWidget;
+		Widget *w = _tabs[i].scrollWidget;
 		while (w) {
 			w->reflowLayout();
 			w = w->next();
@@ -396,7 +408,14 @@ void TabWidget::drawWidget() {
 }
 
 void TabWidget::draw() {
-	Widget::draw();
+	if (_activeTab == -1) {
+		Widget::draw();
+	} else {
+		_tabs[_activeTab].firstWidget = _firstWidget;
+		_firstWidget = _tabs[_activeTab].scrollWidget;
+		Widget::draw();
+		_firstWidget = _tabs[_activeTab].firstWidget;
+	}
 
 	if (_navButtonsVisible) {
 		_navLeft->draw();
diff --git a/gui/widgets/tab.h b/gui/widgets/tab.h
index 526dcdb735a..7c2ddd0b5c4 100644
--- a/gui/widgets/tab.h
+++ b/gui/widgets/tab.h
@@ -38,6 +38,7 @@ class TabWidget : public Widget {
 		Common::U32String title;
 		Common::String dialogName;
 		Widget *firstWidget;
+		ScrollContainerWidget *scrollWidget;
 		int _tabWidth;
 	};
 	typedef Common::Array<Tab> TabList;
@@ -77,6 +78,8 @@ public:
 	 */
 	int addTab(const Common::U32String &title, const Common::String &dialogName);
 
+	virtual Widget *addChild(Widget *newChild);
+
 	/**
 	 * Remove the tab with the given tab ID. Disposes all child widgets of that tab.
 	 * TODO: This code is *unfinished*. In particular, it changes the


Commit: 4ef38a92554ac217910689e5666ec028ea09251e
    https://github.com/scummvm/scummvm/commit/4ef38a92554ac217910689e5666ec028ea09251e
Author: Die4Ever (die4ever2005 at gmail.com)
Date: 2022-01-23T20:28:55+02:00

Commit Message:
GUI: tabs with scrollbars

Changed paths:
    gui/ThemeEngine.h
    gui/editgamedialog.cpp
    gui/themes/residualvm.zip
    gui/themes/residualvm/THEMERC
    gui/themes/scummclassic.zip
    gui/themes/scummclassic/THEMERC
    gui/themes/scummclassic/classic_layout.stx
    gui/themes/scummclassic/classic_layout_lowres.stx
    gui/themes/scummmodern.zip
    gui/themes/scummmodern/THEMERC
    gui/themes/scummremastered.zip
    gui/themes/scummremastered/THEMERC
    gui/widgets/tab.cpp
    gui/widgets/tab.h


diff --git a/gui/ThemeEngine.h b/gui/ThemeEngine.h
index adce2894baf..ffb735d14cc 100644
--- a/gui/ThemeEngine.h
+++ b/gui/ThemeEngine.h
@@ -36,7 +36,7 @@
 #include "graphics/pixelformat.h"
 
 
-#define SCUMMVM_THEME_VERSION_STR "SCUMMVM_STX0.9.0"
+#define SCUMMVM_THEME_VERSION_STR "SCUMMVM_STX0.9.1"
 
 class OSystem;
 
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index d7efc0ebaf9..437dab466b8 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -138,7 +138,7 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 	//
 	// 1) The game tab
 	//
-	tab->addTab(_("Game"), "GameOptions_Game");
+	tab->addTab(_("Game"), "GameOptions_Game", true);
 
 	// GUI:  Label & edit widget for the game ID
 	if (g_system->getOverlayWidth() > 320)
diff --git a/gui/themes/residualvm.zip b/gui/themes/residualvm.zip
index d66dfeea770..a62708c072d 100644
Binary files a/gui/themes/residualvm.zip and b/gui/themes/residualvm.zip differ
diff --git a/gui/themes/residualvm/THEMERC b/gui/themes/residualvm/THEMERC
index ab18b13991e..0a96b70c755 100644
--- a/gui/themes/residualvm/THEMERC
+++ b/gui/themes/residualvm/THEMERC
@@ -1,3 +1,3 @@
-[SCUMMVM_STX0.9.0:ResidualVM Modern Theme Remastered:No Author]
+[SCUMMVM_STX0.9.1:ResidualVM Modern Theme Remastered:No Author]
 %using ../common
 %using ../common-svg
diff --git a/gui/themes/scummclassic.zip b/gui/themes/scummclassic.zip
index 990cace669a..456d6921337 100644
Binary files a/gui/themes/scummclassic.zip and b/gui/themes/scummclassic.zip differ
diff --git a/gui/themes/scummclassic/THEMERC b/gui/themes/scummclassic/THEMERC
index 068fbd4b23b..1bd6884510c 100644
--- a/gui/themes/scummclassic/THEMERC
+++ b/gui/themes/scummclassic/THEMERC
@@ -1 +1 @@
-[SCUMMVM_STX0.9.0:ScummVM Classic Theme:No Author]
+[SCUMMVM_STX0.9.1:ScummVM Classic Theme:No Author]
diff --git a/gui/themes/scummclassic/classic_layout.stx b/gui/themes/scummclassic/classic_layout.stx
index d6ee7b57e82..38ab33f591a 100644
--- a/gui/themes/scummclassic/classic_layout.stx
+++ b/gui/themes/scummclassic/classic_layout.stx
@@ -1211,6 +1211,7 @@
 						type = 'PopUp'
 				/>
 			</layout>
+			<widget name = 'Container'/>
 		</layout>
 	</dialog>
 
@@ -1251,12 +1252,6 @@
 		</layout>
 	</dialog>
 
-	<dialog name = 'GameOptions_Engine' overlays = 'Dialog.GameOptions.TabWidget'>
-		<layout type = 'vertical' padding = '0, 0, 0, 0'>
-			<widget name = 'Container'/>
-		</layout>
-	</dialog>
-
 	<dialog name = 'GlobalMenu' overlays = 'screen_center'>
 		<layout type = 'vertical' padding = '16, 16, 16, 16' align = 'center'>
 			<widget name = 'Title'
diff --git a/gui/themes/scummclassic/classic_layout_lowres.stx b/gui/themes/scummclassic/classic_layout_lowres.stx
index 9e8d7d013e7..4a36b19e983 100644
--- a/gui/themes/scummclassic/classic_layout_lowres.stx
+++ b/gui/themes/scummclassic/classic_layout_lowres.stx
@@ -1223,6 +1223,7 @@
 						type = 'PopUp'
 				/>
 			</layout>
+			<widget name = 'Container'/>
 		</layout>
 	</dialog>
 
@@ -1263,12 +1264,6 @@
 		</layout>
 	</dialog>
 
-	<dialog name = 'GameOptions_Engine' overlays = 'Dialog.GameOptions.TabWidget'>
-		<layout type = 'vertical' padding = '0, 0, 0, 0'>
-			<widget name = 'Container'/>
-		</layout>
-	</dialog>
-
 	<dialog name = 'GlobalMenu' overlays = 'screen_center'>
 		<layout type = 'vertical' padding = '2, 2, 2, 6' align = 'center' spacing='0'>
 			<widget name = 'Title'
diff --git a/gui/themes/scummmodern.zip b/gui/themes/scummmodern.zip
index 6d9ca48f06a..62814213591 100644
Binary files a/gui/themes/scummmodern.zip and b/gui/themes/scummmodern.zip differ
diff --git a/gui/themes/scummmodern/THEMERC b/gui/themes/scummmodern/THEMERC
index 6237fb02a0a..cf23ba05de2 100644
--- a/gui/themes/scummmodern/THEMERC
+++ b/gui/themes/scummmodern/THEMERC
@@ -1,2 +1,2 @@
-[SCUMMVM_STX0.9.0:ScummVM Modern Theme:No Author]
+[SCUMMVM_STX0.9.1:ScummVM Modern Theme:No Author]
 %using ../common
diff --git a/gui/themes/scummremastered.zip b/gui/themes/scummremastered.zip
index 73deee8f61c..2dbec536072 100644
Binary files a/gui/themes/scummremastered.zip and b/gui/themes/scummremastered.zip differ
diff --git a/gui/themes/scummremastered/THEMERC b/gui/themes/scummremastered/THEMERC
index e4f9ab08b40..3122cbf07bf 100644
--- a/gui/themes/scummremastered/THEMERC
+++ b/gui/themes/scummremastered/THEMERC
@@ -1,3 +1,3 @@
-[SCUMMVM_STX0.9.0:ScummVM Modern Theme Remastered:No Author]
+[SCUMMVM_STX0.9.1:ScummVM Modern Theme Remastered:No Author]
 %using ../common
 %using ../common-svg
diff --git a/gui/widgets/tab.cpp b/gui/widgets/tab.cpp
index b84d7e515df..7cdc8ba39a3 100644
--- a/gui/widgets/tab.cpp
+++ b/gui/widgets/tab.cpp
@@ -91,10 +91,18 @@ TabWidget::~TabWidget() {
 	// having been switched using setActiveTab() afterward, then the
 	// firstWidget in the _tabs list for the active tab may not be up to
 	// date. So update it now.
+
+	if (_activeTab != -1)
+		_tabs[_activeTab].firstWidget = _firstWidget;
 	_firstWidget = nullptr;
 	for (uint i = 0; i < _tabs.size(); ++i) {
-		delete _tabs[i].scrollWidget;
+		if (_tabs[i].scrollWidget) {
+			delete _tabs[i].scrollWidget;
+		} else {
+			delete _tabs[i].firstWidget;
+		}
 		_tabs[i].scrollWidget = nullptr;
+		_tabs[i].firstWidget = nullptr;
 	}
 	_tabs.clear();
 	delete _navRight;
@@ -114,7 +122,7 @@ uint16 TabWidget::getHeight() const {
 	return _h + _tabHeight;
 }
 
-int TabWidget::addTab(const Common::U32String &title, const Common::String &dialogName) {
+int TabWidget::addTab(const Common::U32String &title, const Common::String &dialogName, bool withScroll) {
 	// Add a new tab page
 	Tab newTab;
 	newTab.title = title;
@@ -135,7 +143,12 @@ int TabWidget::addTab(const Common::U32String &title, const Common::String &dial
 	// Activate the new tab, also writes back our _firstWidget
 	setActiveTab(numTabs - 1);
 
-	_tabs.back().scrollWidget = new ScrollContainerWidget(this, "", dialogName);
+	if (withScroll) {
+		_tabs.back().scrollWidget = new ScrollContainerWidget(this, "", dialogName, 'gtcr');
+		_tabs.back().scrollWidget->setBackgroundType(ThemeEngine::kWidgetBackgroundNo);
+		_tabs.back().scrollWidget->setTarget(this);
+		_firstWidget = _tabs.back().scrollWidget;
+	}
 
 	return _activeTab;
 }
@@ -145,7 +158,6 @@ Widget *TabWidget::addChild(Widget *newChild) {
 		return Widget::addChild(newChild);
 
 	newChild->setBoss(_tabs[_activeTab].scrollWidget);
-	_firstWidget = newChild;
 	return _tabs[_activeTab].scrollWidget->addChild(newChild);
 }
 
@@ -343,16 +355,17 @@ void TabWidget::reflowLayout() {
 		_tabs[_activeTab].firstWidget = _firstWidget;
 
 	for (uint i = 0; i < _tabs.size(); ++i) {
-		_tabs[i].scrollWidget->setPos(_x, _y);
-		_tabs[i].scrollWidget->setSize(_w, _h);
-		if (!_tabs[i].dialogName.empty()) {
-			g_gui.xmlEval()->reflowDialogLayout(_tabs[i].dialogName, _tabs[i].scrollWidget);
-		}
+		if (_tabs[i].scrollWidget) {
+			_tabs[i].scrollWidget->resize(_x, _y, _w, _h, false);
+			_tabs[i].scrollWidget->reflowLayout();
+		} else {
+			g_gui.xmlEval()->reflowDialogLayout(_tabs[i].dialogName, _tabs[i].firstWidget);
 
-		Widget *w = _tabs[i].scrollWidget;
-		while (w) {
-			w->reflowLayout();
-			w = w->next();
+			Widget *w = _tabs[i].firstWidget;
+			while (w) {
+				w->reflowLayout();
+				w = w->next();
+			}
 		}
 	}
 
@@ -408,14 +421,7 @@ void TabWidget::drawWidget() {
 }
 
 void TabWidget::draw() {
-	if (_activeTab == -1) {
-		Widget::draw();
-	} else {
-		_tabs[_activeTab].firstWidget = _firstWidget;
-		_firstWidget = _tabs[_activeTab].scrollWidget;
-		Widget::draw();
-		_firstWidget = _tabs[_activeTab].firstWidget;
-	}
+	Widget::draw();
 
 	if (_navButtonsVisible) {
 		_navLeft->draw();
diff --git a/gui/widgets/tab.h b/gui/widgets/tab.h
index 7c2ddd0b5c4..7b7a7f71f01 100644
--- a/gui/widgets/tab.h
+++ b/gui/widgets/tab.h
@@ -76,7 +76,7 @@ public:
 	 * Add a new tab with the given title. Returns a unique ID which can be used
 	 * to identify the tab (to remove it / activate it etc.).
 	 */
-	int addTab(const Common::U32String &title, const Common::String &dialogName);
+	int addTab(const Common::U32String &title, const Common::String &dialogName, bool withScroll = false);
 
 	virtual Widget *addChild(Widget *newChild);
 


Commit: 42a27fda40b2c46ee27b867b3477ce04bb215de8
    https://github.com/scummvm/scummvm/commit/42a27fda40b2c46ee27b867b3477ce04bb215de8
Author: Die4Ever (die4ever2005 at gmail.com)
Date: 2022-01-23T20:28:55+02:00

Commit Message:
GUI: tabs with scrollbars for more pages

Changed paths:
    engines/dialogs.cpp
    gui/editgamedialog.cpp
    gui/options.cpp
    gui/widget.cpp
    gui/widgets/tab.cpp
    gui/widgets/tab.h


diff --git a/engines/dialogs.cpp b/engines/dialogs.cpp
index 5b18deb367c..b57f20c9ade 100644
--- a/engines/dialogs.cpp
+++ b/engines/dialogs.cpp
@@ -272,7 +272,7 @@ ConfigDialog::ConfigDialog() :
 	// The game specific options tab
 	//
 
-	int tabId = tab->addTab(_("Game"), "GlobalConfig_Engine");
+	int tabId = tab->addTab(_("Game"), "GlobalConfig_Engine", false);
 
 	if (g_engine->hasFeature(Engine::kSupportsChangingOptionsDuringRuntime)) {
 		_engineOptions = metaEngine->buildEngineOptionsWidgetDynamic(tab, "GlobalConfig_Engine.Container", gameDomain);
@@ -315,14 +315,14 @@ ConfigDialog::ConfigDialog() :
 
 	Common::KeymapArray keymaps = metaEngine->initKeymaps(gameDomain.c_str());
 	if (!keymaps.empty()) {
-		tab->addTab(_("Keymaps"), "GlobalConfig_KeyMapper");
+		tab->addTab(_("Keymaps"), "GlobalConfig_KeyMapper", false);
 		addKeyMapperControls(tab, "GlobalConfig_KeyMapper.", keymaps, gameDomain);
 	}
 
 	//
 	// The backend tab (shown only if the backend implements one)
 	//
-	int backendTabId = tab->addTab(_("Backend"), "GlobalConfig_Backend");
+	int backendTabId = tab->addTab(_("Backend"), "GlobalConfig_Backend", false);
 
 	_backendOptions = g_system->buildBackendOptionsWidget(tab, "GlobalConfig_Backend.Container", _domain);
 
@@ -337,11 +337,11 @@ ConfigDialog::ConfigDialog() :
 	//
 	AchMan.setActiveDomain(metaEngine->getAchievementsInfo(gameDomain));
 	if (AchMan.getAchievementCount()) {
-		tab->addTab(_("Achievements"), "GlobalConfig_Achievements");
+		tab->addTab(_("Achievements"), "GlobalConfig_Achievements", false);
 		addAchievementsControls(tab, "GlobalConfig_Achievements.");
 	}
 	if (AchMan.getStatCount()) {
-		tab->addTab(_("Statistics"), "GlobalConfig_Achievements");
+		tab->addTab(_("Statistics"), "GlobalConfig_Achievements", false);
 		addStatisticsControls(tab, "GlobalConfig_Achievements.");
 	}
 
diff --git a/gui/editgamedialog.cpp b/gui/editgamedialog.cpp
index 437dab466b8..259f7b2e7c1 100644
--- a/gui/editgamedialog.cpp
+++ b/gui/editgamedialog.cpp
@@ -138,7 +138,7 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 	//
 	// 1) The game tab
 	//
-	tab->addTab(_("Game"), "GameOptions_Game", true);
+	tab->addTab(_("Game"), "GameOptions_Game");
 
 	// GUI:  Label & edit widget for the game ID
 	if (g_system->getOverlayWidth() > 320)
@@ -204,7 +204,7 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 	//
 	// 3) The graphics tab
 	//
-	_graphicsTabId = tab->addTab(g_system->getOverlayWidth() > 320 ? _("Graphics") : _("GFX"), "GameOptions_Graphics");
+	_graphicsTabId = tab->addTab(g_system->getOverlayWidth() > 320 ? _("Graphics") : _("GFX"), "GameOptions_Graphics", false);
 	ScrollContainerWidget *graphicsContainer = new ScrollContainerWidget(tab, "GameOptions_Graphics.Container", "GameOptions_Graphics_Container", kGraphicsTabContainerReflowCmd);
 	graphicsContainer->setBackgroundType(ThemeEngine::kWidgetBackgroundNo);
 	graphicsContainer->setTarget(this);
@@ -241,14 +241,14 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 	}
 
 	if (!keymaps.empty()) {
-		tab->addTab(_("Keymaps"), "GameOptions_KeyMapper");
+		tab->addTab(_("Keymaps"), "GameOptions_KeyMapper", false);
 		addKeyMapperControls(tab, "GameOptions_KeyMapper.", keymaps, domain);
 	}
 
 	//
 	// The backend tab (shown only if the backend implements one)
 	//
-	int backendTabId = tab->addTab(_("Backend"), "GameOptions_Backend");
+	int backendTabId = tab->addTab(_("Backend"), "GameOptions_Backend", false);
 
 	if (g_system->getOverlayWidth() > 320)
 		_globalBackendOverride = new CheckboxWidget(tab, "GameOptions_Backend.EnableTabCheckbox", _("Override global backend settings"), Common::U32String(), kCmdGlobalBackendOverride);
@@ -367,11 +367,11 @@ EditGameDialog::EditGameDialog(const Common::String &domain)
 		const MetaEngine &metaEngine = enginePlugin->get<MetaEngine>();
 		AchMan.setActiveDomain(metaEngine.getAchievementsInfo(domain));
 		if (AchMan.getAchievementCount()) {
-			tab->addTab(_("Achievements"), "GameOptions_Achievements");
+			tab->addTab(_("Achievements"), "GameOptions_Achievements", false);
 			addAchievementsControls(tab, "GameOptions_Achievements.");
 		}
 		if (AchMan.getStatCount()) {
-			tab->addTab(_("Statistics"), "GameOptions_Achievements");
+			tab->addTab(_("Statistics"), "GameOptions_Achievements", false);
 			addStatisticsControls(tab, "GameOptions_Achievements.");
 		}
 	}
diff --git a/gui/options.cpp b/gui/options.cpp
index 5a2bb6217a0..9e1cb848ccd 100644
--- a/gui/options.cpp
+++ b/gui/options.cpp
@@ -1981,7 +1981,7 @@ void GlobalOptionsDialog::build() {
 	//
 	// 1) The graphics tab
 	//
-	_graphicsTabId = tab->addTab(g_system->getOverlayWidth() > 320 ? _("Graphics") : _("GFX"), "GlobalOptions_Graphics");
+	_graphicsTabId = tab->addTab(g_system->getOverlayWidth() > 320 ? _("Graphics") : _("GFX"), "GlobalOptions_Graphics", false);
 	ScrollContainerWidget *graphicsContainer = new ScrollContainerWidget(tab, "GlobalOptions_Graphics.Container", "GlobalOptions_Graphics_Container", kGraphicsTabContainerReflowCmd);
 	graphicsContainer->setTarget(this);
 	graphicsContainer->setBackgroundType(ThemeEngine::kWidgetBackgroundNo);
@@ -2026,14 +2026,14 @@ void GlobalOptionsDialog::build() {
 	}
 
 	if (!keymaps.empty()) {
-		tab->addTab(_("Keymaps"), "GlobalOptions_KeyMapper");
+		tab->addTab(_("Keymaps"), "GlobalOptions_KeyMapper", false);
 		addKeyMapperControls(tab, "GlobalOptions_KeyMapper.", keymaps, Common::ConfigManager::kKeymapperDomain);
 	}
 
 	//
 	// The backend tab (shown only if the backend implements one)
 	//
-	int backendTabId = tab->addTab(_("Backend"), "GlobalOptions_Backend");
+	int backendTabId = tab->addTab(_("Backend"), "GlobalOptions_Backend", false);
 
 	g_system->registerDefaultSettings(_domain);
 	_backendOptions = g_system->buildBackendOptionsWidget(tab, "GlobalOptions_Backend.Container", _domain);
@@ -2084,9 +2084,9 @@ void GlobalOptionsDialog::build() {
 	// 6) The miscellaneous tab
 	//
 	if (g_system->getOverlayWidth() > 320)
-		tab->addTab(_("Misc"), "GlobalOptions_Misc");
+		tab->addTab(_("Misc"), "GlobalOptions_Misc", false);
 	else
-		tab->addTab(_c("Misc", "lowres"), "GlobalOptions_Misc");
+		tab->addTab(_c("Misc", "lowres"), "GlobalOptions_Misc", false);
 	ScrollContainerWidget *miscContainer = new ScrollContainerWidget(tab, "GlobalOptions_Misc.Container", "GlobalOptions_Misc_Container");
 	miscContainer->setTarget(this);
 	miscContainer->setBackgroundType(ThemeEngine::kWidgetBackgroundNo);
@@ -2098,9 +2098,9 @@ void GlobalOptionsDialog::build() {
 	// 7) The Cloud tab (remote storages)
 	//
 	if (g_system->getOverlayWidth() > 320)
-		tab->addTab(_("Cloud"), "GlobalOptions_Cloud");
+		tab->addTab(_("Cloud"), "GlobalOptions_Cloud", false);
 	else
-		tab->addTab(_c("Cloud", "lowres"), "GlobalOptions_Cloud");
+		tab->addTab(_c("Cloud", "lowres"), "GlobalOptions_Cloud", false);
 
 	ScrollContainerWidget *container = new ScrollContainerWidget(tab, "GlobalOptions_Cloud.Container", "GlobalOptions_Cloud_Container", kCloudTabContainerReflowCmd);
 	container->setTarget(this);
diff --git a/gui/widget.cpp b/gui/widget.cpp
index 79bccccd6a0..87bc6c24d28 100644
--- a/gui/widget.cpp
+++ b/gui/widget.cpp
@@ -1044,7 +1044,7 @@ void OptionsContainerWidget::reflowLayout() {
 
 	Widget *w = _firstWidget;
 	int16 minY = getAbsY();
-	int maxY = minY;
+	int maxY = minY + _h;
 	while (w) {
 		w->reflowLayout();
 		minY = MIN(minY, w->getAbsY());
diff --git a/gui/widgets/tab.cpp b/gui/widgets/tab.cpp
index 7cdc8ba39a3..08770b47c36 100644
--- a/gui/widgets/tab.cpp
+++ b/gui/widgets/tab.cpp
@@ -161,6 +161,14 @@ Widget *TabWidget::addChild(Widget *newChild) {
 	return _tabs[_activeTab].scrollWidget->addChild(newChild);
 }
 
+void TabWidget::removeWidget(Widget *del) {
+	if (_activeTab == -1 || _tabs[_activeTab].scrollWidget == nullptr){
+		Widget::removeWidget(del);
+		return;
+	}
+	_tabs[_activeTab].scrollWidget->removeWidget(del);
+}
+
 void TabWidget::removeTab(int tabID) {
 	assert(0 <= tabID && tabID < (int)_tabs.size());
 
@@ -171,7 +179,11 @@ void TabWidget::removeTab(int tabID) {
 	}
 
 	// Dispose the widgets in that tab and then the tab itself
-	delete _tabs[tabID].scrollWidget;
+	if (_tabs[tabID].scrollWidget) {
+		delete _tabs[tabID].scrollWidget;
+	} else {
+		delete _tabs[tabID].firstWidget;
+	}
 	_tabs.remove_at(tabID);
 
 	// Adjust _firstVisibleTab if necessary
@@ -201,7 +213,10 @@ void TabWidget::setActiveTab(int tabID) {
 			releaseFocus();
 		}
 		_activeTab = tabID;
-		_firstWidget = _tabs[tabID].firstWidget;
+		if (_tabs[tabID].scrollWidget)
+			_firstWidget = _tabs[_activeTab].scrollWidget;
+		else
+			_firstWidget = _tabs[tabID].firstWidget;
 
 		// Also ensure the tab is visible in the tab bar
 		if (_firstVisibleTab > tabID)
diff --git a/gui/widgets/tab.h b/gui/widgets/tab.h
index 7b7a7f71f01..da89917cda9 100644
--- a/gui/widgets/tab.h
+++ b/gui/widgets/tab.h
@@ -76,9 +76,10 @@ public:
 	 * Add a new tab with the given title. Returns a unique ID which can be used
 	 * to identify the tab (to remove it / activate it etc.).
 	 */
-	int addTab(const Common::U32String &title, const Common::String &dialogName, bool withScroll = false);
+	int addTab(const Common::U32String &title, const Common::String &dialogName, bool withScroll = true);
 
 	virtual Widget *addChild(Widget *newChild);
+	virtual void removeWidget(Widget *del);
 
 	/**
 	 * Remove the tab with the given tab ID. Disposes all child widgets of that tab.


Commit: 626b86fccefccd297559aa6c3af75afbcdb370f9
    https://github.com/scummvm/scummvm/commit/626b86fccefccd297559aa6c3af75afbcdb370f9
Author: Die4Ever (die4ever2005 at gmail.com)
Date: 2022-01-23T20:28:55+02:00

Commit Message:
GUI: fix removeTab not writing back _firstWidget

Changed paths:
    gui/widgets/tab.cpp


diff --git a/gui/widgets/tab.cpp b/gui/widgets/tab.cpp
index 08770b47c36..07af143c5fa 100644
--- a/gui/widgets/tab.cpp
+++ b/gui/widgets/tab.cpp
@@ -174,6 +174,7 @@ void TabWidget::removeTab(int tabID) {
 
 	// Deactivate the tab if it's currently the active one
 	if (tabID == _activeTab) {
+		_tabs[tabID].firstWidget = _firstWidget;
 		releaseFocus();
 		_firstWidget = nullptr;
 	}


Commit: b8e4fb7380605c06bc55d3d14810637bf97d92c7
    https://github.com/scummvm/scummvm/commit/b8e4fb7380605c06bc55d3d14810637bf97d92c7
Author: Die4Ever (die4ever2005 at gmail.com)
Date: 2022-01-23T20:28:55+02:00

Commit Message:
GUI: fix RTL clip rect for tabs with scrollbars

Changed paths:
    gui/widget.cpp


diff --git a/gui/widget.cpp b/gui/widget.cpp
index 87bc6c24d28..651ac1d9e38 100644
--- a/gui/widget.cpp
+++ b/gui/widget.cpp
@@ -104,7 +104,8 @@ void Widget::draw() {
 		_y = getAbsY();
 
 		Common::Rect activeRect = g_gui.theme()->getClipRect();
-		oldClip = g_gui.theme()->swapClipRect(_boss->getClipRect().findIntersectingRect(activeRect));
+		Common::Rect clip = _boss->getClipRect().findIntersectingRect(activeRect);
+		oldClip = g_gui.theme()->swapClipRect(clip);
 
 		if (g_gui.useRTL()) {
 			_x = g_system->getOverlayWidth() - _x - _w;
@@ -116,10 +117,8 @@ void Widget::draw() {
 				_x = _x + g_gui.getOverlayOffset();
 			}
 
-			Common::Rect r = _boss->getClipRect();
-			r.moveTo(_x, r.top);
-
-			g_gui.theme()->swapClipRect(r);
+			clip.moveTo(_x, clip.top);
+			g_gui.theme()->swapClipRect(clip);
 		}
 
 		// Draw border




More information about the Scummvm-git-logs mailing list