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

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

新規登録して質問してみよう
ただいま回答率
85.48%
C#

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

Q&A

4回答

3330閲覧

index out of range

user1041

総合スコア27

C#

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

0グッド

0クリップ

投稿2015/03/20 09:19

using UnityEngine;
using System.Collections;

public class Player_NonPhysics2D:MonoBehaviour {
//宣言
// Inspectorで調整するためのプロパティ
public float speed =15.0f;
public Sprite[] run;
public Sprite[] jump;

// 内部で扱う変数 float jumpVy; int animIndex; bool goalCheck; //メッセージに対応したコード //コンポーネントの実行開始 void Start(){ //初期化 jumpVy = 0.0f; animIndex = 0; goalCheck = false; } //プレイヤーキャラのコリジョンに他のゲームオブジェクトのコリジョンが入った void OnCollisionEnter2D(Collision2D col){ //ゴールチェック if(col.gameObject.name == "Stage_Gate"){ //goal goalCheck =true; return; } //ゴール以外だったらステージを再読み込みしてリセット Application.LoadLevel(Application.loadedLevelName); } //フレームの描き換え void Update() { if(goalCheck) { //ゴールチェック return; //ゴールだったら処理停止 } //現在のプレイヤーキャラの高さを計算 float height= transform.position.y + jumpVy; //接地チェック(高さが0なら接地している) if(height <= 0.0f) { //ジャンプ初期化 height = 0.0f; jumpVy = 0.0f; //ジャンプチェック if(Input.GetButtonDown("Fire1")){ //ジャンプ処理 jumpVy = +1.3f; //ジャンプスプライト画像に切り替え.. GetComponent<SpriteRenderer>().sprite = jump[0]; } else{ //走り処理 animIndex ++; if(animIndex >= run.Length){ animIndex = 0; } //走りスプライト画像に切り替え GetComponent<SpriteRenderer>().sprite = run[animIndex]; } } else{ //ジャンプ後の降下中 jumpVy -= 0.2f; //jumpVy -= 6.0f * Time.deltaTime; //正しい処理はこちら } //プレイヤーキャラの移動(座標設定) transform.position = new Vector3 ( transform.position.x+speed*Time.deltaTime,height,0.0f); //下記のように相対移動で記述してもいい //transfor.Translate(speed*Time.deltaTime,jumpVy,0.0f); //transform.position += new Vector3(speed * Time.deltaTime,jumpVy,0.0f); //ただし次の書き方では雨後置かないので注意 //transform.position.Set( // transform.position.x+speed*Time.deltatime,height,0,0f); //カメラの移動(座標の相対移動) GameObject goCam = GameObject.Find ("Main Camera"); goCam.transform.Translate (speed * Time.deltaTime, 0.0f,0.0f); } // UnitGuIの表示 void OnGUI(){ //デバックテキスト GUI.TextField(new Rect(10,10,300,60), "[Unity 2d Sample 3-1 A]\nマウスの左ボタンを押すと加速\nはなすとジャンプ"); //リセットボタン if(GUI.Button (new Rect(10,80,100,20),"リセット")) { Application.LoadLevel (Application.loadedLevelName); } }

}

上記はunity2dのスクリプトです 再生を押したところ以下のエラーがでました。
IndexOutOfRangeException: Array index is out of range.
Player_NonPhysics2D.Update () (at Assets/Scenes/Player_NonPhysics2D.cs:68)

array index is out of rangeのエラーを調べたところ配列の最大値を超えているという
ことだとわかりましたが、いったいどこが間違っているのかがわかりません。
間違っている文章を指摘くださるか、正常に戻すためのスクリプトがあれば教えてください。

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

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答4

0

黄色の三角の <The referecned script months Behaviour is missing!> が消えないという事でよろしでしょうか?
これは、はじめ、オブジェクトにアタッチされていたスクリプトが、開発者によりファイルごと削除されたなどの理由により中身が空になってしまったScriptComponentが存在していますという警告だったと思います。
この警告は作成するゲームに影響を及ぼす事は特にないと思います。
もし消したい場合は以下のサイトを参考にすれば良いと思います。
http://blog.be-style.jpn.com/article/91794043.html

投稿2015/03/22 22:59

albacrow

総合スコア31

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

user1041

2015/03/22 23:09

maincameraのinspectorにあるスクリプトをremoveconponentすれば 一時的にエラーが解消されて再生を押すとアニメーションが正常に動きますが、もう一度再生を押すと削除したscriptがまた出てくるのでエラーになる。ということです
albacrow

