diff --git a/WeakAuras/BaseRegions/Texture.lua b/WeakAuras/BaseRegions/Texture.lua new file mode 100644 index 0000000..e5502bc --- /dev/null +++ b/WeakAuras/BaseRegions/Texture.lua @@ -0,0 +1,126 @@ +if not WeakAuras.IsLibsOK() then return end + +local AddonName, Private = ... + +local L = WeakAuras.L + +Private.TextureBase = {} + +local SQRT2 = sqrt(2) +local function GetRotatedPoints(degrees, scaleForFullRotate) + local angle = rad(135 - degrees) + local factor = scaleForFullRotate and 1 or SQRT2 + local vx = math.cos(angle) / factor + local vy = math.sin(angle) / factor + + return 0.5+vx,0.5-vy , 0.5-vy,0.5-vx , 0.5+vy,0.5+vx , 0.5-vx,0.5+vy +end + +local funcs = { + ClearAllPoints = function(self) + self.texture:ClearAllPoints() + end, + + SetAllPoints = function(self, ...) + self.texture:SetAllPoints(...) + end, + + DoTexCoord = function(self) + local mirror_h, mirror_v = self.mirror_h, self.mirror_v + if(self.mirror) then + mirror_h = not mirror_h + end + local ulx,uly , llx,lly , urx,ury , lrx,lry + = GetRotatedPoints(self.effectiveRotation, self.canRotate) + if(mirror_h) then + if(mirror_v) then + self.texture:SetTexCoord(lrx,lry , urx,ury , llx,lly , ulx,uly) + else + self.texture:SetTexCoord(urx,ury , lrx,lry , ulx,uly , llx,lly) + end + else + if(mirror_v) then + self.texture:SetTexCoord(llx,lly , ulx,uly , lrx,lry , urx,ury) + else + self.texture:SetTexCoord(ulx,uly , llx,lly , urx,ury , lrx,lry) + end + end + end, + + SetMirrorFromScale = function(self, h, v) + if self.mirror_h == h and self.mirror_v == v then + return + end + self.mirror_h = h + self.mirror_v = v + self:DoTexCoord() + end, + + SetMirror = function(self, b) + if self.mirror == b then + return + end + self.mirror = b + self:DoTexCoord() + end, + + SetTexture = function(self, file) + self.textureName = file + self.texture:SetTexture(file) + self:DoTexCoord() + end, + + SetVertexColor = function(self, r, g, b, a) + self.texture:SetVertexColor(r, g, b,a) + end, + + SetDesaturated = function(self, b) + self.texture:SetDesaturated(b) + end, + + SetAnimRotation = function(self, degrees) + self.animRotation = degrees + self:UpdateEffectiveRotation() + end, + + SetRotation = function(self, degrees) + self.rotation = degrees + self:UpdateEffectiveRotation() + end, + + UpdateEffectiveRotation = function(self) + self.effectiveRotation = self.animRotation or self.rotation + self:DoTexCoord() + end, + + GetBaseRotation = function(self) + return self.rotation + end +} + +function Private.TextureBase.create(frame) + local base = {} + + for funcName, func in pairs(funcs) do + base[funcName] = func + end + + local texture = frame:CreateTexture() + + base.texture = texture + + return base +end + +-- TODO better type for options +function Private.TextureBase.modify(base, options) + base.canRotate = options.canRotate + base.mirror = options.mirror + base.rotation = options.rotation + base.effectiveRotation = base.rotation + base.textureWrapMode = options.textureWrapMode + + base.texture:SetDesaturated(options.desaturate) + base.texture:SetBlendMode(options.blendMode) + base:DoTexCoord() +end diff --git a/WeakAuras/RegionTypes/Texture.lua b/WeakAuras/RegionTypes/Texture.lua index 0e012b6..7fd015e 100644 --- a/WeakAuras/RegionTypes/Texture.lua +++ b/WeakAuras/RegionTypes/Texture.lua @@ -84,7 +84,7 @@ local function create(parent) region:SetResizable(true); region:SetMinResize(1, 1); - local texture = region:CreateTexture(); + local texture = Private.TextureBase.create(region) region.texture = texture; texture:SetAllPoints(region); @@ -93,73 +93,40 @@ local function create(parent) return region; end -local SQRT2 = sqrt(2) -local function GetRotatedPoints(degrees, scaleForFullRotate) - local angle = rad(135 - degrees); - local factor = scaleForFullRotate and 1 or SQRT2 - local vx = math.cos(angle) / factor - local vy = math.sin(angle) / factor - - return 0.5+vx,0.5-vy , 0.5-vy,0.5-vx , 0.5+vy,0.5+vx , 0.5-vx,0.5+vy -end - local function modify(parent, region, data) Private.regionPrototype.modify(parent, region, data); - region.texture:SetDesaturated(data.desaturate) region:SetWidth(data.width); region:SetHeight(data.height); region.width = data.width; region.height = data.height; region.scalex = 1; region.scaley = 1; - region.texture:SetBlendMode(data.blendMode); - region.mirror = data.mirror - - local function DoTexCoord() - local mirror_h, mirror_v = region.mirror_h, region.mirror_v; - if(region.mirror) then - mirror_h = not mirror_h; - end - local ulx,uly , llx,lly , urx,ury , lrx,lry - = GetRotatedPoints(region.effectiveRotation, data.rotate) - if(mirror_h) then - if(mirror_v) then - region.texture:SetTexCoord(lrx,lry , urx,ury , llx,lly , ulx,uly); - else - region.texture:SetTexCoord(urx,ury , lrx,lry , ulx,uly , llx,lly); - end - else - if(mirror_v) then - region.texture:SetTexCoord(llx,lly , ulx,uly , lrx,lry , urx,ury); - else - region.texture:SetTexCoord(ulx,uly , llx,lly , urx,ury , lrx,lry); - end - end - end - - region.rotation = data.rotation - region.effectiveRotation = region.rotation + Private.TextureBase.modify(region.texture, { + canRotate = data.rotate, + desaturate = data.desaturate, + blendMode = data.blendMode, + mirror = data.mirror, + rotation = data.rotation, + textureWrapMode = data.textureWrapMode + }) function region:Scale(scalex, scaley) region.scalex = scalex; region.scaley = scaley; + local mirror_h, mirror_v if(scalex < 0) then - region.mirror_h = true; + mirror_h = true scalex = scalex * -1; - else - region.mirror_h = nil; end region:SetWidth(region.width * scalex); if(scaley < 0) then scaley = scaley * -1; - region.mirror_v = true; - else - region.mirror_v = nil; + mirror_v = true end region:SetHeight(region.height * scaley); - DoTexCoord(); + region.texture:SetMirrorFromScale(mirror_h, mirror_v) end function region:SetRegionWidth(width) @@ -173,26 +140,17 @@ local function modify(parent, region, data) end function region:SetMirror(mirror) - region.mirror = mirror - DoTexCoord() + self.texture:SetMirror(mirror) end function region:Update() if self.state.texture then - self:SetTexture(self.state.texture) + self.texture:SetTexture(self.state.texture) end self:UpdateProgress() end - function region:SetTexture(texture) - if self.textureName == texture then - return - end - self.textureName = texture - self.texture:SetTexture(self.textureName); - DoTexCoord() - end - region:SetTexture(data.texture) + region.texture:SetTexture(data.texture) function region:Color(r, g, b, a) region.color_r = r; @@ -224,26 +182,19 @@ local function modify(parent, region, data) region:Color(data.color[1], data.color[2], data.color[3], data.color[4]); function region:SetDesaturated(b) - region.texture:SetDesaturated(b); + self.texture:SetDesaturated(b) end function region:SetAnimRotation(degrees) - region.animRotation = degrees - region:UpdateEffectiveRotation() + self.texture:SetAnimRotation(degrees) end function region:SetRotation(degrees) - region.rotation = degrees - region:UpdateEffectiveRotation() - end - - function region:UpdateEffectiveRotation() - region.effectiveRotation = region.animRotation or region.rotation - DoTexCoord() + self.texture:SetRotation(degrees) end function region:GetBaseRotation() - return region.rotation + return self.texture:GetBaseRotation() end region:SetRotation(data.rotation) diff --git a/WeakAuras/SubRegionTypes/Texture.lua b/WeakAuras/SubRegionTypes/Texture.lua new file mode 100644 index 0000000..530f4af --- /dev/null +++ b/WeakAuras/SubRegionTypes/Texture.lua @@ -0,0 +1,161 @@ +if not WeakAuras.IsLibsOK() then return end + +local AddonName, Private = ... + +local L = WeakAuras.L + +local default = function(parentType) + local defaults = { + textureVisible = true, + + textureTexture = "Interface\\Addons\\WeakAuras\\PowerAurasMedia\\Auras\\Aura3", + textureDesaturate = false, + textureColor = {1, 1, 1, 1}, + textureBlendMode = "BLEND", + textureMirror = false, + textureRotate = false, + textureRotation = 0, + + anchor_mode = "area", + self_point = "CENTER", + anchor_point = "CENTER", + width = 32, + height = 32, + scale = 1, + mirror = false, + rotate = false, + } + + if parentType == "aurabar" then + defaults.anchor_area = "bar" + else + defaults.anchor_area = "ALL" + end + + return defaults +end + +local properties = { + textureVisible = { + display = L["Visibility"], + setter = "SetVisible", + type = "bool", + defaultProperty = true + }, + textureDesaturate = { + display = L["Desaturate"], + setter = "SetDesaturated", + type = "bool", + }, + textureColor = { + display = L["Color"], + setter = "SetColor", + type = "color" + }, + textureMirror = { + display = L["Mirror"], + setter = "SetMirror", + type = "bool" + }, + textureRotation = { + display = L["Rotation"], + setter = "SetRotation", + type = "number", + min = 0, + max = 360, + bigStep = 1, + default = 0 + } + + -- TODO width? + -- TODO height? + -- +} + +local funcs = { + SetDesaturated = function(self, b) + self.texture:SetDesaturated(b) + end, + SetColor = function(self, ...) + self.texture:SetVertexColor(...) + end, + SetMirror = function(self, b) + self.texture:SetMirror(b) + end, + SetRotation = function(self, rotation) + self.texture:SetRotation(rotation) + end, + SetVisible = function(self, visible) + self.visible = visible + if visible then + self:Show() + else + self:Hide() + end + end +} + +local function create() + local region = CreateFrame("Frame", nil, UIParent) + --region:SetFlattensRenderLayers(true) + + for k, v in pairs(funcs) do + region[k] = v + end + + region.texture = Private.TextureBase.create(region) + region.texture:ClearAllPoints() + region.texture:SetAllPoints(region) + + return region +end + +local function onAcquire(subRegion) + subRegion:Show() +end + +local function onRelease(subRegion) + subRegion:Hide() +end + +local function modify(parent, region, parentData, data, first) + region.parent = parent + region:SetParent(parent) + region.scale = data.scale or 1 + + local arg1 = data.anchor_mode == "point" and data.anchor_point or data.anchor_area + local arg2 = data.anchor_mode == "point" and data.self_point or nil + + if data.anchor_mode == "point" then + region:SetSize(data.width or 0, data.height or 0) + end + + region.Anchor = function() + region:ClearAllPoints() + parent:AnchorSubRegion(region, data.anchor_mode, arg1, arg2, data.xOffset, data.yOffset) + end + + Private.TextureBase.modify(region.texture, { + canRotate = data.textureRotate, + desaturate = data.textureDesaturate, + blendMode = data.textureBlendMode, + mirror = data.textureMirror, + rotation = data.textureRotation, + textureWrapMode = "CLAMPTOBLACKADDITIVE" + }) + + region:SetVisible(data.textureVisible) + region:SetDesaturated(data.textureDesaturate) + region:SetColor(data.textureColor[1], data.textureColor[2], data.textureColor[3], data.textureColor[4]) + region.texture:SetTexture(data.textureTexture) +end + +local function supports(regionType) + return regionType == "texture" + or regionType == "progresstexture" + or regionType == "icon" + or regionType == "aurabar" + or regionType == "text" +end + +WeakAuras.RegisterSubRegionType("subtexture", L["Texture"], supports, create, modify, onAcquire, onRelease, default, nil, properties) diff --git a/WeakAuras/WeakAuras.toc b/WeakAuras/WeakAuras.toc index 2845ccd..d9c8ef0 100644 --- a/WeakAuras/WeakAuras.toc +++ b/WeakAuras/WeakAuras.toc @@ -56,6 +56,7 @@ SubscribableObject.lua RegionTypes\SmoothStatusBarMixin.lua RegionTypes\RegionPrototype.lua RegionTypes\ProgressTexture.lua +BaseRegions\Texture.lua RegionTypes\Texture.lua RegionTypes\AuraBar.lua RegionTypes\Icon.lua @@ -74,6 +75,7 @@ SubRegionTypes\Glow.lua SubRegionTypes\Tick.lua SubRegionTypes\Model.lua SubRegionTypes\StopMotion.lua +SubRegionTypes\Texture.lua #Misc DiscordList.lua \ No newline at end of file diff --git a/WeakAurasOptions/SubRegionOptions/Texture.lua b/WeakAurasOptions/SubRegionOptions/Texture.lua new file mode 100644 index 0000000..2849ab3 --- /dev/null +++ b/WeakAurasOptions/SubRegionOptions/Texture.lua @@ -0,0 +1,106 @@ +if not WeakAuras.IsLibsOK() then return end + +local AddonName, OptionsPrivate = ... + +local L = WeakAuras.L; + +local function createOptions(parentData, data, index, subIndex) + local pointAnchors = {} + local areaAnchors = {} + for child in OptionsPrivate.Private.TraverseLeafsOrAura(parentData) do + WeakAuras.Mixin(pointAnchors, OptionsPrivate.Private.GetAnchorsForData(child, "point")) + WeakAuras.Mixin(areaAnchors, OptionsPrivate.Private.GetAnchorsForData(child, "area")) + end + + -- TODO verfiy order being ordered + local options = { + __title = L["Texture %s"]:format(subIndex), + __order = 1, + textureVisible = { + type = "toggle", + width = WeakAuras.doubleWidth, + name = L["Show Texture"], + order = 1, + }, + textureTexture = { + type = "input", + width = WeakAuras.doubleWidth - 0.15, + name = L["Texture"], + order = 2, + }, + chooseTexture = { + type = "execute", + width = 0.15, + name = L["Choose"], + order = 2, + func = function() + local path = { "subRegions", index } + local paths = {} + for child in OptionsPrivate.Private.TraverseLeafsOrAura(parentData) do + paths[child.id] = path + end + OptionsPrivate.OpenTexturePicker(parentData, paths, { + texture = "textureTexture", + color = "textureColor", + mirror = "textureMirror", + blendMode = "textureBlendMode" + }, OptionsPrivate.Private.texture_types, nil, true) + end, + imageWidth = 24, + imageHeight = 24, + control = "WeakAurasIcon", + image = "Interface\\AddOns\\WeakAuras\\Media\\Textures\\browse", + }, + textureColor = { + type = "color", + width = WeakAuras.normalWidth, + name = L["Color"], + hasAlpha = true, + order = 3 + }, + textureDesaturate = { + type = "toggle", + width = WeakAuras.normalWidth, + name = L["Desaturate"], + order = 4, + }, + textureBlendMode = { + type = "select", + width = WeakAuras.normalWidth, + name = L["Blend Mode"], + order = 11, + values = OptionsPrivate.Private.blend_types + }, + textureMirror = { + type = "toggle", + width = WeakAuras.normalWidth, + name = L["Mirror"], + order = 12 + }, + + textureRotate = { + type = "toggle", + width = WeakAuras.normalWidth, + name = L["Allow Full Rotation"], + order = 13, + }, + textureRotation = { + type = "range", + control = "WeakAurasSpinBox", + width = WeakAuras.normalWidth, + name = L["Rotation"], + min = 0, + max = 360, + step = 1, + bigStep = 3, + order = 14, + }, + } + + OptionsPrivate.commonOptions.PositionOptionsForSubElement(data, options, 15, areaAnchors, pointAnchors) + OptionsPrivate.AddUpDownDeleteDuplicate(options, parentData, index, "subtexture") + + return options +end + + WeakAuras.RegisterSubRegionOptions("subtexture", createOptions, L["Shows a Texture"]); diff --git a/WeakAurasOptions/WeakAurasOptions.toc b/WeakAurasOptions/WeakAurasOptions.toc index 83057e9..5ad377e 100644 --- a/WeakAurasOptions/WeakAurasOptions.toc +++ b/WeakAurasOptions/WeakAurasOptions.toc @@ -38,6 +38,7 @@ SubRegionOptions\Glow.lua SubRegionOptions\Tick.lua SubRegionOptions\Model.lua SubRegionOptions\StopMotion.lua +SubRegionOptions\Texture.lua Cache.lua