示例#1
0
 public ShaderState(int size, World world)
 {
     _world    = world;
     _face     = new FaceShaderState(world);
     _vertex   = new VertexShaderState(size, world);
     _fragment = new FragmentShaderState(size, world);
 }
示例#2
0
        public override void Face(FaceShaderState state, int face)
        {
            var v0 = _geometry.GetVertex(face, 0);
            var v1 = _geometry.GetVertex(face, 1);
            var v2 = _geometry.GetVertex(face, 2);

            var foo1 = Vector3.Subtract(v1, v0);
            var foo2 = Vector3.Subtract(v2, v1);

            var normal = Vector3.Cross(foo1, foo2);

            normal = Vector3.Normalize(normal);

            var intensity = Vector3.Dot(normal, _light);

            if (intensity < 0)
            {
                intensity = 0;
            }

            state.Intensity = intensity;
        }
示例#3
0
 public override void Face(FaceShaderState state, int face)
 {
 }
示例#4
0
        private void DrawFilling(WritableTexture screen, int startY, int endY, Vector3 v0, Vector3 v1, Vector3 v2,
                                 FragmentShaderState fragmentState, FaceShaderState faceState, VertexShaderState vertexState, Shader shader)
        {
            var x0 = (int)Math.Round(v0.X);
            var y0 = (int)Math.Round(v0.Y);
            var x1 = (int)Math.Round(v1.X);
            var y1 = (int)Math.Round(v1.Y);
            var x2 = (int)Math.Round(v2.X);
            var y2 = (int)Math.Round(v2.Y);

            int minX = ClipX(Math3(x0, x1, x2, Math.Min));
            int minY = ClipY(Math3(y0, y1, y2, Math.Min), startY, endY);
            int maxX = ClipX(Math3(x0, x1, x2, Math.Max));
            int maxY = ClipY(Math3(y0, y1, y2, Math.Max), startY, endY);

            float midX = (v0.X + v1.X + v2.X) / 3;
            float midY = (v0.Y + v1.Y + v2.Y) / 3;

            var dirV0 = new Vector3(v0.X - midX, v0.Y - midY, 0);
            var dirV1 = new Vector3(v1.X - midX, v1.Y - midY, 0);

            var direction = Vector3.Cross(dirV0, dirV1).Z;

            if (direction < 0)
            {
                Vector3 tbuf;
                tbuf = v1;
                v1   = v2;
                v2   = tbuf;
            }

            var line1 = new Line(v0.X, v0.Y, v1.X, v1.Y, minX, minY);
            var line2 = new Line(v1.X, v1.Y, v2.X, v2.Y, minX, minY);
            var line3 = new Line(v2.X, v2.Y, v0.X, v0.Y, minX, minY);

            var converter = new BarycentricCoordinatesConverter(v0.X, v0.Y, v1.X, v1.Y, v2.X, v2.Y);

            var writer = screen.GetWriter(minY);

            for (int y = minY; y <= maxY; y++)
            {
                for (int x = minX; x <= maxX; x++)
                {
                    var curr1 = line1.Value;
                    var curr2 = line2.Value;
                    var curr3 = line3.Value;

                    if (curr1 >= 0 && curr2 >= 0 && curr3 >= 0)
                    {
                        var p = converter.Convert(x, y);

                        if (p.A < 0 || p.B < 0 || p.C < 0)
                        {
                            continue;
                        }

                        var z = v0.Z * p.A + v1.Z * p.B + v2.Z * p.C;

                        if (z < _zBuffer[x, y])
                        {
                            continue;
                        }

                        fragmentState.Clear();
                        fragmentState.Intensity = faceState.Intensity;
                        for (var i = 0; i < vertexState.Varying[0].Count; i++)
                        {
                            var fragmentValue = vertexState.Varying[0][i] * p.A + vertexState.Varying[1][i] * p.B +
                                                vertexState.Varying[2][i] * p.C;
                            fragmentState.Varying.Add(fragmentValue);
                        }

                        var resColor = shader.Fragment(fragmentState);

                        if (resColor != null)
                        {
                            _zBuffer[x, y] = z;
                            writer.Write(x, resColor.Value);
                        }
                    }
                    line1.StepX();
                    line2.StepX();
                    line3.StepX();
                }
                line1.StepY();
                line2.StepY();
                line3.StepY();
                writer.NextLine();
            }
        }