1/*
2 * Copyright 2014 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
17#ifndef IMG_UTILS_DNG_UTILS_H
18#define IMG_UTILS_DNG_UTILS_H
19
20#include <img_utils/ByteArrayOutput.h>
21#include <img_utils/EndianUtils.h>
22
23#include <utils/Errors.h>
24#include <utils/Log.h>
25#include <utils/RefBase.h>
26
27#include <cutils/compiler.h>
28#include <stdint.h>
29
30namespace android {
31namespace img_utils {
32
33#define NELEMS(x) ((int) (sizeof(x) / sizeof((x)[0])))
34#define CLAMP(x, low, high) (((x) > (high)) ? (high) : (((x) < (low)) ? (low) : (x)))
35
36/**
37 * Utility class for building values for the OpcodeList tags specified
38 * in the Adobe DNG 1.4 spec.
39 */
40class ANDROID_API OpcodeListBuilder : public LightRefBase<OpcodeListBuilder> {
41    public:
42        enum CfaLayout {
43            CFA_RGGB = 0,
44            CFA_GRBG,
45            CFA_GBRG,
46            CFA_BGGR,
47        };
48
49        OpcodeListBuilder();
50        virtual ~OpcodeListBuilder();
51
52        /**
53         * Get the total size of this opcode list in bytes.
54         */
55        virtual size_t getSize() const;
56
57        /**
58         * Get the number of opcodes defined in this list.
59         */
60        virtual uint32_t getCount() const;
61
62        /**
63         * Write the opcode list into the given buffer.  This buffer
64         * must be able to hold at least as many elements as returned
65         * by calling the getSize() method.
66         *
67         * Returns OK on success, or a negative error code.
68         */
69        virtual status_t buildOpList(/*out*/ uint8_t* buf) const;
70
71        /**
72         * Add GainMap opcode(s) for the given metadata parameters.  The given
73         * CFA layout must match the layout of the shading map passed into the
74         * lensShadingMap parameter.
75         *
76         * Returns OK on success, or a negative error code.
77         */
78        virtual status_t addGainMapsForMetadata(uint32_t lsmWidth,
79                                                uint32_t lsmHeight,
80                                                uint32_t activeAreaTop,
81                                                uint32_t activeAreaLeft,
82                                                uint32_t activeAreaBottom,
83                                                uint32_t activeAreaRight,
84                                                CfaLayout cfa,
85                                                const float* lensShadingMap);
86
87
88        /**
89         * Add a GainMap opcode with the given fields.  The mapGains array
90         * must have mapPointsV * mapPointsH * mapPlanes elements.
91         *
92         * Returns OK on success, or a negative error code.
93         */
94        virtual status_t addGainMap(uint32_t top,
95                                    uint32_t left,
96                                    uint32_t bottom,
97                                    uint32_t right,
98                                    uint32_t plane,
99                                    uint32_t planes,
100                                    uint32_t rowPitch,
101                                    uint32_t colPitch,
102                                    uint32_t mapPointsV,
103                                    uint32_t mapPointsH,
104                                    double mapSpacingV,
105                                    double mapSpacingH,
106                                    double mapOriginV,
107                                    double mapOriginH,
108                                    uint32_t mapPlanes,
109                                    const float* mapGains);
110
111        /**
112         * Add WarpRectilinear opcode for the given metadata parameters.
113         *
114         * Returns OK on success, or a negative error code.
115         */
116        virtual status_t addWarpRectilinearForMetadata(const float* kCoeffs,
117                                                       uint32_t activeArrayWidth,
118                                                       uint32_t activeArrayHeight,
119                                                       float opticalCenterX,
120                                                       float opticalCenterY);
121
122        /**
123         * Add a WarpRectilinear opcode.
124         *
125         * numPlanes - Number of planes included in this opcode.
126         * opticalCenterX, opticalCenterY - Normalized x,y coordinates of the sensor optical
127         *          center relative to the top,left pixel of the produced images (e.g. [0.5, 0.5]
128         *          gives a sensor optical center in the image center.
129         * kCoeffs - A list of coefficients for the polynomial equation representing the distortion
130         *          correction.  For each plane, 6 coefficients must be included:
131         *          {k_r0, k_r1, k_r2, k_r3, k_t0, k_t1}.  See the DNG 1.4 specification for an
132         *          outline of the polynomial used here.
133         *
134         * Returns OK on success, or a negative error code.
135         */
136        virtual status_t addWarpRectilinear(uint32_t numPlanes,
137                                            double opticalCenterX,
138                                            double opticalCenterY,
139                                            const double* kCoeffs);
140
141
142        /**
143         * Add FixBadPixelsList opcode for the given metadata parameters.
144         *
145         * Returns OK on success, or a negative error code.
146         */
147        virtual status_t addBadPixelListForMetadata(const uint32_t* hotPixels,
148                                                    uint32_t xyPairCount,
149                                                    uint32_t colorFilterArrangement);
150
151        /**
152         * Add FixBadPixelsList opcode.
153         *
154         * bayerPhase - 0=top-left of image is red, 1=top-left of image is green pixel in red row,
155         *              2=top-left of image is green pixel in blue row, 3=top-left of image is
156         *              blue.
157         * badPointCount - number of (x,y) pairs of bad pixels are given in badPointRowColPairs.
158         * badRectCount - number of (top, left, bottom, right) tuples are given in
159         *              badRectTopLeftBottomRightTuples
160         *
161         * Returns OK on success, or a negative error code.
162         */
163        virtual status_t addBadPixelList(uint32_t bayerPhase,
164                                         uint32_t badPointCount,
165                                         uint32_t badRectCount,
166                                         const uint32_t* badPointRowColPairs,
167                                         const uint32_t* badRectTopLeftBottomRightTuples);
168
169        // TODO: Add other Opcode methods
170    protected:
171        static const uint32_t FLAG_OPTIONAL = 0x1u;
172        static const uint32_t FLAG_OPTIONAL_FOR_PREVIEW = 0x2u;
173
174        // Opcode IDs
175        enum {
176            WARP_RECTILINEAR_ID = 1,
177            FIX_BAD_PIXELS_LIST = 5,
178            GAIN_MAP_ID = 9,
179        };
180
181        // LSM mosaic indices
182        enum {
183            LSM_R_IND = 0,
184            LSM_GE_IND = 1,
185            LSM_GO_IND = 2,
186            LSM_B_IND = 3,
187        };
188
189        uint32_t mCount;
190        ByteArrayOutput mOpList;
191        EndianOutput mEndianOut;
192
193        status_t addOpcodePreamble(uint32_t opcodeId);
194
195};
196
197} /*namespace img_utils*/
198} /*namespace android*/
199
200#endif /*IMG_UTILS_DNG_UTILS_H*/
201