def __range_to_pos(self, value):
qt_options = QtGui.QStyleOptionSlider()
self.initStyleOption(qt_options)
style = QtGui.QApplication.style()
gr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderGroove, self)
sr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderHandle, self)
if self.orientation() == QtCore.Qt.Horizontal:
slider_length = sr.width()
slider_min = gr.x()
slider_max = gr.right() - slider_length + 1
else:
slider_length = sr.height()
slider_min = gr.y()
slider_max = gr.bottom() - slider_length + 1
return style.sliderValueFromPosition(
self.minimum(),
self.maximum(),
value,
slider_max - slider_min,
qt_options.upsideDown
)
def __range_to_pos(self, value):
i_percent_interval = 100.0 / (self.maximum() - 1.0)
# Size from orientation
if self.orientation() == QtCore.Qt.Horizontal:
f_size = self.rect().width()
else:
f_size = self.rect().height()
# Calculate offset
qt_font_metric = QtGui.QPainter(self).fontMetrics()
f_text_size = float(qt_font_metric.width(str(value)))
i_percent_offset = (f_text_size / f_size) * 100.0
f_offset = f_size / 100.0 * i_percent_offset
if value == 0:
f_offset = 0.0
elif value != self.maximum() - 1:
f_offset /= 2.0
# Position
x_pos = f_size / 100.0 * (i_percent_interval * value)
if self.orientation() == QtCore.Qt.Horizontal:
qt_pos = QtCore.QPoint(x_pos - f_offset, self.rect().bottom())
else:
qt_pos = QtCore.QPoint(self.rect().bottom(), x_pos - f_offset)
return qt_pos
Hello everyone, I have a little problem with the PySide QSlider. I'm trying to draw text on the ticks of my QSlider. I saw that we could use "sliderValueFromPosition" to find the position but impossible to make it work correctly ... It always returns 0. I'll show you my code.
def __range_to_pos(self, value):
qt_options = QtGui.QStyleOptionSlider()
self.initStyleOption(qt_options)
style = QtGui.QApplication.style()
gr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderGroove, self)
sr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderHandle, self)
if self.orientation() == QtCore.Qt.Horizontal:
slider_length = sr.width()
slider_min = gr.x()
slider_max = gr.right() - slider_length + 1
else:
slider_length = sr.height()
slider_min = gr.y()
slider_max = gr.bottom() - slider_length + 1
return style.sliderValueFromPosition(
self.minimum(),
self.maximum(),
value,
slider_max - slider_min,
qt_options.upsideDown
)
from PySide import QtCore, QtGui
slider = QtGui.QSlider()
slider.setRange(0,100)
slider.resize(200,30)
slider.setOrientation(QtCore.Qt.Horizontal)
slider.show()
slider.raise_()
qt_options = QtGui.QStyleOptionSlider()
slider.initStyleOption(qt_options)
style = QtGui.QApplication.style()
gr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderGroove, slider)
sr = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderHandle, slider)
if slider.orientation() == QtCore.Qt.Horizontal:
slider_length = sr.width()
slider_min = gr.x()
slider_max = gr.right() - slider_length + 1
else:
slider_length = sr.height()
slider_min = gr.y()
slider_max = gr.bottom() - slider_length + 1
pos = 100
ret = style.sliderValueFromPosition(
slider.minimum(),
slider.maximum(),
pos,
slider_max - slider_min,
qt_options.upsideDown
)
print ret
# 53
--
You received this message because you are subscribed to the Google Groups "Python Programming for Autodesk Maya" group.
To unsubscribe from this group and stop receiving emails from it, send an email to python_inside_m...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/python_inside_maya/9e2f012c-0fad-4687-81e6-d6561c2bdfed%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
# ================================================================================# Import Modules# ================================================================================
import osimport sys
from PySide import QtGui, QtCore
# ==========================================================# TreeView# ==========================================================
class RDSlider(QtGui.QSlider):
# ====================================================== # Init # ======================================================
def __init__(self, qt_orientation=QtCore.Qt.Horizontal, qt_parent=None, **kwargs): super(RDSlider, self).__init__(qt_orientation, qt_parent)
# Init UI self.setMinimum(kwargs.get("min", 0)) self.setMaximum(kwargs.get("max", 10)) self.setSingleStep(1) self.setPageStep(1) if kwargs.get("ticks", True) is True: self.setTickPosition(kwargs.get("ticks_position", QtGui.QSlider.TicksBelow))
self.__b_range_slider = kwargs.get("range_slider", False) self.__b_ticks_text = kwargs.get("ticks_text", False)
# Range slider self.__low = self.minimum() self.__high = self.maximum() self.__pressed_control = QtGui.QStyle.SC_None self.__hover_control = QtGui.QStyle.SC_None self.__click_offset = 0 self.__active_slider = 0
# ====================================================== # QT EVENT # ======================================================
def paintEvent(self, event):
event.accept()
qt_painter = QtGui.QPainter(self) style = QtGui.QApplication.style()
# ================================================== # For range slider
if self.__b_range_slider is True:
for i, value in enumerate([self.__low, self.__high]):
qt_options = QtGui.QStyleOptionSlider() self.initStyleOption(qt_options)
qt_options.subControls = QtGui.QStyle.SC_SliderHandle
if self.tickPosition() != self.NoTicks: qt_options.subControls |= QtGui.QStyle.SC_SliderTickmarks
if self.__pressed_control: qt_options.activeSubControls = self.__pressed_control qt_options.state |= QtGui.QStyle.State_Sunken else: qt_options.activeSubControls = self.__hover_control
qt_options.sliderPosition = value qt_options.sliderValue = value style.drawComplexControl(QtGui.QStyle.CC_Slider, qt_options, qt_painter, self)
else:
super(RDSlider, self).paintEvent(event)
# ================================================== # For text
if self.__b_ticks_text is True:
i_range = (self.maximum() - self.minimum()) + 1 for i in xrange(i_range):
# Get text and offset s_text = "toto %s" % i i_text_offset = -self.__get_text_offset(s_text)
if i == 0: i_text_offset = 0.0 elif i != i_range - 1: i_text_offset /= 2.0
# Draw text if self.orientation() == QtCore.Qt.Horizontal: qt_pos = QtCore.QPoint(self.__get_pos_from_value(i) + i_text_offset, self.rect().bottom()) else: qt_pos = QtCore.QPoint(self.rect().left(), self.__get_pos_from_value(i) + i_text_offset)
qt_painter.drawText(qt_pos, s_text)
def mousePressEvent(self, event):
if self.__b_range_slider is True:
event.accept() style = QtGui.QApplication.style() button = event.button() # In a normal slider control, when the user clicks on a point in the # slider's total range, but not on the slider part of the control the # control would jump the slider value to where the user clicked. # For this control, clicks which are not direct hits will slide both # slider parts if button:
qt_options = QtGui.QStyleOptionSlider() self.initStyleOption(qt_options)
self.__active_slider = -1 for i, value in enumerate([self.__low, self.__high]):
qt_options.sliderPosition = value hit = style.hitTestComplexControl(style.CC_Slider, qt_options, event.pos(), self)
if hit == style.SC_SliderHandle: self.__active_slider = i self.__pressed_control = hit self.triggerAction(self.SliderMove) self.setRepeatAction(self.SliderNoAction) self.setSliderDown(True) break
if self.__active_slider < 0: self.__pressed_control = QtGui.QStyle.SC_SliderHandle self.__click_offset = self.__get_value_from_pos(self.__pick(event.pos())) self.triggerAction(self.SliderMove) self.setRepeatAction(self.SliderNoAction)
else:
event.ignore()
else:
super(RDSlider, self).mousePressEvent(event) event.ignore()
def mouseMoveEvent(self, event):
if self.__b_range_slider is True:
if self.__pressed_control != QtGui.QStyle.SC_SliderHandle: event.ignore() return event.accept()
new_pos = self.__get_value_from_pos(self.__pick(event.pos()))
qt_options = QtGui.QStyleOptionSlider() self.initStyleOption(qt_options) if self.__active_slider < 0:
offset = new_pos - self.__click_offset self.__high += offset self.__low += offset
if self.__low < self.minimum(): diff = self.minimum() - self.__low self.__low += diff self.__high += diff
if self.__high > self.maximum(): diff = self.maximum() - self.__high self.__low += diff self.__high += diff
elif self.__active_slider == 0:
if new_pos >= self.__high: new_pos = self.__high - 1 self.__low = new_pos
else:
if new_pos <= self.__low: new_pos = self.__low + 1 self.__high = new_pos
self.__click_offset = new_pos
self.update()
self.emit(QtCore.SIGNAL('sliderMoved(int)'), new_pos)
else:
super(RDSlider, self).mouseMoveEvent(event) event.ignore()
# ====================================================== # MISC # ======================================================
def __pick(self, qt_point):
""" !@Brief Mouse position from slider orientation
@type qt_point: QtGui.QPoint @param qt_point: Mouse position
@rtype: float @return: Value X or Y from slider orientation. """
if self.orientation() == QtCore.Qt.Horizontal: return qt_point.x() else: return qt_point.y()
def __get_pos_from_value(self, i_value): """ !@Brief Get Pixel position of slider ticks.
@type i_value: int @param i_value: Tick value.
@rtype: int @return: Tick pixel position. """
qt_options = QtGui.QStyleOptionSlider() self.initStyleOption(qt_options) qt_style = QtGui.QApplication.style() slider_groove = qt_style.subControlRect(qt_style.CC_Slider, qt_options, qt_style.SC_SliderGroove, self) slider_handle = qt_style.subControlRect(qt_style.CC_Slider, qt_options, qt_style.SC_SliderHandle, self) if self.orientation() == QtCore.Qt.Horizontal: slider_length = slider_handle.width() slider_min = slider_groove.x() slider_max = slider_groove.right() - slider_length + 1 else: slider_length = slider_handle.height() slider_min = slider_groove.y() slider_max = slider_groove.bottom() - slider_length + 1 return qt_style.sliderPositionFromValue( self.minimum(), self.maximum(), i_value,
slider_max - slider_min, qt_options.upsideDown )
def __get_value_from_pos(self, f_pos):
""" !@Brief Get Tick value from position.
@type f_pos: float @param f_pos: Mouse position.
@rtype: int @return: Tick value.
"""
qt_options = QtGui.QStyleOptionSlider() self.initStyleOption(qt_options) style = QtGui.QApplication.style()
slider_groove = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderGroove, self) slider_handle = style.subControlRect(style.CC_Slider, qt_options, style.SC_SliderHandle, self) if self.orientation() == QtCore.Qt.Horizontal: slider_length = slider_handle.width() slider_min = slider_groove.x() slider_max = slider_groove.right() - slider_length + 1 else: slider_length = slider_handle.height() slider_min = slider_groove.y() slider_max = slider_groove.bottom() - slider_length + 1 return style.sliderValueFromPosition( self.minimum(), self.maximum(), f_pos - slider_min,
slider_max - slider_min, qt_options.upsideDown )
def __get_text_offset(self, s_text):
""" !@Brief Get text length offset.
@type s_text: string @param s_text: Text for get size.
@rtype: int @return: Offset length.
"""
# Size from orientation if self.orientation() == QtCore.Qt.Horizontal: f_size = self.rect().width() else: f_size = self.rect().height()
qt_painter = QtGui.QPainter(self) qt_font_metric = qt_painter.fontMetrics() f_text_size = float(qt_font_metric.width(s_text))
i_percent_offset = (f_text_size / f_size) * 100.0 f_offset = f_size / 100.0 * i_percent_offset
return f_offset
# =============================================================# INIT Script# =============================================================
def main():
""" !@Brief Main function for launch ui. """
app = QtGui.QApplication(sys.argv) slider = RDSlider(min=0, max=6, range_slider=True) slider.show() sys.exit(app.exec_())
if __name__ == '__main__': main()