示例#1
0
        private byte[,] fillFlatTop(byte[,] image, Mesh.point3[] sortedPoints, Mesh.point3[] unsortedPoints, byte[] brightness, Mesh.point2[] uvs = null)
        {
            float startX = sortedPoints[2].x;
            float endX = sortedPoints[2].x;

            float invslope1 = (float)(sortedPoints[2].x - sortedPoints[0].x) / (float)(sortedPoints[2].y - sortedPoints[0].y);
            float invslope2 = (float)(sortedPoints[2].x - sortedPoints[1].x) / (float)(sortedPoints[2].y - sortedPoints[1].y);

            for (int scanlineY = (int)sortedPoints[2].y; scanlineY > sortedPoints[0].y; scanlineY--)
            {
                drawLine(image, (int)startX, scanlineY, (int)endX, scanlineY, false, unsortedPoints, brightness, uvs);
                startX -= invslope1;
                endX -= invslope2;
            }
            return (image);
        }
示例#2
0
        private byte[,] fillFlatBottom(byte[,] image, Mesh.point3[] sortedPoints, Mesh.point3[] unsortedPoints, byte[] brightness, Mesh.point2[] uvs = null)
        {
            float invslope1 = (float)(sortedPoints[2].x - sortedPoints[0].x) / (float)(sortedPoints[2].y - sortedPoints[0].y);
            float invslope2 = (float)(sortedPoints[0].x - sortedPoints[1].x) / (float)(sortedPoints[0].y - sortedPoints[1].y);

            float curx1 = sortedPoints[0].x;
            float curx2 = sortedPoints[0].x;

            for (int scanlineY = (int)sortedPoints[0].y; scanlineY <= sortedPoints[1].y; scanlineY++)
            {
                drawLine(image, (int)curx1, scanlineY, (int)curx2, scanlineY, false, unsortedPoints, brightness, uvs);
                curx1 += invslope1;
                curx2 += invslope2;
            }
            return (image);
        }
示例#3
0
        public byte[,] drawLine(byte[,] image, /*start*/int x0, int y0, int x1, int y1,/*end*/ bool drawWireFrame, Mesh.point3[] unsortedPoints = null, byte[] color = null, Mesh.point2[] uvs = null)
        {
            float rise = y1 - y0;
            float run = x1 - x0;
            byte txl = 219;
            //if (color != null)
            //{
            //    color[0] = 0;
            //    color[1] = 50;
            //    color[2] = 100;
            //}
            if (run == 0)
            {
                if (drawWireFrame)
                    txl = 124;// |

                if (y0 > y1)
                    swap(ref y0, ref y1);

                while (y0 < y1)//DRAW
                {
                    image[x0, y0] = txl;
                    y0++;
                }
                return (image);
            }

            float m = rise / run;

            if (-1 <= rise / run && rise / run <= 1)
            {

                if (drawWireFrame)
                {
                    if (rise / run > 0.5)
                        txl = 92;// /
                    else if (rise / run < -0.5)
                        txl = 47;// \
                    else
                        txl = 95;// -
                }

                if (x0 > x1)
                {
                    swap(ref x0, ref x1);
                    swap(ref y0, ref y1);
                }

                float y = y0;
                float x = x0;
                float denom = 0;
                if (!drawWireFrame)
                    denom = ((unsortedPoints[1].y - unsortedPoints[2].y) * (unsortedPoints[0].x - unsortedPoints[2].x) + (unsortedPoints[2].x - unsortedPoints[1].x) * (unsortedPoints[0].y - unsortedPoints[2].y));

                while (x <= x1 && y < RENDER_HEIGHT && x < RENDER_WIDTH && y >= 0)
                {
                    if (x > 0)//clipping logic     <    ^
                    {
                        int xtoi = (int)x;
                        int ytoi = (int)y;
                        if (drawWireFrame)
                        {
                            image[xtoi, ytoi] = txl;
                            y += m;
                        }
                        else//HERE'S WHERE WE DRAW TRIANGLES!
                        {
                            float b1 = (((unsortedPoints[1].y - unsortedPoints[2].y) * (x - unsortedPoints[2].x)) + ((unsortedPoints[2].x - unsortedPoints[1].x) * (y - unsortedPoints[2].y))) / denom;
                            float b2 = (((unsortedPoints[2].y - unsortedPoints[0].y) * (x - unsortedPoints[2].x)) + ((unsortedPoints[0].x - unsortedPoints[2].x) * (y - unsortedPoints[2].y))) / denom;
                            float b3 = 1 - b1 - b2;

                            int interpolatedZ = (int)(b1 * unsortedPoints[0].z + b2 * unsortedPoints[1].z + b3 * unsortedPoints[2].z);

                            if (interpolatedZ > zBuffer[xtoi, ytoi])
                            { // use barycentric interpolation to do everything..
                                float interpU = (float)(b1 * uvs[0].x + b2 * uvs[1].x + b3 * uvs[2].x);
                                float interpV = (float)(b1 * uvs[0].y + b2 * uvs[1].y + b3 * uvs[2].y);
                                float interpBright = color[1];// + b2 * (float)color[1] + b3 * (float)color[2]);
                                Material someMat = someShape.matIDs[targFace.matID-1];
                                int xpos = Math.Min(Math.Max((int)(interpU * someMat.SIZE), 0), someMat.SIZE-1);
                                int ypos = Math.Min(Math.Max((int)(interpV * someMat.SIZE), 0), someMat.SIZE-1);

                                byte fa = someMat.bitmapColorsCached[(int)clamp(xpos, 0, someMat.SIZE-1), (int)clamp(ypos, 0, someMat.SIZE-1)];
                                image[xtoi, ytoi] = (byte)(Convert.ToInt32(levels[(int)clamp(fa + interpBright, 0, 255)]));
                                zBuffer[xtoi, ytoi] = interpolatedZ;
                            }
                        }
                    }
                    x++;
                }
            }
            else
            {
                if (run / rise > 0.5)
                    txl = 92;// /
                else if (run / rise < -0.5)
                    txl = 47;// \
                else
                    txl = 124;// -

                if (y0 > y1)
                {
                    swap(ref x0, ref x1);
                    swap(ref y0, ref y1);
                }

                float x = x0;
                float invSlope = 1 / m;

                while (y0 < y1)
                {
                    image[(int)x, y0] = txl;
                    x += invSlope;
                    y0++;
                }
            }
            return (image);
        }
