Unity開啟篇(十三) —— Unity腳本簡介(二)

版本記錄

版本號(hào) 時(shí)間
V1.0 2019.01.26 星期六

前言

Unity是由Unity Technologies開發(fā)的一個(gè)讓玩家輕松創(chuàng)建諸如三維視頻游戲碌嘀、建筑可視化涣旨、實(shí)時(shí)三維動(dòng)畫等類型互動(dòng)內(nèi)容的多平臺(tái)的綜合型游戲開發(fā)工具,是一個(gè)全面整合的專業(yè)游戲引擎筏餐。Unity類似于Director,Blender game engine, Virtools 或 Torque Game Builder等利用交互的圖型化開發(fā)環(huán)境為首要方式的軟件。其編輯器運(yùn)行在Windows 和Mac OS X下牡拇,可發(fā)布游戲至Windows魁瞪、Mac穆律、WiiiPhone导俘、WebGL(需要HTML5)峦耘、Windows phone 8和Android平臺(tái)。也可以利用Unity web player插件發(fā)布網(wǎng)頁游戲旅薄,支持Mac和Windows的網(wǎng)頁瀏覽辅髓。它的網(wǎng)頁播放器也被Mac 所支持。網(wǎng)頁游戲 坦克英雄和手機(jī)游戲王者榮耀都是基于它的開發(fā)少梁。
下面我們就一起開啟Unity之旅洛口。感興趣的看下面幾篇文章。
1. Unity開啟篇(一) —— Unity界面及創(chuàng)建第一個(gè)簡單的游戲 (一)
2. Unity開啟篇(二) —— Unity界面及創(chuàng)建第一個(gè)簡單的游戲 (二)
3. Unity開啟篇(三) —— 一款簡單射擊游戲示例 (一)
4. Unity開啟篇(四) —— 一款簡單射擊游戲示例 (二)
5. Unity開啟篇(五) —— 一款簡單射擊游戲示例 (三)
6. Unity開啟篇(六) —— Unity動(dòng)畫簡介 (一)
7. Unity開啟篇(七) —— Unity動(dòng)畫簡介 (二)
8. Unity開啟篇(八) —— Unity聲音簡介(一)
9. Unity開啟篇(九) —— Unity聲音簡介(二)
10. Unity開啟篇(十) —— Unity粒子系統(tǒng)簡介(一)
11. Unity開啟篇(十一) —— Unity粒子系統(tǒng)簡介(二)
12. Unity開啟篇(十二) —— Unity腳本簡介(一)

Working with Prefabs

簡單地跑來跑去避開敵人是一個(gè)非常片面的游戲凯沪。 是時(shí)候武裝玩家進(jìn)行戰(zhàn)斗了第焰。

單擊“層次結(jié)構(gòu)”中的Create按鈕,然后選擇3D Object/Capsule妨马。 將其命名為Projectile并為其提供以下變換值:

  • 1) Position: (0, 0, 0)
  • 2) Rotation: (90, 0, 0)
  • 3) Scale: (0.075, 0.246, 0.075)

每次玩家射擊時(shí)挺举,它都會(huì)發(fā)射一枚Projectile。 要實(shí)現(xiàn)這一點(diǎn)烘跺,您需要?jiǎng)?chuàng)建一個(gè)預(yù)制件(Prefab)湘纵。 與場(chǎng)景中已有的對(duì)象不同,預(yù)制件是由游戲邏輯按需創(chuàng)建的滤淳。

Assets下創(chuàng)建一個(gè)名為Prefabs的新文件夾梧喷。 現(xiàn)在將Projectile對(duì)象拖動(dòng)到此文件夾中。 就是這樣:你有一個(gè)預(yù)制件娇钱!

你的預(yù)制件需要一些腳本伤柄。 在名為ProjectileScripts文件夾中創(chuàng)建一個(gè)新腳本,并向其添加以下類變量:

public float speed;
public int damage;

Vector3 shootDirection;

就像本教程中到目前為止的任何移動(dòng)物體一樣文搂,這個(gè)也會(huì)有速度和傷害speed and damage變量适刀,因?yàn)樗菓?zhàn)斗邏輯的一部分。 shootDirection向量確定了彈丸(Projectile)的去向煤蹭。

