2D Toolkit Forum

2D Toolkit => Support => Topic started by: fryedrycestyle on January 08, 2013, 02:25:18 am

Title: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 08, 2013, 02:25:18 am
Hey,

So I'm still getting accustomed to the 2DToolkit and have two questions.


Thanks in advance!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 08, 2013, 04:32:51 am
1. Just as you would any other object in Unity. Change camera.transform.position or, call camera.transform.Translate...

2. That really depends on the type of game you're going for. For starters, you could try using the Unity 2d character controller to see if that works for you.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 08, 2013, 06:05:36 pm
Ah okay, so it's just manipulating the mainCamera attribute. That makes sense!

As for my second question, we're making a SNES style RPG, and I figured tile-based movement would be best, as opposed to simply changing the transform's position, basically I want the character to move from one tile to the next in a smooth fashion.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 09, 2013, 05:49:04 am
To constrain movement to a tile, you need to work out the tile positions in world space, and then use HoTween / your favourite tweening middleware to tween the positions. That will be the easiest way to do this without coding all the movement code yourself.

You can get the tile position for a specific tile by calling GetTilePosition(int x, int y) on the tilemap.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 09, 2013, 09:12:04 pm
Okay, I'll look into using iTween for Unity or a solution such as that. Thanks for the suggestion.

But now I'm having some trouble with the camera not centering on the screen. I think I'm misunderstanding a few things about how the tk2d camera works?

http://minus.com/lTe7Xskd1oWJ (http://minus.com/lTe7Xskd1oWJ)

For the record, I'm spawning my character as a prefab using a tile in the tilemap in case that would make any difference.

The only line of code for the camera:
Code: [Select]
tk2dCamera.inst.mainCamera.transform.position = new Vector3(this.transform.position.x , this.transform.position.y, tk2dCamera.inst.transform.position.z);
Is that. I'm simply trying to have it follow the player, but ideally the player would be in the center of the screen. Am I doing something REALLY stupid here, am I missing something important, or what?

Thanks!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 10, 2013, 12:50:24 am
With tk2dCamera, 0, 0, = bottom left of the screen. If you want 0, 0 to be the center of the screen, create an anchor, set it to middle center, and then attach everything to that instead.

Or... when moving the camera to follow the player, make sure it is offset by 1/2 resolution to re-center it.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 10, 2013, 03:05:09 am
Sorry for the staggering amount of questions, but I created an anchor and made the tilemap and the tilemap data children of the anchor. Now the player sprite is in the center of the screen but the anchor doesn't move with the player sprite. I didn't change any code, and when I tried to do it based on the anchor it seemed to cause more harm than good.

So I'm obviously missing something. =S

Any suggestions would be appreciated.

Once again, thanks!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 12, 2013, 01:31:16 pm
How do you move the camera with the player? Do you make it a child under the player or do you have a script to do it?
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 12, 2013, 05:47:20 pm
I actually just tried the alternative method, of offsetting it by half the resolution in the width and height directions. Seems to work just fine.

Thanks though!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 14, 2013, 02:20:33 am
Apologies for the double posting, but I have a question regarding tile based movement now.

Code: [Select]
//  UP
if (Input.GetKey(KeyCode.UpArrow))
{
direction = 0;
walk = true;
// this.transform.position = new Vector3(this.transform.position.x, this.transform.position.y + 1, this.transform.position.z);
if (map.GetTileAtPosition(currTile, out mapX, out mapY))
{
destTile = new Vector3(currTile.x, map.GetTilePosition(mapX, mapY + 1).y + (map.partitionSizeY / 2), currTile.z);
HOTween.To(this.transform, 1, "position", destTile);
}
}

I'm using HOTween to tween him between two spots but it looks rather "janky" for lack of a better term. The player sprite essentially stutters between tiles. I believe this has to do with the duration of the tween, but when setting it to 0 the player can basically fly across the map in a matter of seconds because they move so fast. I understand this is not 2DToolkit related, but do you have any tips on this front?

