Koko-aio shader discussions and updates

This is with integer scanlines:

ultrawide preset
DO_CCORRECTION = "1.000000"
IN_GLOW_POWER = "1.200000"
TEMPERATURE = "7200.000000"
IN_GLOW_GAMMA = "2.200000"
GAMMA_OUT = "0.400000"
DO_SHIFT_RGB = "1.000000"
OFFSET_STRENGTH = "0.300000"
SHIFT_R = "-20.000000"
SHIFT_G = "0.000000"
SHIFT_B = "20.000000"
DO_IN_GLOW = "1.000000"
IN_GLOW_SPREAD = "1.600000"
IN_GLOW_W = "3.999998"
IN_GLOW_H = "7.000000"
DO_PIXELGRID = "1.000000"
DO_PIXELGRID_H = "1.250000"
PIXELGRID_COREY_FAKE_SCAN = "1.000000"
PIXELGRID_MIN_H = "0.000000"
PIXELGRID_MAX_H = "0.500000"
PIXELGRID_GAMMA_H = "1.000000"
PIXELGRID_OFFSET_CORE = "0.050000"
PIXELGRID_DECON_R_H = "-0.600000"
PIXELGRID_DECON_B_H = "0.600000"
PIXELGRID_H_PRST = "1.000000"
PIXELGRID_GAMMA_W = "4.299998"
PIXELGRID_BASAL_GRID = "0.020000"
PIXELGRID_Y_MASK = "0.000000"
PIXELGRID_Y_MASK_COORDS = "0.000000"
PIXELGRID_Y_MASK_HEIGHT = "-2.000000"
PIXELGRID_Y_MASK_SHIFT = "0.260000"
PIXELGRID_Y_MASK_STEEP = "16.000000"
PIXELGRID_Y_MASK_ON_WHITE = "0.100000"
PIXELGRID_Y_SPARK = "0.100000"
DO_HALO = "1.000000"
HALO_NO_PREGAIN = "1.000000"
HALO_POWER = "0.500000"
HALO_SHARPNESS = "6.500000"
HALO_VS_SCAN = "0.700000"
DO_BLOOM = "1.000000"
BLOOM_MIX = "0.400000"
BLOOM_GAMMA = "4.000000"
BLOOM_GAMMA_OUT = "1.200000"
BLOOM_POWER = "1.450000"
BLOOM_EYE_ADPT_SRT = "0.000000"
BLOOM_EYE_INERTIA = "750.000000"
GEOM_CORNER_SIZE = "0.010000"
GEOM_CORNER_SMOOTH = "200.000000"
DO_BEZEL = "1.000000"
BEZEL_USE_STRAIGHT = "1.000000"
BEZEL_INNER_ZOOM = "-0.156000"
BEZEL_FRAME_ZOOM = "0.066000"
DO_VIGNETTE = "1.000000"
V_SIZE = "1.080000"
DO_SPOT = "1.000000"
S_POWER = "0.050000"
DO_GLOBAL_SHZO = "1.000000"
GLOBAL_ZOOM = "0.500000"
ASPECT_X = "12.000000"```
8 Likes

@kokoko3k it looks great, thanks for the great shader presets.

2 Likes

Since the discussion about triple screen/ultrawide screens -> low Y resolution, I made a little change to the shader:

You can guess what it does, from docs-ng.md (bit lazy atm):

Use fake integer scanlines
   [..]
   A negative value will cause the shader to choose when it is appropriate to activate them.
   The decision will be based on the ratio of output dimensions and the core.

The ratio has been set to 4.0, this means that if core scanlines have less than 4 screen pixel to draw themselves, they will switch to fake integer scanlines:

Example:

Screen height is enough, proper scanlines are selected:

Screen height is too low, fake scanlines are selected:

…the logic is skipped when integer scaling is used.
Also, be warned that in some cases even 4 lines are not enough to avoid moire.

I’m still unsure if that parameter has to be set to a negative value by default (so let the shader choose) or not, suggestions welcome!

2 Likes

There you go:

…you can select how much to stagger the odd lines, this is useful if you are using different horizontal masks:
for 2 or 4 sized masks (gm,rgbx,rbgx,wx) use 1.5
for 3 sized masks (gmx,rgb,rbg) use 1.0

The height parameter is mainly for higher resolution screens; for 1080p i’d leave it to 1.0, but i’ve found that you can have nice results, again, depending on the mask; eg: with 4 sized masks like rgbx or rbgx you can try to set this to 3.0, while with 2 sized masks, you can try 2.0.

I admit I started this mainly for MSDOS content, but indeed it looks nice even for arcades, so I made a new preset for low res content, named:
Monitor-Screen_Hmask-ShadowMask.slangp

And another one for doublescanned/hires content (MSDOS) with an higher TVL (gm mask):Monitor-VGA-DoubleScan-ShadowMask.slangp

5 Likes

Thank you very much @kokoko3k. I highly appreciate the work you put into this feature.

1 Like

I Just ported part of this (only the shake part) and added a vibrance parameter, just in case.

I compared Monitor-Screen_Hmask-ShadowMask.slangp with shadow mask presets from Sony Megatron Colour Video Monitor and the result differs. Please, take a look at the attached screenshot to see the different arrangement of the rgb pixels. I tried to achieve it with the X staggering and Phosphor height parameters without success. Could you please help me with that?

When comparing the two screenshots I also realized that the number of TVLs in this preset seems to be high. Is there a way to set (decrease) the TVL?

1 Like

To have a lower TVL you have to increase the phosphors width.

This is doable via the “cell size multiplier x” in the "horizontal mask’ section, under the main “low level phosphor grid section”.

There you can also switch from/to green/magenta to rgb, rbg, rgbx and so on. On 4k I think you can also try to play with phosphor width Min/Max parameters and their gamma, feel free to experiment and take a look to documentation in docs-ng.md file for details.

Oh, and if you came up with something good, feel free to share too :laughing:

At 3x scaling things start to look convincing.
Screenshot_20240113_114229

This preset is a proof of concept that scales the horizontal mask by 3x, set the shadowmask phosphor height to 3, staggers horizontally by 1.5x and with the help of vertical mask, set at 3x (screen coords), gives phosphors a rounder look vertically too for what is possible with 3x3 px.

Naked, it does not uses bloom halo or else.

…also i’ve another change for the code in mind, but this is dangerous, since it would affect basically everything and i can’t remember why the code was that way lol :slight_smile:

It would allow to have rounder phosphors; this is almost the same as before, 3X

Screenshot_20240113_130150

This is the same as before, but for 2x scaling, blockiness is unavoidable here (every phosphor is a 2x2 square), but still we may smooth one out of 2 pixels to have something smoother.

Screenshot_20240113_130906

4K is really needed when using lower TVL, or moire will kick in.

Shadowmask 3x
IN_GLOW_POWER = "1.500000"
LUMINANCE = "0.200000"
TEMPERATURE = "7200.000000"
IN_GLOW_GAMMA = "2.000000"
GAMMA_OUT = "0.400000"
OFFSET_STRENGTH = "0.300000"
SHIFT_R = "-20.000000"
SHIFT_G = "0.000000"
SHIFT_B = "20.000000"
IN_GLOW_W = "-0.800000"
IN_GLOW_H = "7.000000"
RESSWITCH_GLITCH_SIZE = "0.000000"
DO_PIXELGRID = "1.000000"
DO_PIXELGRID_H = "0.000000"
PIXELGRID_MIN_H = "0.500000"
PIXELGRID_MAX_H = "0.700000"
PIXELGRID_GAMMA_H = "5.200000"
PIXELGRID_MUL_X = "3.000000"
PIXELGRID_H_PRST = "0.000000"
PIXELGRID_G_SHIFT = "1.000000"
PIXELGRID_B_SHIFT = "2.000002"
PIXELGRID_MIN_W = "0.200000"
PIXELGRID_MAX_W = "0.300000"
PIXELGRID_GAMMA_W = "5.199997"
PIXELGRID_BASAL_GRID = "0.020000"
PIXELGRID_Y_MASK = "1.000000"
PIXELGRID_Y_MASK_HEIGHT = "-1.500000"
PIXELGRID_Y_MASK_OFFSET = "0.000000"
PIXELGRID_Y_MASK_SHIFT = "0.000000"
PIXELGRID_Y_MASK_STEEP = "1.000000"
PIXELGRID_Y_MASK_ON_WHITE = "0.150000"
PIXELGRID_DO_SHADOWMASK = "1.000000"
PIXELGRID_SHADOWMASK_SHIFT = "1.500000"
PIXELGRID_SHADOWMASK_H = "3.000000"
HALO_NO_PREGAIN = "1.000000"
HALO_POWER = "0.500000"
HALO_SHARPNESS = "6.500000"
HALO_VS_SCAN = "0.700000"
BLOOM_MIX = "0.400000"
BLOOM_GAMMA_OUT = "1.200000"
BLOOM_EYE_ADPT_SRT = "0.600000"
BLOOM_EYE_INERTIA = "750.000000"
GEOM_CORNER_SIZE = "0.010000"
GEOM_CORNER_SMOOTH = "200.000000"
DO_BEZEL = "1.000000"
BEZEL_INNER_ZOOM = "-0.010000"
BEZEL_FRAME_ZOOM = "0.170000"
DO_VIGNETTE = "1.000000"
V_SIZE = "1.080000"
DO_SPOT = "1.000000"
S_POWER = "0.050000"```
Shadowmask 2x
IN_GLOW_POWER = "1.500000"
LUMINANCE = "0.200000"
TEMPERATURE = "7200.000000"
IN_GLOW_GAMMA = "2.000000"
GAMMA_OUT = "0.400000"
OFFSET_STRENGTH = "0.300000"
SHIFT_R = "-20.000000"
SHIFT_G = "0.000000"
SHIFT_B = "20.000000"
IN_GLOW_W = "-0.800000"
IN_GLOW_H = "7.000000"
RESSWITCH_GLITCH_SIZE = "0.000000"
DO_PIXELGRID = "1.000000"
DO_PIXELGRID_H = "0.000000"
PIXELGRID_MIN_H = "0.500000"
PIXELGRID_MAX_H = "0.700000"
PIXELGRID_GAMMA_H = "5.200000"
PIXELGRID_MUL_X = "2.000000"
PIXELGRID_H_PRST = "0.000000"
PIXELGRID_B_SHIFT = "2.000002"
PIXELGRID_MIN_W = "0.140000"
PIXELGRID_MAX_W = "0.300000"
PIXELGRID_GAMMA_W = "5.199997"
PIXELGRID_BASAL_GRID = "0.020000"
PIXELGRID_Y_MASK = "1.000000"
PIXELGRID_Y_MASK_HEIGHT = "-1.000000"
PIXELGRID_Y_MASK_OFFSET = "0.000000"
PIXELGRID_Y_MASK_STEEP = "1.000000"
PIXELGRID_Y_MASK_ON_WHITE = "0.150000"
PIXELGRID_DO_SHADOWMASK = "1.000000"
PIXELGRID_SHADOWMASK_SHIFT = "1.500000"
PIXELGRID_SHADOWMASK_H = "2.000000"
HALO_NO_PREGAIN = "1.000000"
HALO_POWER = "0.500000"
HALO_SHARPNESS = "6.500000"
HALO_VS_SCAN = "0.700000"
BLOOM_MIX = "0.400000"
BLOOM_GAMMA_OUT = "1.200000"
BLOOM_EYE_ADPT_SRT = "0.600000"
BLOOM_EYE_INERTIA = "750.000000"
GEOM_CORNER_SIZE = "0.010000"
GEOM_CORNER_SMOOTH = "200.000000"
DO_BEZEL = "1.000000"
BEZEL_INNER_ZOOM = "-0.010000"
BEZEL_FRAME_ZOOM = "0.170000"
DO_VIGNETTE = "1.000000"
V_SIZE = "1.080000"
DO_SPOT = "1.000000"
S_POWER = "0.050000"```
1 Like

I also achieved good results with 2x scaling (see screenshot) but I needed to set PIXELGRID_MIN_W and PIXELGRID_MAX_W to their default value of 0.25 for a to me unknown reason?

#reference "../../shaders/shaders_slang/bezel/koko-aio/Presets-ng/Monitor-Screen_Hmask-ShadowMask.slangp"
PIXELGRID_MUL_X = "2.000000"
PIXELGRID_MIN_W = "0.250000"
PIXELGRID_MAX_W = "0.250000"
PIXELGRID_SHADOWMASK_SHIFT = "1.500000"
PIXELGRID_SHADOWMASK_H = "2.000000"

2x seems to be the same as 300 TVL in crt-sony-megatron presets so I would prefer that ratio. For a 1x scaling I was unable to achieve the phosphor shift with rgb by 1.5 – it always blends the colours. I wonder how this can be achieved?

I also wonder if rgb is the “corect” subpixel since shadow masks are arranged differently (see e.g. https://1.bp.blogspot.com/-xycsRkq0ZQI/YEtWDgjrdsI/AAAAAAAABD8/o8GQPSemECob5Nnz5BnvtSPqRny8tn0PACLcBGAsYHQ/s320/Screenshot_20210312-171836%7E2.png). I could not find the typical subpixel structure of an arcade back then. If anyone knows, please let me know.

1 Like

This is from a real crt in my lab at work, rgb, but I ignore what was used in Arcade cabs; I mostly see slotmasks tbh.

As per the shift, 1x is the one to be used at 1x scale when using triads to avoid blending; you just cannot draw in the middle of a screen pixel.

If you switch to a green/magenta mask, 1.5x scale can be used even at 1x instead.

As per the phosphor width, it is your choice and what you want to achieve; when width is high, the color starts to blend with adiacent phosphors; when it is low, it does the opposite, it shrinks, and if there are no available screen pixels to shrink, it eventually simply fades away.

If you are on a screen that has not many nits, then maybe you want to emulate more nits by letting the phosphors grow and blend together till white; just saying.

3 Likes

Really liked hyllian’s noscanline presets and tried to get the same look in koko. I think this works really well with smaller screens because masks usually won’t look good with that

6 Likes

Nice, indeed.

Do you used variable width phosphors with a wx mask or maybe integer scanlines with doublescan tated?

Thanks. The first one, with mask 4

1 Like

ofc, I did not zoomed the linked picture ^.^

1 Like

Currently working on a more correct way to “join/mix” masks.

Incidentally, the “sparkling look punch” would be heavilly affected by such change, so I’ve had to rethink it… for good, imho.

It acts like a local/per core pixel contrast increase thing now, it is able to better transfer the energy from the dark part of the mask to the unaffected one.
You can think to it as an overmask setting that just affects thin horizontal lines used to emulate aperturegrille or slotmask and their surroundings; here it is obviously too high, but it gives the idea:

Once finished, the downside is that i will need to adapt the presets to look at least the same as before :frowning:

[…] Done.

4 Likes

NG-1.9 just released. Changelog is bigger than expected, here or in the opening post.

Just submitted for inclusion in online updater.

5 Likes

@kokoko3k I don’t know if they have thought about it and if it would be possible, but will there be any option to be able to use a video file for the background?

I would like to be able to create an atmosphere as if I were in an arcade room. Instead of calling an image file, you could call a .mp4 video file

Definitely not from the shader as per current retroarch implementation.

This is amazing but I wonder what would happen to those beautiful patterns after they pass through the actual LCD/OLED panel? Would they have to align with the subpixels in order to maintain that fidelity of your screenshot?

1 Like