1/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package androidx.media.filterpacks.image;
18
19import androidx.media.filterfw.Filter;
20import androidx.media.filterfw.FrameImage2D;
21import androidx.media.filterfw.FrameType;
22import androidx.media.filterfw.ImageShader;
23import androidx.media.filterfw.InputPort;
24import androidx.media.filterfw.MffContext;
25import androidx.media.filterfw.OutputPort;
26import androidx.media.filterfw.Signature;
27
28public class BrightnessFilter extends Filter {
29
30    private float mBrightness = 1.0f;
31    private ImageShader mShader;
32
33    private static final String mBrightnessShader =
34            "precision mediump float;\n" +
35            "uniform sampler2D tex_sampler_0;\n" +
36            "uniform float brightness;\n" +
37            "varying vec2 v_texcoord;\n" +
38            "void main() {\n" +
39            "  vec4 color = texture2D(tex_sampler_0, v_texcoord);\n" +
40            "  if (brightness < 0.5) {\n" +
41            "    gl_FragColor = color * (2.0 * brightness);\n" +
42            "  } else {\n" +
43            "    vec4 diff = 1.0 - color;\n" +
44            "    gl_FragColor = color + diff * (2.0 * (brightness - 0.5));\n" +
45            "  }\n" +
46            "}\n";
47
48
49    public BrightnessFilter(MffContext context, String name) {
50        super(context, name);
51    }
52
53    @Override
54    public Signature getSignature() {
55        FrameType imageIn = FrameType.image2D(FrameType.ELEMENT_RGBA8888, FrameType.READ_GPU);
56        FrameType imageOut = FrameType.image2D(FrameType.ELEMENT_RGBA8888, FrameType.WRITE_GPU);
57        return new Signature()
58            .addInputPort("image", Signature.PORT_REQUIRED, imageIn)
59            .addInputPort("brightness", Signature.PORT_OPTIONAL, FrameType.single(float.class))
60            .addOutputPort("image", Signature.PORT_REQUIRED, imageOut)
61            .disallowOtherPorts();
62    }
63
64    @Override
65    public void onInputPortOpen(InputPort port) {
66        if (port.getName().equals("brightness")) {
67            port.bindToFieldNamed("mBrightness");
68            port.setAutoPullEnabled(true);
69        }
70    }
71
72    @Override
73    protected void onPrepare() {
74        mShader = new ImageShader(mBrightnessShader);
75    }
76
77    @Override
78    protected void onProcess() {
79        OutputPort outPort = getConnectedOutputPort("image");
80        FrameImage2D inputImage = getConnectedInputPort("image").pullFrame().asFrameImage2D();
81        int[] dim = inputImage.getDimensions();
82        FrameImage2D outputImage = outPort.fetchAvailableFrame(dim).asFrameImage2D();
83        mShader.setUniformValue("brightness", mBrightness);
84        mShader.process(inputImage, outputImage);
85        outPort.pushFrame(outputImage);
86    }
87}
88
89