1// Copyright (c) 2010 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#ifndef PDF_PAINT_AGGREGATOR_H_ 6#define PDF_PAINT_AGGREGATOR_H_ 7 8#include <vector> 9 10#include "ppapi/cpp/image_data.h" 11#include "ppapi/cpp/rect.h" 12#include "ppapi/cpp/rect.h" 13 14// This class is responsible for aggregating multiple invalidation and scroll 15// commands to produce a scroll and repaint sequence. You can use this manually 16// to track your updates, but most applications will use the PaintManager to 17// additionally handle the necessary callbacks on top of the PaintAggregator 18// functionality. 19// 20// See http://code.google.com/p/ppapi/wiki/2DPaintingModel 21class PaintAggregator { 22 public: 23 // Stores information about a rectangle that has finished painting. The 24 // PaintManager will paint it only when everything else on the screen is also 25 // ready. 26 struct ReadyRect { 27 pp::Point offset; 28 pp::Rect rect; 29 pp::ImageData image_data; 30 }; 31 32 struct PaintUpdate { 33 PaintUpdate(); 34 ~PaintUpdate(); 35 36 // True if there is a scroll applied. This indicates that the scroll delta 37 // and scroll_rect are nonzero (just as a convenience). 38 bool has_scroll; 39 40 // The amount to scroll by. Either the X or Y may be nonzero to indicate a 41 // scroll in that direction, but there will never be a scroll in both 42 // directions at the same time (this will be converted to a paint of the 43 // region instead). 44 // 45 // If there is no scroll, this will be (0, 0). 46 pp::Point scroll_delta; 47 48 // The rectangle that should be scrolled by the scroll_delta. If there is no 49 // scroll, this will be (0, 0, 0, 0). We only track one scroll command at 50 // once. If there are multiple ones, they will be converted to invalidates. 51 pp::Rect scroll_rect; 52 53 // A list of all the individual dirty rectangles. This is an aggregated list 54 // of all invalidate calls. Different rectangles may be unified to produce a 55 // minimal list with no overlap that is more efficient to paint. This list 56 // also contains the region exposed by any scroll command. 57 std::vector<pp::Rect> paint_rects; 58 }; 59 60 PaintAggregator(); 61 62 // There is a PendingUpdate if InvalidateRect or ScrollRect were called and 63 // ClearPendingUpdate was not called. 64 bool HasPendingUpdate() const; 65 void ClearPendingUpdate(); 66 67 PaintUpdate GetPendingUpdate(); 68 69 // Sets the result of a call to the plugin to paint. This includes rects that 70 // are finished painting (ready), and ones that are still in-progress 71 // (pending). 72 void SetIntermediateResults(const std::vector<ReadyRect>& ready, 73 const std::vector<pp::Rect>& pending); 74 75 // Returns the rectangles that are ready to be painted. 76 std::vector<ReadyRect> GetReadyRects() const; 77 78 // The given rect should be repainted. 79 void InvalidateRect(const pp::Rect& rect); 80 81 // The given rect should be scrolled by the given amounts. 82 void ScrollRect(const pp::Rect& clip_rect, const pp::Point& amount); 83 84 private: 85 // This structure is an internal version of PaintUpdate. It's different in 86 // two respects: 87 // 88 // - The scroll damange (area exposed by the scroll operation, if any) is 89 // maintained separately from the dirty rects generated by calling 90 // InvalidateRect. We need to know this distinction for some operations. 91 // 92 // - The paint bounds union is computed on the fly so we don't have to keep 93 // a rectangle up-to-date as we do different operations. 94 class InternalPaintUpdate { 95 public: 96 InternalPaintUpdate(); 97 ~InternalPaintUpdate(); 98 99 // Computes the rect damaged by scrolling within |scroll_rect| by 100 // |scroll_delta|. This rect must be repainted. It is not included in 101 // paint_rects. 102 pp::Rect GetScrollDamage() const; 103 104 pp::Point scroll_delta; 105 pp::Rect scroll_rect; 106 107 // Does not include the scroll damage rect unless 108 // synthesized_scroll_damage_rect_ is set. 109 std::vector<pp::Rect> paint_rects; 110 111 // Rectangles that are finished painting. 112 std::vector<ReadyRect> ready_rects; 113 114 // Whether we have added the scroll damage rect to paint_rects yet or not. 115 bool synthesized_scroll_damage_rect_; 116 }; 117 118 pp::Rect ScrollPaintRect(const pp::Rect& paint_rect, 119 const pp::Point& amount) const; 120 void InvalidateScrollRect(); 121 122 // Internal method used by InvalidateRect. If |check_scroll| is true, then the 123 // method checks if there's a pending scroll and if so also invalidates |rect| 124 // in the new scroll position. 125 void InvalidateRectInternal(const pp::Rect& rect, bool check_scroll); 126 127 InternalPaintUpdate update_; 128}; 129 130#endif // PDF_PAINT_AGGREGATOR_H_ 131