• Listen to a special audio message from Bill Roper to the Hive Workshop community (Bill is a former Vice President of Blizzard Entertainment, Producer, Designer, Musician, Voice Actor) 🔗Click here to hear his message!
  • Read Evilhog's interview with Gregory Alper, the original composer of the music for WarCraft: Orcs & Humans 🔗Click here to read the full interview.

Fixed broken UI scripts after 2.0

Macielos

Hosted Project: W3E
Level 23
Joined
Jul 9, 2010
Messages
406
Hey, as you may know, 2.0 patch changed UI structure resulting in breaking some libs that access UI frames. This happens with @Barade 's unit sound set library which uses the 12 labels for selected units. Some time ago I rewrote this lib into LUA and expanded it to my needs, so my version also broke. I tried comparing consoleui.fdf from both versions, but the structure didn't match what I saw in game, so eventually I ended up printing frame structure until I found a frame with 12 children :p.

I tried to tell Barade on PM, but his profile is locked, so I'm posting here a fix to apply to properly find the frame container for selected unit labels.

In case of Barade's lib: Script GetMainSelectedUnit, function init_functionAt0s:

Lua:
Before:

local console = BlzGetFrameByName("ConsoleUI", 0)
local bottomUI = BlzFrameGetChild(console, 1)
local groupframe = BlzFrameGetChild(bottomUI, 5)
local buttonContainer
--globals
containerFrame = BlzFrameGetChild(groupframe, 0)

After:

local console = BlzGetFrameByName("ConsoleUI", 0)
local bottomUI = BlzFrameGetChild(console, 1)
local buttonContainer
--globals
containerFrame = BlzFrameGetChild(bottomUI, 1)

JASS:
Before:
local framehandle console = BlzGetFrameByName("ConsoleUI", 0)
local framehandle bottomUI = BlzFrameGetChild(console, 1)
local framehandle groupframe = BlzFrameGetChild(bottomUI, 5)
local framehandle buttonContainer
//globals
set containerFrame = BlzFrameGetChild(groupframe, 0)
After:

local framehandle console = BlzGetFrameByName("ConsoleUI", 0)
local framehandle bottomUI = BlzFrameGetChild(console, 1)
local framehandle buttonContainer
//globals
set containerFrame = BlzFrameGetChild(bottomUI, 1)

If you use another lib that broke on 2.0 and accesses some other UI frames, there's a good chance a fix will be very similar.

BTW: I'll probably replace all usages of blizz frame functions like BlzFrameGetChild with wrappers that check if a child exists before breaking the game...

Edit: here you go, with utils to print frame structure:

Lua:
FrameUtils = {}

local function getOffset(offset)
    if offset == 0 then
        return ""
    end
    return string.rep("-", 2 * offset)
end

function FrameUtils.printFrameStructure(frame, maxDepth, offset)
    if offset == nil then
        offset = 0
    end
    local childrenCount = BlzFrameGetChildrenCount(frame)
    local visible = BlzFrameIsVisible(frame)
    if visible then
        print(getOffset(offset) .. "FRAME " .. BlzFrameGetName(frame) .. ": [" .. tostring(childrenCount) .. "]")
    end
    if childrenCount > 0 then
        if offset < maxDepth then
            for i = 0, childrenCount - 1 do
                FrameUtils.printFrameStructure(BlzFrameGetChild(frame, i), maxDepth, offset + 1)
            end
        else
            print(getOffset(offset + 1) .. "[...]")
        end
    end
end

function FrameUtils.safeFrameGetChild(parent, childIndex)
    local childrenCount = BlzFrameGetChildrenCount(parent)
    if childIndex < 0 or childIndex >= childrenCount then
        local name = BlzFrameGetName(parent)
        SimpleUtils.printWarn("Attempt to get " .. tostring(childIndex) .. ". child, but frame " .. name .. " only has " .. tostring(childrenCount))
        return nil
    end
    return BlzFrameGetChild(parent, childIndex)
end

Example usages:
FrameUtils.printFrameStructure(BlzGetFrameByName("ConsoleUI", 0), 1)
FrameUtils.printFrameStructure(FrameUtils.safeFrameGetChild(BlzGetFrameByName("ConsoleUI", 0), 1), 1)
 
Last edited:
Top