通過在類中實(shí)現(xiàn)以下方法使該向量起作用:

// 1
void FixedUpdate () {
  this.transform.Translate(shootDirection * speed, Space.World);
}

// 2
public void FireProjectile(Ray shootRay) {
  this.shootDirection = shootRay.direction;
  this.transform.position = shootRay.origin;
}

// 3
void OnCollisionEnter (Collision col) {
  Enemy enemy = col.collider.gameObject.GetComponent<Enemy>();
  if(enemy) {
    enemy.TakeDamage(damage);
  }
  Destroy(this.gameObject);
}

以下是上述代碼中的內(nèi)容:

  • 1) 彈丸的移動(dòng)方式與此游戲中的其他所有方式不同笔喉。 它沒有目標(biāo),或者隨著時(shí)間推移施加一些力量硝皂;相反悦即,它在整個(gè)生命周期中沿預(yù)定方向移動(dòng)。
  • 2) 在這里設(shè)置預(yù)制件的起始位置和方向厘线。 這個(gè)Ray看起來很神秘鸦做,但你很快就會(huì)知道它的計(jì)算方法。
  • 3) 如果射彈與敵人發(fā)生碰撞贝或,它會(huì)調(diào)用TakeDamage()并自行摧毀吼过。

在場(chǎng)景層次結(jié)構(gòu)中锐秦,將Projectile腳本附加到Projectile GameObject。 將Speed設(shè)置為0.2并將Damage設(shè)置為1盗忱,然后單擊位于Inspector頂部附近的Apply按鈕酱床。 這將應(yīng)用您剛剛對(duì)此預(yù)制件的所有實(shí)例所做的更改。

從場(chǎng)景層次結(jié)構(gòu)中移除投射(Projectile)物體——你不再需要它了趟佃。


Firing Projectiles

現(xiàn)在你有一個(gè)預(yù)制件可以移動(dòng)和應(yīng)用傷害扇谣,你準(zhǔn)備好開始射擊。

Player文件夾中闲昭,創(chuàng)建一個(gè)名為PlayerShooting的新腳本罐寨,并將其附加到場(chǎng)景中的Player。在類內(nèi)部汤纸,聲明以下變量:

public Projectile projectilePrefab;
public LayerMask mask;

第一個(gè)變量將包含對(duì)您之前創(chuàng)建的Projectile Prefab的引用衩茸。每次你的玩家發(fā)射射彈時(shí),你都會(huì)從這個(gè)預(yù)制件中創(chuàng)建一個(gè)新實(shí)例贮泞。mask變量用于過濾GameObjects楞慈。

在你的游戲中有時(shí)候你需要知道對(duì)撞是否存在于特定的方向。為此啃擦,Unity可以將不可見光線從某個(gè)點(diǎn)投射到您指定的方向囊蓝。您可能會(huì)遇到許多與光線相交的游戲?qū)ο螅虼耸褂谜谡挚梢赃^濾掉任何不需要的對(duì)象令蛉。

Raycast非常有用聚霜,可用于各種用途。它們通常用于測(cè)試其他玩家是否被射彈擊中珠叔,但您也可以使用它們來測(cè)試鼠標(biāo)指針下方是否有任何幾何形狀蝎宇。要了解有關(guān)Raycast的更多信息,請(qǐng)?jiān)赨nity站點(diǎn)上查看此Unity live training video祷安。

下圖顯示了從立方體到圓錐的光線投射姥芥。由于光線上有一個(gè)圖標(biāo)球面罩,它會(huì)忽略該GameObect并報(bào)告錐體上的命中:

現(xiàn)在是時(shí)候發(fā)射自己的光線了汇鞭。

將以下方法添加到PlayerShooting.cs

void shoot(RaycastHit hit){
  // 1
  var projectile = Instantiate(projectilePrefab).GetComponent<Projectile>();
  // 2
  var pointAboveFloor = hit.point + new Vector3(0, this.transform.position.y, 0);

  // 3
  var direction = pointAboveFloor - transform.position;

  // 4
  var shootRay = new Ray(this.transform.position, direction);
  Debug.DrawRay(shootRay.origin, shootRay.direction * 100.1f, Color.green, 2);

  // 5
  Physics.IgnoreCollision(GetComponent<Collider>(), projectile.GetComponent<Collider>());

  // 6
  projectile.FireProjectile(shootRay);
}

