利用柏林噪声生成噪声函数

噪音函数的生成原理就不多说了,https://zh.wikipedia.org/wiki/Perlin%E5%99%AA%E5%A3%B0 可以参考维基百科

如右图所示,给正方形四个顶点分配四个随机单位向量,正方形内的像素可以利用这四个向量进行插值。

对指向正方形内像素的向量和顶点的随机向量分别进行点积,可以得到四个标量,利用这四个标量插值得到像素的值。

void noiseTexture::make_noise(float noise[][128][4])
{

    Vector2f<GLfloat> randomTable[128]; //生成方向表

    int H[128];                        //将方向表顺序打乱

    const float delta = pi2 / 128;     //用于生成128个方向的单位向量

    for (int i = 0; i < 128; i++)
    {
        float theta = delta*static_cast<float>(i);

        randomTable[i] = Vector2f<GLfloat>(sinf(theta), cosf(theta));
    }

    //初始化H
    for (int i = 0; i < 128; i++)
        H[i] = i;

    //打乱H的顺序
    for (int i = 0; i < 128; i++)
    {
        int j = rand() % 128;
        std::swap(H[i], H[j]);
    }

    //32代表在一个正方形内进行32*32将插值,共有128/32 * 128/32 = 16个正方形
    //He代表插值得到的振辐
    float p = 1.0/32,f; float He = 1.f;

    int k = 0;
    while (k<4)
    {
        //遍历表格的每一个点
        for (int i = 0; i < 128; i++)
        {
            for (int j = 0; j < 128; j++)
            {
                float now_x = p*i;
                float now_y = p*j;

                Vector2f<GLfloat> now_xy(p*i, p*j);      //当前位置

                Vector2f<GLfloat> intxy((float)static_cast<int>(now_x), (float)static_cast<int>(now_y));//正方形左上角位置

                Vector2f<GLfloat> weight_xy = now_xy - intxy; //当前位置相对左上角的位置

                GLfloat delta_x = weight_xy.data[0] * weight_xy.data[0] * (3.f - 2.*weight_xy.data[0]); //函数f(k)

                GLfloat delta_y = weight_xy.data[1] * weight_xy.data[1] * (3.f - 2.*weight_xy.data[1]); //函数f(k)

                //HH(static_cast<int>(now_x), static_cast<int>(now_y))散列到H的一个位置,可以自行定义
                //randomTable[H[HH(static_cast<int>(now_x), static_cast<int>(now_y))]] *(weight_xy - Vector2f<GLfloat>(.0f, .0f))为计算标量值
                //mix为插值函数
                float k1 = mix(randomTable[H[HH(static_cast<int>(now_x), static_cast<int>(now_y))]] *
                    (weight_xy - Vector2f<GLfloat>(.0f, .0f)),
                    randomTable[H[HH(static_cast<int>(now_x) + 1, static_cast<int>(now_y))]] *
                    (weight_xy - Vector2f<GLfloat>(1.0f, .0f)), delta_x);

                float k2 = mix(randomTable[H[HH(static_cast<int>(now_x), static_cast<int>(now_y)+1)]] *
                    (weight_xy - Vector2f<GLfloat>(.0f, 1.0f)),
                    randomTable[H[HH(static_cast<int>(now_x) + 1, static_cast<int>(now_y)+1)]] *
                    (weight_xy - Vector2f<GLfloat>(1.0f, 1.0f)), delta_x);

                float o = mix(k1, k2, delta_y);

                noise[i][j][k]= o*He;
            }
        }
        p = p * 2;   //减少正方形的大小
        He = He*0.75f;//减小振幅
        k++;
    }
}

以上为噪声纹理的生成代码

在像素着色器中如下的简单使用

          vec4 noise = texture2D(gSampler, fract(TexCoord0.st*1));
          return vec4(0.,(noise.x+noise.y+noise.z+noise.w)*0.5+0.6,0,1);

即可生成一张丑陋的草地纹理

时间: 2024-10-05 05:11:30

利用柏林噪声生成噪声函数的相关文章

tflearn kears GAN官方demo代码——本质上GAN是先训练判别模型让你能够识别噪声,然后生成模型基于噪声生成数据,目标是让判别模型出错。GAN的过程就是训练这个生成模型参数!!!

GAN:通过 将 样本 特征 化 以后, 告诉 模型 哪些 样本 是 黑 哪些 是 白, 模型 通过 训练 后, 理解 了 黑白 样本 的 区别, 再输入 测试 样本 时, 模型 就可以 根据 以往 的 经验 判断 是 黑 还是 白. 与 这些 分类 的 算法 不同, GAN 的 基本 原理 是, 有两 个 相生相克 的 模型 Generator 和 Discriminator,Generator 随机 生成 样本, Discriminator 将 真实 样本 标记 为 Real, 将 Gene

