MonoDevelopでコピペが出来ない場合
別でスクリプトを保存してて、それを自分のプロジェクトに突っ込もうと思ってコピペしようとしたらまったくできませんでした。
イライラしながらコピペできないんで手打ちで打ちましたが調べるとものすごい簡単に直りました。
MonoDevelopの再起動
これで解決しました!いやーなんでさきに調べなかったんだろう…無駄な時間を使ってしまった気がする…
Standard AssetsのBloomを使ってオブジェクトを光らせる!
こんにちは。何かやりたい事がうまくできなくて半日調べてばかりで時間が過ぎました。
とりあえず今日は色々とやってたのですが、発行するものをどうやってつくるんだっけな…と久しぶりにやろうと思ったら忘れてたのでちゃんと残しておこうと思います。
Standard Assetsを使う
まずStandard Assetsってなんだ!ってなってしまう人も多いんではないかと思います。
さわってる人にとって当たり前でも初めての人にとってはStandard Assetsを使いましょうって言われるとStandard Assetsって書いてくれてないとわからないものです。
ええ
自分は 「あれ、どれだっけな…」 となりました。
今回使うのはAssetsのImport PackageのEffectsを使います。これをクリックしてImportボタンを押してインポートしましょう。
もしStandard Assetsが見つからない場合
こちらで詳しく書いてますのでぜひ見てみて下さい。
Bloomを使ってみよう
さて、ここから発光させていきますよ
とくに難しいスクリプトも書く必要はありません。
3DオブジェクトのCubeとPlaneを準備しました。
Materialを作成して下さい
CubeオブジェクトにMaterialを突っ込んでInspetorからEmissionを1に変更しましょう。
それでは次に先ほどImportしたEffectsの中にあるBloomをMain Cameraオブジェクトにアタッチしましょう。
アタッチした後Inspectorを確認してみてください。Intensityの数値を変更すると発光の強さが変わります。
実際に動かしてみて確認してみましょう。
発光してますねー!
ちなみにCameraのHDRを使うと通常色では0~1までの色しか出せなかったものを1以上出せるようにする事が出来ます。
さっそくHDRにチェックを入れてみると…
こんなふうに警告が出てしまう方もいると思います。
そういう人はEdifからProject Setting Playerを選択して下さい。
Inspectorに表示されるのでRendering PathをForwardからDeferedに変更しましょう。すると警告がなくなっているはずです。
次にCubeをもう一つ、マテリアルをもう一つ作って同じようにEmissionを設定するのですが、これを1ではなく2にしてみましょう。
とっても親切にHDRと出てます。
それでは並べて発光させてみましょう。
カメラの設定のThresholdを1にしてIntensityを0に設定し徐々にIntensityを増やしてみます。
そうするとEmissionが2のものだけが発光している事がわかります。
Thresholdを0にするとどちらも発光しますし、なんでも発光しますが、HDRで発光させたいものさせたくないものを分ける事が出来るみたいです。
この辺はまだ自分もフワッとしているのでもう少し理解を深めて行きたいと思います。
いやー発光させるだけでも大変ですね(´・ω・`)
LookAtを2Dで再現するには
Quaternion FromToRotation(Vector3 fromDirection, Vector3 toDirection);
fromDirection
から toDirection
への回転を作成します。通常、ワールド空間で Transform を回転させ、座標の 1 つ、例えば、y 座標をターゲットの方向 toDirection
に向かせるために使用します。
LookAtを2Dで再現するには
まず最初に書いたものはUnity公式のリファレンスから引用したものになります。
Transformを回転させ、座標の1つをターゲットの方向に向かせるという事です。ちなみにLookAtはどうしてつかわないかというと。
こんなふうになって2Dの見えちゃいけない部分が見えてしまいます。
今回使うのはこの2行のスクリプトです。
Vector3 diff = (Head.gameObject.transform.position - this.transform.position);
this.transform.rotation = Quaternion.FromToRotation (Vector3.up, diff);
//Vector3.upはVector3(0,1,0)と同じ意味とリファレンスに書いてます。
他にもstatic変数はあるのでこちらで確認してみて下さい。
diffは頭と球体のtransform.positionの差が格納されています。
Quaternion.FromToRotationは二つのポジションの差を自身の回転にするというものらしいです。
実際に動かしてみるとこんな感じです。
コンソールはdiffの値を出力しています。
頭の頂点で追いかけるようにはなってくれました(笑)
この辺はまだちょっと自分には難しいかも…
ちょっと頑張ってやってみましたが、なんだかちょっと反応が遅いですね…
こちらはいつもお世話になっているテラシュールブログさんから知識を拝借いたしました!
コルーチン yield return nullについて yield return new WaitForSeconds(float)も;
最初にスクリプトをバンっと貼っておきます。
using UnityEngine;
using System.Collections;
public class hogehoge : MonoBehaviour {
// Use this for initialization
void Start () {
StartCoroutine("cor");
}
// Update is called once per frame
void Update () {
Debug.Log ("アプデ");
}
private IEnumerator cor(){
for (int i = 0; i < 5; i++) {
Debug.Log (i);
yield return null;
}
}
}
それでは見ていきましょう。コルーチンの動きを見てみようと思いますが、このスクリプトだとStartでまず最初にコルーチンに向かいます。
yield return null;
こいつが入ると一度中断して次のフレームで再度再会するようになります。
どういう風になっているかコンソールを見てみましょう。
forに入ってそのままぐるぐるーっとiが5になるまで回らずにコルーチンの中のforの処理を1周したらアップデートの中を一周して、またコルーチンの中の処理をして、アップデートの処理をして…と1フレーム挟まれている事がわかります。
private IEnumerator cor(){
for (int i = 0; i < 5; i++) {
Debug.Log (i);
}
yield return null;
}
ためしにyield return nullをforの外に出してみましょう。
先にforの中の処理をして、yield return nullに到達した時点でアップデートに戻ります。そして再会されてコルーチンの処理は終わりを迎えます。
永久にループしたいっていう場合はwhile(true)などを使って永久ループを作ってしまってもいいと思います。
ちなみにyield return nullだと1フレーム事に中断されますが、これを秒数で指定したい場合はどう書けばいいのかというと
yield return new WaitForSeconds (float);
float型で秒数を指定するとその秒数が経過したらするまで次の処理に移りません。
コンソールで見てみるとこんな感じです。間は長いので割愛しています。
ちなみに引数を下記のようにすると渡す事も出来ます。
StartCoroutine(コルーチン名, 引数に渡す値);
スクリプトです。
using UnityEngine;
using System.Collections;
public class hogehoge : MonoBehaviour {
// Use this for initialization
void Start () {
StartCoroutine("cor",1.0f);
}
// Update is called once per frame
void Update () {
Debug.Log ("アプデ");
}
private IEnumerator cor(float second){
for (int i = 0; i < 5; i++) {
Debug.Log (i);
yield return new WaitForSeconds(second);
}
}
}
これで動かしてもyield return new WaitForSeconds(1.0f);の時と同じです。
コルーチンを使うと●秒待つ→動く→●秒待つ→動くなどの時間を絡めた作業をする事に向いているようです。
これを覚えていれば色々と使えそうなのでぜひ覚えておきたいですね。
アニメーションの終了をまたずにアニメーションを切り替える方法
すんごい簡単でTransitionをクリックしてInspectorを表示
Has Exit Timeのチェックを外します。これですぐに切り替わってくれます。
実際に切り替えてみましょう。
こんな感じになりました。
今日は自分で3Dのアニメーションを1から作ってたのですが、走ってる姿をウサインボルト見ながら作ってたのでかなりアスリート感がある走り方になりました(笑)
3D LookAtを使って敵をこちらに向けさせる Vector3.Lerpを使って動かす
using UnityEngine;
using System.Collections;
public class hogehoge : MonoBehaviour {
[SerializeField] GameObject enemy;
// Update is called once per frame
void Update () {
enemy.gameObject.transform.LookAt (this.gameObject.transform);
}
}
ざっくりと簡単に
Magica Voxelで作成したひよこを今回使ってます。
一番最初にスクリプトをバンッと書いておきましたが、難しい事は特に書いていません。
LookAtを使うとターゲットとなるenemyというGameObjectを掴んでenemyに対象を向けさせます。
Sphereオブジェクトを作ってその中に一番最初に書いたスクリプトを追加します。
そのあとにSphereのある方向に向いてほしいオブジェクトをenemyの中に突っ込みます。そして再生するとこんな感じに
ボールはScene画面から自分でドラッグして動かしてます。動かすとひよこはボールの方向に向きを変えます。
そしてUpdateにこちらを追加して下さい。
enemy.gameObject.transform.position = Vector3.Lerp(enemy.gameObject.transform.position,this.gameObject.transform.position, Time.deltaTime);
そうすると・・・
ボールを追いかけるようになります。
Vector3.Lerpですが、こちらはaとbを結ぶ直線状をt=0~1で考えられていて、0.5fだとちょうどaとbの真ん中にあたります。
Vector3.Lerp(aのポジション, bのポジション, tの値)
となります。久しぶりに3Dをさわりましたが、3Dもやっぱり面白いですよね。
コルーチンとアップデートの流れ方
コルーチンってプログラミングを1から勉強し始めてる人にとってよくわからないものですよね。
自分もちゃんと説明しろと言われても全然できないのでコルーチンについてこれからまとめていけたらと思います。
実際使わなくてもなんとかなったりしたりもするものもあるのですが、プログラマーから言わせると自分のやり方は邪道というかとにかくプログラムが汚いという事でした(笑)
すべて独学の我流なので…じゃやっぱり通じない部分も一緒にやると出てきます。
using UnityEngine;
using System.Collections;
public class hogehoge : MonoBehaviour {
void Start(){
StartCoroutine("cor");
}
void Update(){
Debug.Log ("アップデート");
}
public IEnumerator cor(){
while (true) {
Debug.Log ("コルーチン");
yield return null;
}
}
}
こんな感じで書いてコンソールを見てみると
アップデートとコルーチンの中を順番に通っている事がわかります。
using UnityEngine;
using System.Collections;
public class hogehoge : MonoBehaviour {
void Start(){
StartCoroutine("cor");
}
void Update(){
Debug.Log ("アップデート");
}
public IEnumerator cor(){
while (true) {
Debug.Log ("コルーチンブレイク");
yield break;
Debug.Log ("コルーチン");
yield return null;
}
}
}
次にブレイクをwhileの中に書いてみました。
最初にコルーチンの中を通りますが、そのあとはアップデートの中をずっと回っています。
breakを通るとそのコルーチンの処理は中断ではなく終了となってしまいます。
とりあえず初歩的なところで、また別の記事で初歩的な使い方をまとめていきたいと思います。
全部をUpdate()の中に書いてしまうとどうしてもプログラムが長くなってあれこれ書かれていて汚くなってしまいがちなので、こうしてコルーチンで別にしておく事がきれいなプログラムを書く為には必要なんだと思いました。