以下是上述代碼的作用:

  • 1) 實(shí)例化彈丸Prefab并獲得其彈丸(Projectile)組件凉唐,以便初始化。
  • 2) 這一點(diǎn)總是看起來像(x霍骄,0.5台囱,z)。 X和Z是平面上從鼠標(biāo)點(diǎn)擊位置投射光線的坐標(biāo)读整。這個(gè)計(jì)算很重要簿训,因?yàn)?code>(Projectile)必須與地面平行 - 否則你將向下射擊,只有業(yè)余射擊者才能射向地面。
  • 3) 計(jì)算從Player GameObjectpointAboveFloor的方向强品。
  • 4) 創(chuàng)建一條新射線豺总,通過其原點(diǎn)和方向描述射彈軌跡。
  • 5) 這條線告訴Unity的物理引擎忽略了Player colliderProjectile collider之間的碰撞择懂。否則,在它有機(jī)會(huì)飛行之前另玖,將調(diào)用Projectile腳本中的OnCollisionEnter()困曙。
  • 6) 最后,它設(shè)定了射彈的軌跡谦去。

注意:在光線投射非常寶貴時(shí)使用Debug.DrawRay()慷丽,因?yàn)樗梢詭椭梢暬饩€的外觀和擊中的內(nèi)容。

使用觸發(fā)邏輯鳄哭,添加以下方法讓玩家實(shí)際拉動(dòng)觸發(fā)器:

// 1
void raycastOnMouseClick () {
  RaycastHit hit;
  Ray rayToFloor = Camera.main.ScreenPointToRay(Input.mousePosition);
  Debug.DrawRay(rayToFloor.origin, rayToFloor.direction * 100.1f, Color.red, 2);

  if(Physics.Raycast(rayToFloor, out hit, 100.0f, mask, QueryTriggerInteraction.Collide)) {
    shoot(hit);
  }
}

// 2
void Update () {
  bool mouseButtonDown = Input.GetMouseButtonDown(0);
  if(mouseButtonDown) {
    raycastOnMouseClick();  
  }
}

下面細(xì)分:

  • 1) 此方法將光線從相機(jī)投射到鼠標(biāo)單擊的位置要糊。 然后它檢查此光線是否與給定的LayerMask的游戲?qū)ο笙嘟弧?/li>
  • 2) 每次更新時(shí),腳本都會(huì)檢查鼠標(biāo)左鍵是否按下妆丘。 如果找到一個(gè)锄俄,則調(diào)用raycastOnMouseClick()

返回Unity并在Inspector中設(shè)置以下變量:

  • Projectile Prefab:從預(yù)制文件夾中引用Projectile
  • Mask:平面

注意:Unity附帶了有限數(shù)量的預(yù)定義圖層勺拣,您可以從中創(chuàng)建蒙版奶赠。

您可以通過單擊GameObjectLayer下拉列表并選擇Add Layer來創(chuàng)建自己的:

要將圖層指定給GameObject,請(qǐng)從圖層下拉列表中選擇它:

有關(guān)圖層的更多信息药有,請(qǐng)查看Unity's Layers documentation毅戈。

運(yùn)行項(xiàng)目并隨意開火! 射彈向所需的方向發(fā)射愤惰,但似乎有點(diǎn)不對(duì)苇经,不是嗎?

如果射彈指向行進(jìn)方向宦言,那將會(huì)更加Cool扇单。 要解決此問題,請(qǐng)打開Projectile.cs腳本并添加以下方法:

void rotateInShootDirection() {
  Vector3 newRotation = Vector3.RotateTowards(transform.forward, shootDirection, 0.01f, 0.0f);
  transform.rotation = Quaternion.LookRotation(newRotation);
}

注意:RotateTowardsMoveTowards非常相似蜡励,但它將向量視為方向而不是位置令花。 此外,您不需要隨時(shí)間更改旋轉(zhuǎn)凉倚,因此使用接近零的步驟就足夠了兼都。 Unity中的變換旋轉(zhuǎn)使用四元數(shù)(quaternions)表示,這超出了本教程的范圍稽寒。 您在本教程中需要了解的是扮碧,在進(jìn)行涉及3D旋轉(zhuǎn)的計(jì)算時(shí),它們優(yōu)于矢量。