示例#4
0
        private byte[,] drawTriangle(byte[,] image, Mesh.point3[] points, Mesh.point2[] uvs, byte[] brightness = null)
        {
            /*
             *      A
             *  B-------
             *          C
             *
             */
            //sort by lowest y value (highest on screen)
            Mesh.point3[] unsortedPoints = new Mesh.point3[3];
            points.CopyTo(unsortedPoints, 0);

            if (points[1].y < points[0].y)
            {//swap point[1] and point[0]
                swap(ref points[0].y, ref points[1].y);
                swap(ref points[0].x, ref points[1].x);
            }
            if (points[2].y < points[0].y)
            {//swap point[0] and point[2]
                swap(ref points[0].y, ref points[2].y);
                swap(ref points[0].x, ref points[2].x);
            }
            if (points[2].y < points[1].y)
            {//swap point[1] & point[2]
                swap(ref points[1].y, ref points[2].y);
                swap(ref points[1].x, ref points[2].x);
            }

            if (points[0].y == points[1].y)
            {//flat top
                image = fillFlatTop(image, points, unsortedPoints, brightness, uvs);
            }
            else if (points[1].y == points[2].y)
            {//flat bottom
                image = fillFlatBottom(image, points, unsortedPoints, brightness, uvs);
            }
            else
            {//nontrivial
                Mesh.point3 midpoint = new Mesh.point3((int)(Math.Ceiling(points[0].x + ((float)(points[1].y - points[0].y) / (float)(points[2].y - points[0].y)) * (points[2].x - points[0].x))), points[1].y);
                fillFlatBottom(image, new Mesh.point3[] { points[0], points[1], midpoint }, unsortedPoints, brightness, uvs);
                fillFlatTop(image, new Mesh.point3[] { points[1], midpoint, points[2] }, unsortedPoints, brightness, uvs);
            }
            return (image);
        }
示例#5
0
        public byte[,] renderWire(Mesh someShape)
        {
            byte[,] image = new byte[RENDER_WIDTH, RENDER_HEIGHT];//

            for (int x = 0; x < RENDER_WIDTH; x++)
                for (int y = 0; y < RENDER_HEIGHT; y++)
                    image[x, y] = 32;

            foreach (Mesh.triangle f in someShape.faces)
            {
                for (int i = 0; i < 3; i++)//each vertex
                {
                    double depth = someShape.verts[f.vertIDs[i]].z;
                    int P_x1 = (int)((RENDER_WIDTH / 2) + someShape.verts[f.vertIDs[i]].x / depth);
                    int P_y1 = (int)(((RENDER_HEIGHT - 15) / 2) + someShape.verts[f.vertIDs[i]].y / depth);

                    if (P_y1 < RENDER_HEIGHT - 1 && P_y1 >= 0 && P_x1 < RENDER_WIDTH - 1 && P_x1 >= 0)//the vert is in bounds with the screen
                        for (int j = 0; j < 2; j++)//each of the 2 neighboring verts
                        {
                            double depth2 = someShape.verts[f.vertIDs[j]].z;
                            int P_x = (int)((RENDER_WIDTH / 2) + someShape.verts[f.vertIDs[j]].x / depth2);
                            int P_y = (int)(((RENDER_HEIGHT - 15) / 2) + someShape.verts[f.vertIDs[j]].y / depth2);

                            if (P_y < RENDER_HEIGHT - 1 && P_y >= 0 && P_x < RENDER_WIDTH - 1 && P_x >= 0)
                                image = drawLine(image, P_x, P_y, P_x1, P_y1, true);
                        }
                }
            }
            return (image);
        }
示例#6
0
        public byte[,] renderVerts(Mesh someShape)
        {
            byte[,] image = new byte[RENDER_WIDTH, RENDER_HEIGHT];//

            for (int x = 0; x < RENDER_WIDTH; x++)
                for (int y = 0; y < RENDER_HEIGHT; y++)
                    image[x, y] = 32;

            foreach (Mesh.triangle f in someShape.faces)
            {
                for (int i = 0; i < 3; i++)//each vertex
                {
                    double depth = someShape.verts[f.vertIDs[i]].z;
                    int P_x1 = (int)(someShape.verts[f.vertIDs[i]].x / depth);
                    int P_y1 = (int)(someShape.verts[f.vertIDs[i]].y / depth);

                    if (P_y1 < RENDER_HEIGHT - 1 && P_y1 >= 0 && P_x1 < RENDER_WIDTH - 1 && P_x1 >= 0)//the vert is in bounds with the screen
                        image[P_x1, P_y1] = 177;
                }
            }
            return (image);
        }