Thread Tools Display Modes
04-02-11, 08:48 AM   #1
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
reverse status bars (again)

I know this topic came out a couple of times already in the past, but uhm, I've ran search few times and have yet to find a solution to my problem regarding reverse status bars.

So I want my health status bar to fill in reverse, i.e. the bigger amount of health missing - the bigger health status bar is (starting from right to left).

If I understand correctly neither default wow API or oUF allows us to do that with some simple method, so I need to make a PostUpdateHealth hook and change this by my own, but I struggle with that one ...

Setting the new value is easy, but I can't reanchor the texture itself
my PostUpdateHealth function looks like this:
lua Code:
  1. lib.PostUpdateHealth = function(s, unit, min, max)
  2.     if unit=='player' or unit=='target' then
  3.         s:SetValue(max-min)
  4.         s.t = s:GetStatusBarTexture()
  5.         s.t:SetPoint('TOPRIGHT', s, 'TOPLEFT', 0, 0)
  6.     end
  7. end

and hp bar function:
lua Code:
  1. lib.gen_hpbar = function(f)
  2.     local s = CreateFrame("StatusBar", nil, f)
  3.     s:SetStatusBarTexture(cfg.statusbar_texture)
  4.     fixStatusbar(s)
  5.     s:SetHeight(f.height)
  6.     s:SetWidth(f.width)
  7.     s:SetPoint("TOPLEFT",0,0)
  8.     s:SetAlpha(0.65)
  9.     s:SetOrientation("HORIZONTAL")
  10.     local h = CreateFrame("Frame", nil, s)
  11.     h:SetFrameLevel(0)
  12.     h:SetPoint("TOPLEFT",-4,4)
  13.     h:SetPoint("BOTTOMRIGHT",4,-4)
  14.     lib.gen_backdrop(h)
  15.     local b = s:CreateTexture(nil, "BACKGROUND")
  16.     b:SetTexture(cfg.statusbar_texture)
  17.     b:SetAllPoints(s)
  18.     s.PostUpdate = lib.PostUpdateHealth
  19.     f.Health = s
  20.     f.Health.bg = b
  21.   end

So basically I get bar with the right value, but it's placed at default position, i.e. anchored to right and filling up towards left. Any help or some kind of clues would be appreciated!

Last edited by Monolit : 04-02-11 at 02:05 PM.
  Reply With Quote
04-02-11, 12:36 PM   #2
Saiket
A Chromatic Dragonspawn
 
Saiket's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 154
I think that StatusBars delay re-anchoring their textures until just before the next OnUpdate, so you'll have to use an OnUpdate handler to re-position the texture. Here's the function I use to create a reverse status bar in my UI:
http://code.google.com/p/wow-saiket/...lua?r=1574#313

Last edited by Saiket : 04-03-11 at 07:47 PM.
  Reply With Quote
04-03-11, 05:44 AM   #3
zork
A Pyroguard Emberseer
 
zork's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 1,740
Couldn't you just switch colors. (dark foreground, light background). That way if the bar depletes the bright color will become more and more visible.
__________________
| Simple is beautiful.
| WoWI AddOns | GitHub | Zork (WoW)

"I wonder what the non-pathetic people are doing tonight?" - Rajesh Koothrappali (The Big Bang Theory)
  Reply With Quote
04-03-11, 07:30 AM   #4
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
Originally Posted by Saiket View Post
I think that StatusBars delay re-anchoring their textures until just before the next OnUpdate, so you'll have to use an OnUpdate handler to re-position the texture. Here's the function I use to create a reverse status bar in my UI:
http://code.google.com/p/wow-saiket/...ts.oUF.lua#313
hm, that definitely helps although I thought it was possible to avoid using OnUpdate scripts

Originally Posted by zork View Post
Couldn't you just switch colors. (dark foreground, light background). That way if the bar depletes the bright color will become more and more visible.
I thought about that too, but the problem is that I want to have 3d portrait in the background and you can't really do that with portraits :/
i.e. I want this bar to overlay the background with the portrait

Last edited by Monolit : 04-03-11 at 08:08 AM.
  Reply With Quote
04-03-11, 12:28 PM   #5
Saiket
A Chromatic Dragonspawn
 