【转】利用matlab生成随机数函数

原文地址:利用matlab生成随机数函数 rand(n):生成0到1之间的n阶随机数方阵  rand(m,n):生成0到1之间的m×n的随机数矩阵 (现成的函数) betarnd:贝塔分布的随机数生成器 binornd:二项分布的随机数生成器 chi2rnd:卡方分布的随机数生成器 exprnd:指数分布的随机数生成器 frnd:f分布的随机数生成器 gamrnd:伽玛分布的随机数生成器 geornd:几何分布的随机数生成器 hygernd:超几何分布的随机数生成器 lognrnd:对数正态分布

利用STM32CubeMX来生成USB_HID_Mouse工程【添加ADC】(1)

现在原来的基础上添加ADC的功能. 现在(利用STM32CubeMX来生成USB_HID_Mouse工程)基础上新增硬件 JoyStick Shield 游戏摇杆扩展板 与STM32F103C8的连接 目前使用 JoyStick Shield   STM32F103C8 X----PA1(ADC1_IN1) Y----PA2(ADC1_IN2) 好了我们现在STM32CubeMX来打开之前的工程 现在我们先设置ADC1_IN1 让我们来看其adc的默认配置 现在直接生成工程. 会发现在原来的工程

【Effective c++】条款6:若不想使用编译器自动生成的函数就应该明确拒绝

地产中介卖的是房子,其使用的中介软件系统应该有个类用来描述卖掉的房子 class HomeFoeSale { ......} 但是任何房子都是独一无二的,不应该存在两个房子拥有同样的属性,因此以下操作不应该正确! HomeForSale h; HomeForSale h1(h); //调用复制构造函数 HomeForSale h2 = h; //调用赋值操作符 阻止这两个操作(复制.赋值)可以不声明它们,but自己不声明,编译器会自动生成,并且访问权限还是public.没办法只好声明出来,但是如

利用jquery的淡入淡出函数(fadeIn和fadeOut)--实现轮播

首先说下,我在网上找的例子全是用的UL 实现,其实大可不必,只要是能包含img标签的HTML标签都可以做轮播效果.利用jquery的淡入淡出函数(fadeIn和fadeOut).废话也不多说,边上代码边讲解.最后附上demo效果地址. <!--整体容器-->    <div class="imgbox">        <!--图片列表,除第一张显示外,其余隐藏-->        <ul>            <li style

利用wsdl.exe生成webservice代理类

根据提供的wsdl生成webservice代理类 1.开始->程序->Visual Studio 2005 命令提示 2.输入如下红色标记部分 D:/Program Files/Microsoft Visual Studio 8/VC>wsdl /language:c# /n:TestDemo /out:d:/Temp/TestService.cs D:/Temp/TestService.wsdl 在d:/Temp下就会产生一个TestService.cs 文件 注意:D:/Temp/T

利用GCC编译器生成动态链接库和静态链接库

转载请标明:http://www.cnblogs.com/winifred-tang94/ 1.编译过程 gcc –fPIC –c xxx.c 其中-fPIC是通知gcc编译器产生位置独立的目标代码.链接的时候不通过拷贝来进行. 2.链接过程 gcc –shared –o libxxx.so xxx.o 经过编译链接就可以生成动态链接库,其扩展名为.so Eg. 还可以gcc –fPIC –shared -o libhello.so hello.c 举个例子: //Hello.h //hello

条款6:如果不想使用编译器自动生成的函数,就应该明确的拒绝。

有些情况自己是不希望生成拷贝构造函数以及拷贝赋值运算符的,这种时候不能只是自己不去编写这些函数,因为这样编译器会自动的去生成这些函数.保险一点的做法是将拷贝构造函数以及拷贝赋值运算符都声明为private的.这样既阻止了编译器生成默认的版本,而且又阻止了别人去调用它. 注意上面的这条“将成员函数声明为private而故意的不去实现它”是一种常用手段,即使是标准程序库中有的部分也是这样做的. class HomeForSale//很明显,销售的两个方子一般内容都是不相同的,所以拷贝构造函数以及 {

解析利用wsdl.exe生成webservice代理类的详解

利用wsdl.exe生成webservice代理类:根据提供的wsdl生成webservice代理类1.开始->程序->Visual Studio 2005 命令提示2.输入如下红色标记部分D:/Program Files/Microsoft Visual Studio 8/VC>wsdl /language:c# /n:TestDemo /out:d:/Temp/TestService.cs D:/Temp/TestService.wsdl在d:/Temp下就会产生一个TestServ