/*
 * Copyright (C) 2008-2012 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package android.renderscript;

import android.compat.annotation.UnsupportedAppUsage;

import java.util.Vector;

/**
 * @hide
 * @deprecated in API 16
 * <p>This class is a container for geometric data displayed with
 * RenderScript. Internally, a mesh is a collection of allocations that
 * represent vertex data (positions, normals, texture
 * coordinates) and index data such as triangles and lines. </p>
 * <p>
 * Vertex data could either be interleaved within one
 * allocation that is provided separately, as multiple allocation
 * objects, or done as a combination of both. When a
 * vertex channel name matches an input in the vertex program,
 * RenderScript automatically connects the two together.
 * </p>
 * <p>
 *  Parts of the mesh can be rendered with either explicit
 *  index sets or primitive types.
 * </p>
 **/
public class Mesh extends BaseObj {

    /**
    * @deprecated in API 16
    * Describes the way mesh vertex data is interpreted when rendering
    *
    **/
    public enum Primitive {
        /**
        * @deprecated in API 16
        * Vertex data will be rendered as a series of points
        */
        @UnsupportedAppUsage
        POINT (0),
        /**
        * @deprecated in API 16
        * Vertex pairs will be rendered as lines
        */
        LINE (1),
        /**
        * @deprecated in API 16
        * Vertex data will be rendered as a connected line strip
        */
        LINE_STRIP (2),
        /**
        * @deprecated in API 16
        * Vertices will be rendered as individual triangles
        */
        @UnsupportedAppUsage
        TRIANGLE (3),
        /**
        * @deprecated in API 16
        * Vertices will be rendered as a connected triangle strip
        * defined by the first three vertices with each additional
        * triangle defined by a new vertex
        */
        TRIANGLE_STRIP (4),
        /**
        * @deprecated in API 16
        * Vertices will be rendered as a sequence of triangles that all
        * share first vertex as the origin
        */
        TRIANGLE_FAN (5);

        int mID;
        Primitive(int id) {
            mID = id;
        }
    }

    Allocation[] mVertexBuffers;
    Allocation[] mIndexBuffers;
    Primitive[] mPrimitives;

    Mesh(long id, RenderScript rs) {
        super(id, rs);
        guard.open("destroy");
    }

    /**
    * @deprecated in API 16
    * @return number of allocations containing vertex data
    *
    **/
    public int getVertexAllocationCount() {
        if(mVertexBuffers == null) {
            return 0;
        }
        return mVertexBuffers.length;
    }
    /**
    * @deprecated in API 16
    * @param slot index in the list of allocations to return
    * @return vertex data allocation at the given index
    *
    **/
    @UnsupportedAppUsage
    public Allocation getVertexAllocation(int slot) {
        return mVertexBuffers[slot];
    }

    /**
    * @deprecated in API 16
    * @return number of primitives or index sets in the mesh
    *
    **/
    public int getPrimitiveCount() {
        if(mIndexBuffers == null) {
            return 0;
        }
        return mIndexBuffers.length;
    }

    /**
    * @deprecated in API 16
    * @param slot locaton within the list of index set allocation
    * @return allocation containing primtive index data or null if
    *         the index data is not specified explicitly
    *
    **/
    public Allocation getIndexSetAllocation(int slot) {
        return mIndexBuffers[slot];
    }
    /**
    * @deprecated in API 16
    * @param slot locaiton within the list of index set primitives
    * @return index set primitive type
    *
    **/
    public Primitive getPrimitive(int slot) {
        return mPrimitives[slot];
    }

