Mr 3d Geschrieben 3. Januar 2017 Melden Share Geschrieben 3. Januar 2017 Hi, ich spiele gerade mal wieder etwas mit ComputeShadern und bin auf ein mir nicht erklärbares Verhalten gestoßen... Ich habe ein float-Array mit 9 Elementen. In meinem ComputeShader habe ich ein ein Array aus drei float3`s ( da es anscheinend keinen direkten Weg gibt eine 3x3 Matrix zu übertragen .. ) Wenn ich jetzt per "SetFloats();" versuche mein Array an den ComputeShader zu übergeben, kommt im ComputeShader dann das an: (x1, y1, z1 ) (y2, z2, x3 ) (z3, 0 , 0 ) anstatt: (x1,y1,z1) (x2,y2,z2) (x3,y3,z3) Also so, wie wenn immer alle drei Elemente ein Element übersprungen wird. Nur warum? ^.^ Wenn ich mein Array statt 9 Elementen 12 Elemente gebe und dafür nach jedem 3. Element ( das ja ahnscheinend übersprungen wird ) ein Element "leer" lasse, dann kommen im ComputeShader die "richtigen" Werte an. Aber ich finde es nicht so schön jeden Frame 12 "unnötige" bytes zu versenden.. also weiß jemand was ich falsch mache? Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 3. Januar 2017 Melden Share Geschrieben 3. Januar 2017 Also, bei mir klappt das bestens, und ich schiebe im Megabyte-Bereich Daten in meine Shader. Zeig doch mal den C#-Code mit dem Array und SetFloats. Außerdem: Welchen Buffertyp benutzt du im Shader? Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Mr 3d Geschrieben 3. Januar 2017 Autor Melden Share Geschrieben 3. Januar 2017 okay ^ .. ich bin wirklich noch ziemlich neu auf dem Gebiet also, im Grunde der Code auf C# Seite ist: void Update(){ myComputeShader.SetFloats("rotation", generateRotationMatrix(transform.rotation)); } //Quaternion to Matrix private float[] generateRotationMatrix(Quaternion rot) { float[] matrix = new float[9]; matrix[0] = 1 - 2 * rot.y * rot.y - 2 * rot.z * rot.z; matrix[1] = 2 * rot.x * rot.y - 2 * rot.z * rot.w; matrix[2] = 2 * rot.x * rot.z + 2 * rot.y * rot.w; matrix[3] = 2 * rot.x * rot.y + 2 * rot.z * rot.w; matrix[4] = 1 - 2 * rot.x * rot.x - 2 * rot.z * rot.z; matrix[5] = 2 * rot.y * rot.z - 2 * rot.x * rot.w; matrix[6] = 2 * rot.x * rot.z - 2 * rot.y * rot.w; matrix[7] = 2 * rot.y * rot.w + 2 * rot.x * rot.w; matrix[8] = 1 - 2 * rot.x * rot.x - 2 * rot.y * rot.y; return matrix; } und auf Shader Seite gibt es einfach: float3 rotation[3]; Ansonsten hat bisher auch alles ohne Probleme geklappt also sämmtliche ComputeBuffer oder Vectoren zu übertragen.. nur eben mit SetFloats scheint es Probleme zu haben.. Welchen Buffertyp benutzt du im Shader? Ehrlich gesagt hab ich keine Ahnung ^^ ich hab nur gesehen dass man bei ComputeBuffern einen ComputeBufferTyp angeben kann aber nicht bei SetFloats().. Oder soll ich vtl doch einfach einen ComputeBuffer dafür benutzen? das mit SetFloats kam mir einfach irgendwie schöner vor.. btw.. ich schiebe im Megabyte-Bereich Daten in meine Shader. Ich habe gehört man soll so wenig traffic zwischen vram und ram erzeugen wie möglich.. sind Megabyte noch ok oder ist das dann schon zu viel? Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 3. Januar 2017 Melden Share Geschrieben 3. Januar 2017 Ah gut - ich habe einfach einen ComputeBuffer und benutze SetData. Nur so am Rand: Auf meinem Arbeitsrechner geht das mit den vielen Daten in gut unter einer Millisekunde. Warum das mit SetFloats jetzt nicht geht, kann ich leider nicht sagen. Auf beiden Seiten hast du 9 32bit-Floats, sieht also gut aus. Da ich auch nicht über Vor- und Nachteile von float-Arrays und ComputeBuffern Bescheid weiß, würde ich sagen: Probier's einfach mal mit einem ComputeBuffer aus. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Mr 3d Geschrieben 3. Januar 2017 Autor Melden Share Geschrieben 3. Januar 2017 Ok danke^ also gerade läuft es ganz gut indem ich, wie oben schon beschrieben, einfach drei float4 versende und die w-Koordinate ignoriere.. Wenn das Probleme macht, oder ich noch Lust und Zeit hab, stell ichs eben auf ComputeBuffer um. Dürfte ja theoretisch kein Problem sein ( theoretisch ^ ) Aber vtl kannst Du ( oder natürlich auch wer anders ) mir noch eine Frage beantworten die mir gerade noch gekommen ist.. Wenn man einen ComputeBuffer setzt, dann muss man eine art "Zielkernel" angeben. Und von anderen Kerneln lässt sich dann auf diesen Buffer nicht direkt zugreifen, wie ich festgestellt habe, außer man schreibt ".SetBuffer" auch nochmal für den anderen Kernel. Nur wird dann jedes mal wieder der Buffer von Ram in vRam kopiert, oder wird dann nur ein Pointer an den neuen Kernel übergeben, der zeigt wo der Buffer im vRam schon liegt? ( ich bin mir nicht 100% sicher ob das so richtig formuliert ist.. ) Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 3. Januar 2017 Melden Share Geschrieben 3. Januar 2017 Das kann ich leider nicht sagen, aber in der Regel gilt: Grafikkarten und ihre Treiber sind extrem clever und verdammt magisch. Würde mich also stark wundern, wenn die das grundlos verhunzt hätten. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Mr 3d Geschrieben 5. Januar 2017 Autor Melden Share Geschrieben 5. Januar 2017 Dann vertrau ich fürs erste einfach darauf, dass auf magische weise alles gut funktionieren wird..^^ Wenn ich zufällig eine Antwort finde melde ich mich nochmal.. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Recommended Posts
Archiviert
Dieses Thema ist jetzt archiviert und für weitere Antworten gesperrt.