1

1D テクスチャに手動で値を入力し、そのテクスチャを計算シェーダーに渡そうとしています (これらはコードで設定したい 2 つのピクセルであり、画像を表しているわけではありません)。

現在、Metal のサンプルが少ないため、ロードされたデータを生のバイト データに変換することでテクスチャをロードする2D テクスチャUIImageを扱っているサンプルをすべて見つけることができましたが、ダミーを作成するのUIImageはハックのように感じました。

これは私が始めた「素朴な」方法です -

...
var manualTextureData: [Float] = [ 1.0, 0.0, 0.0, 1.0,
                                   0.0, 0.0, 1.0, 1.0 ];
let region: MTLRegion = MTLRegionMake1D(0, textureDescriptor.width);
myTexture.replaceRegion(region, mipmapLevel: 0, withBytes: &manualTextureData, bytesPerRow: 0);

しかし、Metal はシェーダーでこれらの値を認識しません (最初の値を除いて、空のテクスチャを取得します)。

おそらく Float 配列をバイト配列 (たとえば ) に変換する必要があることにすぐに気付きましたが、どちらにも変換するUInt8方法が見つかりませんでした。[Float][UInt8]

私が考えている別の可能なオプションは、CVPixelBufferオブジェクトを使用することですが、それも問題の回避策のように感じました.

では、それに取り組む正しい方法は何ですか?

前もって感謝します。

  • 私はObjective-CCVPixelBufferに精通していないため、 /の使用UIImageが単純である必要があるものに対して誇張されているかどうかはわかりません。
4

4 に答える 4

1

簡潔な回答で申し訳ありませんが、Swift と Metal を使った私の実験をご覧になると役立つかもしれません。Swift でパーティクル システムを作成しました。このシステムは、パーティクル構造体の 1 次元配列として Metal コンピューティング シェーダに渡されます。posix_memalign を使用することで、Metal と Swift の間で配列を渡すことによって生じるボトルネックを解消できます。

私はこれについて広くブログを書いています: http://flexmonkey.blogspot.co.uk/search/label/Metal

これが役立つことを願っています。

サイモン

于 2015-02-13T09:49:40.000 に答える
0

1D テクスチャを使用してデータを渡す理由がわかりません。代わりに、バッファを渡すだけで済みます。このような:

var dataBuffer:MTLBuffer? = device.newBufferWithBytes(&manualTextureData, length: sizeOf(manualTextureData), options: MTLResourceOptions.OptionCPUCacheModeDefault)

次に、次のようにフックしますrenderCommandEncoder

renderCommandEncoder.setFragmentBuffer(dataBuffer, offset: 0, atIndex: 1)//Note that if you want this buffer to be passed to you vertex shader you should use setVertexBuffer

次に、シェーダーで、次のようなパラメーターを追加する必要がありますconst device float* bufferPassed [[ buffer(1) ]]

そして、シェーダー実装内で次のように使用します。

float firstFloat = bufferPassed[0];

これで仕事がはかどります。

于 2014-11-03T11:16:20.520 に答える
0

あなたの質問に実際には答えていませんが、値をテクスチャとして渡す代わりに、金属シェーダーで配列を定義することができます。

何かのようなもの:

constant float manualData[8] = { 1.0, 0.0, 0.0, 1.0,
                               0.0, 0.0, 1.0, 1.0 };

vertex float4 world_vertex(unsigned int vid[[vertex_id]], ...) {
    int manualIndex = vid % 8;
    float manualValue = manualData[manualIndex];
    // something deep and meaningful here...
    return float4(manualValue);
}
于 2014-11-05T17:29:49.157 に答える