質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

90.47%

  • C#

    7437questions

    C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

  • Unity

    4201questions

    Unityは、ユニティテクノロジーが開発したゲームエンジンです。 主にモバイルやブラウザ向けのゲーム製作に利用されていましたが、3Dの重力付きゲームが簡単に作成できることから需要が増え、現在はマルチプラットフォームに対応しています。 言語はC言語/C++で書かれていますが、C#、JavaScript、Booで書かれたコードにも対応しています。

  • Unity2D

    924questions

クリックした際にダメージを与えるようにしたいです。

解決済

回答 2

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 432

sundome

score 6

2Dゲームで、左から流れてくる敵をクリックして倒すタワーディフェンスのようなゲームを作ろうと考えました。
左クリックをした時に、敵にダメージが入るように設定したいと思ったのですが、うまく行きませんでした。
当初はクリック一撃で破壊していたのですが、攻撃力があったほうが後々アップグレードしていくシステムを入れやすいかと思ってこのような形にしました。

初心者なので、読みづらいかもしれませんがご回答よろしくお願いします。

発生している問題・エラーメッセージ

/Users/Assets/Script/ClickScript.cs(15,15): Warning CS0219: The variable `enemyscript' is assigned but its value is never used (CS0219) (Assembly-CSharp)

/Users/Assets/Script/ClickScript.cs(21,21): Error CS0103: The name `enemyscript' does not exist in the current context (CS0103) (Assembly-CSharp)
上記がもう一つ

ClickScript

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ClickScript : MonoBehaviour {

    public GameObject explosion;
    public int power = 100;

    // 左クリックしたオブジェクトを取得する関数(2D)
    private GameObject getClickObject() {
        GameObject result = null;
        // 左クリックされた場所のオブジェクトを取得
        if(Input.GetMouseButtonDown(0)) {
            Vector2 tapPoint = Camera.main.ScreenToWorldPoint(Input.mousePosition);
            Collider2D collition2d = Physics2D.OverlapPoint(tapPoint);
            if (collition2d) {
                result = collition2d.transform.gameObject;
                }
            }
        return result;
    }
    void Start (){
        EnemyScript enemyscript = GetComponent<EnemyScript> ();
    }

    void Update () {
        GameObject obj = getClickObject ();
        if (obj != null) {
            // 以下オブジェクトがクリックされた時の処理
            enemyscript.hp = enemyscript.hp - power;
            }
    }
}

EnemyScript

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class EnemyScript : MonoBehaviour {

    Rigidbody2D N_rigidbody2D;
    public int speed = 3;
    public int hp = 100;
    public GameObject explosion;

    void Start (){
        N_rigidbody2D = GetComponent<Rigidbody2D> ();
    }

    void Update (){
        N_rigidbody2D.velocity = new Vector2 (speed, N_rigidbody2D.velocity.y);
        if(hp <= 0){
            Debug.Log("破壊された");
            Destroy(gameObject);
            Instantiate (explosion, transform.position, transform.rotation);
        }
    }
}

補足情報(言語/FW/ツール等のバージョンなど)

Mac Sierra 10.12.6
Unity 2017 2.0b11

9/19追記

2つの解決策を出していただいて、本当に助かりました!
ベストアンサーは迷ったのですが、投稿が早かったことと、僕がしょうもない迷惑をかけたということもあって今回はIShikawanにさせていただきました。
お二方とも、本当にありがとうございました。

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 2

checkベストアンサー

+1

EnemyにRaycasterのあたり判定を持たせると楽です。

オブジェクトのタップをUpdateに処理を書くのではなくRaycasterに任せると楽に実装できます。 Raycasterを使う点は楽なだけではなく、判定をUnityのイベントに任せるので最適化された環境で処理を実行できます。それから、ゲームにUIがある場合Imageを持っていればオブジェクト同士が重なった場合、後ろのオブジェクトが反応しなくなるので前後関係を意識するだけで処理を止めたりできます。

[導入手順]

  1. カメラにPhysics 2D Raycasterをアタッチ
    レイキャスター

  2. オブジェクトにCollider 2Dをアタッチ
    コライダ

  3. [追記]EventSystemをHierarchyに追加
    イベントシステム

  4. スクリプトにIPointerClickHandlerを実装

※検証する際はClickScriptを外してください。

[追記]▼ Unity サンプルプロジェクト

制作環境:Unity 5.6.3f1 mac
保存期間:7日
http://firestorage.jp/download/58e099fc19dcb204d1f534b53b721c1a6cc6511c

サンプルスクリプト

