コード例 #1
0
            private WorkingTexture GenerateMipmap(WorkingTexture source)
            {
                int sx = Mathf.Max(source.Width >> 1, 1);
                int sy = Mathf.Max(source.Height >> 1, 1);

                WorkingTexture mipmap = new WorkingTexture(Allocator.Persistent, source.Format, sx, sy, source.Linear);

                mipmap.Name = source.Name;

                for (int y = 0; y < sy; ++y)
                {
                    for (int x = 0; x < sx; ++x)
                    {
                        Color color = new Color();

                        int x1 = Mathf.Min(x * 2 + 0, source.Width - 1);
                        int x2 = Mathf.Min(x * 2 + 1, source.Width - 1);
                        int y1 = Mathf.Min(y * 2 + 0, source.Height - 1);
                        int y2 = Mathf.Min(y * 2 + 1, source.Height - 1);

                        color += source.GetPixel(x1, y1);
                        color += source.GetPixel(x1, y2);
                        color += source.GetPixel(x2, y1);
                        color += source.GetPixel(x2, y2);

                        color /= 4;

                        mipmap.SetPixel(x, y, color);
                    }
                }

                return(mipmap);
            }
コード例 #2
0
 private void RemapTexture(WorkingTexture source, Color min, Color max)
 {
     for (int y = 0; y < source.Height; ++y)
     {
         for (int x = 0; x < source.Width; ++x)
         {
             var color = source.GetPixel(x, y);
             color = color * max + min;
             source.SetPixel(x, y, color);
         }
     }
 }
コード例 #3
0
        static private WorkingTexture CreateEmptyTexture(int width, int height, Color color, bool linear)
        {
            WorkingTexture texture = new WorkingTexture(Allocator.Persistent, TextureFormat.RGB24, width, height, linear);

            for (int y = 0; y < height; ++y)
            {
                for (int x = 0; x < width; ++x)
                {
                    texture.SetPixel(x, y, color);
                }
            }

            return(texture);
        }
コード例 #4
0
            private void ApplyTintColor(WorkingTexture texture, Color tintColor)
            {
                for (int ty = 0; ty < texture.Height; ++ty)
                {
                    for (int tx = 0; tx < texture.Width; ++tx)
                    {
                        Color c = texture.GetPixel(tx, ty);

                        c.r = c.r * tintColor.r;
                        c.g = c.g * tintColor.g;
                        c.b = c.b * tintColor.b;
                        c.a = c.a * tintColor.a;

                        texture.SetPixel(tx, ty, c);
                    }
                }
            }
コード例 #5
0
        private WorkingTexture BakeNormal(string name, Bounds bounds, int resolution)
        {
            WorkingTexture normalTexture = new WorkingTexture(Allocator.Persistent, TextureFormat.RGB24, resolution, resolution, true);

            normalTexture.Name     = name + "_Normal";
            normalTexture.WrapMode = TextureWrapMode.Clamp;

            m_queue.EnqueueJob(() =>
            {
                float ustart = (bounds.min.x) / m_size.x;
                float vstart = (bounds.min.z) / m_size.z;
                float usize  = (bounds.max.x - bounds.min.x) / m_size.x;
                float vsize  = (bounds.max.z - bounds.min.z) / m_size.z;

                for (int y = 0; y < resolution; ++y)
                {
                    for (int x = 0; x < resolution; ++x)
                    {
                        float u = (float)x / (float)resolution * usize + ustart;
                        float v = (float)y / (float)resolution * vsize + vstart;

                        Vector3 normal = m_heightmap.GetInterpolatedNormal(u, v);

                        Color color = new Color(0.0f, 0.0f, 0.0f, 0.0f);
                        color.r     = normal.x * 0.5f + 0.5f;
                        color.g     = -normal.z * 0.5f + 0.5f;
                        color.b     = normal.y * 0.5f + 0.5f;

                        color.a = 1.0f;
                        normalTexture.SetPixel(x, y, color);
                    }
                }
            });


            return(normalTexture);
        }