有興趣了解有關(guān)四元數(shù)的更多信息以及為什么它們有用嗎慎王? 看看這篇優(yōu)秀的文章:How I learned to Stop Worrying and Love Quaternions

FireProjectile()的末尾蚓土,添加對(duì)rotateInShootDirection()的調(diào)用。 FireProjectile()現(xiàn)在應(yīng)該如下所示:

public void FireProjectile(Ray shootRay) {
  this.shootDirection = shootRay.direction;
  this.transform.position = shootRay.origin;
  rotateInShootDirection();
}

再次運(yùn)行游戲并向幾個(gè)不同的方向開火赖淤;這次射彈將指向他們射擊的方向:

刪除Debug.DrawRay調(diào)用蜀漆,因?yàn)槟鷮⒉辉傩枰鼈儭?/p>


Generating More Bad Guys

只有一個(gè)敵人并不是非常具有挑戰(zhàn)性。 但是既然你了解了Prefabs咱旱,你就可以產(chǎn)生你想要的所有對(duì)手确丢!

為了讓玩家猜測(cè),你可以隨機(jī)化每個(gè)敵人的生命吐限,速度和位置鲜侥。

創(chuàng)建一個(gè)空的游戲?qū)ο?- GameObject \ Create Empty。 將其命名為EnemyProducer并添加Box Collider組件诸典。 在Inspector中設(shè)置值描函,如下所示:

  • 1)Position: (0, 0, 0)
  • 2)Box Collider:
    • Is Trigger: true
    • Center: (0, 0.5, 0)
    • Size: (29, 1, 29)

您附加的對(duì)撞定義了競(jìng)技場(chǎng)內(nèi)的特定3D空間。 要查看此內(nèi)容狐粱,請(qǐng)?jiān)趯哟谓Y(jié)構(gòu)中選擇Enemy Producer GameObject舀寓,然后在Scene視圖中查看:

The green wire outlines represent a collider

您將編寫一個(gè)腳本,沿X和Z軸在此空間中選擇一個(gè)隨機(jī)位置肌蜻,并實(shí)例化一個(gè)敵人預(yù)制件基公。

創(chuàng)建一個(gè)名為EnemyProducer的新腳本,并將其附加到EnemyProducer GameObject宋欺。 在新設(shè)置的類中轰豆,添加以下實(shí)例成員:

public bool shouldSpawn;
public Enemy[] enemyPrefabs;
public float[] moveSpeedRange;
public int[] healthRange;

private Bounds spawnArea;
private GameObject player;

第一個(gè)變量啟用和禁用spawning。 該腳本將從enemyPrefabs中挑選一個(gè)隨機(jī)的敵人預(yù)制件并實(shí)例化它齿诞。 接下來的兩個(gè)數(shù)組將指定速度和生命值的最小值和最大值酸休。 生成區(qū)域是您在“場(chǎng)景”視圖中看到的綠色框。 最后祷杈,你需要一個(gè)對(duì)玩家的引用并將其作為目標(biāo)傳遞給壞人斑司。

在腳本內(nèi)部,定義以下方法:

public void SpawnEnemies(bool shouldSpawn) {
  if(shouldSpawn) {
    player = GameObject.FindGameObjectWithTag("Player");
  }
  this.shouldSpawn = shouldSpawn;
}

void Start () {
  spawnArea = this.GetComponent<BoxCollider>().bounds;
  SpawnEnemies(shouldSpawn);
  InvokeRepeating("spawnEnemy", 0.5f, 1.0f);
}

SpawnEnemies()獲取帶有標(biāo)記Player的游戲?qū)ο蟮囊玫⒋_定敵人是否應(yīng)該生成宿刮。

Start()初始化生成區(qū)域并在游戲開始后0.5秒調(diào)度方法的調(diào)用。 它會(huì)每秒重復(fù)調(diào)用一次私蕾。 除了充當(dāng)setter方法之外僵缺,SpawnEnemies()還獲得帶有標(biāo)記Player的游戲?qū)ο蟮囊谩?/p>

