1

When we use mobile or semiprofessional cameras in the room with bad light they increase ISO as a rule, the result is shown below:

Screenshot

This is a frame from video, as you can see there is a lot of noise. Maybe it's a little weird but I need to generate a similar noise on high quality video. However, a simple noise generator will produce a something like that:

Sample

Does anyone have some ideas how to get result like on the first frame? Or maybe there is a some existing noise generator/algorithm to make it? I will be grateful for any help.

Denis Sologub
  • 7,277
  • 11
  • 56
  • 123
  • 1
    I assume you simply added small random RGB to your image... I would leave color as is and try to substract a small random from color intensity instead .. or multiplky your RGB color with random number between `0.9` and `1.0` ... however that just my wild guess ... if you want also darken the image just use different multiplication range like `0.5 .. 0.75` ... – Spektre Jun 19 '21 at 07:18

3 Answers3

2

I assume you simply added small random RGB to your image...

I would leave color as is and try to reduce color intensity by small random amount to darken the image and create a similar form of noise. Just by multiply your RGB color with random number less than one ...

To improve result visual the random value should be with gauss distribution or similar. Here small C++/VCL example:

//$$---- Form CPP ----
//---------------------------------------------------------------------------
#include <vcl.h>
#include <math.h>
#pragma hdrstop
#include "win_main.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TMain *Main;
Graphics::TBitmap *bmp0,*bmp1;
//---------------------------------------------------------------------------
__fastcall TMain::TMain(TComponent* Owner) : TForm(Owner)
    {
    // init bmps and load from file
    bmp0=new Graphics::TBitmap;
    bmp1=new Graphics::TBitmap;
    bmp0->LoadFromFile("in.bmp");
    bmp0->HandleType=bmDIB;
    bmp0->PixelFormat=pf32bit;
    bmp1->Assign(bmp0);
    ClientWidth=bmp0->Width;
    ClientHeight=bmp0->Height;
    Randomize();
    }
//---------------------------------------------------------------------------
void __fastcall TMain::FormDestroy(TObject *Sender)
    {
    // free bmps before exit
    delete bmp0;
    delete bmp1;
    }
//---------------------------------------------------------------------------
void __fastcall TMain::tim_updateTimer(TObject *Sender)
    {
    // skip if App not yet initialized
    if (bmp0==NULL) return;
    if (bmp1==NULL) return;
    int x,y,i,a;
    union _color
        {
        BYTE db[4];
        DWORD dd;
        };
    // copy bmp0 into bmp1 with light reduction and noise
    for (y=0;y<bmp0->Height;y++)
        {
        _color *p0=(_color*)bmp0->ScanLine[y];
        _color *p1=(_color*)bmp1->ScanLine[y];
        for (x=0;x<bmp0->Width;x++)
            {
            p1[x]=p0[x];
            for (a=40,i=0;i<10;i++) a+=Random(10);                      // "gauss" PRNG in range 40 .. 140
            for (i=0;i<3;i++) p1[x].db[i]=(DWORD(p1[x].db[i])*a)>>8;    // multiply RGB by a/256
            }
        }
    // render frame on App canvas
    Canvas->Draw(0,0,bmp1);
//  bmp1->SaveToFile("out.bmp");
    }
//---------------------------------------------------------------------------

input image:

in

output image:

output

You can play with the PRNG properties to tweak light and noissyness.

Spektre
  • 49,595
  • 11
  • 110
  • 380
  • Thank you very much for real example of the code! – Denis Sologub Jun 21 '21 at 11:50
  • 1
    @Шах The "gauss" PRNG is using standard uniform distribution PRNG based on this [Understanding “randomness”](https://stackoverflow.com/a/3956538/2521214) and the VCL gfx stuff is more or less explained in here [#3 VCL/GDI Bitmap](https://stackoverflow.com/a/21699076/2521214) – Spektre Jun 21 '21 at 12:12
2

What you see in that frame is not the raw sensor noise, nor a simulation of film grain as the accepted answer seems to suggest. Instead, it is the result of a noise-reduction filter that is applied to the high-ISO image. Without the filter, you’d see a lot of noise, mostly Poisson noise.

I don’t know what noise-reduction filter is built into the camera, but it likely is applied to the raw image, before conversion to RGB. Here are many papers describing such filters.

Cris Luengo
  • 55,762
  • 10
  • 62
  • 120
  • So its Poisson instead of Gauss +1 ... I chose Gauss with trial&error just because it looks like the CCD noise visually even with animation in comparison to normal distribution) – Spektre Jun 20 '21 at 06:30
1

You basically need to increase "grain" size, and maybe flat out your noise spots.

It will be hard to obtain a natural-looking result, as those grain spots in a video are obtained from various types of interpolations over values obtained from the camera sensor (with specific noise that a sensor produces).
Take for example "analog" film cameras (the pictures taken with the film have that grainy natural look from the effective grains sizes/shapes of minerals that are used in the film itself). If it were so easy to produce a natural-looking film alike filter over digital images the film industry would not see the comeback that happens now.

With that said there are three things that come to my mind that could work:

Median Blur over (image + some noise):
https://docs.opencv.org/master/d4/d13/tutorial_py_filtering.html enter image description here

An image that has is generated with Perlin noise, scaled accordingly to your specific frame size + added over colors of your image * some factor:
https://github.com/ruslangrimov/perlin-noise-python-numpy
enter image description here * factor + your image = result


Film a really dark room with a camera set up to produce the same frame resolution and with high iso, add obtained video frames over your video (some image manipulation to be applied).
Hope any of this helps and good luck with your project.
Dan Butmalai
  • 100
  • 1
  • 8
  • I can get all cameras are different and noise is based on physical principles but at least it looks like a noise on the first picture, I was needed that. Thank you very much for detailed explanation and solution! – Denis Sologub Jun 19 '21 at 10:33
  • “If it were so easy to produce a natural-looking film alike filter over digital images the film industry would not see the comeback that happens now.” It is actually not hard at all. If this is the reason for filmmakers to want to use actual film, then the fad is similar to the comeback of vinyl—stupid. – Cris Luengo Jun 19 '21 at 13:33
  • @CrisLuengo it is hard to get a digital picture to look like an analog one. Film images have some grainy greeny yellowish tint to them. In terms of just applying some filters over a digital image, yep one would get a look that is close enough, but not exactly alike of a film image. – Dan Butmalai Jun 19 '21 at 14:48
  • Reproducing color is not a problem with digital imaging. Using modern screens, we have a wider gamut and can reproduce color much more precisely than with traditional film. The only advantage of traditional film is resolution. Some people estimate 35mm film (100 ISO) has a resolution equivalent to 20M pixels, whereas the best digital film cameras (Red) have 33M pixels. But those are very expensive and lower res is still the norm I think. In the end, it is the lens that controls resolution. – Cris Luengo Jun 19 '21 at 15:17