Search

You're browsing our forum as a Guest meaning you can only see a portion of the forum in read-only mode.
To view all forum nodes and be able to create threads/posts please register or log-in with your existing account.

Authorized

Couldn't you just get the name with UnitName'target' before the loop and then retarget with TargetByName(name, true) when finished? Seems pointless to keep retargeting 40 times while looping through the raid.

New Member

Then one should choose a refreshrate that makes them out of sync, I guess. I noticed that LUF's Units.lua has a pauseUpdates, so I tried using that before the loop above and resuming after, but I could still see TOT and TOTOT "blinking" (appear and reappear in a fraction of a second).

As for choppiness, maybe it would work if one scanned one group of five on each refresh instead of the whole raid?

New Member

This is what I use for range.lua at the moment. It is... not horrible. But still.. when someone walks out of the 40yd range, the frame does not update with new alpha. Anyone have an idea why? I didn't really look into the proximityLib.

Code:

local Range = {}
LunaUF:RegisterModule(Range, "range", LunaUF.L["Range"])
local proximity = ProximityLib:GetInstance("1")
local within40yd = {}
local lastUpdate = 0
local REFRESH_INTERVAL = 1
do
local f = CreateFrame'Frame'
f:SetScript('OnEvent', function()this[event]() end)
f:RegisterEvent'PLAYER_LOGIN'
CreateFrame('GameTooltip', 'RangeCheckTooltip', nil, 'GameTooltipTemplate')
local spell, slot
do
function f.UPDATE()
local Time = GetTime()
if this.lastUpdate==nil then this.lastUpdate=0 end
if (this.lastUpdate < Time) then
local openFrame = (InspectFrame and InspectFrame:IsVisible()) or (LootFrame and LootFrame:IsVisible()) or (XLootFrame and XLootFrame:IsVisible()) or (TradeFrame and TradeFrame:IsVisible())
local enemyTargeted = UnitExists('target') and not UnitIsFriend('target','player')
local str, unitID
if GetNumRaidMembers() > 0 then
str = "raid"
elseif GetNumPartyMembers() > 0 and not UnitInRaid('player') then
str = "party"
else
this.lastUpdate = Time + 5;
return
end
if not (openFrame or enemyTargeted) then
local oldTargetName,_ = UnitName('target')
for i = 1, (GetNumRaidMembers() or GetNumPartyMembers()) do
unitID = str..i
if UnitIsConnected(unitID) and (not UnitIsDeadOrGhost(unitID)) and UnitIsVisible(unitID) and UnitIsFriend('player',unitID) then --because Mind Control?
if CheckInteractDistance(unitID, 4) then
within40yd[unitID] = GetTime()
else
TargetUnit(unitID)
within40yd[unitID] = slot and IsActionInRange(slot) and GetTime()
end
end
end
if oldTargetName then TargetByName(oldTargetName,true) else ClearTarget() end
end
this.lastUpdate = Time + REFRESH_INTERVAL;
end
end
end
function f.ACTIONBAR_SLOT_CHANGED()
local newSlot
for i = 1, 120 do
RangeCheckTooltip:SetOwner(UIParent, 'ANCHOR_NONE')
RangeCheckTooltip:SetAction(i)
if RangeCheckTooltipTextLeft1:GetText() == spell then
newSlot = i
end
end
slot = newSlot
if not slot then f:SetScript('OnUpdate', nil) else f:SetScript('OnUpdate', f.UPDATE) end
end
function f.PLAYER_LOGIN()
spell = ({ Paladin='Holy Light', Priest='Flash Heal', Druid='Healing Touch', Shaman='Healing Wave' })[UnitClass'player']
if spell then
f:RegisterEvent'ACTIONBAR_SLOT_CHANGED'
f.ACTIONBAR_SLOT_CHANGED()
f:SetScript('OnUpdate', f.UPDATE)
end
end
end
local function OnUpdate()
Range:FullUpdate(this:GetParent())
end
function Range:OnEnable(frame)
if not frame.range then
frame.range = CreateFrame("Frame", nil, frame)
end
frame.range:SetScript("OnUpdate", OnUpdate)
end
function Range:OnDisable(frame)
if frame.range then
frame.range:SetScript("OnUpdate", nil)
end
end
function Range:FullUpdate(frame)
if frame.DisableRangeAlpha then return end
local range, lastseen = proximity:GetUnitRange(frame.unit)
if (not range or range > 30) and within40yd[frame.unit] then
range, lastseen = 40, within40yd[frame.unit]
end
if range and ((GetTime()-lastseen) < REFRESH_INTERVAL + 1 ) then
if range <= 30 then
frame:SetAlpha(LunaUF.db.profile.units[frame.unitGroup].fader.enabled and LunaUF.db.profile.units[frame.unitGroup].fader.combatAlpha or 1)
elseif range <= 40 and slot then
frame:SetAlpha(LunaUF.db.profile.units[frame.unitGroup].fader.enabled and LunaUF.db.profile.units[frame.unitGroup].fader.combatAlpha or .8)
end
else
frame:SetAlpha(LunaUF.db.profile.units[frame.unitGroup].range.alpha)
end
end