using UnityEngine;
using UnityEngine.EventSystems;

public class EnemyScript : MonoBehaviour, IPointerClickHandler
{

    Rigidbody2D N_rigidbody2D;
    public int speed = 3;
    public int hp = 100;
    public GameObject explosion;

    void Start()
    {
        N_rigidbody2D = GetComponent<Rigidbody2D>();
    }

    void Update()
    {
        N_rigidbody2D.velocity = new Vector2(speed, N_rigidbody2D.velocity.y);
        if (hp <= 0)
        {
            Debug.Log("破壊された");
            Destroy(gameObject);
            Instantiate(explosion, transform.position, transform.rotation);
        }
    }

    public void OnPointerClick(PointerEventData eventData)
    {
        //ダメージ処理 管理を考えるならシングルトンのクラスなどからPowerを参照するといいと思います。
        hp -= 100;
    }
}

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2017/09/18 17:53

    ご回答、ありがとうございます!
    画像もあってすごくわかりやすいです!
    手順の通り、Main CameraにPhysics 2D Raycasterを取り付け、EnemyScriptを書き換えてみましたが、敵を倒すことができませんでした。
    クリックを認識していないのか、ダメージが入ってないのかわからないですが、調べて見ます。エラーなどは出ていません。
    まだ理解が進んでいませんので、いじりながら勉強してみます。

    キャンセル

  • 2017/09/18 22:36

    2. オブジェクトにCollider 2Dをアタッチ
    は敵にCollider 2Dをアタッチするということなんですが敵につけましたか?

    キャンセル

  • 2017/09/18 23:04

    わざわざご返事ありがとうございます。
    Box Collider2Dを付けていたので書き損じていました。
    すでに敵に付けております。

    キャンセル

  • 2017/09/19 14:16

    サンプルプロジェクトを作ってみたので追記しました。
    必要な機能のみ入れたので分かりやすいと思います。

    キャンセル

  • 2017/09/19 15:42

    ありがとうございます!
    サンプルの細かい所を見てもなにが違うか全然わからなかったのですが、EventSystemをHierarchyに入れたらすぐに動きました!
    判定をUnityのイベントに任せるというものなんだから当たり前ですよね。
    しょうもない見落としでお時間を取ってしまい、申し訳ありません。

    キャンセル

  • 2017/09/19 20:13 編集

    なるほど!イベントシステムも必要ですね。
    いつも入れているので全然気づいてませんでした。
    申し訳ないです。追記もしました。

    キャンセル

  • 2017/09/20 07:21

    いえいえ、とんでもございません!
    こんかいはありがとうございました。
    今後とも、よろしくお願いします。

    キャンセル

+1

(a)

    void Start (){
        EnemyScript enemyscript = GetComponent<EnemyScript> ();
    }

(b)

            // 以下オブジェクトがクリックされた時の処理
            enemyscript.hp = enemyscript.hp - power;

(a)において、enemyscriptが関数の中で定義されているため、他の関数で使うことができません。
そのため、(b)でエラーとなります。

ついでに、(a)の場合だと、EnemyScriptが複数存在する場合に、どのEnemyScriptが使われるか分からなくなります。
それを踏まえると、(a)を削除した後、ClickScriptのUpdate()を以下のように修正したほうがよろしいと思います。

    void Update () {
        GameObject obj = getClickObject ();

        if (obj != null) {
            EnemyScript enemyscript = obj.GetComponent<EnemyScript>();

            if (enemyscript != null) {    // EnemyScriptの有無をチェック
                // 以下オブジェクトがクリックされた時の処理
                enemyscript.hp = enemyscript.hp - power;
            }
        }
    }

IShikawanさんに先を越されましたが、エラーの原因について書かれていなかったので、とりあえず投稿しました。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2017/09/18 18:16

    言葉が足りず、不明瞭な中で適切なご回答、ありがとうございます!
    とてもわかりやすく、大変助かりました。
    言われたとおりに書き直すと、うまくできました。
    いつも本当にありがとうございます!

    キャンセル

関連した質問

同じタグがついた質問を見る

  • C#

    7437questions

    C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

  • Unity

    4201questions

    Unityは、ユニティテクノロジーが開発したゲームエンジンです。 主にモバイルやブラウザ向けのゲーム製作に利用されていましたが、3Dの重力付きゲームが簡単に作成できることから需要が増え、現在はマルチプラットフォームに対応しています。 言語はC言語/C++で書かれていますが、C#、JavaScript、Booで書かれたコードにも対応しています。

  • Unity2D

    924questions