// Set up shared/commonly used variables and macros void sampler_prelude(struct gl_shader_cache *sc, int tex_num) { GLSLF("#undef tex\n"); GLSLF("#define tex texture%d\n", tex_num); GLSLF("vec2 pos = texcoord%d;\n", tex_num); GLSLF("vec2 size = texture_size%d;\n", tex_num); GLSLF("vec2 pt = vec2(1.0) / size;\n"); }
void pass_nnedi3(GL *gl, struct gl_shader_cache *sc, int planes, int tex_num, int step, float tex_mul, const struct nnedi3_opts *conf, struct gl_transform *transform) { assert(0 <= step && step < 2); if (!conf) conf = &nnedi3_opts_def; const int neurons = nnedi3_neurons[conf->neurons]; const int width = nnedi3_window_width[conf->window]; const int height = nnedi3_window_height[conf->window]; const int offset = nnedi3_weight_offsets[conf->window * 4 + conf->neurons]; const uint32_t *weights = (const int*)(nnedi3_weights + offset * 4); GLSLF("// nnedi3 (step %d, neurons %d, window %dx%d, mode %d)\n", step, neurons, width, height, conf->upload); // This is required since each row will be encoded into vec4s assert(width % 4 == 0); const int sample_count = width * height / 4; if (conf->upload == NNEDI3_UPLOAD_UBO) { char buf[32]; snprintf(buf, sizeof(buf), "vec4 weights[%d];", neurons * (sample_count * 2 + 1)); gl_sc_uniform_buffer(sc, "NNEDI3_WEIGHTS", buf, 0); if (!gl->es && gl->glsl_version < 140) gl_sc_enable_extension(sc, "GL_ARB_uniform_buffer_object"); } else if (conf->upload == NNEDI3_UPLOAD_SHADER) { // Somehow necessary for hard coding approach. GLSLH(#pragma optionNV(fastprecision on)) }
static void pass_sample_separated_get_weights(struct gl_shader_cache *sc, struct scaler *scaler) { gl_sc_uniform_texture(sc, "lut", scaler->lut); GLSLF("float ypos = LUT_POS(fcoord, %d.0);\n", scaler->lut_size); int N = scaler->kernel->size; int width = (N + 3) / 4; // round up GLSLF("float weights[%d];\n", N); for (int i = 0; i < N; i++) { if (i % 4 == 0) GLSLF("c = texture(lut, vec2(%f, ypos));\n", (i / 4 + 0.5) / width); GLSLF("weights[%d] = c[%d];\n", i, i % 4); } }
static void pass_sample_separated_get_weights(struct gl_shader_cache *sc, struct scaler *scaler) { gl_sc_uniform_sampler(sc, "lut", scaler->gl_target, TEXUNIT_SCALERS + scaler->index); // Define a new variable to cache the corrected fcoord. GLSLF("float fcoord_lut = LUT_POS(fcoord, %d.0);\n", scaler->lut_size); int N = scaler->kernel->size; if (N == 2) { GLSL(vec2 c1 = texture(lut, vec2(0.5, fcoord_lut)).RG;)
static void update_osd(struct vo *vo) { struct priv *p = vo->priv; if (!p->enable_osd) return; mpgl_osd_generate(p->osd, p->osd_res, p->osd_pts, 0, 0); int64_t osd_change_counter = mpgl_get_change_counter(p->osd); if (p->osd_change_counter == osd_change_counter) { p->skip_osd = true; return; } p->osd_change_counter = osd_change_counter; MP_STATS(vo, "start rpi_osd"); p->egl.gl->ClearColor(0, 0, 0, 0); p->egl.gl->Clear(GL_COLOR_BUFFER_BIT); for (int n = 0; n < MAX_OSD_PARTS; n++) { enum sub_bitmap_format fmt = mpgl_osd_get_part_format(p->osd, n); if (!fmt) continue; gl_sc_uniform_sampler(p->sc, "osdtex", GL_TEXTURE_2D, 0); switch (fmt) { case SUBBITMAP_RGBA: { GLSLF("// OSD (RGBA)\n"); GLSL(color = texture(osdtex, texcoord).bgra;) break; } case SUBBITMAP_LIBASS: { GLSLF("// OSD (libass)\n"); GLSL(color = vec4(ass_color.rgb, ass_color.a * texture(osdtex, texcoord).r);) break; } default: abort(); }