New Member

function Range:FullUpdate(frame)
if frame.DisableRangeAlpha then return end
local lastseen = within40yd[frame.unit]
if lastseen and ((GetTime()-lastseen) < REFRESH_INTERVAL + 1 ) then
frame:SetAlpha(LunaUF.db.profile.units[frame.unitGroup].fader.enabled and LunaUF.db.profile.units[frame.unitGroup].fader.combatAlpha or 1)
else
frame:SetAlpha(LunaUF.db.profile.units[frame.unitGroup].range.alpha)
end
end

P.S.
I think I got it, it should be IsActionInRange(slot)==1 on line 43. There is still the problem of resetting the portrait animation, though. It looks very annoying.

New Member

I already used Units.pauseUpdates for this purpose. Not sure if that's very smart, but before the loop I pause updates and I unpause after the loop is done (I think I will change this). However, this does not work with the resetCamera() function. If you make this function empty, it still resets (because the function is called OnShow, I guess) I think one should instead never execute frame:Hide() for the target frames if the target is changed during the loop.

I think this can be accomplished by changing (i.e. disabling) Portrait:OnDisable(frame) in portrait.lua or perhaps Portrait:FullUpdate(frame) and Portrait:Update(frame). I am not sure which ones are called when we cycle through targets. I will do some more testing.

New Member

The 40yd check is now implemented. It is not fully tested, expect strange things. As discussed here, it will not refresh the range if you have an enemy targeted, if you have trade/loot/inspect windows open, if you are not a class that can heal or if you don't have your main healing spell on one of your actionbars. If you want to thank someone, thank the good people of this thread who contributed, bit and Renew in particular.

Next step is to optimize this, I guess. If graded alpha is disabled, there is really no point in using ProximityLib at all.

New Member

Another thing I noticed is that sometimes that annoying sound that plays when a target is acquired/cleared plays over and over again. It doesn't happen all the time, but when I noticed it, it was when the rest of the raid was not visible to the client (I was on the other continent). So perhaps one needs to override some of the game's functions. Please keep an eye out for this and tell me if you learn anything new.

For some reason, I couldn't use the minimal .wav files for this because they kept crashing the client. These have some tiny amount of sound in them, but you shouldn't hear anything. If someone finds a way to modify an empty wav so that it doesn't crash the game, I'd be happy to hear about it.

New Member

Renew, I tested this in DunMorogh by testing Frostbolt range with two characters and I got

Code:

x=0.00022299666,y=0.00033462445

which I think is slightly better. Yours was off by .8yd or so versus the 30yd spell-range check. I meant to ask you how exactly did you measure this. You teleported your char to exact coords in a flat area? That's very nice, I don't have access to that. But how did you measure the actual yards? Did you teleport another char to the second location with the same x-coord (resp. y-coord)? Also, what happens when one of the UnitID's is offline?

I'm still not sure how to implement this. Maybe as a separate BG-only module for a start? If you use this in BG's and the world, you can make the range indicator very sophisticated, having alpha move from some small value to 1 as you get closer. The indicators as they are now only cover three ranges (1-29, 29-40 and 40+).

P.S.
I made a mistake in the code in the last edition and the range indicators didn't work in 5man groups. This should be fixed now (not tested). I also added icons to the castbar. Here's the link: https://www.mediafire.com/?wcvl7hgbdpkf11m

New Member

It reports more than 30yd, and terrain can only add to this, but Frostbolt is still in range. Could it be that the values are different on Kronos?

I still think you can be more precise; Here's what I did just now. Make a dummy char and fix his location. Log main char and make a frame that checks OnUpdate when CheckInteractDistance() against the dummy char changes value; when this happens, record your coordinates. When you have two points at which this happens (that aren't colinear or close to) and the third, fixed point of the dummy char, you have enough information to exactly recover the rescale values. I will try to test this in water and see how accurate it is. I'll get back to you

Do you know what is the exact value of CheckInteractDistance(unit,3)? Is it 10? 9.9? It would help to use smaller distances for higher precision.

New Member

That is right, larger distances are actually better because the numbers are very small (and they get squared) so there's more room for error.

I tested my triangle method in lake Al'ameth and came up with x=0.00021,y=0.0003158. The two positions need to be chosen so that the two chars are roughly on the NW-SE line or the NE-SW line, to minimize the error. I still couldn't do better than what you did because the results can varry ~3% on multiple measurements, but even if this is more precise (idk how close you got to zero by minimizing x and y difference; when I tried, I could only get within 5 decimal places by moving the char), at 40yds in water my measurement differs from yours by 0.05yd , so it doesn't really matter.

When I get the time, I will probably implement this as a 38yd check. Thanks for taking the time, really. It must have been tedious to measure this in every single zone.

New Member

The map coords method is now added. As discussed, this is only approximate, but it shouldn't strain the CPU as much as target->check healing range->retarget. The old method is also improved (it doesn't check the full raid at once so it shouldn't be as choppy). Please report bugs and unusual behaviour. Also check lines 237-239 in locales/enUS.lua if you want to change the [gridname] indicators for "dead" and "ghost".