    @Override
    void updateFromNative() {
        super.updateFromNative();
        int vtxCount = mRS.nMeshGetVertexBufferCount(getID(mRS));
        int idxCount = mRS.nMeshGetIndexCount(getID(mRS));

        long[] vtxIDs = new long[vtxCount];
        long[] idxIDs = new long[idxCount];
        int[] primitives = new int[idxCount];

        mRS.nMeshGetVertices(getID(mRS), vtxIDs, vtxCount);
        mRS.nMeshGetIndices(getID(mRS), idxIDs, primitives, idxCount);

        mVertexBuffers = new Allocation[vtxCount];
        mIndexBuffers = new Allocation[idxCount];
        mPrimitives = new Primitive[idxCount];

        for(int i = 0; i < vtxCount; i ++) {
            if(vtxIDs[i] != 0) {
                mVertexBuffers[i] = new Allocation(vtxIDs[i], mRS, null, Allocation.USAGE_SCRIPT);
                mVertexBuffers[i].updateFromNative();
            }
        }

        for(int i = 0; i < idxCount; i ++) {
            if(idxIDs[i] != 0) {
                mIndexBuffers[i] = new Allocation(idxIDs[i], mRS, null, Allocation.USAGE_SCRIPT);
                mIndexBuffers[i].updateFromNative();
            }
            mPrimitives[i] = Primitive.values()[primitives[i]];
        }
    }

    /**
    * @deprecated in API 16
    * Mesh builder object. It starts empty and requires you to
    * add the types necessary to create vertex and index
    * allocations.
    *
    */
    public static class Builder {
        RenderScript mRS;
        int mUsage;

        class Entry {
            Type t;
            Element e;
            int size;
            Primitive prim;
            int usage;
        }

        int mVertexTypeCount;
        Entry[] mVertexTypes;
        Vector mIndexTypes;

        /**
        * @deprecated in API 16
        * Creates builder object
        * @param rs Context to which the mesh will belong.
        * @param usage specifies how the mesh allocations are to be
        *              handled, whether they need to be uploaded to a
        *              buffer on the gpu, maintain a cpu copy, etc
        */
        public Builder(RenderScript rs, int usage) {
            mRS = rs;
            mUsage = usage;
            mVertexTypeCount = 0;
            mVertexTypes = new Entry[16];
            mIndexTypes = new Vector();
        }

        /**
        * @deprecated in API 16
        * @return internal index of the last vertex buffer type added to
        *         builder
        **/
        public int getCurrentVertexTypeIndex() {
            return mVertexTypeCount - 1;
        }

        /**
        * @deprecated in API 16
        * @return internal index of the last index set added to the
        *         builder
        **/
        public int getCurrentIndexSetIndex() {
            return mIndexTypes.size() - 1;
        }

