Author Topic: Mindboggling scaling numbers  (Read 7402 times)

sluresylta

  • Guest
Mindboggling scaling numbers
« on: September 11, 2012, 01:11:11 PM »
...well, they boggle *my* mind, anyway - I'm sure there's a perfectly logical solution to my problem:

I have sprites where the original PSD files are 44px wide and 44px high. Since their dimensions might change in the future, I instantiate a temporary sprite at Awake() and use this to figure out its size at runtime:

Bounds tempSquareBounds = NGUIMath.CalculateAbsoluteWidgetBounds(tempSquare.transform);
SquareDimensions = tempSquareBounds.size.x;

(SquareDimensions has a setter that sets private variables squareWidth and squareHeight)

This correctly sets the width and height variables to 44px. Now, when I later instantiate these sprites, I use this:

GameObject currentSquare = Instantiate(BoardValuesRepo.BasicSquarePrefab, nextSquarePosition, new Quaternion(0, 0, 0, 0)) as GameObject;
currentSquare.transform.parent = BoardValuesRepo.boardReference.transform;

(I have a loop that increments nextSquareposition by the sprite size)

This lays the squares out neatly in rows and columns, just like I want. Except for one thing, and this is where my mind boggles: They're created at a ridiculously large scale. X is 10296, and so is Y.

I did a bit of calculation, and it turns out that 10296 divided by 44 is 234 - exactly half of what UIRoot sets the Manual Height field to when I keep Automatic checked. This leads me to suspect that the big instantiation scale is connected to what UIRoot is doing behind the scenes. I could be wrong, of course, I'm both a Unity newbie and NGUI newbie.

The game objects involved in this is structured like this:
UI Root
->Camera
-->Anchor
--->Panel
---->Sprite1
---->Sprite2
---->[etc]

Camera has Size 1 and Scale XYZ 1. Anchor also has Scale XYZ 1. And so does Panel. UIRoot gets a self-assigned Scale of 0.004273504.

Oh, and what I actually want is to have the sprites display at their original screen size, ie. 44px.

Anyone have any ideas?

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Mindboggling scaling numbers
« Reply #1 on: September 11, 2012, 01:35:07 PM »
You need to use NGUITools.AddChild instead. It does some things you're missing.

Nicki

  • Global Moderator
  • Hero Member
  • *****
  • Thank You
  • -Given: 33
  • -Receive: 141
  • Posts: 1,768
    • View Profile
Re: Mindboggling scaling numbers
« Reply #2 on: September 11, 2012, 04:43:37 PM »
UIRoot scale is 1 / screen height, so that localposition is in pixel units.

Use NGUITools.AddChild like Aren says, and while you're at it, take a good look at the other methods in NGUITools, there might be a bunch you can use - I sorta discovered things when I rummaged through that one. :D

sluresylta

  • Guest
Re: Mindboggling scaling numbers
« Reply #3 on: September 12, 2012, 09:13:17 AM »
Thank you both - I did have a look at all the NGUITools methods, and it looks like there is a lot of useful stuff there :-)

I am now using NGUITools.AddChild instead, and that does indeed remove the huge scaling numbers. However, I now seem to get the opposite problem. All the instantiated sprites end up with a scale of 1,1,1.

If I call MakePixelPerfect on the sprites, they get the scale I expected (44,44,1) and display correctly. This makes a new problem appear, though; my grid positioning no longer works as expected. The first sprite created gets positioned at 0,0,0 - which is fine. The next ones, though, are positioned at intervals of 10296. Which leads me to think that there's something I'm missing again. Should I be using a NGUI-specific method to set the sprite's position?

Here's the code I'm currently using for creating the squares:

  1. GameObject currentSquare = NGUITools.AddChild(BoardValuesRepo.boardReference, BoardValuesRepo.BasicSquarePrefab);
  2. UISprite squareSprite = currentSquare.GetComponent<UISprite>();
  3. squareSprite.spriteName = SquareType + "_44x44";
  4. squareSprite.MakePixelPerfect();
  5. currentSquare.transform.position = nextSquarePosition;

nextSquarePosition is a Vector 3, which for the second square to be created has the value (44.0, 0.0, 0.0) and for the third square has the value (88.0, 0.0, 0.0). And so on.

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Mindboggling scaling numbers
« Reply #4 on: September 12, 2012, 10:19:16 AM »
That's correct. You shouldn't instantiate sprites one at a time. Instantiate their parent instead. Ideally you'd be doing this on an object that contains multiple sprites underneath, not one sprite at a time.

sluresylta

  • Guest