2015/03/22 23:10

すみません、消したコンポーネントが復活するという事でしたか。 unityではプログラムからでもコンポーネントを追加する事が出来ます。( AddComponent<T>()等 ) おそらくどこかのスクリプトにこれがあり、MainCameraに対してコンポーネントを追加していたかと。 また、他に考えられる原因としては、 ・ゲームの起動中にコンポーネントを削除した ゲームは停止させると、ゲームの起動前の状態に戻ってしまいます。なので、コンポーネントを削除するときには一度停止してから行った方が良いと思います。 ・Sceneを更新していない unityは1つの画面がどうやって構成されているかをScene単位で保存しています。シーンをまたいでゲームを作成する場合、きちんとSceneをセーブしておかないと、うまく動作しません。 ・Prefabを更新していない unityはオブジェクトをprefabという単位でProject内に持っています。 これをInstantiate()でゲーム内に出す事が出来ます。prefab化しているオブジェクトは青色で名前が表示されます。ヒエラルキー上のオブジェクトをいじっても、Applyをしてやらない限り、project上のprefabは更新されません。
user1041

2015/03/22 23:27

おっしゃるとおりsceneセーブしていなかったことが原因でした。The referecned script months Behaviour is missingは問題ないのであれば無視します。 エラーも消えましたが、 ただ、ゲーム内の boxと接触するとアニメーションがそこから進まなくなってしまいまいます。 http://gyazo.com/9d14b5a6a44befcdb64b7f7e70a107fa   画像でいうとクリックした箇所です。 これはinspectorの問題かと思うのですが、どうでしょうか。。
albacrow

2015/03/22 23:37

