web-dev-qa-db-ja.com

Unity3dで実行時にPNG画像をテクスチャとしてロードする

Unityの拡張現実アプリケーション用に平面上にアニメーションを作成するために、一連のPNG画像をスプライトとして使用しています。 PNGイメージはテクスチャとして読み込まれ、テクスチャが平面に適用されて、拡張現実ターゲットで追跡するアニメーションシーケンスが作成されます。

これは、飛行機に取り付けられ、アニメーションシーケンスを制御するスクリプトです。

ファイルPNGSequence.js

#pragma strict
var tecture : Texture[];

var changeInterval : float = 0.06;
var isRunning = false;
var isLooping = false;

function Start () {
    var isRunning = true;
}

function Update () {
    if( isRunning == true) {
        Animation ();
    }
}

function Animation () {
    var index : int = Time.time/changeInterval;
    index = index % tecture.Length;
    renderer.material.mainTexture = tecture[index];
    if ( index == tecture.Length-1){
        if( isLooping == false){
            isRunning = false;
        }
           renderer.material.mainTexture = tecture[0];
    }
}

エディターでは、PNGファイルのドラッグアンドドロップによってテクスチャが割り当てられ、PNG数を制限すると、すべてが正常に機能します。ただし、テクスチャ数が増えると、Androidでメモリ不足エラーが発生します。

メモリ数を制限するために実行時にPNGファイルをテクスチャとしてロードしたいのですが、コードを機能させるのに問題があります。

LoadImageを試しました。

var imageTextAsset : TextAsset = Resources.Load("test.png");
var tex = new Texture2D (4, 4);
tex.LoadImage(imageTextAsset.bytes);
renderer.material.mainTexture = tex;

また、イメージをテクスチャとして直接ロードしてみました(これはエディタで動作するように見えるため)。

renderer.material.mainTexture = Resources.LoadAssetAtPath"Assets/Images/test.png",Texture);

どちらでも運がありません。これを達成する方法について何か提案はありますか?

[〜#〜]編集済み[〜#〜]

Xerosigmaから提供されたリンクのおかげで、これを機能させることができました。パスに問題がありました(そして、ロード時のテクスチャ要件に疑いがあります)。

PNGテクスチャをロードする以外に、Unityがテクスチャのメモリ管理を行わないことも発見しました。メモリを回復するには、テクスチャを使用後に手動でアンロードする必要があります。

テクスチャはすべて「Resources」フォルダに配置されます。リソースフォルダーは、アセット階層の任意の場所に配置できます。PNGシーケンスごとにいくつかの個別のフォルダーを作成して整理し、実際のP​​NGを保持するために各フォルダー内にリソースフォルダーを追加しました。

テクスチャは、テクスチャカウント(つまり100)、ベース名(たとえば、「texture_」)、およびゼロパディングを指定することにより、エディタを介して割り当てられます。

ファイルPNGSequenceRunTime.js

#pragma strict

var imageCount : int = 0;
var imageNameBase : String = "";
var imageNameZeroPadding : int = 0;

var changeInterval : float = 0.06;
var isRunning = false;
var isLooping = false;

private var texture : Texture = null;

function PlayRocket () {
    isRunning = true;
}

function Start () {
    var isRunning = false;
    var fileName : String = imageNameBase + ZeroPad(0,imageNameZeroPadding);
    texture = Resources.Load(fileName);
}

function Update () {
    if( isRunning == true) {
        PNGAnimation ();
    }
}

function PNGAnimation () {
    var index : int = Time.time/changeInterval;
    index = index % imageCount;
    var fileName : String = imageNameBase + ZeroPad(index,imageNameZeroPadding);
    Resources.UnloadAsset(texture);
    texture = Resources.Load(fileName);
    renderer.material.mainTexture = texture;


    if ( index == imageCount-1){
        Debug.Log("End of Animation");
        Debug.LogWarning("End of Animation");
        if( isLooping == false){
            isRunning = false;
        }
        fileName = imageNameBase + ZeroPad(0,imageNameZeroPadding);
        Resources.UnloadAsset(texture);
        texture = Resources.Load(fileName);
        renderer.material.mainTexture = texture;
    }
}

function ZeroPad(number : int, size : int) {
    var numberString : String = number.ToString();
    while (numberString.Length < size) numberString = "0" + numberString;
    return numberString;
}
9
Jason George

C#の場合:

// Load all textures into an array
Object[] textures = Resources.LoadAll("Textures", typeof(Texture2D));

// Load a single texture
Texture2D texture = Resources.Load("Texture") as Texture2D;

renderer.material.mainTexture = texture;

それが役に立てば幸い。問題なくJSに変換できるはずです。 Unityのドキュメントをご覧ください。

http://docs.unity3d.com/Documentation/ScriptReference/Resources.html

12
Nestor Ledon

メインのAssetsフォルダー内のResources/Sequence1フォルダーに.png画像のシーケンス(アルファチャネルを含む)を配置することで同じことを実現しました。出力は、画像のアルファチャネルに正確に一致する透明度で再生されるシームレスなムービーです。

このコードは、透明/拡散シェーダー付きのデフォルトの新しいマテリアルが割り当てられている平面に適用されます。このシェーダは、透明度がアルファのPNG画像をサポートしています。画像を含むフォルダの名前を変数framespathに与えるだけです。

#pragma strict

var framespath: String = "";
var vidframes: Object[];
var count: int;

function Start () {

    vidframes = Resources.LoadAll(framespath, Texture);
    Debug.Log(vidframes.Length);

    count = 0;
    renderer.material.mainTexture = vidframes[count];
}

function Update () {
    count++;
    renderer.material.mainTexture = vidframes[count];
    if (count == vidframes.Length-1)
    {
        count = 0;
    }
}
2
user3004240