枪械展示项目 :全记录
先来一张效果图:【感觉自己的PS又进步了
项目分为三个场景以及主要实现功能:
主场景 点击相应按钮实例化相应模型,点击左侧资料按钮,显示模型对应的资料;
时间线场景 时间线为NGUI搭建,使用tween动画实现出动态效果;
拆装演示场景 模型的拆装动画。
主场景:——————
NGUI搭建UI界面,底边栏按钮用于实例化对应模型,将按钮全部挂载EventListener脚本,并且整合在一个脚本中,挂载与场景的空物体中。
由于每个按钮都会执行实例化与模型自旋转的函数, 将它们写在一个GunsScript.cs脚本中
内中 静态函数实例化,以及静态函数模型自旋转,
注意:声明一个静态变量,用于其他脚本调用时赋值。【这样便可以拿到正确的变量值
GunsScript.cs完整代码:
1 using UnityEngine; 2 using System . Collections; 3 4 /// <summary> 5 /// 枪械模型的脚本,目前包含【实例化,模型自转 6 /// </summary> 7 public class GunsScript : MonoBehaviour 8 { 9 //只需要在这里声明一个静态变量,用于存储实例化出来的物体 10 public static GameObject newGuns ; 11 12 /// <summary> 13 /// 实例化 14 /// </summary> 15 /// <param name="go"> 模型 </param> 16 /// <param name="particlesOne"> 随模型一起的粒子</param> 17 public static void ShiLiHua ( GameObject Guns , GameObject particlesOne ) 18 { 19 //实例化出来一把枪械【具体哪一把,在脚本调用时候会赋值 20 newGuns = Instantiate ( Guns , Vector3 . zero , Quaternion . identity ) as GameObject; 21 22 //实例化出来一个初始的粒子【魔法阵那个 23 Instantiate ( particlesOne , Vector3 . zero , Quaternion . identity ); 24 } 25 26 /// <summary> 27 /// 模型自旋转方法 28 /// </summary> 29 /// <param name="Gun"> 模型 </param> 30 public static void GunRotate ( GameObject Gun) 31 { 32 Gun . transform . Rotate ( Vector3 . up , 35 * Time . deltaTime , Space . World ); 33 34 Debug . Log ( "自转" +Gun ); 35 } 36 }
底边栏多个按钮的统一脚本 ButtonsEL.cs 完整代码:
1 using UnityEngine; 2 using System . Collections; 3 /// <summary> 4 /// 底边栏多个按钮的统一控制脚本【包含,调用实例化,调用模型自旋转,粒子效果,详细信息按钮的Label文本,以及正上方Label枪械名称 5 /// </summary> 6 public class ButtonsEL : MonoBehaviour 7 { 8 public GameObject MAGun;//M4A1模型 9 public GameObject AKGun;// AK-47模型 10 public GameObject ACOGGun; //瞄准器 11 public GameObject particlesOne;//魔法阵粒子 12 public GameObject particles;//光球 13 public float myTimer = 5.0f;//计时器 14 15 public UILabel gunsLabelText;//详细信息的文本 16 17 public UILabel gunsNameText;//枪械名字的Label 18 19 void Awake() 20 { 21 //找到按钮【绝对路径要写对 22 GameObject MABtn =GameObject . Find ( "UI Root/Camera/Panel/DiLan/MABtn" ); 23 GameObject AKBtn =GameObject . Find ( "UI Root/Camera/Panel/DiLan/AKBtn" ); 24 GameObject ACOGBtn=GameObject.Find ("UI Root/Camera/Panel/DiLan/ACOGBtn"); 25 26 Debug . Log ( "M4A1:" + MABtn + "AK-47:" + AKBtn +"ACOG:"+ACOGBtn ); 27 28 //事件监听 29 UIEventListener . Get ( MABtn ) . onClick = MABtnClick; 30 UIEventListener . Get ( AKBtn ) . onClick = AKBtnClick; 31 UIEventListener . Get ( ACOGBtn ) . onClick = ACOGBtnClick; 32 33 //文本默认 空 34 gunsLabelText . text = ""; 35 gunsNameText . text = ""; 36 } 37 38 /// <summary> 39 /// 点击 M4A1按钮 执行的函数 40 /// </summary> 41 /// <param name="go"></param> 42 private void MABtnClick(GameObject go) 43 { 44 //实例化一把M4A1 45 GunsScript . ShiLiHua ( MAGun ,particlesOne); 46 //M4A1 = 主角本 的 实例化出来的枪械那个变量 47 MAGun = GunsScript . newGuns; 48 Debug . Log ( "实例化M4A1:" + MAGun ); 49 50 //枪械名字的Label,以及枪械的详细信息Label 51 gunsNameText . text = "M4a1"; 52 gunsLabelText . text = 53 "中文名:M4A1卡宾枪\r\n" + 54 "外文名:M4A1carbine\r\n" + 55 "类型:突击步枪、卡宾枪\r\n" + 56 "原产国:美国\r\n" + 57 "服役期间:1995年-至今" + 58 "生产商:柯尔特、Fabrique Nationale(生产承包)\r\n" + 59 "军用价格:800-1200美元/支\r\n" + 60 "生产日期:1993年-至今\r\n" + 61 "衍生型:M4A1、CQBR 、SOPMODM4\r\n" + 62 "\r\n" + 63 "基本规格-------\r\n" + 64 "\r\n"+ 65 "空枪:2.68公斤\r\n" + 66 "连30发弹匣:3.13公斤\r\n" + 67 "全长 :缩起枪托状态下757 毫米(22.7 寸),展开枪托状态下840 毫米(25.3 寸)\r\n" + 68 "枪管长度 368.3 毫米(11.06寸)\r\n" + 69 "弹药:5.56 x 45毫米\r\n" + 70 "口径:5.56毫米(0.223寸,北约各国通用,使用相同口径:Famas,AR-15、SG550、SG552、M249。)\r\n" + 71 "枪机种类:气动式,转拴式枪机\r\n" + 72 "发射速率:800–980发/分\r\n" + 73 "枪口初速:884 m/秒\r\n" + 74 "供弹方式: 20 30、35发STANAG弹匣\r\n" + 75 "有效射程:400米\r\n" + 76 "设计:M4卡宾枪的设计可追溯至早期卡宾枪版本的M16及XM177,都是由尤金·斯通纳开发的。"; 77 78 //将AK-47移走 79 AKGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 80 //将瞄准器移走 81 ACOGGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 82 } 83 84 private void AKBtnClick(GameObject go) 85 { 86 GunsScript . ShiLiHua ( AKGun , particlesOne ); 87 AKGun = GunsScript . newGuns; 88 Debug . Log ( "AKBtn" + AKGun); 89 90 // 91 gunsNameText . text = "AK-47"; 92 gunsLabelText . text = 93 "中文名:AK-47突击步枪\r\n" + 94 "外文名:AK-47 assault rifle\r\n" + 95 "原产国:苏联\r\n" + 96 "弹容量:30发\r\n" + 97 "膛 线:4条/右旋\r\n" + 98 "射 速:600发/分\r\n" + 99 "服役时间:1947-\r\n" + 100 "售 价:约450美元\r\n" + 101 "枪 重:4.1千克\r\n" + 102 "固定型全长:870毫米\r\n" + 103 "折叠型全长:645毫米\r\n" + 104 "口 径:7.62毫米\r\n" + 105 "有效射程:300-350米\r\n" + 106 "表尺射程:800米\r\n" + 107 "枪口动能:1989J\r\n" + 108 "生产数:7000万-1.5亿支\r\n" + 109 "枪口初速:710米/每秒\r\n" + 110 "\r\n" + 111 "АК-47是由苏联枪械设计师米哈伊尔·季莫费耶维奇·卡拉什尼科夫(Михаил Тимофеевич Калашников)设计的自动步枪。AK是Автомат Калашникова (卡拉什尼科夫1947年制造的自动步枪)的首字母缩写。是苏联的第一代突击步枪。\r\n" + 112 "\r\n" + 113 "AK-47属于突击步枪,与第二次世界大战时期的步枪相比,枪身短小、射程较短,适合较近距离的战斗。采用气动式自动原理,导气管位于枪管上方,通过活塞推动枪机动作,回转式闭锁枪机。\r\n" ; 114 //将M4A1移走 115 MAGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 116 //将瞄准器移走 117 ACOGGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 118 } 119 120 private void ACOGBtnClick(GameObject go) 121 { 122 GunsScript . ShiLiHua ( ACOGGun , particlesOne ); 123 ACOGGun = GunsScript . newGuns; 124 Debug . Log ( "ACOGBtn" + ACOGGun); 125 126 gunsNameText . text = "ACOG"; 127 gunsLabelText.text = 128 "中文名:ACOG\r\n" + 129 "外文名:Advanced Combat Optical Gunsight\r\n" + 130 "全 称:先进战斗光学瞄准镜\r\n" + 131 "目 的:专为M16系列步枪使用而制作\r\n" + 132 "\r\n" + 133 "ACOG瞄准镜装置在设计上是用在M16系列步枪(即是M4卡宾枪也可装上),但Trijicon公司制造的ACOG配件亦可协助安装于其他的武器。此型号可提供1.5—6 倍的放大倍率。\r\n" + 134 "\r\n" + 135 "与许多反射式瞄准镜(例如Aimpoint Comp M2)相反,ACOG内部的叠加式分划标记是由内置式萤光粉作夜间照明。有些型号更会在瞄准镜的外部顶部端加上一条采光用途的被动外置式光纤导光管系统,以便在白天时间吸收自然光(光纤有多种花纹和颜色,而目前最常见的是红色),然后在自然光不足时使用安装于ACOG内置式低放射性的氢同位素氚灯提供光源。由于氚的半衰期约为10—15 年,在这段时间亮度会因为放射性衰变而在一般的时间内减少了一半并且失去光泽,这时便需要更换内部的氚灯。\r\n" + 136 "\r\n" + 137 " 这个系列始创于1987年,当时是作为美国先进战斗步枪——ACR计划的其中一部分。ACOG是望远式瞄准镜和光点瞄准镜的结合体,既有放大的功能,又兼具双目快速瞄准的功能。"; 138 139 140 //将M4A1移走 141 MAGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 142 //将AK-47移走 143 AKGun . transform . position += new Vector3 ( 200 , 0 , 0 ); 144 } 145 146 void Update() 147 { 148 //调用 枪械主脚本中 模型旋转的方法(参数为 实例化出来的物体) 149 GunsScript . GunRotate ( GunsScript . newGuns ); 150 //每隔五秒实例化一个光球粒子效果 151 if ( myTimer > 0 ) 152 { 153 myTimer -= Time . deltaTime; 154 } 155 if ( myTimer < 0 ) 156 { 157 Instantiate ( particles , Vector3 . zero , Quaternion . identity ); 158 myTimer = 5.0f; 159 } 160 } 161 }
时间线场景中的时间线动画【也就是图片的一些tween效果
为了避免不同分辨率下的错位现象,全部图片统一像素,在代码中直接控制其播放
注意:由于不考虑性能优化,才可以这样写。
tweenScript.cs 完整代码:
1 using UnityEngine; 2 using System . Collections; 3 4 public class tweenScript : MonoBehaviour 5 { 6 public UISprite timeLine1132;//时间线 7 public UISprite timeLine1259; 8 public UISprite timeLine14; 9 public UISprite timeLine15; 10 public UISprite timeLine16; 11 public UISprite timeLine17; 12 public UISprite timeLine19; 13 14 public UISprite TL1132T;//描述 15 public UISprite TL1259T; 16 public UISprite TL14T; 17 public UISprite TL15T; 18 public UISprite TL16T; 19 public UISprite TL17T; 20 public UISprite Tl19T; 21 22 public UISprite LeftBottom;//枪械图 23 public UISprite RighTop; 24 public UISprite LeftTop; 25 public UISprite RightBottom; 26 27 public float timer = 0.0f;//时间【用于计时器 28 29 void Start ( ) 30 { 31 //图片 的 透明度 = 初始为0 32 LeftBottom . alpha = 0; 33 RighTop . alpha = 0; 34 LeftTop . alpha = 0; 35 RightBottom . alpha = 0; 36 } 37 38 void Update ( ) 39 { 40 //计时器启动 41 timer += Time . deltaTime; 42 //如果时间>1秒 43 if ( timer >= 0.5f ) 44 { 45 //获得时间线控件的 TweenPosition(位移)组件 并且播放 46 timeLine1132 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 47 Debug . Log ( "测试输出" + timer ); 48 } 49 if ( timer >= 0.8f ) 50 { 51 TL1132T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 52 } 53 if ( timer >= 1.6f ) 54 { 55 timeLine1259 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 56 } 57 if ( timer >= 2.4f ) 58 { 59 TL1259T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 60 } 61 if ( timer >= 3.2f ) 62 { 63 timeLine14 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 64 } 65 if ( timer >= 4.0f ) 66 { 67 TL14T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 68 } 69 if ( timer >= 4.8f ) 70 { 71 timeLine15 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 72 } 73 if ( timer >= 5.6f ) 74 { 75 TL15T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 76 } 77 if ( timer >= 6.4f ) 78 { 79 timeLine16 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 80 } 81 if ( timer >= 7.2f ) 82 { 83 TL16T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 84 } 85 if ( timer >= 8.0f ) 86 { 87 timeLine17 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 88 } 89 if ( timer >= 8.8f ) 90 { 91 TL17T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 92 } 93 if ( timer >= 9.6f ) 94 { 95 timeLine19 . GetComponent<TweenPosition> ( ) . PlayForward ( ); 96 } 97 if ( timer >= 10.4f ) 98 { 99 Tl19T . GetComponent<TweenPosition> ( ) . PlayForward ( ); 100 } 101 102 // ======枪图的渐显效果 103 //如果 时间 > 7秒 104 if ( timer >= 3 ) 105 { 106 //枪械图片控件的 TweenAlpha(渐显动画) 播放 107 LeftBottom . GetComponent<TweenAlpha> ( ) . PlayForward ( ); 108 } 109 if ( timer >= 6 ) 110 { 111 RighTop . GetComponent<TweenAlpha> ( ) . PlayForward ( ); 112 } 113 if ( timer >= 9 ) 114 { 115 LeftTop . GetComponent<TweenAlpha> ( ) . PlayForward ( ); 116 } 117 if ( timer >= 12 ) 118 { 119 RightBottom . GetComponent<TweenAlpha> ( ) . PlayForward ( ); 120 } 121 } 122 }
拆装演示场景:
由于模型来自官网, 只有枪身,准镜及弹匣三个部分, 将其分别拖入场景的空物体下,【这样可以使它们的Transform全部在0的位置上,方便内部操作。
使用Animation 制作一个 准镜由上而下,弹匣由下而上的简易Y轴移动动画。
Loop Time 取消勾选。【只播放一次
由于第一次使用动画系统,代码控制尚未学习。
为了不过与单调,也为了练手,加了一个鼠标控制模型预览的脚本,直接挂载在拆装演示场景的Main Camera上。
MainCameraScript.cs 完整代码:
1 using UnityEngine; 2 using System . Collections; 3 4 /// <summary> 5 /// 挂载在主相机的脚本【出了ESC退出功能外,其余为鼠标控制模型拖拽旋转及缩放 6 /// </summary> 7 public class MainCameraScript : MonoBehaviour 8 { 9 public Transform target;//目标物体 10 private int MouseWheelSensitivity =1;//鼠标滚轮灵敏度 11 private int MouseZoomMin =1;//鼠标最小缩放值 12 private int MouseZoomMax = 10;//鼠标最大缩放值 13 private float normalDistance =10;//正常的距离 14 15 private Vector3 normalized;//标准化 16 17 private float xSpeed = 250.0f;//X轴速度 18 private float ySpeed = 120.0f;//Y轴速度 19 20 private int yMinLimit = -20;//Y轴最小限制 21 private int yMaxLimit =80;//Y轴最大限制 22 23 private float x =0.0f; 24 private float y = 0.0f; 25 26 private Vector3 screenPoint;//屏幕点 27 private Vector3 offset;//偏移 28 // 四元数 旋转 29 private Quaternion rotation =Quaternion . Euler ( new Vector3 ( 30f , 0f , 0f ) ); 30 private Vector3 CameraTarget;//摄像机目标 31 32 void Start ( ) 33 { 34 //摄像机目标 = 目标 的 坐标值 35 CameraTarget = target . position; 36 //定义了一个Z轴 =目标 的 变换 的 坐标值 的Z轴 - 标准距离 37 float z =target . transform . position . z - normalDistance; 38 transform . position = rotation * new Vector3 ( transform . position . x , transform . position . y , z ); 39 40 transform . LookAt ( target ); 41 42 var angles =transform . eulerAngles; 43 44 x = angles . y; 45 y = angles . x; 46 } 47 48 void Update ( ) 49 { 50 //如果按下ESC键,返回到主场景 51 if ( Input . GetKeyDown ( KeyCode . Escape ) ) 52 { 53 Application . LoadLevel ( "Main Scene" ); 54 } 55 56 //鼠标控制场景中的模型 57 //鼠标右键 58 if ( Input . GetMouseButton ( 1 ) ) 59 { 60 x += Input . GetAxis ( "Mouse X" ) * xSpeed * 0.02f; 61 y -= Input . GetAxis ( "Mouse Y" ) * ySpeed * 0.02f; 62 63 y = ClampAngle ( y , yMinLimit , yMaxLimit ); 64 65 var rotation = Quaternion . Euler ( y , x , 0 ); 66 var position = rotation * new Vector3 ( 0.0f , 0.0f , -normalDistance ) + CameraTarget; 67 68 transform . rotation = rotation; 69 transform . position = position; 70 } 71 //鼠标滚轮 72 else if ( Input . GetAxis ( "Mouse ScrollWheel" ) != 0 ) 73 { 74 normalized = ( transform . position - CameraTarget ) . normalized; 75 76 if ( normalDistance >= MouseZoomMin && normalDistance <= MouseZoomMax ) 77 { 78 normalDistance -= Input . GetAxis ( "Mouse ScrollWheel" ) * MouseWheelSensitivity; 79 } 80 if ( normalDistance < MouseZoomMin ) 81 { 82 normalDistance = MouseZoomMin; 83 } 84 if ( normalDistance > MouseZoomMax ) 85 { 86 normalDistance = MouseZoomMax; 87 } 88 transform . position = normalized * normalDistance; 89 90 } 91 //鼠标中键 92 else if ( Input . GetMouseButtonDown ( 2 ) ) 93 { 94 screenPoint = Camera . main . WorldToScreenPoint ( target . transform . position ); 95 offset = target . transform . position - Camera . main . ScreenToWorldPoint ( new Vector3 ( Input . mousePosition . x , Input . mousePosition . y , screenPoint . z ) ); 96 } 97 //鼠标中键 98 if ( Input . GetMouseButton ( 2 ) ) 99 { 100 Vector3 curScreenPoint = new Vector3 ( Input . mousePosition . x , Input . mousePosition . y , screenPoint . z ); 101 102 Vector3 curPosition = Camera . main . ScreenToWorldPoint ( curScreenPoint ) + offset; 103 target . transform . position = curPosition; 104 } 105 transform . LookAt ( CameraTarget ); 106 107 } 108 // 夹角 109 static float ClampAngle ( float angle , float min , float max ) 110 { 111 if ( angle < -360 ) 112 angle += 360; 113 if ( angle > 360 ) 114 angle -= 360; 115 return Mathf . Clamp ( angle , min , max ); 116 } 117 }
最后再来几张图吧,
时间: 2024-10-12 23:52:21