• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright 2022 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 ULTRAHDR_JPEGENCODERHELPER_H
18 #define ULTRAHDR_JPEGENCODERHELPER_H
19 
20 #include <stdio.h>  // For jpeglib.h.
21 
22 // C++ build requires extern C for jpeg internals.
23 #ifdef __cplusplus
24 extern "C" {
25 #endif
26 
27 #include <jerror.h>
28 #include <jpeglib.h>
29 
30 #ifdef __cplusplus
31 }  // extern "C"
32 #endif
33 
34 #include <cstdint>
35 #include <vector>
36 
37 #include "ultrahdr_api.h"
38 
39 namespace ultrahdr {
40 
41 /*!\brief module for managing output */
42 struct destination_mgr_impl : jpeg_destination_mgr {
43   static const int kBlockSize = 16384;  // result buffer resize step
44   std::vector<JOCTET> mResultBuffer;    // buffer to store encoded data
45 };
46 
47 /*!\brief Encapsulates a converter from raw to jpg image format. This class is not thread-safe */
48 class JpegEncoderHelper {
49  public:
50 
51   JpegEncoderHelper() = default;
52   ~JpegEncoderHelper() = default;
53 
54   /*!\brief This function encodes the raw image that is passed to it and stores the results
55    * internally. The result is accessible via getter functions.
56    *
57    * \param[in]  planes     pointers of all planes of input image
58    * \param[in]  strides    strides of all planes of input image
59    * \param[in]  width      image width
60    * \param[in]  height     image height
61    * \param[in]  format     input raw image format
62    * \param[in]  qfactor    quality factor [1 - 100, 1 being poorest and 100 being best quality]
63    * \param[in]  iccBuffer  pointer to icc segment that needs to be added to the compressed image
64    * \param[in]  iccSize    size of icc segment
65    *
66    * \returns true if operation succeeds, false otherwise.
67    */
68   bool compressImage(const uint8_t* planes[3], const size_t strides[3], const int width,
69                      const int height, const uhdr_img_fmt_t format, const int qfactor,
70                      const void* iccBuffer, const unsigned int iccSize);
71 
72   /*! Below public methods are only effective if a call to compressImage() is made and it returned
73    * true. */
74 
75   /*!\brief returns pointer to compressed image output */
getCompressedImagePtr()76   void* getCompressedImagePtr() { return mDestMgr.mResultBuffer.data(); }
77 
78   /*!\brief returns size of compressed image */
getCompressedImageSize()79   size_t getCompressedImageSize() { return mDestMgr.mResultBuffer.size(); }
80 
81  private:
82   // max number of components supported
83   static constexpr int kMaxNumComponents = 3;
84 
85   bool encode(const uint8_t* planes[3], const size_t strides[3], const int width, const int height,
86               const uhdr_img_fmt_t format, const int qfactor, const void* iccBuffer,
87               const unsigned int iccSize);
88 
89   bool compressYCbCr(jpeg_compress_struct* cinfo, const uint8_t* planes[3],
90                      const size_t strides[3]);
91 
92   destination_mgr_impl mDestMgr;  // object for managing output
93 
94   // temporary storage
95   std::unique_ptr<uint8_t[]> mPlanesMCURow[kMaxNumComponents];
96 
97   size_t mPlaneWidth[kMaxNumComponents];
98   size_t mPlaneHeight[kMaxNumComponents];
99 };
100 
101 } /* namespace ultrahdr  */
102 
103 #endif  // ULTRAHDR_JPEGENCODERHELPER_H
104