1 // Copyright (c) the JPEG XL Project Authors. All rights reserved.
2 //
3 // Use of this source code is governed by a BSD-style
4 // license that can be found in the LICENSE file.
5 
6 #ifndef LIB_JXL_BLENDING_H_
7 #define LIB_JXL_BLENDING_H_
8 #include "lib/jxl/dec_cache.h"
9 #include "lib/jxl/dec_patch_dictionary.h"
10 #include "lib/jxl/image_bundle.h"
11 
12 namespace jxl {
13 
14 Status PerformBlending(const float* const* bg, const float* const* fg,
15                        float* const* out, size_t xsize,
16                        const PatchBlending& color_blending,
17                        const PatchBlending* ec_blending,
18                        const std::vector<ExtraChannelInfo>& extra_channel_info);
19 
20 class ImageBlender {
21  public:
22   class RectBlender {
23    public:
24     // Does the blending for a given row of the rect passed to
25     // ImageBlender::PrepareRect.
26     Status DoBlending(size_t y);
27 
28     // If this returns true, then nothing needs to be done for this rect and
29     // DoBlending can be skipped (but does not have to).
done()30     bool done() const { return done_; }
31 
32    private:
33     friend class ImageBlender;
RectBlender(bool done)34     explicit RectBlender(bool done) : done_(done) {}
35 
36     bool done_;
37     Rect current_overlap_;
38     Rect current_cropbox_;
39     ImageBundle* dest_;
40     std::vector<const float*> fg_ptrs_;
41     std::vector<size_t> fg_strides_;
42     std::vector<float*> bg_ptrs_;
43     std::vector<size_t> bg_strides_;
44     std::vector<const float*> fg_row_ptrs_;
45     std::vector<float*> bg_row_ptrs_;
46     std::vector<PatchBlending> blending_info_;
47   };
48 
49   static bool NeedsBlending(PassesDecoderState* dec_state);
50 
51   Status PrepareBlending(PassesDecoderState* dec_state,
52                          FrameOrigin foreground_origin, size_t foreground_xsize,
53                          size_t foreground_ysize,
54                          const ColorEncoding& frame_color_encoding,
55                          ImageBundle* output);
56   // rect is relative to the full decoded foreground.
57   // But foreground here can be a subset of the full foreground, and input_rect
58   // indicates where that rect is in that subset. For example, if rect =
59   // Rect(10, 10, 20, 20), and foreground is subrect (7, 7, 30, 30) of the full
60   // foreground, then input_rect should be (3, 3, 20, 20), because that is where
61   // rect is relative to the foreground crop.
62   ImageBlender::RectBlender PrepareRect(
63       const Rect& rect, const Image3F& foreground,
64       const std::vector<ImageF>& extra_channels, const Rect& input_rect) const;
65 
66   // If this returns true, then it is not necessary to call further methods on
67   // this ImageBlender to achieve blending, although it is not forbidden either
68   // (those methods will just return immediately in that case).
done()69   bool done() const { return done_; }
70 
71  private:
72   BlendingInfo info_;
73   // Destination, as well as background before DoBlending is called.
74   ImageBundle* dest_;
75   Rect cropbox_;
76   Rect overlap_;
77   bool done_ = false;
78   const std::vector<BlendingInfo>* ec_info_;
79   FrameOrigin o_{};
80 };
81 
82 }  // namespace jxl
83 
84 #endif  // LIB_JXL_BLENDING_H_
85