Also more related to the plugin, is there an easier way to make sure the player aligns with the tile properly? currTile represents the players world position in a Vector3() (I need to change the name of that variable >.>), destTile is also a Vector3 that represents the world position (also should change the name of that variable).

Thanks again!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 14, 2013, 09:14:59 am
Have you tried the other easeTypes with the transition? I'm sure you can find one which looks & works better for you. HoTween also supports custom easeTypes, with that you should be able to perfect your tween.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: rylgh on January 14, 2013, 05:09:35 pm
I'm in a similar situation (trying to move a tk2dCamera around to keep it centered on the player), but I'm finding that there is significant jittering, and on iOS there is 'tearing' (the appearance of white lines on the edge of the moving player sprite).

Is this to be expected when moving both the camera and the sprites at the same time? Should I be keeping the camera stationary and moving only the world objects, or is there something I can do to reduce the jittering?

Right now I'm simply doing this for my tk2dCamera:
Code: [Select]
_transform.position = new Vector3(_playerTransform.position.x - _width * 0.5f, _playerTransform.position.y - _height * 0.5f, _transform.position.z);while my player is also having its position manipulated in a similar way.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 14, 2013, 06:52:03 pm
There should be no difference to moving the camera or the sprites by the inverse camera movement - they all reduce to the same thing. There are a lot of solutions to perceived jitter - most of the time it is due to moving the camera by different amounts (different deltaTime per frame). Check that your frame times arent changing too much.

About tearing, I suggest updating to 1.90 beta (just the shaders will be sufficient if you don't want to update everything) to test there, that should be gone - it is likely the shader precision issue which was solved in that version.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: rylgh on January 15, 2013, 06:05:27 am
Thanks unikron! It seems like the tearing is gone after trying out the beta. The jitteriness also seems to be improved on iOS, though it remains in the editor. Mind mentioning a couple of the solutions for camera jitter? My frame times do seem to have small spikes pretty often.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 15, 2013, 11:15:38 am
There isn't a general solution to this - you'll have to find out why its jittering by looking in the profiler. It should at least give you some hints as to why one or two frames are taking longer than others.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 20, 2013, 10:53:30 pm
Hey, so I'm still having some minor annoyances with the camera:

If you look at this gallery you'll see what I mean:

http://minus.com/mbrRDDKMQAHr2L (http://minus.com/mbrRDDKMQAHr2L)

Essentially I have this code to check the bounds of the map (so the camera doesn't pass them):

Code: [Select]
void pCamera()
{

tk2dCamera.inst.mainCamera.transform.position = new Vector3(this.transform.position.x - tk2dCamera.inst.nativeResolutionWidth / 2,
this.transform.position.y - tk2dCamera.inst.nativeResolutionHeight / 2, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.x < 0)
tk2dCamera.inst.transform.position = new Vector3(map.width - map.partitionSizeX * map.width, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);
if (tk2dCamera.inst.transform.position.y < 0)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, map.height - map.partitionSizeY * map.height, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.x > map.partitionSizeX * map.width - tk2dCamera.inst.nativeResolutionWidth)
tk2dCamera.inst.transform.position = new Vector3(map.partitionSizeX * map.width - tk2dCamera.inst.nativeResolutionWidth, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);
if (tk2dCamera.inst.transform.position.y > map.partitionSizeY * map.height - tk2dCamera.inst.nativeResolutionHeight)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, map.partitionSizeY * map.height - tk2dCamera.inst.nativeResolutionHeight, tk2dCamera.inst.transform.position.z);
}

As you can see in the linked image gallery, when I go to the bottom (and also the left hand side of the map), I do not see the complete tiles on the edges of the tile map. However, when I go to right (and also the top of the map) I see past the edge of the tilemap.

Any idea for possible fixes?

Thanks again!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on January 22, 2013, 11:27:05 am
This is likely to be because your calculation is perhaps ignoring the tile offset? How is the anchor set up on the sprite? Is it bottom left?

It almost looks like the whole thing is offset by 1/2 a tile. You can easily fix this by offsetting by half a tile dimension, or change the offset in the tile itself. The first solution is probably quicker to implement.