Re: Mindboggling scaling numbers
« Reply #5 on: September 12, 2012, 10:43:50 AM »
Hm...I'm not sure I understood that. Should I not be making prefabs of sprites?

What I've done is basically:
1. Created a sprite with the Widget Tool
2. Made a prefab by dragging this sprite object from the Hierarchy to the Prefabs folder
3. Instantiated this sprite object multiple times, using the code I provided in my previous post

My goal with all of this is to build a board for a board game by parsing a string that specifies the squares on the board, one by one. I plan to generate any one of several hundreds of boards like this, at runtime, all composed of different combinations of squares/sprites.

Am I going about the whole process wrong? I'm not sure what you mean by "Instantiate their parent instead". Do you mean that I should have a panel of premade sprites as a prefab, and then instantiate this panel?
« Last Edit: September 12, 2012, 11:55:35 AM by sluresylta »

ArenMook

  • Administrator
  • Hero Member
  • *****
  • Thank You
  • -Given: 337
  • -Receive: 1171
  • Posts: 22,128
  • Toronto, Canada
    • View Profile
Re: Mindboggling scaling numbers
« Reply #6 on: September 12, 2012, 02:32:30 PM »
There is little reason to prefab an individual sprite. If you do need that, consider creating a parent object for it instead. This parent object should have a scale of (1, 1, 1).

Nicki

  • Global Moderator
  • Hero Member
  • *****
  • Thank You
  • -Given: 33
  • -Receive: 141
  • Posts: 1,768
    • View Profile
Re: Mindboggling scaling numbers
« Reply #7 on: September 12, 2012, 04:08:18 PM »
When you instantiate a prefab it's always placed in 0,0,0 and scaled 1,1,1. If you just assume this to be true, you always make an "empty" parent on your prefabs that you place sprites, labels etc inside. And everything works. :D

sluresylta

  • Guest
Re: Mindboggling scaling numbers
« Reply #8 on: September 13, 2012, 06:44:22 AM »
Thank you both for helping out a newbie. There must be something fundamental I'm not getting here.

I tried making a new prefab, with this structure: Empty GameObject->Sprite

I then made my script instantiate that new prefab for each square on the board. I have no idea why this would work better than just instantiating the sprite, and I've obviously misunderstood you guys, since the result was exactly the same as with the "bare" sprite instantiation: huge spaces between each square.

Did you mean that I have to make a prefab with one parent gameobject containing a full row of square sprites (ie. not one parent gameobject per sprite)? If so, I'm guessing my whole approach is unworkable, since one row of squares might be anything from 15 to 100 squares long.

Perhaps I'd be better off asking the following question: If you were to dynamically construct a game board/matrix of squares at runtime, with a row and column count that varied greatly between each level, how would you go about it? Keeping in mind that each square could be any of several types.

Nicki

  • Global Moderator
  • Hero Member
  • *****
  • Thank You
  • -Given: 33
  • -Receive: 141
  • Posts: 1,768
    • View Profile
Re: Mindboggling scaling numbers
« Reply #9 on: September 13, 2012, 07:37:34 AM »
Look into NGUITools.AddChild for how to instantiate properly.

I would make a board (panel) and make a prefab of a single piece (with an empty gameObject parent) that I reference on the board filler script in and instantiate that as much as I needed with NGUITools.AddChild.

Each piece could have a helper script that setup the type, which I provide from my filler script.

Obviously you need to have your board as a child of UIRoot somewhere, but that's a given.

sluresylta

  • Guest
Re: Mindboggling scaling numbers
« Reply #10 on: September 13, 2012, 08:46:19 AM »
Thanks, Nicki, I really appreciate it. That's actually almost exactly the way I'm doing it. Good to know I'm not barrelling down the wrong road :-)

Anyway, I had a peek at the code for the AddChild method, and got a forehead-slapping revelation. What I did wrong was this:
currentSquare.transform.position = nextSquarePosition;

...which - obviously, I guess - should be:
currentSquare.transform.localPosition = nextSquarePosition;

I suspect that's a typical n00b mistake :-D

JRoch

  • Full Member
  • ***
  • Thank You
  • -Given: 0
  • -Receive: 0
  • Posts: 140
    • View Profile
Re: Mindboggling scaling numbers
« Reply #11 on: September 13, 2012, 12:48:13 PM »
The vagaries of Position and LocalPosition aren't all that intuitive when you're getting your feet under you.  Nothing to be ashamed of!

sluresylta

  • Guest
Re: Mindboggling scaling numbers
« Reply #12 on: September 14, 2012, 03:28:48 AM »
The vagaries of Position and LocalPosition aren't all that intuitive when you're getting your feet under you.  Nothing to be ashamed of!

Thanks! I won't be, then :)