Player游戲?qū)ο笊形礃?biāo)記 - 您現(xiàn)在就可以執(zhí)行此操作。 從Hierarchy中選擇Player對(duì)象踩叭,然后在Inspector選項(xiàng)卡中磕潮,從Tag下拉菜單中選擇Player

現(xiàn)在翠胰,您需要為單個(gè)敵人編寫實(shí)際的產(chǎn)卵代碼。

打開Enemy script并添加以下方法:

public void Initialize(Transform target, float moveSpeed, int health) {
  this.targetTransform = target;
  this.moveSpeed = moveSpeed;
  this.health = health;
}

這只是作為創(chuàng)建對(duì)象的setter自脯。 接下來:產(chǎn)生你的敵人聯(lián)盟的代碼之景。 打開EnemyProducer.cs并添加以下方法:

Vector3 randomSpawnPosition() {
  float x = Random.Range(spawnArea.min.x, spawnArea.max.x);
  float z = Random.Range(spawnArea.min.z, spawnArea.max.z);
  float y = 0.5f;

  return new Vector3(x, y, z);
}

void spawnEnemy() {
  if(shouldSpawn == false || player == null) {
    return;
  }

  int index = Random.Range(0, enemyPrefabs.Length);
  var newEnemy = Instantiate(enemyPrefabs[index], randomSpawnPosition(), Quaternion.identity) as Enemy;
  newEnemy.Initialize(player.transform, 
      Random.Range(moveSpeedRange[0], moveSpeedRange[1]), 
      Random.Range(healthRange[0], healthRange[1]));
}

spawnEnemy()所做的就是選擇一個(gè)隨機(jī)敵人預(yù)制件,在隨機(jī)位置實(shí)例化它并初始化敵人腳本公共變量膏潮。

EnemyProducer.cs幾乎準(zhǔn)備好了锻狗!

返回Unity。 通過將Enemy對(duì)象從Hierarchy拖動(dòng)到Prefabs文件夾來創(chuàng)建Enemy預(yù)制件焕参。 從場(chǎng)景中移除敵人對(duì)象 - 你不再需要它了屋谭。 接下來設(shè)置Enemy Producer腳本公共變量,如下所示:

  • 1) Should Spawn: True
  • 2) Enemy Prefabs:
    • Size: 1
    • Element 0: Reference the enemy prefab
  • 3) Move Speed Range:
    • Size: 2
    • Element 0: 3
    • Element 1: 8
  • 4) Health Range:
    • Size: 2
    • Element 0: 2
    • Element 1: 6

運(yùn)行游戲并查看它 - 無窮無盡的壞人龟糕!

好吧,那些立方體看起來并不十分可怕悔耘。 是時(shí)候把事情搞清楚了讲岁。

在場(chǎng)景中創(chuàng)建3D CylinderCapsule。 分別將它們命名為Enemy2Enemy3衬以。 正如您之前對(duì)第一個(gè)敵人所做的那樣缓艳,將兩個(gè)Rigidbody組件和Enemy script添加到它們中。 選擇Enemy2并在Inspector中更改其配置看峻,如下所示:

  • 1) Scale: (0, 0.5, 0)
  • 2) Rigidbody:
    • Use Gravity: False
    • Freeze Position: Y
    • Freeze Rotation: X, Y, Z
  • 3) Enemy Component:
    • Move Speed: 5
    • Health: 2
    • Damage: 1
    • Target Transform: None

現(xiàn)在對(duì)Enemy3做同樣的事情阶淘,但是將它的Scale設(shè)置為0.7:

接下來,將它們變成Prefabs互妓,就像你對(duì)原始敵人一樣溪窒,并在Enemy Producer中引用所有這些。 檢查器中的值應(yīng)如下所示:

  • Enemy Prefabs:
    • Size: 3
    • Element 0: Enemy
    • Element 1: Enemy2
    • Element 2: Enemy3

運(yùn)行游戲冯勉,你會(huì)看到不同的預(yù)制件在競(jìng)技場(chǎng)內(nèi)產(chǎn)生澈蚌。

