Linked Questions

Popular Questions

Filament image viewer on Android

Asked by At

Try create image-viewer use Kotlin & lib: Filament, i follow c++ example cpp & material image.mat, convert to Kotlin but it doesn't work

My code: Mesh:

    private fun createMesh() {
        val intSize = 4
        val floatSize = 4
        val shortSize = 2
        val vertexSize = 4 * floatSize

        // Define a vertex and a function to put a vertex in a ByteBuffer
        data class Vertex(val x: Float, val y: Float, val z: Float, val w: Float)
        fun ByteBuffer.put(v: Vertex): ByteBuffer {
            putFloat(v.x)
            putFloat(v.y)
            putFloat(v.z)
            putFloat(v.w)
            return this
        }

        val vertexCount = 3

        val vertexData = ByteBuffer.allocate(vertexCount * vertexSize)
            // It is important to respect the native byte order
            .order(ByteOrder.nativeOrder())
            .put(Vertex(-1.0f, -1.0f, 1.0f, 1.0f))
            .put(Vertex(3.0f, -1.0f, 1.0f, 1.0f))
            .put(Vertex(-1.0f,  3.0f, 1.0f, 1.0f))
            // Make sure the cursor is pointing in the right place in the byte buffer
            .flip()

        vertexBuffer = VertexBuffer.Builder()
            .bufferCount(1)
            .vertexCount(vertexCount)
            .attribute(VertexAttribute.POSITION, 0, AttributeType.FLOAT4, 0, vertexSize)
            .build(engine)

        vertexBuffer.setBufferAt(engine, 0, vertexData)

        val indexData = ByteBuffer.allocate(3 * shortSize)
            .order(ByteOrder.nativeOrder())
            .putShort(0)
            .putShort(1)
            .putShort(2)
            .flip()

        indexBuffer = IndexBuffer.Builder()
            .indexCount(3)
            .bufferType(IndexBuffer.Builder.IndexType.USHORT)
            .build(engine)
        indexBuffer.setBuffer(engine, indexData)
    }

Load Material

    private fun loadMaterial() {
        readUncompressedAsset("materials/image.filamat").let {
            val texture = loadTexture(engine, resources, R.drawable.bg, TextureType.COLOR)
            material = Material.Builder().payload(it, it.remaining()).build(engine)
            val sampler = TextureSampler()
            sampler.magFilter = TextureSampler.MagFilter.LINEAR
            sampler.minFilter = TextureSampler.MinFilter.LINEAR_MIPMAP_LINEAR
            sampler.wrapModeS = TextureSampler.WrapMode.REPEAT
            sampler.wrapModeT = TextureSampler.WrapMode.REPEAT
            material.setDefaultParameter("image", texture, sampler)
            material.setDefaultParameter("transform", MaterialInstance.FloatElement.MAT3, Mat3().toFloatArray(), 0, 9)
            material.setDefaultParameter("showImage", 1)
            material.setDefaultParameter("backgroundColor", MaterialInstance.FloatElement.FLOAT3,  Float3(0f, 0f ,0f), 3)
        }
    }

renderable

    renderable = EntityManager.get().create()
    RenderableManager.Builder(1)
            .boundingBox(Box(0.0f, 0.0f, 0.0f, 1.0f, 1.0f, 1f))
            .material(0, material.defaultInstance)
            .geometry(0, PrimitiveType.TRIANGLES, vertexBuffer, indexBuffer, 0, 3)
            .culling(false)
            .build(engine, renderable)
    scene.addEntity(renderable)

That always crash with error:

showImage uniform not exist

If i try change image.mat always show image and don't require background color, apps not crash but dont render anything.

image.mat after change:

     material {
        name : Image,
        parameters :
        [
            {
                type : sampler2d,
                name : image
            }
        ],
        variables : [ imageUV ],
        vertexDomain : device,
        depthWrite : false,
        shadingModel : unlit,
        variantFilter : [ skinning, shadowReceiver, vsm ],
        culling: none
    }

    vertex {
        void materialVertex(inout MaterialVertexInputs material) {
            material.imageUV.st = getPosition().st * 0.5 + 0.5;
        }
    }

    fragment {
        void material(inout MaterialInputs material) {
            prepareMaterial(material);
            vec4 bg = vec4(0.0, 0.0, 0.0, 1.0);
            highp vec2 uv = vec3(saturate(variable_imageUV.st), 1.0).st;
            uv.t = 1.0 - uv.t;
            vec4 color = max(texture(materialParams_image, uv.st), 0.0);
            color.rgb *= color.a;
            // Manual, pre-multiplied srcOver with opaque destination optimization
            material.baseColor.rgb = color.rgb + bg.rgb * (1.0 - color.a);
        }
    }

I dont know why it crash while showImage exist ? while i change image.mat, it can run but why didn't render anything ?

Related Questions