audio-reactive-led-strip/python/lib/qfloatslider.py

62 lines
2.1 KiB
Python
Raw Normal View History

from PyQt5 import QtCore, QtGui, QtWidgets
__all__ = ['QFloatSlider']
class QFloatSlider(QtWidgets.QSlider):
"""
Subclass of QtWidgets.QSlider
Horizontal slider giving floating point values.
Usage: QFloatSlider(min, max, step, default)
where min = minimum value of slider
max = maximum value of slider
step = interval between values. Must be a factor of (max-min)
default = default (starting) value of slider
"""
def __init__(self, min_value, max_value, step, default):
super().__init__(QtCore.Qt.Horizontal)
self.precision = 0.001
self.min_value = min_value
self.max_value = max_value
self.step = step
self.default = default
self.quotient, self.remainder = self._float_divmod(\
self.max_value-self.min_value, self.step)
if self.remainder:
raise ValueError("{} does not fit evenly between {} and {}"\
.format(step, min_value, max_value))
super().setMinimum(0)
super().setMaximum(self.quotient)
super().setSingleStep(1)
super().setValue(self._float_to_int(self.default))
super().valueChanged.connect(self._value_handler)
self.slider_value = 2.0
# This is mostly disgusting python i hate floating points >:(
def _float_divmod(self,a,b):
"""
Basically the divmod function but it works for floats (try 0.3 % 0.1 smh)
Returns the quotient, and a remainder.
"""
a = abs(a)
b = abs(b)
n = 1
while True:
c = a - b
c = abs(c)
if c < self.precision:
return (n, 0)
elif c > a:
return (n-1, a)
a = c
n += 1
def _float_to_int(self, a):
return int(round(a/self.step))
def _int_to_float(self, a):
return self.min_value+a*self.step
def _value_handler(self):
self.slider_value = self._int_to_float(super().value())