Saiket's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 154
Originally Posted by Monolit View Post
hm, that definitely helps although I thought it was possible to avoid using OnUpdate scripts
Those OnUpdate scripts don't run all the time; They run once right after the bar value changes, and then they shut themselves off. The CPU usage for that kind of throttle is insignificant.
  Reply With Quote
04-03-11, 03:33 PM   #6
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
Originally Posted by Saiket View Post
Those OnUpdate scripts don't run all the time; They run once right after the bar value changes, and then they shut themselves off. The CPU usage for that kind of throttle is insignificant.
Oh well, you're right and this method worked, got exactly what I was looking for, thank you.

P.S.
Just out of curiosity why do you wrap your OnUpdate functions in 'do ... end' loop? I've read something about this a while ago... something about optimizing lua code, but can't really find it right now, so could you please enlighten me?

Last edited by Monolit : 04-03-11 at 03:44 PM.
  Reply With Quote
04-03-11, 07:46 PM   #7
Saiket
A Chromatic Dragonspawn
 
Saiket's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 154
They don't improve performance, but they are useful for creating private variable scopes. Only the CreateBarReverse function can see and use OnChanged and UpdaterOnUpdate, since they're declared inside of the do-end block.
  Reply With Quote
04-05-11, 03:16 PM   #8
zork
A Pyroguard Emberseer
 
zork's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 1,740
Other thing you can do. Have a transparent statusbar just for the values and have two simple textures that get updated once the statusbar OnValueChanged event get's fired.
__________________
| Simple is beautiful.
| WoWI AddOns | GitHub | Zork (WoW)

"I wonder what the non-pathetic people are doing tonight?" - Rajesh Koothrappali (The Big Bang Theory)
  Reply With Quote
04-06-11, 06:53 AM   #9
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
Originally Posted by zork View Post
Other thing you can do. Have a transparent statusbar just for the values and have two simple textures that get updated once the statusbar OnValueChanged event get's fired.
Well it is pretty much what Saiket offered, but in his case he doesn't create those textures, but use already existing one.

Anyway I got it working, just not sure whether I like the outcome or not :P

Last edited by Monolit : 04-06-11 at 07:15 AM.
  Reply With Quote
04-07-11, 08:55 AM   #10
Dawn
A Molten Giant
 
Dawn's Avatar
AddOn Author - Click to view addons
Join Date: May 2006
Posts: 918
You might consider sharing your solution, other might be interested in it, too. As this has been brought up quite a few times in the past.
__________________
Rock: "We're sub-standard DPS. Nerf Paper, Scissors are fine."
Paper: "OMG, WTF, Scissors!"
Scissors: "Rock is OP and Paper are QQers. We need PvP buffs."

"neeh the game wont be remembered as the game who made blizz the most money, it will be remembered as the game who had the most QQ'ers that just couldnt quit the game for some reason..."

  Reply With Quote
04-07-11, 04:31 PM   #11
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
Originally Posted by Dawn View Post
You might consider sharing your solution, other might be interested in it, too. As this has been brought up quite a few times in the past.
sure, it's based on Saiket's solution, slightly simplified though:

so first of all we make updater frame and ReverseBar function that will be used to create our reverse bars
lua Code:
  1. local ReverseBar
  2. do
  3.     local UpdaterOnUpdate = function(Updater)
  4.         Updater:Hide()
  5.         local b = Updater:GetParent()
  6.         local tex = b:GetStatusBarTexture()
  7.         tex:ClearAllPoints()
  8.         tex:SetPoint("BOTTOMRIGHT")
  9.         tex:SetPoint("TOPLEFT", b, "TOPRIGHT", (b:GetValue()/select(2,b:GetMinMaxValues())-1)*b:GetWidth(), 0)
  10.     end
  11.     local OnChanged = function(bar)
  12.         bar.Updater:Show()
  13.     end
  14.     function ReverseBar(f)
  15.         local bar = CreateFrame("StatusBar", nil, f)
  16.         bar.Updater = CreateFrame("Frame", nil, bar)
  17.         bar.Updater:Hide()
  18.         bar.Updater:SetScript("OnUpdate", UpdaterOnUpdate)
  19.         bar:SetScript("OnSizeChanged", OnChanged)
  20.         bar:SetScript("OnValueChanged", OnChanged)
  21.         bar:SetScript("OnMinMaxChanged", OnChanged)
  22.         return bar;
  23.     end
  24. end