コード例 #6
0
            public Layer(TerrainLayer layer)
            {
                var texture = layer.diffuseTexture;

                bool linear = !GraphicsFormatUtility.IsSRGBFormat(texture.graphicsFormat);

                m_diffuseTexstures = new DisposableList <WorkingTexture>();

                m_offset = layer.tileOffset;
                m_size   = layer.tileSize;
                var diffuseRemapMin = layer.diffuseRemapMin;
                var diffuseRemapMax = layer.diffuseRemapMax;

                diffuseRemapMin.x = Mathf.Pow(diffuseRemapMin.x, 0.45f);
                diffuseRemapMin.y = Mathf.Pow(diffuseRemapMin.y, 0.45f);
                diffuseRemapMin.z = Mathf.Pow(diffuseRemapMin.z, 0.45f);

                diffuseRemapMax.x = Mathf.Pow(diffuseRemapMax.x, 0.45f);
                diffuseRemapMax.y = Mathf.Pow(diffuseRemapMax.y, 0.45f);
                diffuseRemapMax.z = Mathf.Pow(diffuseRemapMax.z, 0.45f);


                //make to texture readable.
                var assetImporter        = AssetImporter.GetAtPath(AssetDatabase.GetAssetPath(texture));
                var textureImporter      = assetImporter as TextureImporter;
                TextureImporterType type = TextureImporterType.Default;

                if (textureImporter)
                {
                    type = textureImporter.textureType;
                    textureImporter.isReadable  = true;
                    textureImporter.textureType = TextureImporterType.Default;
                    textureImporter.SaveAndReimport();
                }

                try
                {
                    for (int i = 0; i < texture.mipmapCount; ++i)
                    {
                        int            width          = texture.width >> i;
                        int            height         = texture.height >> i;
                        WorkingTexture workingTexture = new WorkingTexture(Allocator.Persistent, texture.format, width, height, linear);
                        Color[]        colors         = texture.GetPixels(i);
                        for (int y = 0; y < height; ++y)
                        {
                            for (int x = 0; x < width; ++x)
                            {
                                workingTexture.SetPixel(x, y, colors[y * width + x]);
                            }
                        }

                        RemapTexture(workingTexture, diffuseRemapMin, diffuseRemapMax);
                        m_diffuseTexstures.Add(workingTexture);
                    }
                }
                finally
                {
                    if (textureImporter)
                    {
                        textureImporter.isReadable  = false;
                        textureImporter.textureType = type;
                        textureImporter.SaveAndReimport();
                    }
                }
            }
コード例 #7
0
        private WorkingTexture BakeAlbedo(string name, Bounds bounds, int resolution)
        {
            WorkingTexture albedoTexture = new WorkingTexture(Allocator.Persistent, TextureFormat.RGB24, resolution, resolution, false);

            albedoTexture.Name     = name + "_Albedo";
            albedoTexture.WrapMode = TextureWrapMode.Clamp;

            m_queue.EnqueueJob(() =>
            {
                float ustart = (bounds.min.x) / m_size.x;
                float vstart = (bounds.min.z) / m_size.z;
                float usize  = (bounds.max.x - bounds.min.x) / m_size.x;
                float vsize  = (bounds.max.z - bounds.min.z) / m_size.z;

                for (int y = 0; y < resolution; ++y)
                {
                    for (int x = 0; x < resolution; ++x)
                    {
                        float u = (float)x / (float)resolution * usize + ustart;
                        float v = (float)y / (float)resolution * vsize + vstart;

                        Color color = new Color(0.0f, 0.0f, 0.0f, 0.0f);

                        for (int li = 0; li < m_layers.Count; ++li)
                        {
                            float weight = 0.0f;
                            switch (li % 4)
                            {
                            case 0:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).r;
                                break;

                            case 1:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).g;
                                break;

                            case 2:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).b;
                                break;

                            case 3:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).a;
                                break;
                            }

                            //optimize to skip not effect pixels.
                            if (weight < 0.01f)
                            {
                                continue;
                            }

                            float wx = (float)x / (float)resolution * bounds.size.x + bounds.min.x;
                            float wy = (float)y / (float)resolution * bounds.size.z + bounds.min.z;

                            Color c = m_layers[li].GetColorByWorld(wx, wy, bounds.size.x, bounds.size.z);

                            color.r += Mathf.Pow(c.r, 2.2f) * weight;
                            color.g += Mathf.Pow(c.g, 2.2f) * weight;
                            color.b += Mathf.Pow(c.b, 2.2f) * weight;
                        }

                        color.r = Mathf.Pow(color.r, 0.454545f);
                        color.g = Mathf.Pow(color.g, 0.454545f);
                        color.b = Mathf.Pow(color.b, 0.454545f);
                        color.a = 1.0f;
                        albedoTexture.SetPixel(x, y, color);
                    }
                }
            });


            return(albedoTexture);
        }
