From 3abdef58bee4133c47a47ca4960c26edeb44fc9c Mon Sep 17 00:00:00 2001 From: Travis Abendshien <46939827+CyanVoxel@users.noreply.github.com> Date: Tue, 5 Aug 2025 00:09:23 -0700 Subject: [PATCH 1/2] ui: add arrow icons for nav buttons --- src/tagstudio/qt/main_window.py | 24 ++++++++++++------ src/tagstudio/qt/resources.json | 8 ++++++ .../resources/qt/images/bxs-left-arrow.png | Bin 0 -> 1985 bytes .../resources/qt/images/bxs-right-arrow.png | Bin 0 -> 2024 bytes 4 files changed, 24 insertions(+), 8 deletions(-) create mode 100644 src/tagstudio/resources/qt/images/bxs-left-arrow.png create mode 100644 src/tagstudio/resources/qt/images/bxs-right-arrow.png diff --git a/src/tagstudio/qt/main_window.py b/src/tagstudio/qt/main_window.py index a70294096..59e86670b 100644 --- a/src/tagstudio/qt/main_window.py +++ b/src/tagstudio/qt/main_window.py @@ -8,9 +8,10 @@ from pathlib import Path import structlog +from PIL import Image, ImageQt from PySide6 import QtCore from PySide6.QtCore import QMetaObject, QSize, QStringListModel, Qt -from PySide6.QtGui import QAction +from PySide6.QtGui import QAction, QPixmap from PySide6.QtWidgets import ( QComboBox, QCompleter, @@ -36,8 +37,10 @@ from tagstudio.core.library.alchemy.enums import SortingModeEnum from tagstudio.qt.controller.widgets.preview_panel_controller import PreviewPanel from tagstudio.qt.flowlayout import FlowLayout +from tagstudio.qt.helpers.color_overlay import theme_fg_overlay from tagstudio.qt.pagination import Pagination from tagstudio.qt.platform_strings import trash_term +from tagstudio.qt.resource_manager import ResourceManager from tagstudio.qt.translations import Translations from tagstudio.qt.widgets.landing import LandingWidget @@ -430,6 +433,7 @@ class MainWindow(QMainWindow): def __init__(self, driver: "QtDriver", parent: QWidget | None = None) -> None: super().__init__(parent) + self.rm = ResourceManager() # region Type declarations for variables that will be initialized in methods # initialized in setup_search_bar @@ -514,23 +518,27 @@ def setup_central_widget(self, driver: "QtDriver"): def setup_search_bar(self): """Sets up Nav Buttons, Search Field, Search Button.""" - nav_button_style = "font-size:14;font-weight:bold;" self.search_bar_layout = QHBoxLayout() self.search_bar_layout.setObjectName("search_bar_layout") self.search_bar_layout.setSizeConstraint(QLayout.SizeConstraint.SetMinimumSize) - self.back_button = QPushButton("<", self.central_widget) + self.back_button = QPushButton(self.central_widget) + back_icon: Image.Image = self.rm.get("bxs-left-arrow") # pyright: ignore[reportAssignmentType] + back_icon = theme_fg_overlay(back_icon, use_alpha=False) + self.back_button.setIcon(QPixmap.fromImage(ImageQt.ImageQt(back_icon))) self.back_button.setObjectName("back_button") - self.back_button.setMinimumSize(QSize(0, 32)) + self.back_button.setMinimumSize(QSize(32, 32)) self.back_button.setMaximumSize(QSize(32, 16777215)) - self.back_button.setStyleSheet(nav_button_style) self.search_bar_layout.addWidget(self.back_button) - self.forward_button = QPushButton(">", self.central_widget) + self.forward_button = QPushButton(self.central_widget) + forward_icon: Image.Image = self.rm.get("bxs-right-arrow") # pyright: ignore[reportAssignmentType] + forward_icon = theme_fg_overlay(forward_icon, use_alpha=False) + self.forward_button.setIcon(QPixmap.fromImage(ImageQt.ImageQt(forward_icon))) + self.forward_button.setIconSize(QSize(16, 16)) self.forward_button.setObjectName("forward_button") - self.forward_button.setMinimumSize(QSize(0, 32)) + self.forward_button.setMinimumSize(QSize(32, 32)) self.forward_button.setMaximumSize(QSize(32, 16777215)) - self.forward_button.setStyleSheet(nav_button_style) self.search_bar_layout.addWidget(self.forward_button) self.search_field = QLineEdit(self.central_widget) diff --git a/src/tagstudio/qt/resources.json b/src/tagstudio/qt/resources.json index c2404889c..5e4138f15 100644 --- a/src/tagstudio/qt/resources.json +++ b/src/tagstudio/qt/resources.json @@ -122,5 +122,13 @@ "thumb_loading": { "path": "qt/images/thumb_loading.png", "mode": "pil" + }, + "bxs-left-arrow": { + "path": "qt/images/bxs-left-arrow.png", + "mode": "pil" + }, + "bxs-right-arrow": { + "path": "qt/images/bxs-right-arrow.png", + "mode": "pil" } } diff --git a/src/tagstudio/resources/qt/images/bxs-left-arrow.png b/src/tagstudio/resources/qt/images/bxs-left-arrow.png new file mode 100644 index 0000000000000000000000000000000000000000..a4cda208db6fa85ebf8eb3758b8601a63997ac17 GIT binary patch literal 1985 zcmah~Yfuwc7+n=R8p>E&P)iZlRTP9|lVCzv6DTAI0fG>oK`RN#hO8vnkX=Z4)duiE zwIYeVrlKHJp(=HBs)!D~Nf1=D{jtg3d(L<6chC3T zyA=uXQEm(`1_VKF(rAes{Il)PtXIHq+Vqjl5ae={NKU8IWpS9AG_X_}G7D!}4JLp? zkTA?@QmJ!r8qUJA38M%ZKG}@Gghqs<@nme7NsQ}==t47|R2ZMEF3eGfXppc_hR})u z0Rv8}V5>oIq%f-pap+>;-9C*Xu!BP9h>&zy0xTxYILu@5SZpMe0SnCN zLJu%X9u)ygBgK492%pd7vYab`qG2GG&=yEkG+=SrTpp7xV6s;vbGaCghq1X#b}+_f zJCq%4a27NwTJ?W?dq=}U5FwLc(F8@4<^so*v(1z6T<6F+)Dw>WhG9pQF_qeGk_a)G zNll&_*Ekjja!!;YwX{WL#>2BgfkjBTR!aao3*ZEM=fYf=%i^<~)=q?2bU2WE`R35^ z)KL48dy<U%;1)(|9-|*2%1((fVxbn z2L$<57bj7&)D~|i}<2nmgon1m1uh(@x?kS4DU+3DTluHLwjM4j#XDC~*@1DaH z+(a)C4WD{pt?wV+{_yen>yBeCN@670RkGy!S^~2WlUnnm2 z8+ucH-Pg?x^~_&y4)0x)ROvC&-EXaGj_WG5agOj^SN7rF{%YU){pAA#_x4qX4BQX> zGuCVG;J1p3%YE~p9`6tU*f9H;>wUOG7gkAyd(j7ne zua7?%<=Y{tJRMyfJUaGuW1;?B(xINKWkbu_tbffMo$JAOyLR^+n-QffD&I=`hf$Dt zcrUs0L|ut4WApJd)pNUTcinCjC$wceh&ooWM$NH`Y#pziSS!Aqbu_zq)ccCqB>QfN zk$->B>R*GIB{KqdWS^mY>Po@)Vzwz-K|zq~8}?@!^zkS2L5cjNlJI1m?N)a{e7kb~ zs@`S1YaM;v(5xkzub>=d`i#KoT~JXAk_fxQQDu@v-^}{0e_3tKy7sXW>1z2{-M(9c z8*6K8{SMtJjq*Fu4Fdg+GGLb=iwP&~4s zSYRs=4h9Qr-Y#=3p3e_0Z(-ebTj&#U_0{2y%EqNfm@$M)(_W8^J*#V48TUSr3vBg? z3}5!rm_;rJB%e36T<}Zr6tG1xDKl>`-!{xV7grM-{xE4v|GeDTGD=D|_!d=fI;641 z7Hd6q3h6_3+OhULt!=0J)OPQ;BHrt7tntl}W)8*5H>47^uQw-btH=~=>Ocbnq+yM_ w?p0(mn)-Hax)3%J6MyHX<&kQD85Bf3n1*|9tmK)yw%WhE(#Uwp;Rt2vzma9g-v9sr literal 0 HcmV?d00001 diff --git a/src/tagstudio/resources/qt/images/bxs-right-arrow.png b/src/tagstudio/resources/qt/images/bxs-right-arrow.png new file mode 100644 index 0000000000000000000000000000000000000000..8f9dcb7963a88559f4fb9c2521507a9c6cb4dfff GIT binary patch literal 2024 zcmah~X;c$e7#+j~gA`Osl><7CML|s_1i~^BC?p6$0s(>oE+r(BWH6ZtnE?VQ6~uD1 zJ+injpe$CaJr)J3wpJ)q>yFd|>N#jZp)Oqz^%NABz61mnZGTKM@7?>|_r3dl@69@C zM2HQ`kp)4JjW|>k4gR^N$7(G2T|DYZJ_Lf^@Ht$>p9T9FlqxJ*v|un8j0A{= zVe}Y^rl+TK(mgnoL5;fm`ud_=9?Ijf0fS9vkc`~OCh3_bi2)4}PAd$Ao*^g_HfhR} zs8mLPAOMF4#c?AstWMH{+XqIVCIofoaM9Q4454}t-Gq#w>opWZ(HcrWw1GF47=lLx z0{h+_VwCIOMV3hZo37Knu??CDP6I{^n)*gguNI(X8G0Oz#%U_mpumIEaFUs6cEaQf zCMArxHcmw7aFPb@3J_19x4`)KfI>=38Dc76%Kx+g*gVd_3ZQ5hh$U1RA~^$CJT8yV=K8R?o-!T}ILO9&3uGM`d&7&64vg+>?_kzRWBB%KcoT$D<3j{D9@%7c0*$x;`gN z`z+zXM^&+{VH4frt6jXpn=%$${Fo;1lr}xTnHAAnYTcR`Exs2^hVHFSNNl*X&6e%+ zCwh&jC~?FZ)*ssN^!XK8O~L$msuL;OYv=6lzj}Xb#rLDOBy>y+ZaLDhvEjoUNackM#(c9|t*SMXY+ISvnLn-d zv(kF^L|*b{udL&UB7mpjHR&X_&aA=K&?;f7%T3$h#xzX zuGz!&tYc%oD{;CyX|f$T*6FF{g(Pe>w6NXr+QUNUnS8j-qpG{T-&(gCvTi?e;$h^A z$PMx}_H6?XB}aarMh~un798r)hJT)IO>+O&tZq7tYemGVQ245=z}gT zTtCim#=Af4_@3O)YHALEV(!1V9M~8D literal 0 HcmV?d00001 From 77a785e6eebfafd986454b15d9b6633c03351cd9 Mon Sep 17 00:00:00 2001 From: Travis Abendshien <46939827+CyanVoxel@users.noreply.github.com> Date: Tue, 5 Aug 2025 00:34:34 -0700 Subject: [PATCH 2/2] ui: use arrow icons for pagination buttons --- src/tagstudio/qt/pagination.py | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/src/tagstudio/qt/pagination.py b/src/tagstudio/qt/pagination.py index fa6d9d5dd..6cf11be96 100644 --- a/src/tagstudio/qt/pagination.py +++ b/src/tagstudio/qt/pagination.py @@ -5,11 +5,14 @@ """A pagination widget created for TagStudio.""" +from PIL import Image, ImageQt from PySide6.QtCore import QObject, QSize, Signal -from PySide6.QtGui import QIntValidator +from PySide6.QtGui import QIntValidator, QPixmap from PySide6.QtWidgets import QHBoxLayout, QLabel, QLineEdit, QSizePolicy, QWidget +from tagstudio.qt.helpers.color_overlay import theme_fg_overlay from tagstudio.qt.helpers.qbutton_wrapper import QPushButtonWrapper +from tagstudio.qt.resource_manager import ResourceManager class Pagination(QWidget, QObject): @@ -19,6 +22,7 @@ class Pagination(QWidget, QObject): def __init__(self, parent=None) -> None: super().__init__(parent) + self.rm = ResourceManager() self.page_count: int = 0 self.current_page_index: int = 0 self.buffer_page_count: int = 4 @@ -39,7 +43,10 @@ def __init__(self, parent=None) -> None: # [<] ---------------------------------- self.prev_button = QPushButtonWrapper() - self.prev_button.setText("<") + prev_icon: Image.Image = self.rm.get("bxs-left-arrow") # pyright: ignore[reportAssignmentType] + prev_icon = theme_fg_overlay(prev_icon, use_alpha=False) + self.prev_button.setIcon(QPixmap.fromImage(ImageQt.ImageQt(prev_icon))) + self.prev_button.setIconSize(QSize(12, 12)) self.prev_button.setMinimumSize(self.button_size) self.prev_button.setMaximumSize(self.button_size) @@ -89,7 +96,10 @@ def __init__(self, parent=None) -> None: # ---------------------------------- [>] self.next_button = QPushButtonWrapper() - self.next_button.setText(">") + next_icon: Image.Image = self.rm.get("bxs-right-arrow") # pyright: ignore[reportAssignmentType] + next_icon = theme_fg_overlay(next_icon, use_alpha=False) + self.next_button.setIcon(QPixmap.fromImage(ImageQt.ImageQt(next_icon))) + self.next_button.setIconSize(QSize(12, 12)) self.next_button.setMinimumSize(self.button_size) self.next_button.setMaximumSize(self.button_size)