Criei uma QMenuBar com um QMenu com duas ações. No entanto, não consigo descobrir como estilizar o menu suspenso que aparece.
Minha tentativa de estilizar o menu suspenso simplesmente não está funcionando. Pelo que percebi, QAction não pode receber estilos, então tentei QMenu, mas também não funcionou. Então, não sei como estilizar este menu suspenso...
SO: Windows 11 usando PyQt5
from PyQt5.QtWidgets import QApplication, QWidget, QMenuBar, QMenu, QAction, QVBoxLayout, QMainWindow
class test(QMainWindow):
def __init__(self):
super(test, self).__init__()
self.setWindowTitle('test')
self.resize(200,200)
self.mainWindow = QWidget()
self.mainLayout = QVBoxLayout()
self.bar = QMenuBar()
self.menuItem = QMenu('Help')
self.bar.addMenu(self.menuItem)
self.menuAction = QAction('Action')
self.menuItem.addAction(self.menuAction)
self.mainLayout.addWidget(self.bar)
self.mainWindow.setStyleSheet("""
QWidget {
background-color: #222;
color: #cfcfcf;
font-family: Roboto;
font-size: 14pt;
}
QMenuBar {
background-color: #222;
padding-top: 4px;
}
QMenuBar::item {
border-radius: 4px;
border-width: 0;
padding: 4px 8px;
}
QMenuBar::item:selected {
background-color: #777777;
}
QMenu, QAction {
background-color: red;
border-radius: 4px;
border-width: 0;
}
QMenu::item {
color: blue;
}
QMenu::item:selected {
background-color: aqua;
color: orange;
}
""")
self.mainWindow.setLayout(self.mainLayout)
self.setCentralWidget(self.mainWindow)
if __name__ in '__main__':
app = QApplication([])
main = test()
main.show()
app.exec_()
Seu código tem muitos problemas conceituais, e a maioria deles causa o resultado que você está enfrentando.
Em primeiro lugar, o QMainWindow já fornece uma API de "barra de menus" (consulte
menuBar()
). Você não deve tentar adicionar uma QMenuBar ao widget central, a menos que saiba realmente o que está fazendo.Assim, as Folhas de Estilo Qt são aplicadas a widgets relacionados somente quando estes são filhos do widget em que estão definidos. Criar um QMenu separado que é adicionado a um QMenu ou QMenuBar não cria uma relação pai/filho.
Você está definindo a folha de estilo no
mainWindow
widget, mas estemenuItem
é um QMenu independente que não possui um QMenu pai, portanto, não herdará a folha de estilo. Adicionar um menu "estrangeiro" a outro QMenu ou QMenuBar NÃO tornará esse menu um filho deles.Considerando o exposto acima, a solução mais simples (mas não totalmente apropriada) seria alterar a
setStyleSheet()
chamada para isto:Observe, porém, que isso não seria totalmente apropriado, principalmente porque aplicaria a folha de estilos a qualquer widget do aplicativo, o que pode não ser desejável.
Além disso, um widget não deve ser capaz de definir um aspecto tão global que possa afetar outros widgets não relacionados.
Mesmo ignorando a
menuBar()
API mencionada acima, normalmente é preferível usarQLayout.setMenuBar()
em vez deaddWidget()
. Além disso, a menos que você precise de um uso global/mais flexível de uma ação, você deve usar asaddAction()
sobrecargas do QMenu (como esta ), em vez de adicionar uma QAction criada manualmente.As seguintes alterações resolveriam o problema corretamente:
Observe que deixei a
self.bar
criação do atributo, embora não seja necessária (nem muito apropriada): você poderia simplesmente criar uma variável local (por exemplo:bar = self.menuBar()
) como uma referência de conveniência dentro do contexto da função, mas seria mais apropriado sempre usá-la emself.menuBar()
qualquer outro lugar no contexto da subclasse QMainWindow, a menos que você tenha certeza absoluta de que a barra de menu não será alterada em tempo de execução por outra.Outras questões não relacionadas, mas ainda importantes:
mainWindow
é claramente inapropriado, além de confuso;QWidget {}
seletor) é sempre desencorajado, pois pode afetar a aparência de widgets complexos, como QComboBox, QSlider e áreas de rolagem (veja a nota no final da documentação do Sub-Ccontrols ); não faça isso a menos que você realmente saiba o que está fazendo;super()
dentro do mesmo contexto de classe;exec
, pois não é mais uma palavra-chave protegida no Python 3; livre-se desse caractere, pois esse atributo pode não estar disponível em versões futuras do PyQt;