1 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* ***** BEGIN LICENSE BLOCK *****
3 : * Version: MPL 1.1/GPL 2.0/LGPL 2.1
4 : *
5 : * The contents of this file are subject to the Mozilla Public License Version
6 : * 1.1 (the "License"); you may not use this file except in compliance with
7 : * the License. You may obtain a copy of the License at
8 : * http://www.mozilla.org/MPL/
9 : *
10 : * Software distributed under the License is distributed on an "AS IS" basis,
11 : * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
12 : * for the specific language governing rights and limitations under the
13 : * License.
14 : *
15 : * The Original Code is mozilla.org code.
16 : *
17 : * The Initial Developer of the Original Code is
18 : * Netscape Communications Corporation.
19 : * Portions created by the Initial Developer are Copyright (C) 1998
20 : * the Initial Developer. All Rights Reserved.
21 : *
22 : * Contributor(s):
23 : *
24 : * Alternatively, the contents of this file may be used under the terms of
25 : * either of the GNU General Public License Version 2 or later (the "GPL"),
26 : * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
27 : * in which case the provisions of the GPL or the LGPL are applicable instead
28 : * of those above. If you wish to allow use of your version of this file only
29 : * under the terms of either the GPL or the LGPL, and not to allow others to
30 : * use your version of this file under the terms of the MPL, indicate your
31 : * decision by deleting the provisions above and replace them with the notice
32 : * and other provisions required by the GPL or the LGPL. If you do not delete
33 : * the provisions above, a recipient may use your version of this file under
34 : * the terms of any one of the MPL, the GPL or the LGPL.
35 : *
36 : * ***** END LICENSE BLOCK ***** */
37 :
38 : /* rendering objects for replaced elements implemented by a plugin */
39 :
40 : #ifndef nsObjectFrame_h___
41 : #define nsObjectFrame_h___
42 :
43 : #include "nsPluginInstanceOwner.h"
44 : #include "nsIObjectFrame.h"
45 : #include "nsFrame.h"
46 : #include "nsRegion.h"
47 : #include "nsDisplayList.h"
48 : #include "nsIReflowCallback.h"
49 : #include "Layers.h"
50 : #include "ImageLayers.h"
51 :
52 : #ifdef ACCESSIBILITY
53 : class nsIAccessible;
54 : #endif
55 :
56 : class nsPluginHost;
57 : class nsPresContext;
58 : class nsDisplayPlugin;
59 : class nsIOSurface;
60 : class PluginBackgroundSink;
61 :
62 : #define nsObjectFrameSuper nsFrame
63 :
64 : class nsObjectFrame : public nsObjectFrameSuper,
65 : public nsIObjectFrame,
66 : public nsIReflowCallback {
67 : public:
68 : typedef mozilla::LayerState LayerState;
69 : typedef mozilla::layers::Layer Layer;
70 : typedef mozilla::layers::LayerManager LayerManager;
71 : typedef mozilla::layers::ImageContainer ImageContainer;
72 :
73 : NS_DECL_FRAMEARENA_HELPERS
74 :
75 : friend nsIFrame* NS_NewObjectFrame(nsIPresShell* aPresShell, nsStyleContext* aContext);
76 :
77 : NS_DECL_QUERYFRAME
78 :
79 : NS_IMETHOD Init(nsIContent* aContent,
80 : nsIFrame* aParent,
81 : nsIFrame* aPrevInFlow);
82 : virtual nscoord GetMinWidth(nsRenderingContext *aRenderingContext);
83 : virtual nscoord GetPrefWidth(nsRenderingContext *aRenderingContext);
84 : NS_IMETHOD Reflow(nsPresContext* aPresContext,
85 : nsHTMLReflowMetrics& aDesiredSize,
86 : const nsHTMLReflowState& aReflowState,
87 : nsReflowStatus& aStatus);
88 : NS_IMETHOD DidReflow(nsPresContext* aPresContext,
89 : const nsHTMLReflowState* aReflowState,
90 : nsDidReflowStatus aStatus);
91 : NS_IMETHOD BuildDisplayList(nsDisplayListBuilder* aBuilder,
92 : const nsRect& aDirtyRect,
93 : const nsDisplayListSet& aLists);
94 :
95 : NS_IMETHOD HandleEvent(nsPresContext* aPresContext,
96 : nsGUIEvent* aEvent,
97 : nsEventStatus* aEventStatus);
98 :
99 : #ifdef XP_MACOSX
100 : NS_IMETHOD HandlePress(nsPresContext* aPresContext,
101 : nsGUIEvent* aEvent,
102 : nsEventStatus* aEventStatus);
103 : #endif
104 :
105 : virtual nsIAtom* GetType() const;
106 :
107 0 : virtual bool IsFrameOfType(PRUint32 aFlags) const
108 : {
109 0 : return nsObjectFrameSuper::IsFrameOfType(aFlags & ~(nsIFrame::eReplaced));
110 : }
111 :
112 0 : virtual bool NeedsView() { return true; }
113 :
114 : #ifdef DEBUG
115 : NS_IMETHOD GetFrameName(nsAString& aResult) const;
116 : #endif
117 :
118 : virtual void DestroyFrom(nsIFrame* aDestructRoot);
119 :
120 : virtual void DidSetStyleContext(nsStyleContext* aOldStyleContext);
121 :
122 : NS_METHOD GetPluginInstance(nsNPAPIPluginInstance** aPluginInstance);
123 :
124 : virtual void SetIsDocumentActive(bool aIsActive);
125 :
126 : NS_IMETHOD GetCursor(const nsPoint& aPoint, nsIFrame::Cursor& aCursor);
127 :
128 : // Compute the desired position of the plugin's widget, on the assumption
129 : // that it is not visible (clipped out or covered by opaque content).
130 : // This will only be called for plugins which have been registered
131 : // with the root pres context for geometry updates.
132 : // The widget, its new position, size and (empty) clip region are appended
133 : // as a Configuration record to aConfigurations.
134 : // If there is no widget associated with the plugin, this
135 : // simply does nothing.
136 0 : void GetEmptyClipConfiguration(nsTArray<nsIWidget::Configuration>* aConfigurations) {
137 0 : ComputeWidgetGeometry(nsRegion(), nsPoint(0,0), aConfigurations);
138 0 : }
139 :
140 : void DidSetWidgetGeometry();
141 :
142 : // accessibility support
143 : #ifdef ACCESSIBILITY
144 : virtual already_AddRefed<nsAccessible> CreateAccessible();
145 : #ifdef XP_WIN
146 : NS_IMETHOD GetPluginPort(HWND *aPort);
147 : #endif
148 : #endif
149 :
150 : //local methods
151 : nsresult PrepForDrawing(nsIWidget *aWidget);
152 :
153 : // for a given aRoot, this walks the frame tree looking for the next outFrame
154 : static nsIObjectFrame* GetNextObjectFrame(nsPresContext* aPresContext,
155 : nsIFrame* aRoot);
156 :
157 : // nsIReflowCallback
158 : virtual bool ReflowFinished();
159 : virtual void ReflowCallbackCanceled();
160 :
161 : void UpdateImageLayer(const gfxRect& aRect);
162 :
163 : /**
164 : * Builds either an ImageLayer or a ReadbackLayer, depending on the type
165 : * of aItem (TYPE_PLUGIN or TYPE_PLUGIN_READBACK respectively).
166 : */
167 : already_AddRefed<Layer> BuildLayer(nsDisplayListBuilder* aBuilder,
168 : LayerManager* aManager,
169 : nsDisplayItem* aItem);
170 :
171 : virtual LayerState GetLayerState(nsDisplayListBuilder* aBuilder,
172 : LayerManager* aManager);
173 :
174 : already_AddRefed<ImageContainer> GetImageContainer();
175 : /**
176 : * Get the rectangle (relative to this frame) which it will paint. Normally
177 : * the frame's content-box but may be smaller if the plugin is rendering
178 : * asynchronously and has a different-sized image temporarily.
179 : */
180 : nsRect GetPaintedRect(nsDisplayPlugin* aItem);
181 :
182 : /**
183 : * If aContent has a nsObjectFrame, then prepare it for a DocShell swap.
184 : * @see nsSubDocumentFrame::BeginSwapDocShells.
185 : * There will be a call to EndSwapDocShells after we were moved to the
186 : * new view tree.
187 : */
188 : static void BeginSwapDocShells(nsIContent* aContent, void*);
189 : /**
190 : * If aContent has a nsObjectFrame, then set it up after a DocShell swap.
191 : * @see nsSubDocumentFrame::EndSwapDocShells.
192 : */
193 : static void EndSwapDocShells(nsIContent* aContent, void*);
194 :
195 : bool PaintedByGecko();
196 :
197 0 : nsIWidget* GetWidget() { return mWidget; }
198 :
199 : /**
200 : * Adjust the plugin's idea of its size, using aSize as its new size.
201 : * (aSize must be in twips)
202 : */
203 : void FixupWindow(const nsSize& aSize);
204 :
205 : /*
206 : * Sets up the plugin window and calls SetWindow on the plugin.
207 : */
208 : nsresult CallSetWindow(bool aCheckIsHidden = true);
209 :
210 : void SetInstanceOwner(nsPluginInstanceOwner* aOwner);
211 :
212 : protected:
213 : nsObjectFrame(nsStyleContext* aContext);
214 : virtual ~nsObjectFrame();
215 :
216 : // NOTE: This frame class does not inherit from |nsLeafFrame|, so
217 : // this is not a virtual method implementation.
218 : void GetDesiredSize(nsPresContext* aPresContext,
219 : const nsHTMLReflowState& aReflowState,
220 : nsHTMLReflowMetrics& aDesiredSize);
221 :
222 : bool IsFocusable(PRInt32 *aTabIndex = nsnull, bool aWithMouse = false);
223 :
224 : // check attributes and optionally CSS to see if we should display anything
225 : bool IsHidden(bool aCheckVisibilityStyle = true) const;
226 :
227 : bool IsOpaque() const;
228 : bool IsTransparentMode() const;
229 :
230 : nsIntPoint GetWindowOriginInPixels(bool aWindowless);
231 :
232 : static void PaintPrintPlugin(nsIFrame* aFrame,
233 : nsRenderingContext* aRenderingContext,
234 : const nsRect& aDirtyRect, nsPoint aPt);
235 : void PrintPlugin(nsRenderingContext& aRenderingContext,
236 : const nsRect& aDirtyRect);
237 : void PaintPlugin(nsDisplayListBuilder* aBuilder,
238 : nsRenderingContext& aRenderingContext,
239 : const nsRect& aDirtyRect, const nsRect& aPluginRect);
240 :
241 : /**
242 : * Get the widget geometry for the plugin. aRegion is in some appunits
243 : * coordinate system whose origin is device-pixel-aligned (if possible),
244 : * and aPluginOrigin gives the top-left of the plugin frame's content-rect
245 : * in that coordinate system. It doesn't matter what that coordinate
246 : * system actually is, as long as aRegion and aPluginOrigin are consistent.
247 : * This will append a Configuration object to aConfigurations
248 : * containing the widget, its desired position, size and clip region.
249 : */
250 : void ComputeWidgetGeometry(const nsRegion& aRegion,
251 : const nsPoint& aPluginOrigin,
252 : nsTArray<nsIWidget::Configuration>* aConfigurations);
253 :
254 : void NotifyPluginReflowObservers();
255 :
256 : friend class nsPluginInstanceOwner;
257 : friend class nsDisplayPlugin;
258 : friend class PluginBackgroundSink;
259 :
260 : private:
261 :
262 0 : class PluginEventNotifier : public nsRunnable {
263 : public:
264 0 : PluginEventNotifier(const nsString &aEventType) :
265 0 : mEventType(aEventType) {}
266 :
267 : NS_IMETHOD Run();
268 : private:
269 : nsString mEventType;
270 : };
271 :
272 : nsPluginInstanceOwner* mInstanceOwner; // WEAK
273 : nsIView* mInnerView;
274 : nsCOMPtr<nsIWidget> mWidget;
275 : nsIntRect mWindowlessRect;
276 : /**
277 : * This is owned by the ReadbackLayer for this nsObjectFrame. It is
278 : * automatically cleared if the PluginBackgroundSink is destroyed.
279 : */
280 : PluginBackgroundSink* mBackgroundSink;
281 :
282 : bool mReflowCallbackPosted;
283 :
284 : // A reference to the ImageContainer which contains the current frame
285 : // of plugin to display.
286 : nsRefPtr<ImageContainer> mImageContainer;
287 : };
288 :
289 : class nsDisplayPlugin : public nsDisplayItem {
290 : public:
291 0 : nsDisplayPlugin(nsDisplayListBuilder* aBuilder, nsIFrame* aFrame)
292 0 : : nsDisplayItem(aBuilder, aFrame)
293 : {
294 0 : MOZ_COUNT_CTOR(nsDisplayPlugin);
295 0 : }
296 : #ifdef NS_BUILD_REFCNT_LOGGING
297 0 : virtual ~nsDisplayPlugin() {
298 0 : MOZ_COUNT_DTOR(nsDisplayPlugin);
299 0 : }
300 : #endif
301 :
302 : virtual nsRect GetBounds(nsDisplayListBuilder* aBuilder);
303 : virtual nsRegion GetOpaqueRegion(nsDisplayListBuilder* aBuilder,
304 : bool* aForceTransparentSurface = nsnull);
305 : virtual void Paint(nsDisplayListBuilder* aBuilder,
306 : nsRenderingContext* aCtx);
307 : virtual bool ComputeVisibility(nsDisplayListBuilder* aBuilder,
308 : nsRegion* aVisibleRegion,
309 : const nsRect& aAllowVisibleRegionExpansion);
310 :
311 0 : NS_DISPLAY_DECL_NAME("Plugin", TYPE_PLUGIN)
312 :
313 : // Compute the desired position and clip region of the plugin's widget.
314 : // This will only be called for plugins which have been registered
315 : // with the root pres context for geometry updates.
316 : // The widget, its new position, size and clip region are appended as
317 : // a Configuration record to aConfigurations.
318 : // If the plugin has no widget, no configuration is added, but
319 : // the plugin visibility state may be adjusted.
320 : void GetWidgetConfiguration(nsDisplayListBuilder* aBuilder,
321 : nsTArray<nsIWidget::Configuration>* aConfigurations);
322 :
323 0 : virtual already_AddRefed<Layer> BuildLayer(nsDisplayListBuilder* aBuilder,
324 : LayerManager* aManager,
325 : const ContainerParameters& aContainerParameters)
326 : {
327 : return static_cast<nsObjectFrame*>(mFrame)->BuildLayer(aBuilder,
328 : aManager,
329 0 : this);
330 : }
331 :
332 0 : virtual LayerState GetLayerState(nsDisplayListBuilder* aBuilder,
333 : LayerManager* aManager)
334 : {
335 : return static_cast<nsObjectFrame*>(mFrame)->GetLayerState(aBuilder,
336 0 : aManager);
337 : }
338 :
339 : private:
340 : nsRegion mVisibleRegion;
341 : };
342 :
343 : #endif /* nsObjectFrame_h___ */
|