You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
bastion/libs/StdUi/widgets/Slider.lua

295 lines
8.5 KiB

--- @type StdUi
local StdUi = LibStub and LibStub('StdUi', true);
if not StdUi then
return
end
local module, version = 'Slider', 7;
if not StdUi:UpgradeNeeded(module, version) then return end
----------------------------------------------------
--- SliderButton
----------------------------------------------------
function StdUi:SliderButton(parent, width, height, direction)
local button = self:Button(parent, width, height);
local texture = self:ArrowTexture(button, direction);
texture:SetPoint('CENTER');
local textureDisabled = self:ArrowTexture(button, direction);
textureDisabled:SetPoint('CENTER');
textureDisabled:SetDesaturated(0);
button:SetNormalTexture(texture);
button:SetDisabledTexture(textureDisabled);
return button;
end
----------------------------------------------------
--- StyleScrollBar
----------------------------------------------------
--- This is only useful for scrollBars not created using StdUi
function StdUi:StyleScrollBar(scrollBar)
local buttonUp, buttonDown = scrollBar:GetChildren();
scrollBar.background = StdUi:Panel(scrollBar);
scrollBar.background:SetFrameLevel(scrollBar:GetFrameLevel() - 1);
scrollBar.background:SetWidth(scrollBar:GetWidth());
self:GlueAcross(scrollBar.background, scrollBar, 0, 1, 0, -1);
self:StripTextures(buttonUp);
self:StripTextures(buttonDown);
self:ApplyBackdrop(buttonUp, 'button');
self:ApplyBackdrop(buttonDown, 'button');
buttonUp:SetWidth(scrollBar:GetWidth());
buttonDown:SetWidth(scrollBar:GetWidth());
local upTex = self:ArrowTexture(buttonUp, 'UP');
upTex:SetPoint('CENTER');
local upTexDisabled = self:ArrowTexture(buttonUp, 'UP');
upTexDisabled:SetPoint('CENTER');
upTexDisabled:SetDesaturated(0);
buttonUp:SetNormalTexture(upTex);
buttonUp:SetDisabledTexture(upTexDisabled);
local downTex = self:ArrowTexture(buttonDown, 'DOWN');
downTex:SetPoint('CENTER');
local downTexDisabled = self:ArrowTexture(buttonDown, 'DOWN');
downTexDisabled:SetPoint('CENTER');
downTexDisabled:SetDesaturated(0);
buttonDown:SetNormalTexture(downTex);
buttonDown:SetDisabledTexture(downTexDisabled);
local thumbSize = scrollBar:GetWidth();
scrollBar:GetThumbTexture():SetWidth(thumbSize);
self:StripTextures(scrollBar);
scrollBar.thumb = self:Panel(scrollBar);
scrollBar.thumb:SetAllPoints(scrollBar:GetThumbTexture());
self:ApplyBackdrop(scrollBar.thumb, 'button');
end
----------------------------------------------------
--- Slider
----------------------------------------------------
local SliderMethods = {
SetPrecision = function(self, numberOfDecimals)
self.precision = numberOfDecimals;
end,
GetPrecision = function(self)
return self.precision;
end,
GetValue = function(self)
local minimum, maximum = self:GetMinMaxValues();
return Clamp(StdUi.Util.roundPrecision(self:OriginalGetValue(), self.precision), minimum, maximum);
end
};
local SliderEvents = {
OnValueChanged = function(self, value, ...)
if self.lock then return end
self.lock = true;
value = self:GetValue();
if self.OnValueChanged then
self:OnValueChanged(value, ...);
end
self.lock = false;
end
}
function StdUi:Slider(parent, width, height, value, vertical, min, max)
local slider = CreateFrame('Slider', nil, parent);
self:InitWidget(slider);
self:ApplyBackdrop(slider, 'panel');
self:SetObjSize(slider, width, height);
slider.vertical = vertical;
slider.precision = 1;
local thumbWidth = vertical and width or 20;
local thumbHeight = vertical and 20 or height;
slider.ThumbTexture = self:Texture(slider, thumbWidth, thumbHeight, self.config.backdrop.texture);
slider.ThumbTexture:SetVertexColor(
self.config.backdrop.slider.r,
self.config.backdrop.slider.g,
self.config.backdrop.slider.b,
self.config.backdrop.slider.a
);
slider:SetThumbTexture(slider.ThumbTexture);
slider.thumb = self:Frame(slider);
slider.thumb:SetAllPoints(slider:GetThumbTexture());
self:ApplyBackdrop(slider.thumb, 'button');
if vertical then
slider:SetOrientation('VERTICAL');
slider.ThumbTexture:SetPoint('LEFT');
slider.ThumbTexture:SetPoint('RIGHT');
else
slider:SetOrientation('HORIZONTAL');
slider.ThumbTexture:SetPoint('TOP');
slider.ThumbTexture:SetPoint('BOTTOM');
end
slider.OriginalGetValue = slider.GetValue;
for k, v in pairs(SliderMethods) do
slider[k] = v;
end
slider:SetMinMaxValues(min or 0, max or 100);
slider:SetValue(value or min or 0);
for k, v in pairs(SliderEvents) do
slider:HookScript(k, v);
end
return slider;
end
----------------------------------------------------
--- SliderWithBox
----------------------------------------------------
local SliderWithBoxMethods = {
SetValue = function(self, v)
self.lock = true;
self.slider:SetValue(v);
v = self.slider:GetValue();
self.editBox:SetValue(v);
self.value = v;
self.lock = false;
if self.OnValueChanged then
self.OnValueChanged(self, v);
end
end,
GetValue = function(self)
return self.value;
end,
SetValueStep = function(self, step)
self.slider:SetValueStep(step);
end,
SetPrecision = function(self, numberOfDecimals)
self.slider.precision = numberOfDecimals;
end,
GetPrecision = function(self)
return self.slider.precision;
end,
SetMinMaxValues = function(self, min, max)
self.min = min;
self.max = max;
self.editBox:SetMinMaxValue(min, max);
self.slider:SetMinMaxValues(min, max);
self.leftLabel:SetText(min);
self.rightLabel:SetText(max);
end
};
local SliderWithBoxOnValueChanged = function(self, val)
if self.widget.lock then return end;
self.widget:SetValue(val);
end
function StdUi:SliderWithBox(parent, width, height, value, min, max)
local widget = CreateFrame('Frame', nil, parent);
self:SetObjSize(widget, width, height);
widget.slider = self:Slider(widget, 100, 12, value, false);
widget.editBox = self:NumericBox(widget, 80, 16, value);
widget.value = value;
widget.editBox:SetNumeric(false);
widget.leftLabel = self:Label(widget, '');
widget.rightLabel = self:Label(widget, '');
widget.slider.widget = widget;
widget.editBox.widget = widget;
for k, v in pairs(SliderWithBoxMethods) do
widget[k] = v;
end
if min and max then
widget:SetMinMaxValues(min, max);
end
widget.slider.OnValueChanged = SliderWithBoxOnValueChanged;
widget.editBox.OnValueChanged = SliderWithBoxOnValueChanged;
widget.slider:SetPoint('TOPLEFT', widget, 'TOPLEFT', 0, 0);
widget.slider:SetPoint('TOPRIGHT', widget, 'TOPRIGHT', 0, 0);
self:GlueBelow(widget.editBox, widget.slider, 0, -5, 'CENTER');
widget.leftLabel:SetPoint('TOPLEFT', widget.slider, 'BOTTOMLEFT', 0, 0);
widget.rightLabel:SetPoint('TOPRIGHT', widget.slider, 'BOTTOMRIGHT', 0, 0);
return widget;
end
----------------------------------------------------
--- ScrollBar
----------------------------------------------------
function StdUi:ScrollBar(parent, width, height, horizontal)
local panel = self:Panel(parent, width, height);
local scrollBar = self:Slider(parent, width, height, 0, not horizontal);
scrollBar.ScrollDownButton = self:SliderButton(parent, width, 16, 'DOWN');
scrollBar.ScrollUpButton = self:SliderButton(parent, width, 16, 'UP');
scrollBar.panel = panel;
scrollBar.ScrollUpButton.scrollBar = scrollBar;
scrollBar.ScrollDownButton.scrollBar = scrollBar;
if horizontal then
--@TODO do this
--scrollBar.ScrollUpButton:SetPoint('TOPLEFT', panel, 'TOPLEFT', 0, 0);
--scrollBar.ScrollUpButton:SetPoint('TOPRIGHT', panel, 'TOPRIGHT', 0, 0);
--
--scrollBar.ScrollDownButton:SetPoint('BOTTOMLEFT', panel, 'BOTTOMLEFT', 0, 0);
--scrollBar.ScrollDownButton:SetPoint('BOTTOMRIGHT', panel, 'BOTTOMRIGHT', 0, 0);
--
--scrollBar:SetPoint('TOPLEFT', scrollBar.ScrollUpButton, 'TOPLEFT', 0, 1);
--scrollBar:SetPoint('TOPRIGHT', scrollBar.ScrollUpButton, 'TOPRIGHT', 0, 1);
--scrollBar:SetPoint('BOTTOMLEFT', scrollBar.ScrollDownButton, 'BOTTOMLEFT', 0, -1);
--scrollBar:SetPoint('BOTTOMRIGHT', scrollBar.ScrollDownButton, 'BOTTOMRIGHT', 0, -1);
else
scrollBar.ScrollUpButton:SetPoint('TOPLEFT', panel, 'TOPLEFT', 0, 0);
scrollBar.ScrollUpButton:SetPoint('TOPRIGHT', panel, 'TOPRIGHT', 0, 0);
scrollBar.ScrollDownButton:SetPoint('BOTTOMLEFT', panel, 'BOTTOMLEFT', 0, 0);
scrollBar.ScrollDownButton:SetPoint('BOTTOMRIGHT', panel, 'BOTTOMRIGHT', 0, 0);
scrollBar:SetPoint('TOPLEFT', scrollBar.ScrollUpButton, 'BOTTOMLEFT', 0, 1);
scrollBar:SetPoint('TOPRIGHT', scrollBar.ScrollUpButton, 'BOTTOMRIGHT', 0, 1);
scrollBar:SetPoint('BOTTOMLEFT', scrollBar.ScrollDownButton, 'TOPLEFT', 0, -1);
scrollBar:SetPoint('BOTTOMRIGHT', scrollBar.ScrollDownButton, 'TOPRIGHT', 0, -1);
end
return scrollBar, panel;
end
StdUi:RegisterModule(module, version);