これはプログラム上の問題だと思います。 スクリプトを見ると、毎フレーム行われる関数であるUpdate()の最初に、 if(goalCheck) { //ゴールチェック return; //ゴールだったら処理停止 } とあります。これだと一度ゴールしてフラグがたってしまうと、return;文でこの先のスクリプトが実行される事なく終わってしまいます。この先に、run配列画像を切り替える処理があるので、ゴールするとアニメーションが切り替わらないのだと思います。 ゴールしても動いてよいと言うなら、上の文を消せば良いと思います。
guest

0

このプログラムをちゃんと動作させるためにはInspector上から、run配列とjump配列の配列数を決めてやって、その配列数の数だけ、Spriteをアタッチする必要があります。おそらくそれを行っていないのでエラーが発生していると思うのですが。

そのままコピペしてrun配列とjump配列にSpriteを入れてあげたところ、問題なく動作しました。
![イメージ説明]WIDTH:600

投稿2015/03/21 14:18

albacrow

総合スコア31

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

user1041

2015/03/22 21:17

inspectorは確認してみましたが、jumpとrunのElementにsprite?の画像も入っていました。 質問ばかりで恐縮ですが、いまのところjump配列は正常でrun配列にはspriteが入っていないということでよろしいでしょうか。とすれば、runにspriteを入れるためにはコードを追加する必要があると思うのですが、どう書けばよろしいでしょうか
albacrow

2015/03/22 21:39

unityは特性上、変数がpublicであればGUIであるInspector上からリソースを編集可能です。おそらく最初に解答した方が言っている通り、エラーが発生している原因はrun配列が初期化されていない事による、配列の範囲外参照だと思います。unityはInspector上からでも配列数を決定する事ができ、その際にrun配列の長さをを1以上にしていれば、配列内にspriteもとい、画像をセットしなくていても、エラーは発生しないはずです。キャラクタの画像が画面に映し出されなくなるだけなので。こちら側でコピペで正常に作動している以上、コードの書き足しは必要ないと思います。すみませんが、もし良ければ編集画面を見せてもらってもよろしいでしょうか?
albacrow

2015/03/22 22:28

ありがとうございます。 見たところ、特に間違ってそうなところは全く見当たりません。Inspector上も問題はなさそうです。 エラーコードを見たところ、68行目から、73行目に変わっていたのですが、上のスクリプトに何か付け足したものとかはありませんか? 良ければ、最新のコードを拝見したいのですが。
user1041

2015/03/22 22:32

少しだけいじったので行がずれたのだと思います。 using UnityEngine; using System.Collections; public class Player_NonPhysics2D:MonoBehaviour { //宣言 // Inspectorで調整するためのプロパティ public float speed =15.0f; public Sprite[] run; public Sprite[] jump; // 内部で扱う変数 float jumpVy; int animIndex; bool goalCheck; //メッセージに対応したコード //コンポーネントの実行開始 void Start(){ //初期化 jumpVy = 0.0f; animIndex = 0; goalCheck = false; } //プレイヤーキャラのコリジョンに他のゲームオブジェクトのコリジョンが入った void OnCollisionEnter2D(Collision2D col){ //ゴールチェック if(col.gameObject.name == "Stage_Gate"){ //goal goalCheck =true; return; } //ゴール以外だったらステージを再読み込みしてリセット Application.LoadLevel(Application.loadedLevelName); } //フレームの描き換え void Update() { if(goalCheck) { //ゴールチェック return; //ゴールだったら処理停止 } //現在のプレイヤーキャラの高さを計算 float height= transform.position.y + jumpVy; //接地チェック(高さが0なら接地している) if(height <= 0.0f) { //ジャンプ初期化 height = 0.0f; jumpVy = 0.0f; //ジャンプチェック if(Input.GetButtonDown("Fire1")){ //ジャンプ処理 jumpVy = +1.3f; //ジャンプスプライト画像に切り替え.. GetComponent<SpriteRenderer>().sprite = jump[0]; GetComponent<SpriteRenderer>().sprite = run[0]; } else{ //走り処理 animIndex ++; if(animIndex >= run.Length){ animIndex = 1; } //走りスプライト画像に切り替え GetComponent<SpriteRenderer>().sprite = run[animIndex]; } } else{ //ジャンプ後の降下中 jumpVy -= 0.2f; //jumpVy -= 6.0f * Time.deltaTime; //正しい処理はこちら } //プレイヤーキャラの移動(座標設定) transform.position = new Vector3 ( transform.position.x+speed*Time.deltaTime,height,0.0f); //下記のように相対移動で記述してもいい //transfor.Translate(speed*Time.deltaTime,jumpVy,0.0f); //transform.position += new Vector3(speed * Time.deltaTime,jumpVy,0.0f); //ただし次の書き方では雨後置かないので注意 //transform.position.Set( // transform.position.x+speed*Time.deltatime,height,0,0f); //カメラの移動(座標の相対移動) GameObject goCam = GameObject.Find ("Main Camera"); goCam.transform.Translate (speed * Time.deltaTime, 0.0f,0.0f); } // UnitGuIの表示 void OnGUI(){ //デバックテキスト GUI.TextField(new Rect(10,10,300,60), "[Unity 2d Sample 3-1 A]\nマウスの左ボタンを押すと加速\nはなすとジャンプ"); //リセットボタン if(GUI.Button (new Rect(10,80,100,20),"リセット")) { Application.LoadLevel (Application.loadedLevelName); } } }
albacrow

2015/03/22 22:38

問題ありませんね・・・。 今も動作させるとエラーコードは新たに出されますか? Consoleのデバッグコードリストは自分で消さない限り、エラーコードは残ります。 そういうオチではないとは思いますが・・・。
albacrow

2015/03/22 22:49

すみません。 問題ないとか言っていましたが、 70行目の animIndex = 1;は animIndex = 0;にしたほうが良いと思います。 だからといって、これが現状のエラー回復に繋がる訳ではありませんが・・・。
user1041

2015/03/22 22:50

エラーがでたときに maincamera等が黄色くなるので確認してみたら、scriptがあったので それをremoveconponentで消してみたらエラーが消えました。が、再生すると消したはずのscriptがまた復活してしまいます。。
guest

0

いえ、run[animIndex] は問題ないと思います。
IndexOutOfRangeExceptionが発生するならrunはどこかで代入されているはず(そうしないとNullPointerExceptionになるので)ですが、
あげていただいたコードには代入されている箇所がありません。
クラスの外でrunに代入しているようなのでそこを調べてみるのがいいと思います。

投稿2015/03/21 13:58

編集2015/03/21 14:01
toki_td

総合スコア2850

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

68行目の直前にanimIndexがrunの長さ以上なら0に戻る処理が入っているので
IndexOutOfRangeException が発生するのはrun[0]が範囲外、
つまり runの長さが0(空の配列)で1つもオブジェクトを持てない場合です。
runへ代入している箇所をチェックしてみましょう。

投稿2015/03/20 12:17

toki_td

総合スコア2850

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

user1041

2015/03/21 07:13

これ 一応unity本のサンプルコードをそのままコピペしたんですけど、本が間違っているということでしょうか。。。 run[animIndex] →run[0] ですか?
toki_td

2015/03/21 13:59

すみません、新規に書いてしまいました。 ↓が返答です。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

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

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問