不久之后你就會(huì)意識(shí)到自己是無敵的! 這很棒灼狰,你需要稍微調(diào)整一下比賽場(chǎng)地宛瞄。


Implementing the Game Controller

既然你有射擊,移動(dòng)和敵人交胚,你將實(shí)現(xiàn)一個(gè)基本的游戲控制器份汗。 一旦Player“死”,它將重新開始游戲蝴簇。 但首先杯活,您必須創(chuàng)建一種機(jī)制來通知任何感興趣的玩家已達(dá)到0健康狀態(tài)。

打開Player script并在類聲明上面添加以下內(nèi)容:

using System;

在類內(nèi)添加以下新的公共事件:

public event Action<Player> onPlayerDeath;

事件是一種C#語言功能熬词,允許您將對(duì)象的更改廣播到任何監(jiān)聽者轩猩。 要了解如何使用活動(dòng),請(qǐng)查看Unity's live training on events.

編輯collidedWithEnemy()如下:

void collidedWithEnemy(Enemy enemy) {
  enemy.Attack(this);
  if(health <= 0) {
    if(onPlayerDeath != null) {
      onPlayerDeath(this);
    }
  }
}

事件為對(duì)象提供了一種簡潔的方式來表示它們之間的狀態(tài)變化均践。 游戲控制器會(huì)對(duì)上面聲明的事件非常感興趣晤锹。 在Scripts文件夾中,創(chuàng)建一個(gè)名為GameController的新腳本彤委。 雙擊該文件進(jìn)行編輯鞭铆,并添加以下變量:

public EnemyProducer enemyProducer;
public GameObject playerPrefab;

腳本需要對(duì)敵人的生產(chǎn)有一些控制權(quán),因?yàn)橐坏┩婕宜劳鼋褂埃a(chǎn)生敵人是沒有意義的车遂。 此外,重新啟動(dòng)游戲意味著您必須重新創(chuàng)建Player斯辰,這意味著......這是正確的舶担,它將成為預(yù)制件。

添加以下方法:

void Start () {
  var player = GameObject.FindGameObjectWithTag("Player").GetComponent<Player>();
  player.onPlayerDeath += onPlayerDeath;
}

void onPlayerDeath(Player player) {
  enemyProducer.SpawnEnemies(false);
  Destroy(player.gameObject);

  Invoke("restartGame", 3);
}

Start()中彬呻,腳本獲取對(duì)Player腳本的引用衣陶,并訂閱您之前創(chuàng)建的事件。 一旦玩家的生命值達(dá)到0闸氮,將調(diào)用onPlayerDeath()剪况,停止敵人生產(chǎn),從場(chǎng)景中移除Player對(duì)象并在3秒后調(diào)用restartGame()方法蒲跨。

最后译断,添加重啟游戲動(dòng)作的實(shí)現(xiàn):

void restartGame() {
  var enemies = GameObject.FindGameObjectsWithTag("Enemy");
  foreach (var enemy in enemies)
  {
    Destroy(enemy);
  }

  var playerObject = Instantiate(playerPrefab, new Vector3(0, 0.5f, 0), Quaternion.identity) as GameObject;
  var cameraRig = Camera.main.GetComponent<CameraRig>();
  cameraRig.target = playerObject;
  enemyProducer.SpawnEnemies(true);
  playerObject.GetComponent<Player>().onPlayerDeath += onPlayerDeath;
}

在這里你做了一些清理工作:你摧毀場(chǎng)景中的所有敵人并創(chuàng)建一個(gè)新的Player對(duì)象。 然后或悲,您將攝像機(jī)裝備的目標(biāo)重新分配給此實(shí)例孙咪,恢復(fù)敵方的產(chǎn)生,并將Game Controller訂閱到玩家死亡事件巡语。

現(xiàn)在返回Unity该贾,打開Prefabs文件夾,將所有Enemy預(yù)制件的標(biāo)簽更改為Enemy捌臊。 接下來杨蛋,將Player游戲?qū)ο笸先?code>Prefabs文件夾中,使其成為Prefab理澎。 創(chuàng)建一個(gè)空的游戲?qū)ο蟪蚜Γ瑢⑵涿麨?code>GameController并附加剛剛創(chuàng)建的腳本。 在Inspector中連接所有必需的引用糠爬。

