Пример #1
0
        public void CalcWeights(LAND cell)
        {
            WeightVertex[] WeightData = new WeightVertex[65 * 65];

            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    //Figure out which index to use
                    int i = x * 65 + y;

                    //Figure out which texture is used here
                    int cell_x = cell.xpos;
                    int cell_y = cell.ypos;
                    int tex_x  = (int)Math.Floor(((float)y - 1.0f) / 4.0f); //-2.0f
                    int tex_y  = (int)Math.Floor(((float)x - 3.0f) / 4.0f); //-2.0f

                    DistantLandForm.ModCell(ref cell_x, ref tex_x);
                    DistantLandForm.ModCell(ref cell_y, ref tex_y);

                    LTEX   tmp       = DistantLandForm.GetTex(cell_x, cell_y, tex_x, tex_y);
                    string tex_index = tmp.FilePath;

                    //Write values
                    if (t1 != null && t1.FilePath == tex_index)
                    {
                        WeightData[i].w1 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w1 = 0;
                    }

                    if (t2 != null && t2.FilePath == tex_index)
                    {
                        WeightData[i].w2 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w2 = 0;
                    }

                    if (t3 != null && t3.FilePath == tex_index)
                    {
                        WeightData[i].w3 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w3 = 0;
                    }

                    if (t4 != null && t4.FilePath == tex_index)
                    {
                        WeightData[i].w4 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w4 = 0;
                    }
                }
            }

            //Blur the weights as we transfer them so the transitions aren't quite so blocky and horrible.

            ////Normal Gaussian
            //float bf1 = 0.00081723f;
            //float bf2 = 0.02804153f;
            //float bf3 = 0.23392642f;
            //float bf4 = 0.47442968f;

            //Reduced center influence
            float bf1 = 0.1f;
            float bf2 = 0.15f;
            float bf3 = 0.2f;
            float bf4 = 0.1f;

            //Horizontal Pass
            WeightVertex[] FirstPassWD = new WeightVertex[65 * 65];
            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    //Figure out which index to use
                    int i = y * 65 + x;

                    if (x == 0 || x == 64 || y == 0 || y == 64)
                    {
                        //We're at the edge, so just copy the value (don't want to interfere with the way the edges of cells look
                        FirstPassWD[i] = WeightData[i];
                        continue;
                    }

                    //We're not at the edge, so add some influence from the surrounding weights
                    //Additional incides
                    WeightVertex wv0, wv1, wv2, wv3, wv4, wv5, wv6;

                    wv0 = SampleWeightData(ref WeightData, x - 3, y);
                    wv1 = SampleWeightData(ref WeightData, x - 2, y);
                    wv2 = SampleWeightData(ref WeightData, x - 1, y);
                    wv3 = SampleWeightData(ref WeightData, x, y);
                    wv4 = SampleWeightData(ref WeightData, x + 1, y);
                    wv5 = SampleWeightData(ref WeightData, x + 2, y);
                    wv6 = SampleWeightData(ref WeightData, x + 3, y);

                    float value;
                    value             = 0.0f;
                    value            += (float)wv0.w1 * bf1;
                    value            += (float)wv1.w1 * bf2;
                    value            += (float)wv2.w1 * bf3;
                    value            += (float)wv3.w1 * bf4;
                    value            += (float)wv4.w1 * bf3;
                    value            += (float)wv5.w1 * bf2;
                    value            += (float)wv6.w1 * bf1;
                    FirstPassWD[i].w1 = (byte)value;

                    value             = 0.0f;
                    value            += (float)wv0.w2 * bf1;
                    value            += (float)wv1.w2 * bf2;
                    value            += (float)wv2.w2 * bf3;
                    value            += (float)wv3.w2 * bf4;
                    value            += (float)wv4.w2 * bf3;
                    value            += (float)wv5.w2 * bf2;
                    value            += (float)wv6.w2 * bf1;
                    FirstPassWD[i].w2 = (byte)value;

                    value             = 0.0f;
                    value            += (float)wv0.w3 * bf1;
                    value            += (float)wv1.w3 * bf2;
                    value            += (float)wv2.w3 * bf3;
                    value            += (float)wv3.w3 * bf4;
                    value            += (float)wv4.w3 * bf3;
                    value            += (float)wv5.w3 * bf2;
                    value            += (float)wv6.w3 * bf1;
                    FirstPassWD[i].w3 = (byte)value;

                    value             = 0.0f;
                    value            += (float)wv0.w4 * bf1;
                    value            += (float)wv1.w4 * bf2;
                    value            += (float)wv2.w4 * bf3;
                    value            += (float)wv3.w4 * bf4;
                    value            += (float)wv4.w4 * bf3;
                    value            += (float)wv5.w4 * bf2;
                    value            += (float)wv6.w4 * bf1;
                    FirstPassWD[i].w4 = (byte)value;
                }
            }

            //Vertical pass - writes to final vertex buffer
            DataStream FinalWeightData = wBuffer.Lock(0, 0, LockFlags.None);

            //Blur the weights as we transfer them so the transitions aren't quite so blocky and horrible.
            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    if (x == 0 || x == 64 || y == 0 || y == 64)
                    {
                        //We're at the edge, so just copy the value (don't want to interfere with the way the edges of cells look
                        FinalWeightData.Write(WeightData[65 * y + x]);
                        continue;
                    }

                    //We're not at the edge, so add some influence from the surrounding weights
                    //Additional incides
                    WeightVertex wv0, wv1, wv2, wv3, wv4, wv5, wv6, wvfinal;
                    wv0 = SampleWeightData(ref FirstPassWD, x, y - 3);
                    wv1 = SampleWeightData(ref FirstPassWD, x, y - 2);
                    wv2 = SampleWeightData(ref FirstPassWD, x, y - 1);
                    wv3 = SampleWeightData(ref FirstPassWD, x, y);
                    wv4 = SampleWeightData(ref FirstPassWD, x, y + 1);
                    wv5 = SampleWeightData(ref FirstPassWD, x, y + 2);
                    wv6 = SampleWeightData(ref FirstPassWD, x, y + 3);

                    float value;
                    value      = 0.0f;
                    value     += (float)wv0.w1 * bf1;
                    value     += (float)wv1.w1 * bf2;
                    value     += (float)wv2.w1 * bf3;
                    value     += (float)wv3.w1 * bf4;
                    value     += (float)wv4.w1 * bf3;
                    value     += (float)wv5.w1 * bf2;
                    value     += (float)wv6.w1 * bf1;
                    wvfinal.w1 = (byte)value;

                    value      = 0.0f;
                    value     += (float)wv0.w2 * bf1;
                    value     += (float)wv1.w2 * bf2;
                    value     += (float)wv2.w2 * bf3;
                    value     += (float)wv3.w2 * bf4;
                    value     += (float)wv4.w2 * bf3;
                    value     += (float)wv5.w2 * bf2;
                    value     += (float)wv6.w2 * bf1;
                    wvfinal.w2 = (byte)value;

                    value      = 0.0f;
                    value     += (float)wv0.w3 * bf1;
                    value     += (float)wv1.w3 * bf2;
                    value     += (float)wv2.w3 * bf3;
                    value     += (float)wv3.w3 * bf4;
                    value     += (float)wv4.w3 * bf3;
                    value     += (float)wv5.w3 * bf2;
                    value     += (float)wv6.w3 * bf1;
                    wvfinal.w3 = (byte)value;

                    value      = 0.0f;
                    value     += (float)wv0.w4 * bf1;
                    value     += (float)wv1.w4 * bf2;
                    value     += (float)wv2.w4 * bf3;
                    value     += (float)wv3.w4 * bf4;
                    value     += (float)wv4.w4 * bf3;
                    value     += (float)wv5.w4 * bf2;
                    value     += (float)wv6.w4 * bf1;
                    wvfinal.w4 = (byte)value;

                    FinalWeightData.Write(wvfinal);
                }
            }

            wBuffer.Unlock();
        }