        /**
        * @deprecated in API 16
        * Adds a vertex data type to the builder object
        *
        * @param t type of the vertex data allocation to be created
        *
        * @return this
        **/
        public Builder addVertexType(Type t) throws IllegalStateException {
            if (mVertexTypeCount >= mVertexTypes.length) {
                throw new IllegalStateException("Max vertex types exceeded.");
            }

            mVertexTypes[mVertexTypeCount] = new Entry();
            mVertexTypes[mVertexTypeCount].t = t;
            mVertexTypes[mVertexTypeCount].e = null;
            mVertexTypeCount++;
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds a vertex data type to the builder object
        *
        * @param e element describing the vertex data layout
        * @param size number of elements in the buffer
        *
        * @return this
        **/
        public Builder addVertexType(Element e, int size) throws IllegalStateException {
            if (mVertexTypeCount >= mVertexTypes.length) {
                throw new IllegalStateException("Max vertex types exceeded.");
            }

            mVertexTypes[mVertexTypeCount] = new Entry();
            mVertexTypes[mVertexTypeCount].t = null;
            mVertexTypes[mVertexTypeCount].e = e;
            mVertexTypes[mVertexTypeCount].size = size;
            mVertexTypeCount++;
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds an index set data type to the builder object
        *
        * @param t type of the index set data, could be null
        * @param p primitive type
        *
        * @return this
        **/
        public Builder addIndexSetType(Type t, Primitive p) {
            Entry indexType = new Entry();
            indexType.t = t;
            indexType.e = null;
            indexType.size = 0;
            indexType.prim = p;
            mIndexTypes.addElement(indexType);
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds an index set primitive type to the builder object
        *
        * @param p primitive type
        *
        * @return this
        **/
        public Builder addIndexSetType(Primitive p) {
            Entry indexType = new Entry();
            indexType.t = null;
            indexType.e = null;
            indexType.size = 0;
            indexType.prim = p;
            mIndexTypes.addElement(indexType);
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds an index set data type to the builder object
        *
        * @param e element describing the index set data layout
        * @param size number of elements in the buffer
        * @param p primitive type
        *
        * @return this
        **/
        public Builder addIndexSetType(Element e, int size, Primitive p) {
            Entry indexType = new Entry();
            indexType.t = null;
            indexType.e = e;
            indexType.size = size;
            indexType.prim = p;
            mIndexTypes.addElement(indexType);
            return this;
        }

        Type newType(Element e, int size) {
            Type.Builder tb = new Type.Builder(mRS, e);
            tb.setX(size);
            return tb.create();
        }

        /**
        * @deprecated in API 16
        * Create a Mesh object from the current state of the builder
        *
        **/
        public Mesh create() {
            mRS.validate();
            long[] vtx = new long[mVertexTypeCount];
            long[] idx = new long[mIndexTypes.size()];
            int[] prim = new int[mIndexTypes.size()];

            Allocation[] vertexBuffers = new Allocation[mVertexTypeCount];
            Allocation[] indexBuffers = new Allocation[mIndexTypes.size()];
            Primitive[] primitives = new Primitive[mIndexTypes.size()];

            for(int ct = 0; ct < mVertexTypeCount; ct ++) {
                Allocation alloc = null;
                Entry entry = mVertexTypes[ct];
                if (entry.t != null) {
                    alloc = Allocation.createTyped(mRS, entry.t, mUsage);
                } else if(entry.e != null) {
                    alloc = Allocation.createSized(mRS, entry.e, entry.size, mUsage);
                } else {
                    // Should never happen because the builder will always set one
                    throw new IllegalStateException("Builder corrupt, no valid element in entry.");
                }
                vertexBuffers[ct] = alloc;
                vtx[ct] = alloc.getID(mRS);
            }

            for(int ct = 0; ct < mIndexTypes.size(); ct ++) {
                Allocation alloc = null;
                Entry entry = (Entry)mIndexTypes.elementAt(ct);
                if (entry.t != null) {
                    alloc = Allocation.createTyped(mRS, entry.t, mUsage);
                } else if(entry.e != null) {
                    alloc = Allocation.createSized(mRS, entry.e, entry.size, mUsage);
                } else {
                    // Should never happen because the builder will always set one
                    throw new IllegalStateException("Builder corrupt, no valid element in entry.");
                }
                long allocID = (alloc == null) ? 0 : alloc.getID(mRS);
                indexBuffers[ct] = alloc;
                primitives[ct] = entry.prim;

                idx[ct] = allocID;
                prim[ct] = entry.prim.mID;
            }

            long id = mRS.nMeshCreate(vtx, idx, prim);
            Mesh newMesh = new Mesh(id, mRS);
            newMesh.mVertexBuffers = vertexBuffers;
            newMesh.mIndexBuffers = indexBuffers;
            newMesh.mPrimitives = primitives;

            return newMesh;
        }
    }

    /**
    * @deprecated in API 16
    * Mesh builder object. It starts empty and requires the user to
    * add all the vertex and index allocations that comprise the
    * mesh
    *
    */
    public static class AllocationBuilder {
        RenderScript mRS;

        class Entry {
            Allocation a;
            Primitive prim;
        }

        int mVertexTypeCount;
        Entry[] mVertexTypes;

        Vector mIndexTypes;

        /**
        * @deprecated in API 16
        **/
        @UnsupportedAppUsage
        public AllocationBuilder(RenderScript rs) {
            mRS = rs;
            mVertexTypeCount = 0;
            mVertexTypes = new Entry[16];
            mIndexTypes = new Vector();
        }

        /**
        * @deprecated in API 16
        * @return internal index of the last vertex buffer type added to
        *         builder
        **/
        public int getCurrentVertexTypeIndex() {
            return mVertexTypeCount - 1;
        }

        /**
        * @deprecated in API 16
        * @return internal index of the last index set added to the
        *         builder
        **/
        public int getCurrentIndexSetIndex() {
            return mIndexTypes.size() - 1;
        }

        /**
        * @deprecated in API 16
        * Adds an allocation containing vertex buffer data to the
        * builder
        *
        * @param a vertex data allocation
        *
        * @return this
        **/
        @UnsupportedAppUsage
        public AllocationBuilder addVertexAllocation(Allocation a) throws IllegalStateException {
            if (mVertexTypeCount >= mVertexTypes.length) {
                throw new IllegalStateException("Max vertex types exceeded.");
            }

            mVertexTypes[mVertexTypeCount] = new Entry();
            mVertexTypes[mVertexTypeCount].a = a;
            mVertexTypeCount++;
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds an allocation containing index buffer data and index type
        * to the builder
        *
        * @param a index set data allocation, could be null
        * @param p index set primitive type
        *
        * @return this
        **/
        @UnsupportedAppUsage
        public AllocationBuilder addIndexSetAllocation(Allocation a, Primitive p) {
            Entry indexType = new Entry();
            indexType.a = a;
            indexType.prim = p;
            mIndexTypes.addElement(indexType);
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds an index set type to the builder
        *
        * @param p index set primitive type
        *
        * @return this
        **/
        @UnsupportedAppUsage
        public AllocationBuilder addIndexSetType(Primitive p) {
            Entry indexType = new Entry();
            indexType.a = null;
            indexType.prim = p;
            mIndexTypes.addElement(indexType);
            return this;
        }

        /**
        * @deprecated in API 16
        * Create a Mesh object from the current state of the builder
        *
        **/
        @UnsupportedAppUsage
        public Mesh create() {
            mRS.validate();

            long[] vtx = new long[mVertexTypeCount];
            long[] idx = new long[mIndexTypes.size()];
            int[] prim = new int[mIndexTypes.size()];

            Allocation[] indexBuffers = new Allocation[mIndexTypes.size()];
            Primitive[] primitives = new Primitive[mIndexTypes.size()];
            Allocation[] vertexBuffers = new Allocation[mVertexTypeCount];

            for(int ct = 0; ct < mVertexTypeCount; ct ++) {
                Entry entry = mVertexTypes[ct];
                vertexBuffers[ct] = entry.a;
                vtx[ct] = entry.a.getID(mRS);
            }

            for(int ct = 0; ct < mIndexTypes.size(); ct ++) {
                Entry entry = (Entry)mIndexTypes.elementAt(ct);
                long allocID = (entry.a == null) ? 0 : entry.a.getID(mRS);
                indexBuffers[ct] = entry.a;
                primitives[ct] = entry.prim;

                idx[ct] = allocID;
                prim[ct] = entry.prim.mID;
            }

            long id = mRS.nMeshCreate(vtx, idx, prim);
            Mesh newMesh = new Mesh(id, mRS);
            newMesh.mVertexBuffers = vertexBuffers;
            newMesh.mIndexBuffers = indexBuffers;
            newMesh.mPrimitives = primitives;

            return newMesh;
        }
    }

    /**
    * @deprecated in API 16
    * Builder that allows creation of a mesh object point by point
    * and triangle by triangle
    *
    **/
    public static class TriangleMeshBuilder {
        float mVtxData[];
        int mVtxCount;
        int mMaxIndex;
        short mIndexData[];
        int mIndexCount;
        RenderScript mRS;
        Element mElement;

        float mNX = 0;
        float mNY = 0;
        float mNZ = -1;
        float mS0 = 0;
        float mT0 = 0;
        float mR = 1;
        float mG = 1;
        float mB = 1;
        float mA = 1;

        int mVtxSize;
        int mFlags;

        /**
        * @deprecated in API 16
        **/
        public static final int COLOR = 0x0001;
        /**
        * @deprecated in API 16
        **/
        public static final int NORMAL = 0x0002;
        /**
        * @deprecated in API 16
        **/
        public static final int TEXTURE_0 = 0x0100;

        /**
        * @deprecated in API 16
        * @param rs Context to which the mesh will belong.
        * @param vtxSize specifies whether the vertex is a float2 or
        *                float3
        * @param flags bitfield that is a combination of COLOR, NORMAL,
        *              and TEXTURE_0 that specifies what vertex data
        *              channels are present in the mesh
        *
        **/
        @UnsupportedAppUsage
        public TriangleMeshBuilder(RenderScript rs, int vtxSize, int flags) {
            mRS = rs;
            mVtxCount = 0;
            mMaxIndex = 0;
            mIndexCount = 0;
            mVtxData = new float[128];
            mIndexData = new short[128];
            mVtxSize = vtxSize;
            mFlags = flags;

            if (vtxSize < 2 || vtxSize > 3) {
                throw new IllegalArgumentException("Vertex size out of range.");
            }
        }

        private void makeSpace(int count) {
            if ((mVtxCount + count) >= mVtxData.length) {
                float t[] = new float[mVtxData.length * 2];
                System.arraycopy(mVtxData, 0, t, 0, mVtxData.length);
                mVtxData = t;
            }
        }

        private void latch() {
            if ((mFlags & COLOR) != 0) {
                makeSpace(4);
                mVtxData[mVtxCount++] = mR;
                mVtxData[mVtxCount++] = mG;
                mVtxData[mVtxCount++] = mB;
                mVtxData[mVtxCount++] = mA;
            }
            if ((mFlags & TEXTURE_0) != 0) {
                makeSpace(2);
                mVtxData[mVtxCount++] = mS0;
                mVtxData[mVtxCount++] = mT0;
            }
            if ((mFlags & NORMAL) != 0) {
                makeSpace(4);
                mVtxData[mVtxCount++] = mNX;
                mVtxData[mVtxCount++] = mNY;
                mVtxData[mVtxCount++] = mNZ;
                mVtxData[mVtxCount++] = 0.0f;
            }
            mMaxIndex ++;
        }

        /**
        * @deprecated in API 16
        * Adds a float2 vertex to the mesh
        *
        * @param x position x
        * @param y position y
        *
        * @return this
        *
        **/
        @UnsupportedAppUsage
        public TriangleMeshBuilder addVertex(float x, float y) {
            if (mVtxSize != 2) {
                throw new IllegalStateException("add mistmatch with declared components.");
            }
            makeSpace(2);
            mVtxData[mVtxCount++] = x;
            mVtxData[mVtxCount++] = y;
            latch();
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds a float3 vertex to the mesh
        *
        * @param x position x
        * @param y position y
        * @param z position z
        *
        * @return this
        *
        **/
        public TriangleMeshBuilder addVertex(float x, float y, float z) {
            if (mVtxSize != 3) {
                throw new IllegalStateException("add mistmatch with declared components.");
            }
            makeSpace(4);
            mVtxData[mVtxCount++] = x;
            mVtxData[mVtxCount++] = y;
            mVtxData[mVtxCount++] = z;
            mVtxData[mVtxCount++] = 1.0f;
            latch();
            return this;
        }

        /**
        * @deprecated in API 16
        * Sets the texture coordinate for the vertices that are added after this method call.
        *
        * @param s texture coordinate s
        * @param t texture coordinate t
        *
        * @return this
        **/
        public TriangleMeshBuilder setTexture(float s, float t) {
            if ((mFlags & TEXTURE_0) == 0) {
                throw new IllegalStateException("add mistmatch with declared components.");
            }
            mS0 = s;
            mT0 = t;
            return this;
        }

        /**
        * @deprecated in API 16
        * Sets the normal vector for the vertices that are added after this method call.
        *
        * @param x normal vector x
        * @param y normal vector y
        * @param z normal vector z
        *
        * @return this
        **/
        public TriangleMeshBuilder setNormal(float x, float y, float z) {
            if ((mFlags & NORMAL) == 0) {
                throw new IllegalStateException("add mistmatch with declared components.");
            }
            mNX = x;
            mNY = y;
            mNZ = z;
            return this;
        }

        /**
        * @deprecated in API 16
        * Sets the color for the vertices that are added after this method call.
        *
        * @param r red component
        * @param g green component
        * @param b blue component
        * @param a alpha component
        *
        * @return this
        **/
        public TriangleMeshBuilder setColor(float r, float g, float b, float a) {
            if ((mFlags & COLOR) == 0) {
                throw new IllegalStateException("add mistmatch with declared components.");
            }
            mR = r;
            mG = g;
            mB = b;
            mA = a;
            return this;
        }

        /**
        * @deprecated in API 16
        * Adds a new triangle to the mesh builder
        *
        * @param idx1 index of the first vertex in the triangle
        * @param idx2 index of the second vertex in the triangle
        * @param idx3 index of the third vertex in the triangle
        *
        * @return this
        **/
        @UnsupportedAppUsage
        public TriangleMeshBuilder addTriangle(int idx1, int idx2, int idx3) {
            if((idx1 >= mMaxIndex) || (idx1 < 0) ||
               (idx2 >= mMaxIndex) || (idx2 < 0) ||
               (idx3 >= mMaxIndex) || (idx3 < 0)) {
               throw new IllegalStateException("Index provided greater than vertex count.");
            }
            if ((mIndexCount + 3) >= mIndexData.length) {
                short t[] = new short[mIndexData.length * 2];
                System.arraycopy(mIndexData, 0, t, 0, mIndexData.length);
                mIndexData = t;
            }
            mIndexData[mIndexCount++] = (short)idx1;
            mIndexData[mIndexCount++] = (short)idx2;
            mIndexData[mIndexCount++] = (short)idx3;
            return this;
        }

        /**
        * @deprecated in API 16
        * Creates the mesh object from the current state of the builder
        *
        * @param uploadToBufferObject specifies whether the vertex data
        *                             is to be uploaded into the buffer
        *                             object indicating that it's likely
        *                             not going to be modified and
        *                             rendered many times.
        *                             Alternatively, it indicates the
        *                             mesh data will be updated
        *                             frequently and remain in script
        *                             accessible memory
        *
        **/
        @UnsupportedAppUsage
        public Mesh create(boolean uploadToBufferObject) {
            Element.Builder b = new Element.Builder(mRS);
            b.add(Element.createVector(mRS,
                                       Element.DataType.FLOAT_32,
                                       mVtxSize), "position");
            if ((mFlags & COLOR) != 0) {
                b.add(Element.F32_4(mRS), "color");
            }
            if ((mFlags & TEXTURE_0) != 0) {
                b.add(Element.F32_2(mRS), "texture0");
            }
            if ((mFlags & NORMAL) != 0) {
                b.add(Element.F32_3(mRS), "normal");
            }
            mElement = b.create();

            int usage = Allocation.USAGE_SCRIPT;
            if (uploadToBufferObject) {
                usage |= Allocation.USAGE_GRAPHICS_VERTEX;
            }

            Builder smb = new Builder(mRS, usage);
            smb.addVertexType(mElement, mMaxIndex);
            smb.addIndexSetType(Element.U16(mRS), mIndexCount, Primitive.TRIANGLE);

            Mesh sm = smb.create();

            sm.getVertexAllocation(0).copy1DRangeFromUnchecked(0, mMaxIndex, mVtxData);
            if(uploadToBufferObject) {
                sm.getVertexAllocation(0).syncAll(Allocation.USAGE_SCRIPT);
            }

            sm.getIndexSetAllocation(0).copy1DRangeFromUnchecked(0, mIndexCount, mIndexData);
            if (uploadToBufferObject) {
                sm.getIndexSetAllocation(0).syncAll(Allocation.USAGE_SCRIPT);
            }

            return sm;
        }
    }
}

