superqt icon indicating copy to clipboard operation
superqt copied to clipboard

Problem with themes (e.g. qdarkstyle)

Open piplus2 opened this issue 4 years ago • 8 comments

Describe the bug Using global stylesheets (such as qdarkstyle) breaks the QRangeSlider visualization.

To Reproduce Steps to reproduce the behavior: Used the example stylesheet for QLabeledRangeSlider and then set the qdarkstyle style sheet to the MainWindow.

This is my style sheet for the slider:

QSS = """
QSlider {
    min-height: 10px;
}

QSlider::groove:horizontal {
    border: 0px;
    background: qlineargradient(x1:0, y1:0, x2:1, y2:1, stop:0 #888, stop:1 #ddd);
    height: 10px;
    border-radius: 5px;
}

QSlider:focus {
  border: none;
}

QSlider::handle {
    background: qradialgradient(cx:0, cy:0, radius: 1.2, fx:0.35,
                                fy:0.3, stop:0 #eef, stop:1 #002);
    height: 10px;
    width: 10px;
    border-radius: 5px;
}

QSlider::handle:horizontal:hover {
    background: qradialgradient(cx:0, cy:0, radius: 1.2, fx:0.35,
                                fy:0.3, stop:0 #efe, stop:1 #222);
}

QSlider::sub-page:horizontal {
    background: qlineargradient(x1:0, y1:0, x2:1, y2:1, stop:0 #227, stop:1 #77a);
    border-top-left-radius: 5px;
    border-bottom-left-radius: 5px;
}
"""

QSS += """QRangeSlider {
    # This function just defines the stops for the gradient
    qproperty-barColor: """ + gen_style_string_from_hex_colors(
    colormap='viridis') + \
       """\n}"""

This is how I set the qdarkstyle theme:

import qdarkstyle
...
app = QtWidgets.QApplication(sys.argv)
m = MainWindow()
style_sheet = qdarkstyle.load_stylesheet()
m.setStyleSheet(style_sheet)

Screenshots

Without qdarkstyle (I've customized the barColor with a gradient):

image

With qdarkstyle:

image

Desktop (please complete the following information):

  • OS with version = macOS 12.1
  • Qt Backend = PyQt5
  • Python version = 3.9

piplus2 avatar Jan 25 '22 00:01 piplus2

I do encounter the same problem. When I tried to use the qdarkstyle with qrangeslider which has two handles, one of the handle disappear.

jingxuxie avatar Feb 19 '22 00:02 jingxuxie

But I guess this is more about an issue related to the qdarkstyle?

jingxuxie avatar Feb 19 '22 00:02 jingxuxie

After some test, I believe this is not a problem of qdarkstyle, this might be a bug of setting style in _generic_range_slider.py

jingxuxie avatar Feb 19 '22 01:02 jingxuxie

Thanks, yes the range slider does rely on a few internal styles (though, I would have expected it to affect mostly the inner bar color, not the handles themselves, unless qdarkstyle is overriding the handle as well?) I'm aware we need to make qrangeslider a bit more robust to custom styles (see also https://github.com/napari/superqt/issues/35) but I'm afraid I don't have the bandwidth to dig deeper in to this at the moment. Any help debugging would be greatly appreciated here!

tlambert03 avatar Feb 19 '22 02:02 tlambert03

After checking the style.qss file in qdarkstyle. I found that this can be solved by adding the following to the qrangeslider QSS style, this will be consistent with the Light plate in qdarkstyle. You can change the qproperty-barColor so that it has a consistent color with the dark theme:

QSS = """
QSlider{
 background-color: none;
}

QSlider::add-page:vertical {
  background: none;
  border: none;
}

QRangeSlider {
      qproperty-barColor: #9FCBFF;
}

jingxuxie avatar Feb 19 '22 03:02 jingxuxie

Interestingly, the label clipping only occurs when the range is asymmetric (i.e. -5 to 5 shows up fine, but 0 to 5 exhibits clipping). For example (mask threshold symmetric interval, flow threshold asymmetric interval): image I found the primary line in pyqtdarktheme causing this:QAbstractSpinBox {padding: 3px 4px;}. Removing it produces image Now it is legible, but the bar endpoints on the right do not line up. Is there any way to set a fixed width?

kevinjohncutler avatar Aug 25 '22 07:08 kevinjohncutler

thanks @kevinjohncutler ... good find. pixel precise styles with arbitrary style sheets is definitely a challenge!

for what it's worth, i think the key bit of label-positioning code on the superqt side is probable right here:

https://github.com/napari/superqt/blob/e7e8dfc44c4c984126e52385015eed4942519f87/src/superqt/sliders/_labeled.py#L321-L345

I don't have time to play with it at the moment, but if you're so inclined, i think I'd probably start tweaking there.

tlambert03 avatar Aug 25 '22 14:08 tlambert03