You can get the bounds by looking in tileMap.data.tileSize.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on January 22, 2013, 10:59:19 pm
It was an issue with the tile's anchors. Derp.

Thanks though!
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on February 04, 2013, 03:25:16 am
Sorry for reviving the thread but I've upgraded to 1.9 and now my camera is acting up again. Essentially the problem from a few posts up (seeing past the edge of the map) has become true again... but only on the X axis.

Code: [Select]
tk2dCamera.inst.mainCamera.transform.position = new Vector3(this.transform.position.x - tk2dCamera.inst.nativeResolutionWidth / 2,
this.transform.position.y - tk2dCamera.inst.nativeResolutionHeight / 2, tk2dCamera.inst.transform.position.z);


if (tk2dCamera.inst.transform.position.x < 0)
tk2dCamera.inst.transform.position = new Vector3(0, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);
if (tk2dCamera.inst.transform.position.y < 0)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, 0, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.x > map.data.tileSize.x * map.width - tk2dCamera.inst.nativeResolutionWidth)
tk2dCamera.inst.transform.position = new Vector3(map.data.tileSize.x * map.width - tk2dCamera.inst.nativeResolutionWidth, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.y > map.data.tileSize.y * map.height - tk2dCamera.inst.nativeResolutionHeight)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, map.data.tileSize.y * map.height - tk2dCamera.inst.nativeResolutionHeight, tk2dCamera.inst.transform.position.z);

The code is pretty much the same, just using tile data instead of partition size. Either way it has not made a difference which I use. My tile sheet sprites are set to have a lower left anchor as suggested, but like I said the problem has popped up again, and only on the x-axis.

Any suggestions?

Thanks again.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on February 04, 2013, 09:52:00 am
Can you set up a simple test case for me? I'd like to try and work out what has changed (nothing should have changed and thats why I worry slightly). support@unikronsoftware.com if you can.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on February 05, 2013, 01:49:49 am
Sure, I can try to send you something tomorrow.
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: unikronsoftware on February 05, 2013, 06:38:10 pm
Thanks for your sample, it would have taken a LONG time to work out otherwise.

The reason the sample worked before, is likely that your "Force Editor Resolution" was set to the same aspect ratio as the native resolution. The calculation is still correct, just that the fitting algorithm now displays a bit more in the horizontal axis than before.

If you set auto-scale to "Stretch to Fit" your image should be correct, though it will be stretched horizontally to fit the screen.

You can get the exact "extents" of the visible screen at the current adjusted resolution using tk2dCamera.ScreenExtents. Your code modified to work at any resolution and/or scaling option is below:

Code: [Select]
tk2dCamera.inst.mainCamera.transform.position = new Vector3(this.transform.position.x - tk2dCamera.inst.nativeResolutionWidth / 2,
this.transform.position.y - tk2dCamera.inst.nativeResolutionHeight / 2, tk2dCamera.inst.transform.position.z);

Rect extents = tk2dCamera.inst.ScreenExtents;
if (tk2dCamera.inst.transform.position.x < -extents.xMin)
tk2dCamera.inst.transform.position = new Vector3(-extents.xMin, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);
if (tk2dCamera.inst.transform.position.y < -extents.yMax)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, -extents.yMax, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.x > map.data.tileSize.x * map.width - extents.xMax)
tk2dCamera.inst.transform.position = new Vector3(map.data.tileSize.x * map.width - extents.xMax, tk2dCamera.inst.transform.position.y, tk2dCamera.inst.transform.position.z);

if (tk2dCamera.inst.transform.position.y > map.data.tileSize.y * map.height - extents.yMin)
tk2dCamera.inst.transform.position = new Vector3(tk2dCamera.inst.transform.position.x, map.data.tileSize.y * map.height - extents.yMin, tk2dCamera.inst.transform.position.z);

Also note you should cache tk2dCamera.inst.transform.position and use it instead of accessing it every time
Title: Re: Two Questions (Camera / Tilebased Movement)
Post by: fryedrycestyle on February 06, 2013, 02:51:54 am
Excellent, thanks! And yes you're probably right about the caching.