Пример #2
0
        public void SetCell(LAND cell)
        {
            //Write the new colors and normals into the color buffer
            DataStream        ColorNormalData = colorBuffer.Lock(0, 0, LockFlags.None);
            NormalColorVertex ncv;

            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    ncv.r = cell.Color[x, y].r;
                    ncv.g = cell.Color[x, y].g;
                    ncv.b = cell.Color[x, y].b;
                    ncv.a = 255;

                    ncv.nx = cell.Normals[x, y].X;
                    ncv.ny = cell.Normals[x, y].Y;
                    ncv.nz = cell.Normals[x, y].Z;

                    ColorNormalData.Write(ncv);
                }
            }
            colorBuffer.Unlock();

            //Dispose of any current texture banks
            texBanks.Clear();

            //Group the unique textures in this cell in fours

            //Find all te uniqe textures in this cell
            System.Collections.Generic.Dictionary <string, LTEX> tex_dict = new System.Collections.Generic.Dictionary <string, LTEX>();
            for (int x = 0; x <= 64; ++x)
            {
                for (int y = 0; y <= 64; ++y)
                {
                    int cell_x = cell.xpos;
                    int cell_y = cell.ypos;
                    int tex_x  = (int)Math.Floor(((float)y - 1.0f) / 4.0f); //-2.0f
                    int tex_y  = (int)Math.Floor(((float)x - 3.0f) / 4.0f); //-2.0f

                    DistantLandForm.ModCell(ref cell_x, ref tex_x);
                    DistantLandForm.ModCell(ref cell_y, ref tex_y);

                    LTEX   tmp = DistantLandForm.GetTex(cell_x, cell_y, tex_x, tex_y);
                    string idx = tmp.FilePath;
                    tex_dict[idx] = tmp;
                }
            }

            //Create one bank for each group of 4 textures
            int         index = 0;
            TextureBank tb    = new TextureBank();

            foreach (LTEX tex in tex_dict.Values)
            {
                switch (index)
                {
                case 0:
                    tb.t1 = tex;
                    ++index;
                    break;

                case 1:
                    tb.t2 = tex;
                    ++index;
                    break;

                case 2:
                    tb.t3 = tex;
                    ++index;
                    break;

                case 3:
                    tb.t4 = tex;
                    texBanks.Add(tb);
                    tb    = new TextureBank();
                    index = 0;
                    break;
                }
            }

            if (index != 0)
            {
                texBanks.Add(tb);
            }

            if (texBanks.Count > 1)
            {
                int blah   = 4;
                int blu    = 7;
                int blablu = blah + blu;
            }

            //Calculate weights for all banks
            foreach (TextureBank bank in texBanks)
            {
                bank.CalcWeights(cell);
            }
        }