コード例 #8
0
        private void EnqueueBlendTextureJob(WorkingTexture texture, Bounds bounds, int resolution, System.Func <int, float, float, float, float, bool, Color> getColor, System.Func <Color, Color> packColor = null)
        {
            bool linear = texture.Linear;

            m_queue.EnqueueJob(() =>
            {
                float ustart = (bounds.min.x) / m_size.x;
                float vstart = (bounds.min.z) / m_size.z;
                float usize  = (bounds.max.x - bounds.min.x) / m_size.x;
                float vsize  = (bounds.max.z - bounds.min.z) / m_size.z;

                for (int y = 0; y < resolution; ++y)
                {
                    for (int x = 0; x < resolution; ++x)
                    {
                        float u = (float)x / (float)resolution * usize + ustart;
                        float v = (float)y / (float)resolution * vsize + vstart;

                        Color color = new Color(0.0f, 0.0f, 0.0f, 0.0f);

                        for (int li = 0; li < m_layers.Count; ++li)
                        {
                            float weight = 0.0f;
                            switch (li % 4)
                            {
                            case 0:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).r;
                                break;

                            case 1:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).g;
                                break;

                            case 2:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).b;
                                break;

                            case 3:
                                weight = m_alphamaps[li / 4].GetPixel(u, v).a;
                                break;
                            }

                            //optimize to skip not effect pixels.
                            if (weight < 0.01f)
                            {
                                continue;
                            }

                            float wx = (float)x / (float)resolution * bounds.size.x + bounds.min.x;
                            float wy = (float)y / (float)resolution * bounds.size.z + bounds.min.z;

                            Color c = getColor(li, wx, wy, bounds.size.x, bounds.size.z, linear);

                            // blend in linear space.
                            color.r += c.r * weight;
                            color.g += c.g * weight;
                            color.b += c.b * weight;
                            color.a += c.a * weight;
                        }

                        if (packColor != null)
                        {
                            color = packColor(color);
                        }

                        if (!linear)
                        {
                            color = color.gamma;
                        }

                        texture.SetPixel(x, y, color);
                    }
                }
            });
        }
コード例 #9
0
            void MakeTexture(TerrainLayer layer, Texture2D texture, Vector4 min, Vector4 max, DisposableList <WorkingTexture> results)
            {
                bool linear = !GraphicsFormatUtility.IsSRGBFormat(texture.graphicsFormat);

                var offset = layer.tileOffset;
                var size   = layer.tileSize;

                if (!linear)
                {
                    min.x = Mathf.Pow(min.x, 0.45f);
                    min.y = Mathf.Pow(min.y, 0.45f);
                    min.z = Mathf.Pow(min.z, 0.45f);

                    max.x = Mathf.Pow(max.x, 0.45f);
                    max.y = Mathf.Pow(max.y, 0.45f);
                    max.z = Mathf.Pow(max.z, 0.45f);
                }


                //make to texture readable.
                var assetImporter        = AssetImporter.GetAtPath(AssetDatabase.GetAssetPath(texture));
                var textureImporter      = assetImporter as TextureImporter;
                TextureImporterType type = TextureImporterType.Default;

                if (textureImporter)
                {
                    type = textureImporter.textureType;
                    textureImporter.isReadable  = true;
                    textureImporter.textureType = TextureImporterType.Default;
                    textureImporter.SaveAndReimport();
                }

                try
                {
                    for (int i = 0; i < texture.mipmapCount; ++i)
                    {
                        int            width          = texture.width >> i;
                        int            height         = texture.height >> i;
                        WorkingTexture workingTexture = new WorkingTexture(Allocator.Persistent, texture.format, width, height, linear);
                        Color[]        colors         = texture.GetPixels(i);
                        for (int y = 0; y < height; ++y)
                        {
                            for (int x = 0; x < width; ++x)
                            {
                                workingTexture.SetPixel(x, y, colors[y * width + x]);
                            }
                        }

                        RemapTexture(workingTexture, min, max);
                        results.Add(workingTexture);
                    }
                }
                finally
                {
                    if (textureImporter)
                    {
                        textureImporter.isReadable  = false;
                        textureImporter.textureType = type;
                        textureImporter.SaveAndReimport();
                    }
                }
            }