I also noticed that sometimes hp statusbar stays at 100% (instead of 0) when player is dead or ghost, so I use simple PostUpdateHealth hook to fix that:
lua Code:
  1. lib.PostUpdateHealth = function(s, u, min, max)
  2.     if UnitIsDeadOrGhost(u) then s:SetValue(0) end
  3. end

So then in your style function you just use ReverseBar() instead of 'CreateFrame("StatusBar"...' to make hp bar.
lua Code:
  1. s = ReverseBar(f)
  2. s.PostUpdate = lib.PostUpdateHealth  
  3. f.Health = s

here's the result:

and I actually quite like it
  Reply With Quote
01-14-12, 06:45 AM   #12
Othgar
"That" Guy
 
Othgar's Avatar
AddOn Author - Click to view addons
Join Date: Nov 2010
Posts: 228
I feel like I'm necro-ing this thread a bit but ohh well here goes....

I'm working on modifying a version oUF_Sandman for my UI, and I am trying to get this to work for me, but I just can't seem to get it. Not sure if I'm missing something or just being an overtired/over-caffinated idiot. I haven't changed any other code from the original yet, just messing with getting the textures right for now. Where should this be added to the code/or what needs to be changed to get this to work?
__________________


  Reply With Quote
01-14-12, 11:44 AM   #13
haste
Featured Artist
 
haste's Avatar
Premium Member
Featured
Join Date: Dec 2005
Posts: 1,027
As of 4.3, you only need to do StatusBar:SetReverseFill(true) to reverse the direction of the statusbar.
__________________
「貴方は1人じゃないよ」
  Reply With Quote
01-14-12, 03:49 PM   #14
Othgar
"That" Guy
 
Othgar's Avatar
AddOn Author - Click to view addons
Join Date: Nov 2010
Posts: 228
OK let me try editing the right version of the file first before I say it didn't work /facepalm. Never code before coffee and smoke in the morning.....
__________________



Last edited by Othgar : 01-14-12 at 03:58 PM. Reason: I.D.1.0.T error
  Reply With Quote
01-14-12, 04:15 PM   #15
Othgar
"That" Guy
 
Othgar's Avatar
AddOn Author - Click to view addons
Join Date: Nov 2010
Posts: 228
I added the SetReverseFill(true) to the style section:

Code:
  --gen healthbar func
  lib.gen_hpbar = function(f)
    --statusbar
    local s = CreateFrame("StatusBar", nil, f)
    s:SetStatusBarTexture(cfg.statusbar_texture)
	if f.mystyle == "target" then
		s:SetReverseFill(true)
	elseif f.mystyle == "pet" then
		s:SetHeight(32)
	else
		s:SetHeight(retVal(f,64,48,40))
    end
	s:SetWidth(f:GetWidth())
    s:SetPoint("TOP",0,0)
    s:SetFrameLevel(4)
	
	--helper
	local h = CreateFrame("StatusBar", nil, s)
	h:SetFrameLevel(0)
    h:SetStatusBarTexture(cfg.backline)
	if f.mystyle == "player" then
		h:SetPoint("TOPLEFT",-16,10)
		h:SetPoint("BOTTOMRIGHT",11,-82)
	elseif f.mystyle == "target" then
		h:SetReverseFill(true)
		h:SetPoint("TOPRIGHT",10,-16)
		h:SetPoint("BOTTOMLEFT",-82,11)
	elseif f.mystyle == "party" then
		h:SetPoint("TOPLEFT",-9,8)
		h:SetPoint("BOTTOMRIGHT",6,-53)
	elseif f.mystyle == "pet" then
		h:SetPoint("TOPLEFT",-16,4)
		h:SetPoint("BOTTOMRIGHT",5,-40)
	else
		h:SetPoint("TOPLEFT",-10,7)
		h:SetPoint("BOTTOMRIGHT",6,-62)
	end
Now the texture doesn't show up at all on the target frame. (but at least I edited the right file this time ) I tried a few different variations on the setpoints for the "target" and it didn't change anything. I'm not getting any errors just no textures at all.
__________________


  Reply With Quote
01-14-12, 04:37 PM   #16
Othgar
"That" Guy
 
Othgar's Avatar
AddOn Author - Click to view addons
Join Date: Nov 2010
Posts: 228
Here's a quick screenshot of what I have now. Not sure if I just need to mess with the set points more or what, but I'll try again in the morning when I get home from work . I'm still working on powerbar textures which is why they're just green blobs in the screenie.