Пример #3
0
        public void CalcWeights(LAND cell)
        {
            WeightVertex[] WeightData = new WeightVertex[65 * 65];

            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    // Figure out which index to use
                    int i = y * 65 + x;

                    // Figure out which texture is used here, match Morrowind rounding
                    int cell_x = cell.xpos;
                    int cell_y = cell.ypos;
                    int tex_x  = (int)Math.Floor(((float)x - 2.0f) / 4.0f);
                    int tex_y  = (int)Math.Ceiling(((float)y - 2.0f) / 4.0f);

                    DistantLandForm.ModCell(ref cell_x, ref tex_x);
                    DistantLandForm.ModCell(ref cell_y, ref tex_y);

                    LTEX   tmp       = DistantLandForm.GetTex(cell_x, cell_y, tex_x, tex_y);
                    string tex_index = tmp.FilePath;

                    // Write values
                    if (t1 != null && t1.FilePath == tex_index)
                    {
                        WeightData[i].w1 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w1 = 0;
                    }

                    if (t2 != null && t2.FilePath == tex_index)
                    {
                        WeightData[i].w2 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w2 = 0;
                    }

                    if (t3 != null && t3.FilePath == tex_index)
                    {
                        WeightData[i].w3 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w3 = 0;
                    }

                    if (t4 != null && t4.FilePath == tex_index)
                    {
                        WeightData[i].w4 = 255;
                        continue;
                    }
                    else
                    {
                        WeightData[i].w4 = 0;
                    }
                }
            }

            // Blur the weights as we transfer them so the transitions aren't quite so blocky and horrible.
            // Blur kernel
            float[] blur = new float[] { 0.04f, 0.16f, 0.6f, 0.16f, 0.04f };

            // Horizontal Pass
            WeightVertex[] FirstPassWD = new WeightVertex[65 * 65];
            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    // Figure out which index to use
                    int i = y * 65 + x;

                    if (x == 0 || x == 64 || y == 0 || y == 64)
                    {
                        // We're at the edge, so just copy the value (don't want to interfere with the way the edges of cells look
                        FirstPassWD[i] = WeightData[i];
                        continue;
                    }

                    // We're not at the edge, so add some influence from the surrounding weights
                    // Additional incides
                    WeightVertex wv0, wv1, wv2, wv3, wv4;
                    float        value;

                    wv0 = SampleWeightData(ref WeightData, x - 2, y);
                    wv1 = SampleWeightData(ref WeightData, x - 1, y);
                    wv2 = SampleWeightData(ref WeightData, x, y);
                    wv3 = SampleWeightData(ref WeightData, x + 1, y);
                    wv4 = SampleWeightData(ref WeightData, x + 2, y);

                    value             = (float)wv0.w1 * blur[0] + (float)wv1.w1 * blur[1] + (float)wv2.w1 * blur[2] + (float)wv3.w1 * blur[3] + (float)wv4.w1 * blur[4];
                    FirstPassWD[i].w1 = (byte)value;

                    value             = (float)wv0.w2 * blur[0] + (float)wv1.w2 * blur[1] + (float)wv2.w2 * blur[2] + (float)wv3.w2 * blur[3] + (float)wv4.w2 * blur[4];
                    FirstPassWD[i].w2 = (byte)value;

                    value             = (float)wv0.w3 * blur[0] + (float)wv1.w3 * blur[1] + (float)wv2.w3 * blur[2] + (float)wv3.w3 * blur[3] + (float)wv4.w3 * blur[4];
                    FirstPassWD[i].w3 = (byte)value;

                    value             = (float)wv0.w4 * blur[0] + (float)wv1.w4 * blur[1] + (float)wv2.w4 * blur[2] + (float)wv3.w4 * blur[3] + (float)wv4.w4 * blur[4];
                    FirstPassWD[i].w4 = (byte)value;
                }
            }

            // Vertical pass - writes to final vertex buffer
            DataStream FinalWeightData = wBuffer.Lock(0, 0, LockFlags.None);

            // Blur the weights as we transfer them so the transitions aren't quite so blocky and horrible.
            for (int y = 0; y <= 64; y++)
            {
                for (int x = 0; x <= 64; x++)
                {
                    if (x == 0 || x == 64 || y == 0 || y == 64)
                    {
                        // We're at the edge, so just copy the value (don't want to interfere with the way the edges of cells look
                        FinalWeightData.Write(WeightData[65 * y + x]);
                        continue;
                    }

                    // We're not at the edge, so add some influence from the surrounding weights
                    // Additional incides
                    WeightVertex wv0, wv1, wv2, wv3, wv4, wvfinal;
                    float        value;

                    wv0 = SampleWeightData(ref FirstPassWD, x, y - 2);
                    wv1 = SampleWeightData(ref FirstPassWD, x, y - 1);
                    wv2 = SampleWeightData(ref FirstPassWD, x, y);
                    wv3 = SampleWeightData(ref FirstPassWD, x, y + 1);
                    wv4 = SampleWeightData(ref FirstPassWD, x, y + 2);

                    value      = (float)wv0.w1 * blur[0] + (float)wv1.w1 * blur[1] + (float)wv2.w1 * blur[2] + (float)wv3.w1 * blur[3] + (float)wv4.w1 * blur[4];
                    wvfinal.w1 = (byte)value;

                    value      = (float)wv0.w2 * blur[0] + (float)wv1.w2 * blur[1] + (float)wv2.w2 * blur[2] + (float)wv3.w2 * blur[3] + (float)wv4.w2 * blur[4];
                    wvfinal.w2 = (byte)value;

                    value      = (float)wv0.w3 * blur[0] + (float)wv1.w3 * blur[1] + (float)wv2.w3 * blur[2] + (float)wv3.w3 * blur[3] + (float)wv4.w3 * blur[4];
                    wvfinal.w3 = (byte)value;

                    value      = (float)wv0.w4 * blur[0] + (float)wv1.w4 * blur[1] + (float)wv2.w4 * blur[2] + (float)wv3.w4 * blur[3] + (float)wv4.w4 * blur[4];
                    wvfinal.w4 = (byte)value;

                    FinalWeightData.Write(wvfinal);
                }
            }

            wBuffer.Unlock();
        }