1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/layout/generic/nsQueryFrame.h Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,96 @@ 1.4 +/* This Source Code Form is subject to the terms of the Mozilla Public 1.5 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.6 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.7 + 1.8 +#ifndef nsQueryFrame_h 1.9 +#define nsQueryFrame_h 1.10 + 1.11 +#include "nscore.h" 1.12 +#include "mozilla/Assertions.h" 1.13 +#include "mozilla/TypeTraits.h" 1.14 + 1.15 +// NOTE: the long lines in this file are intentional to make compiler error 1.16 +// messages more readable. 1.17 + 1.18 +#define NS_DECL_QUERYFRAME_TARGET(classname) \ 1.19 + static const nsQueryFrame::FrameIID kFrameIID = nsQueryFrame::classname##_id; \ 1.20 + typedef classname Has_NS_DECL_QUERYFRAME_TARGET; 1.21 + 1.22 +#define NS_DECL_QUERYFRAME \ 1.23 + virtual void* QueryFrame(FrameIID id); 1.24 + 1.25 +#define NS_QUERYFRAME_HEAD(class) \ 1.26 + void* class::QueryFrame(FrameIID id) { switch (id) { 1.27 + 1.28 +#define NS_QUERYFRAME_ENTRY(class) \ 1.29 + case class::kFrameIID: { \ 1.30 + static_assert(mozilla::IsSame<class, class::Has_NS_DECL_QUERYFRAME_TARGET>::value, \ 1.31 + #class " must declare itself as a queryframe target"); \ 1.32 + return static_cast<class*>(this); \ 1.33 + } 1.34 + 1.35 +#define NS_QUERYFRAME_ENTRY_CONDITIONAL(class, condition) \ 1.36 + case class::kFrameIID: \ 1.37 + if (condition) { \ 1.38 + static_assert(mozilla::IsSame<class, class::Has_NS_DECL_QUERYFRAME_TARGET>::value, \ 1.39 + #class " must declare itself as a queryframe target"); \ 1.40 + return static_cast<class*>(this); \ 1.41 + } \ 1.42 + break; 1.43 + 1.44 +#define NS_QUERYFRAME_TAIL_INHERITING(class) \ 1.45 + default: break; \ 1.46 + } \ 1.47 + return class::QueryFrame(id); \ 1.48 +} 1.49 + 1.50 +#define NS_QUERYFRAME_TAIL_INHERITANCE_ROOT \ 1.51 + default: break; \ 1.52 + } \ 1.53 + MOZ_ASSERT(id != GetFrameId(), \ 1.54 + "A frame failed to QueryFrame to its *own type*. " \ 1.55 + "It may be missing NS_DECL_QUERYFRAME, or a " \ 1.56 + "NS_QUERYFRAME_ENTRY() line with its own type name"); \ 1.57 + return nullptr; \ 1.58 +} 1.59 + 1.60 +class nsQueryFrame 1.61 +{ 1.62 +public: 1.63 + enum FrameIID { 1.64 +#define FRAME_ID(classname) classname##_id, 1.65 +#include "nsFrameIdList.h" 1.66 +#undef FRAME_ID 1.67 + 1.68 + // The PresArena implementation uses this bit to distinguish objects 1.69 + // allocated by size from objects allocated by type ID (that is, frames 1.70 + // using AllocateByFrameID, and other objects using AllocateByObjectID). 1.71 + // It should not collide with any frame ID (above) or Object ID (in 1.72 + // nsPresArena.h). It is not 0x80000000 to avoid the question of 1.73 + // whether enumeration constants are signed. 1.74 + NON_FRAME_MARKER = 0x20000000 1.75 + }; 1.76 + 1.77 + virtual void* QueryFrame(FrameIID id) = 0; 1.78 +}; 1.79 + 1.80 +class do_QueryFrame 1.81 +{ 1.82 +public: 1.83 + do_QueryFrame(nsQueryFrame *s) : mRawPtr(s) { } 1.84 + 1.85 + template<class Dest> 1.86 + operator Dest*() { 1.87 + static_assert(mozilla::IsSame<Dest, typename Dest::Has_NS_DECL_QUERYFRAME_TARGET>::value, 1.88 + "Dest must declare itself as a queryframe target"); 1.89 + if (!mRawPtr) 1.90 + return nullptr; 1.91 + 1.92 + return reinterpret_cast<Dest*>(mRawPtr->QueryFrame(Dest::kFrameIID)); 1.93 + } 1.94 + 1.95 +private: 1.96 + nsQueryFrame *mRawPtr; 1.97 +}; 1.98 + 1.99 +#endif // nsQueryFrame_h