到現(xiàn)在為止寇荧,你對(duì)這種模式非常熟悉。 嘗試自己放置引用执隧,然后根據(jù)下面隱藏的插圖檢查結(jié)果:

Game Controller:

  • Enemy Producer:來自層次結(jié)構(gòu)的敵人生產(chǎn)者引用
  • Player Prefab:從Prefabs文件夾中引用它

再次運(yùn)行游戲以查看game controller的運(yùn)行情況揩抡。

就是這樣 - 你編寫了第一個(gè)Unity游戲户侥!恭喜!

到現(xiàn)在為止峦嗤,你應(yīng)該很好地理解將一個(gè)簡單的動(dòng)作游戲結(jié)合起來所需要的東西蕊唐。制作游戲不是一項(xiàng)簡單的任務(wù);它絕對(duì)需要大量工作烁设,腳本只是將項(xiàng)目變?yōu)楝F(xiàn)實(shí)所需的元素之一替梨。要增加良好的潤色程度,您還需要為游戲添加動(dòng)畫和UI装黑。

后記

本篇主要講述了Unity腳本簡介副瀑,感興趣的給個(gè)贊或者關(guān)注~~~

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市恋谭,隨后出現(xiàn)的幾起案子糠睡,更是在濱河造成了極大的恐慌,老刑警劉巖疚颊,帶你破解...
    沈念sama閱讀 222,000評(píng)論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件狈孔,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡串稀,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,745評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門狮杨,熙熙樓的掌柜王于貴愁眉苦臉地迎上來母截,“玉大人,你說我怎么就攤上這事橄教∏蹇埽” “怎么了?”我有些...
    開封第一講書人閱讀 168,561評(píng)論 0 360
  • 文/不壞的土叔 我叫張陵护蝶,是天一觀的道長华烟。 經(jīng)常有香客問我,道長持灰,這世上最難降的妖魔是什么盔夜? 我笑而不...
    開封第一講書人閱讀 59,782評(píng)論 1 298
  • 正文 為了忘掉前任,我火速辦了婚禮堤魁,結(jié)果婚禮上喂链,老公的妹妹穿的比我還像新娘。我一直安慰自己妥泉,他們只是感情好椭微,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,798評(píng)論 6 397
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著盲链,像睡著了一般蝇率。 火紅的嫁衣襯著肌膚如雪迟杂。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,394評(píng)論 1 310
  • 那天本慕,我揣著相機(jī)與錄音排拷,去河邊找鬼。 笑死间狂,一個(gè)胖子當(dāng)著我的面吹牛攻泼,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播鉴象,決...
    沈念sama閱讀 40,952評(píng)論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼忙菠,長吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來了纺弊?” 一聲冷哼從身側(cè)響起牛欢,我...
    開封第一講書人閱讀 39,852評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎淆游,沒想到半個(gè)月后傍睹,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,409評(píng)論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡犹菱,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,483評(píng)論 3 341
  • 正文 我和宋清朗相戀三年拾稳,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片腊脱。...
    茶點(diǎn)故事閱讀 40,615評(píng)論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡访得,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出陕凹,到底是詐尸還是另有隱情悍抑,我是刑警寧澤,帶...
    沈念sama閱讀 36,303評(píng)論 5 350
  • 正文 年R本政府宣布杜耙,位于F島的核電站搜骡,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏佑女。R本人自食惡果不足惜记靡,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,979評(píng)論 3 334
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望团驱。 院中可真熱鬧簸呈,春花似錦、人聲如沸店茶。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,470評(píng)論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽贩幻。三九已至轿腺,卻和暖如春两嘴,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背族壳。 一陣腳步聲響...
    開封第一講書人閱讀 33,571評(píng)論 1 272
  • 我被黑心中介騙來泰國打工憔辫, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人仿荆。 一個(gè)月前我還...
    沈念sama閱讀 49,041評(píng)論 3 377
  • 正文 我出身青樓贰您,卻偏偏與公主長得像,于是被迫代替她去往敵國和親拢操。 傳聞我的和親對(duì)象是個(gè)殘疾皇子锦亦,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,630評(píng)論 2 359

推薦閱讀更多精彩內(nèi)容