- add sources.
[platform/framework/web/crosswalk.git] / src / webkit / renderer / cpp_bound_class.h
1 // Copyright (c) 2012 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 /*
6   CppBoundClass class:
7   This base class serves as a parent for C++ classes designed to be bound to
8   JavaScript objects.
9
10   Subclasses should define the constructor to build the property and method
11   lists needed to bind this class to a JS object.  They should also declare
12   and define member variables and methods to be exposed to JS through
13   that object.
14
15   See cpp_binding_example.{h|cc} for an example.
16 */
17
18 #ifndef WEBKIT_RENDERER_CPP_BOUND_CLASS_H_
19 #define WEBKIT_RENDERER_CPP_BOUND_CLASS_H_
20
21 #include <map>
22 #include <vector>
23
24 #include "base/callback.h"
25 #include "webkit/renderer/cpp_variant.h"
26 #include "webkit/renderer/webkit_renderer_export.h"
27
28 namespace WebKit {
29 class WebFrame;
30 }
31
32 namespace webkit_glue {
33
34 typedef std::vector<CppVariant> CppArgumentList;
35
36 // CppBoundClass lets you map Javascript method calls and property accesses
37 // directly to C++ method calls and CppVariant* variable access.
38 class WEBKIT_RENDERER_EXPORT CppBoundClass {
39  public:
40   class PropertyCallback {
41    public:
42     virtual ~PropertyCallback() { }
43
44     // Sets |value| to the value of the property. Returns false in case of
45     // failure. |value| is always non-NULL.
46     virtual bool GetValue(CppVariant* value) = 0;
47
48     // sets the property value to |value|. Returns false in case of failure.
49     virtual bool SetValue(const CppVariant& value) = 0;
50   };
51
52   // The constructor should call BindCallback, BindProperty, and
53   // BindFallbackCallback as needed to set up the methods, properties, and
54   // fallback method.
55   CppBoundClass();
56   virtual ~CppBoundClass();
57
58   // Return a CppVariant representing this class, for use with BindProperty().
59   // The variant type is guaranteed to be NPVariantType_Object.
60   CppVariant* GetAsCppVariant();
61
62   // Given a WebFrame, BindToJavascript builds the NPObject that will represent
63   // this CppBoundClass object and binds it to the frame's window under the
64   // given name.  This should generally be called from the WebView delegate's
65   // WindowObjectCleared(). This CppBoundClass object will be accessible to
66   // JavaScript as window.<classname>. The owner of this CppBoundClass object is
67   // responsible for keeping it around while the frame is alive, and for
68   // destroying it afterwards.
69   void BindToJavascript(WebKit::WebFrame* frame, const std::string& classname);
70
71   // The type of callbacks.
72   typedef base::Callback<void(const CppArgumentList&, CppVariant*)> Callback;
73   typedef base::Callback<void(CppVariant*)> GetterCallback;
74
75   // Used by a test.  Returns true if a method with name |name| exists,
76   // regardless of whether a fallback is registered.
77   bool IsMethodRegistered(const std::string& name) const;
78
79  protected:
80   // Bind the Javascript method called |name| to the C++ callback |callback|.
81   void BindCallback(const std::string& name, const Callback& callback);
82
83   // Bind Javascript property |name| to the C++ getter callback |callback|.
84   // This can be used to create read-only properties.
85   void BindGetterCallback(const std::string& name,
86                           const GetterCallback& callback);
87
88   // Bind the Javascript property called |name| to a CppVariant |prop|.
89   void BindProperty(const std::string& name, CppVariant* prop);
90
91   // Bind Javascript property called |name| to a PropertyCallback |callback|.
92   // CppBoundClass assumes control over the life time of the |callback|.
93   void BindProperty(const std::string& name, PropertyCallback* callback);
94
95   // Set the fallback callback, which is called when when a callback is
96   // invoked that isn't bound.
97   // If it is NULL (its default value), a JavaScript exception is thrown in
98   // that case (as normally expected). If non NULL, the fallback method is
99   // invoked and the script continues its execution.
100   // Passing NULL for |callback| clears out any existing binding.
101   // It is used for tests and should probably only be used in such cases
102   // as it may cause unexpected behaviors (a JavaScript object with a
103   // fallback always returns true when checked for a method's
104   // existence).
105   void BindFallbackCallback(const Callback& fallback_callback) {
106     fallback_callback_ = fallback_callback;
107   }
108
109   // Some fields are protected because some tests depend on accessing them,
110   // but otherwise they should be considered private.
111
112   typedef std::map<NPIdentifier, PropertyCallback*> PropertyList;
113   typedef std::map<NPIdentifier, Callback> MethodList;
114   // These maps associate names with property and method pointers to be
115   // exposed to JavaScript.
116   PropertyList properties_;
117   MethodList methods_;
118
119   // The callback gets invoked when a call is made to an nonexistent method.
120   Callback fallback_callback_;
121
122  private:
123   // NPObject callbacks.
124   friend struct CppNPObject;
125   bool HasMethod(NPIdentifier ident) const;
126   bool Invoke(NPIdentifier ident, const NPVariant* args, size_t arg_count,
127               NPVariant* result);
128   bool HasProperty(NPIdentifier ident) const;
129   bool GetProperty(NPIdentifier ident, NPVariant* result) const;
130   bool SetProperty(NPIdentifier ident, const NPVariant* value);
131
132   // A lazily-initialized CppVariant representing this class.  We retain 1
133   // reference to this object, and it is released on deletion.
134   CppVariant self_variant_;
135
136   // TODO(wez): Remove once crrev.com/14019005 lands.
137   bool bound_to_frame_;
138
139   // Dummy NPP to use to register as owner for NPObjects.
140   scoped_ptr<NPP_t> npp_;
141
142   DISALLOW_COPY_AND_ASSIGN(CppBoundClass);
143 };
144
145 }  // namespace webkit_glue
146
147 #endif  // WEBKIT_RENDERER_CPP_BOUND_CLASS_H_