Author Topic: Centering a dynamic grid / table of buttons  (Read 4828 times)

82apps

  • Newbie
  • *
  • Thank You
  • -Given: 0
  • -Receive: 0
  • Posts: 5
    • View Profile
Centering a dynamic grid / table of buttons
« on: January 21, 2014, 02:52:59 PM »
I have a 'button bar' in my menu which is a row of 1-4 buttons. I'd like it to be horizontally centered based on how many buttons are active in the bar. So if it contains a single button it should be perfectly centered, and if it contains two buttons the left button and right buttons should each be offset from the center so that the entire group is centered. 

I can't seem to find the right combination of widgets, grids, tables, or anchors to do this seemingly simple task. I could hard-code the values, but I'd love to find a 'best practice' to do this using the automatic layout tools because this is something that I will be doing throughout all my menus. 

Any suggestions would be much appreciated.

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #1 on: January 22, 2014, 04:19:57 AM »
This is indeed a simple task. NGUIMath.CalculateRelativeWidgetBounds(buttonBarTransform) will tell you the dimensions of your content. Adjust the transform.localPosition by half of the width.

82apps

  • Newbie
  • *
  • Thank You
  • -Given: 0
  • -Receive: 0
  • Posts: 5
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #2 on: January 22, 2014, 01:32:34 PM »
Thanks for the response. It doesn't appear to work though if the pivot is in the middle (like the button default).

I have 4 buttons, with width 120, in a grid with Cell Width = 130. These are the grid offsets necessary to center the button bar given the number of visible buttons:

1 button: width = 120 (120 x 1) center offset = 0 (not -60)
2 buttons: width = 250 (120 x 2 + 10) center offset  = -65 (not -125)
3 buttons: width = 380 (120 x 3 + 20) center offset  = -130  (not -190)
4 buttons: width = 510 (120 x 4 + 30) center offset  = -195 (not -255)

So the correct calculation is (numButtons - 1) * (Cell Width) * .5. Which is easy enough to add, but requires a bit of a hassle every time I want to center a group of objects (which is very often). This also involves calculating the number of columns/rows in a grid based on child object counts or something. That's why a simpler 'Center' option would be extremely useful.

I've also tried the CalculateRelativeWidgetBounds method on a table that I populated with labels dynamically, and it would always appear first in the wrong location and then snap to the correct one. My guess is that the label objects were being created after the first repositioning update, and then were fixed on a subsequent update. So that's another drawback.
« Last Edit: January 23, 2014, 10:29:02 AM by 82apps »

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #3 on: January 23, 2014, 06:46:09 AM »
CalculateRelative function implies that it's relative to something. If you pass another parent transform there, it can be relative to that. Generally when computing bounds of something, you want to make it relative to that something's parent, otherwise the position won't be what you expect.

82apps

  • Newbie
  • *
  • Thank You
  • -Given: 0
  • -Receive: 0
  • Posts: 5
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #4 on: January 23, 2014, 03:41:43 PM »
CalculateRelative is returning the correct bounds, but the technique of offsetting by half the width of the bounds does not correctly center grids in all cases. So is there any other technique for automatically and easily centering grids?

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #5 on: January 24, 2014, 10:16:37 AM »
Why wouldn't it? Assuming you do your logic after the reposition call on the grid, it should work as expected.

82apps

  • Newbie
  • *
  • Thank You
  • -Given: 0
  • -Receive: 0
  • Posts: 5
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #6 on: January 24, 2014, 11:24:24 AM »
The width offset doesn't achieve the correct result if the child objects have a center pivot. (Picture a grid with a single button - you don't want to offset grid by half the width. Grid and button should both be at X=0).

I can adjust for this with hardcoding or perhaps by digging into the hierarchy and performing another bounds check on child objects to get the necessary additional offset value, but just seems like there should be a cleaner solution for something so common.

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Centering a dynamic grid / table of buttons
« Reply #7 on: January 25, 2014, 02:31:01 AM »
The function I mentioned returns bounds -- both min and max. Calculate the difference between the min and your transform's position, and include that difference in your offset.

Consider this diagram:

[_a__b__c_]

The first element is "a", so it will be positioned at grid's XYZ, exactly. But the width of the grid, indicated by the square brackets, is wider than that. You can either use Calculate and take the offset between the left side and the 'a' into consideration, or, even easier -- just calculate the difference between the first and the last elements.

You could even write your own logic to create a new set of Bounds() by iterating through each of the children and adding their position to the bounds. This way there will be no need to take the 'min' into consideration.