using UnityEngine;
using System.Collections;
[RequireComponent( typeof( TweenPosition ) )]
public class FloatingTextUp2D : MonoBehaviour
{
public enum Side
{
Left,
Right,
Center,
NoOutOfScreen,
NoTouch
}
private UILabel mLabel; // from ScriptIncluded
private Vector3 mObjPos;
public Camera guiCamera = null;
public Camera worldCamera = null;
public GameObject targetObject = null;
public float tweenDuration = 2.5f;
public float tweenDistance = 350f;
public Side startSide = Side.NoOutOfScreen;
///
/// move up by Percent from -1 ~ 1. 0 is middle of scrren. If this is false, tweenDistance used to end of tween moving.
///
public bool moveUpByPercent = false;
///
/// how much move up? this value from -1 to 1. 0 is middle of screen.
///
[Range(-1, 1)]
public float moveUpPercent = 0f;
///
/// Auto Scale by screen width. if zero, use original size. if 1, full width.
///
[Range( 0, 1 )]
public float scaleByScreen = 0f;
///
/// If scaleByScreen not setted. use this.
///
//public Vector2 defaultSize = new Vector2( 1, 1 );
public void destroySelf()
{
Destroy( gameObject );
}
// get UILabel width, height roughly. code from UILabel.MakePixelPerfect()
public Vector2 getUILabelSize()
{
float pixelSize = (mLabel.font.atlas != null) ? mLabel.font.atlas.pixelSize : 1f;
Vector3 scale = mLabel.cachedTransform.localScale;
if( scaleByScreen != 0f )
scale.x = ((guiCamera.pixelWidth / mLabel.relativeSize.x) * scaleByScreen);
else
scale.x = mLabel.font.size * pixelSize;
scale.y = scale.x;
scale.z = 1f;
return (mLabel.relativeSize * scale.x);
}
public Vector3 fixPosition( Vector3 value_ )
{
Rect rect = new Rect();
rect = guiCamera.pixelRect;
if( startSide != Side.NoTouch )
{
Vector3 _tmpPos = guiCamera.WorldToScreenPoint( value_ );
Vector2 _labelSize = getUILabelSize();
float _middleX = Mathf.Abs( _labelSize.x * mLabel.pivotOffset.x );
if( startSide == Side.Center )
{
_tmpPos.x = (rect.xMin + rect.xMax) * 0.5f;
}
else if( startSide == Side.Left )
{
_tmpPos.x = (rect.xMin + _middleX);
}
else if( startSide == Side.Right )
{
_tmpPos.x = (rect.xMax - _middleX);
}
else if( startSide == Side.NoOutOfScreen )
{
if( (_tmpPos.x - _middleX) < rect.xMin ) _tmpPos.x = rect.xMin + _middleX;
if( (_tmpPos.x + _middleX) > rect.xMax ) _tmpPos.x = rect.xMax - _middleX;
}
value_ = guiCamera.ScreenToWorldPoint( _tmpPos );
}
return value_;
}
public void adjustPosition( Vector3 pos_ )
{
mObjPos = worldCamera.WorldToViewportPoint( pos_ );
mObjPos = guiCamera.ViewportToWorldPoint( mObjPos );
mObjPos = fixPosition( mObjPos );
mObjPos.z = 0f;
transform.position = mObjPos;
}
public void adjustScale()
{
if( scaleByScreen == 0f )
{
mLabel.MakePixelPerfect(); // why bigger???
return;
}
else if( mLabel.font != null )
{
float pixelSize = (mLabel.font.atlas != null) ? mLabel.font.atlas.pixelSize : 1f;
//pixelSize = 4;
Vector3 scale = mLabel.cachedTransform.localScale;
//scale.x = mLabel.font.size * pixelSize;
scale.x = ((guiCamera.pixelWidth / mLabel.relativeSize.x) * scaleByScreen);
scale.y = scale.x;
scale.z = 1f;
Vector2 actualSize = mLabel.relativeSize * scale.x;
int x = Mathf.RoundToInt( actualSize.x / pixelSize );
int y = Mathf.RoundToInt( actualSize.y / pixelSize );
Vector3 pos = mLabel.cachedTransform.localPosition;
pos.x = Mathf.FloorToInt( pos.x / pixelSize );
pos.y = Mathf.CeilToInt( pos.y / pixelSize );
pos.z = Mathf.RoundToInt( pos.z );
if( mLabel.cachedTransform.localRotation == Quaternion.identity )
{
if( (x % 2 == 1) && (mLabel.pivot == UILabel.Pivot.Top || mLabel.pivot == UILabel.Pivot.Center || mLabel.pivot == UILabel.Pivot.Bottom) ) pos.x += 0.5f;
if( (y % 2 == 1) && (mLabel.pivot == UILabel.Pivot.Left || mLabel.pivot == UILabel.Pivot.Center || mLabel.pivot == UILabel.Pivot.Right) ) pos.y -= 0.5f;
}
pos.x *= pixelSize;
pos.y *= pixelSize;
mLabel.cachedTransform.localPosition = pos;
mLabel.cachedTransform.localScale = scale;
}
}
public void startMoveUp( Vector3 initPos_, float tweenDuration_, float tweenEnd_ )
{
adjustScale();
adjustPosition( initPos_ );
TweenPosition _tp = this.tweenPosition;
_tp.eventReceiver = gameObject;
_tp.callWhenFinished = "destroySelf";
_tp.from = transform.localPosition;
if( moveUpByPercent )
{
_tp.to = Vector3.up * (Screen.height * 0.5f) * moveUpPercent;
_tp.to.x = _tp.from.x;
}
else
{
_tp.to = _tp.from + Vector3.up * tweenEnd_;
}
if( tweenDuration_ != 0 )
{
_tp.duration = tweenDuration_;
}
}
public void initAndStartMoving( Vector3 initPos_, Camera mainCam_ = null, Camera guiCam_ = null )
{
if( mainCam_ != null ) worldCamera = mainCam_;
if( guiCam_ != null ) guiCamera = guiCam_;
startMoveUp( initPos_, tweenDuration, tweenDistance );
}
// Unity3d reaction function
public void Awake()
{
mLabel = GetComponent();
}
void Start()
{
if( guiCamera == null ) {
guiCamera = NGUITools.FindCameraForLayer( gameObject.layer );
}
if( worldCamera == null ) {
worldCamera = Camera.mainCamera;
}
if( targetObject != null ) {
startMoveUp( targetObject.transform.position, tweenDuration, tweenDistance );
}
}
public TweenPosition tweenPosition
{
get {
TweenPosition _tp = GetComponent();
if( _tp == null ) _tp = gameObject.AddComponent();
return _tp;
}
}
}