Click image for larger version

Name:	WoWScrnShot_011412_173417.jpg
Views:	1070
Size:	494.0 KB
ID:	6756

well I tried messing with this some more this morning, and I'm still having no luck. I tried adding a new texture file that is a mirror image of the player hpbar texture and pointing to it in the style functions and still got no where. StatusBar:SetReverseFill(true) either breaks the textures without throwing an error (see previous post) or just doesn't work if I only put it in the gen healthbar function or the helper section individually. I know I have to be missing something, I just have no idea what.
__________________



Last edited by Othgar : 01-15-12 at 08:31 AM. Reason: update
  Reply With Quote
01-15-12, 11:18 AM   #17
Monolit
A Black Drake
AddOn Author - Click to view addons
Join Date: Jan 2006
Posts: 81
Originally Posted by haste View Post
As of 4.3, you only need to do StatusBar:SetReverseFill(true) to reverse the direction of the statusbar.
That's a little bit different thing,
StatusBar:SetReverseFill(true) will just essentially mirror your status bar, and what I meant with "Reverse status bars" is that it also changes the way it behaves, i.e. at 100% HP status bar would stay at 0% mark, at 70% HP it would be 30% filled etc. (picture above actually represents it quite well).

The method posted above still works flawlessly @ live realms and should be quite easy to implement in any layout.

Actually I think it can be done a little bit differently using SetReverseFill, but it would require pretty much the same texture manipulations in PostUpdate or Override callbacks. MAYBE it would be a little bit more efficient performance-wise though.

Last edited by Monolit : 01-15-12 at 11:40 AM.
  Reply With Quote
01-17-12, 04:20 PM   #18
Othgar
"That" Guy
 
Othgar's Avatar
AddOn Author - Click to view addons
Join Date: Nov 2010
Posts: 228
I finally got my textures switched around so everything looked better but SetReverseFill(true) still didn't really work out for me. I tried to enable it on my player frame to get the bars to fill from left to right, and instead of filling the bars it actually shifted the textures and skewed them as the bar depleted. I tried a bunch of stuff to try to get them right but nothing seemed to work. I'll probably try again either later tonight or tomorrow and I'll see if I can fraps a vid of it.

oUF_Lust is the outcome of it for now.
__________________



Last edited by Othgar : 01-17-12 at 04:21 PM. Reason: added link
  Reply With Quote
01-20-12, 07:36 AM   #19
zork
A Pyroguard Emberseer
 
zork's Avatar
AddOn Author - Click to view addons
Join Date: Jul 2008
Posts: 1,740
Originally Posted by haste View Post
As of 4.3, you only need to do StatusBar:SetReverseFill(true) to reverse the direction of the statusbar.
... Holy smokes. Need to remember that.
__________________
| Simple is beautiful.
| WoWI AddOns | GitHub | Zork (WoW)

"I wonder what the non-pathetic people are doing tonight?" - Rajesh Koothrappali (The Big Bang Theory)

Last edited by zork : 01-20-12 at 07:43 AM.
  Reply With Quote
01-21-12, 04:46 AM   #20
haste
Featured Artist
 
haste's Avatar
Premium Member
Featured
Join Date: Dec 2005
Posts: 1,027
Originally Posted by Monolit View Post
That's a little bit different thing,
StatusBar:SetReverseFill(true) will just essentially mirror your status bar, and what I meant with "Reverse status bars" is that it also changes the way it behaves, i.e. at 100% HP status bar would stay at 0% mark, at 70% HP it would be 30% filled etc. (picture above actually represents it quite well).

The method posted above still works flawlessly @ live realms and should be quite easy to implement in any layout.

Actually I think it can be done a little bit differently using SetReverseFill, but it would require pretty much the same texture manipulations in PostUpdate or Override callbacks. MAYBE it would be a little bit more efficient performance-wise though.
You could simplify it down to:
Lua Code:
  1. Health:SetReverseFill(true)
  2. Health.PostUpdate = function(Health, unit, min, max)
  3.    Health:SetValue(max - Health:GetValue())
  4. end
__________________
「貴方は1人じゃないよ」
  Reply With Quote

WoWInterface » Featured Projects » oUF (Otravi Unit Frames) » reverse status bars (again)


Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off