Diff
Modified: trunk/Source/WebCore/ChangeLog (200606 => 200607)
--- trunk/Source/WebCore/ChangeLog 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/ChangeLog 2016-05-10 02:31:03 UTC (rev 200607)
@@ -1,3 +1,70 @@
+2016-05-09 Darin Adler <da...@apple.com>
+
+ Change Notification constructor to take an IDL dictionary instead of a WebCore::Dictionary
+ https://bugs.webkit.org/show_bug.cgi?id=157466
+
+ Reviewed by Alex Christensen.
+
+ * Modules/notifications/Notification.cpp: Got rid of unneeded includes.
+ (WebCore::Notification::Notification): Deleted the unused default constructor. Changed
+ NotificationCenter argument to be reference rather than PassRefPtr. Changed one of the
+ ScriptExecutionContext arguments to be a Document since the code relies on that already.
+ Used the lambda form of timer creation instead of the class member form. Added a FIXME
+ about when m_notificationCenter can be null.
+ (WebCore::Notification::create): Changed NotificationCenter argument to be reference
+ rather than PassRefPtr. Changed options argument to be Options rather than Dictionary.
+ (WebCore::directionString): Added. Helper because the class still wants to store the
+ direction as a string, at least for now.
+ (WebCore::Notification::show): Streamlined the code a bit.
+ (WebCore::Notification::taskTimerFired): Deleted. Not needed now that we use a lambda
+ inside the constructor.
+ (WebCore::Notification::permission): Removed unneeded const from return type.
+ (WebCore::Notification::permissionString): Ditto.
+
+ * Modules/notifications/Notification.h: Used pragma once, updated for changes above.
+ Removed a number of unused functions, including cancel, setIconURL, setLang,
+ stopLoadingIcon, detachPresenter, setBody, startLoadingIcon, finishLoadingIcon, and
+ taskTimerFired.
+
+ * Modules/notifications/Notification.idl: Add NotificationOptions and pass it instead
+ of Dictionary to the constructor. Note that this is only a subset of what is
+ currently specified in the Notifications API document. The latest document specifies
+ a much more complex feature with lots more options.
+
+ * Modules/notifications/NotificationCenter.cpp:
+ (WebCore::NotificationCenter::createNotification): Pass a reference rather than a
+ pointer to this.
+ * Modules/notifications/NotificationClient.h: Use pragma once. Removed unneeded
+ includes and forward declarations. Fixed #if to be easier to read.
+
+ * bindings/js/JSDOMConvert.h: Reworked the convert functions to use Converter and
+ DefaultConverter structs so we can do partial specialization in the future and so
+ we can get custom types for optional values. Used this to make an optional String
+ just be a null String, so it won't try to use Optional<String> instead. Might get
+ more complex latter when we add support for nullable.
+
+ * bindings/scripts/CodeGeneratorJS.pm:
+ (GenerateEnumerationImplementationContent): Generate a blank line to make the output
+ slightly clearer. Tweaked a comment.
+ (GenerateDefaultValue): Added. Converts the default syntax from IDL into the syntax
+ needed in C++ code.
+ (GenerateDefaultValueWithLeadingComma): Added. Helper for use below.
+ (GenerateDictionaryImplementationContent): Use GenerateDefaultValue and
+ GenerateDefaultValueWithLeadingComma to make default values.
+ (GenerateParametersCheck): Use GenerateDefaultValue here in the enumeration code
+ path. This is a step in the direction of being able to make the whole thing more
+ generic in the future.
+
+ * bindings/scripts/test/GObject/WebKitDOMTestObj.cpp:
+ * bindings/scripts/test/GObject/WebKitDOMTestObj.h:
+ * bindings/scripts/test/JS/JSTestObj.cpp:
+ * bindings/scripts/test/ObjC/DOMTestObj.h:
+ * bindings/scripts/test/ObjC/DOMTestObj.mm:
+ Regenerated.
+
+ * bindings/scripts/test/TestObj.idl: Simplified and extended some of the test cases
+ to cover more combinations of the dictionary and enumeration support.
+
2016-05-09 Brady Eidson <beid...@apple.com>
Modern IDB: Have server database connections remember the OpenDB request that spawned them.
Modified: trunk/Source/WebCore/Modules/notifications/Notification.cpp (200606 => 200607)
--- trunk/Source/WebCore/Modules/notifications/Notification.cpp 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/Modules/notifications/Notification.cpp 2016-05-10 02:31:03 UTC (rev 200607)
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2009 Google Inc. All rights reserved.
- * Copyright (C) 2009, 2011, 2012 Apple Inc. All rights reserved.
+ * Copyright (C) 2009, 2011, 2012, 2016 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -37,34 +37,24 @@
#include "DOMWindow.h"
#include "DOMWindowNotifications.h"
-#include "Dictionary.h"
#include "Document.h"
-#include "ErrorEvent.h"
+#include "Event.h"
#include "EventNames.h"
#include "NotificationCenter.h"
-#include "NotificationClient.h"
#include "NotificationController.h"
#include "NotificationPermissionCallback.h"
-#include "ResourceRequest.h"
-#include "ResourceResponse.h"
-#include "ThreadableLoader.h"
+#include "VoidCallback.h"
#include "WindowFocusAllowedIndicator.h"
-#include "WorkerGlobalScope.h"
namespace WebCore {
-Notification::Notification()
- : ActiveDOMObject(nullptr)
-{
-}
+#if ENABLE(LEGACY_NOTIFICATIONS)
-#if ENABLE(LEGACY_NOTIFICATIONS)
-Notification::Notification(const String& title, const String& body, const String& iconURI, ScriptExecutionContext& context, ExceptionCode& ec, PassRefPtr<NotificationCenter> provider)
+Notification::Notification(const String& title, const String& body, const String& iconURI, ScriptExecutionContext& context, ExceptionCode& ec, NotificationCenter& notificationCenter)
: ActiveDOMObject(&context)
, m_title(title)
, m_body(body)
- , m_state(Idle)
- , m_notificationCenter(provider)
+ , m_notificationCenter(¬ificationCenter)
{
if (m_notificationCenter->checkPermission() != NotificationClient::PermissionAllowed) {
ec = SECURITY_ERR;
@@ -77,20 +67,24 @@
return;
}
}
+
#endif
#if ENABLE(NOTIFICATIONS)
-Notification::Notification(ScriptExecutionContext& context, const String& title)
- : ActiveDOMObject(&context)
+
+Notification::Notification(Document& document, const String& title)
+ : ActiveDOMObject(&document)
, m_title(title)
, m_state(Idle)
- , m_taskTimer(std::make_unique<Timer>(*this, &Notification::taskTimerFired))
+ , m_notificationCenter(DOMWindowNotifications::webkitNotifications(*document.domWindow()))
+ , m_taskTimer(std::make_unique<Timer>([this] () { show(); }))
{
- m_notificationCenter = DOMWindowNotifications::webkitNotifications(*downcast<Document>(context).domWindow());
-
+ // FIXME: Seems that m_notificationCenter can be null so should not be changed from RefPtr to Ref.
+ // But the rest of the code in this class isn't trying to handle that case.
ASSERT(m_notificationCenter->client());
m_taskTimer->startOneShot(0);
}
+
#endif
Notification::~Notification()
@@ -98,36 +92,50 @@
}
#if ENABLE(LEGACY_NOTIFICATIONS)
-Ref<Notification> Notification::create(const String& title, const String& body, const String& iconURI, ScriptExecutionContext& context, ExceptionCode& ec, PassRefPtr<NotificationCenter> provider)
+
+Ref<Notification> Notification::create(const String& title, const String& body, const String& iconURI, ScriptExecutionContext& context, ExceptionCode& ec, NotificationCenter& provider)
{
auto notification = adoptRef(*new Notification(title, body, iconURI, context, ec, provider));
notification.get().suspendIfNeeded();
return notification;
}
+
#endif
#if ENABLE(NOTIFICATIONS)
-Ref<Notification> Notification::create(Document& context, const String& title, const Dictionary& options)
+
+static String directionString(Notification::Direction direction)
{
+ // FIXME: Storing this as a string is not the right way to do it.
+ // FIXME: Seems highly unlikely that this does the right thing for Auto.
+ switch (direction) {
+ case Notification::Direction::Auto:
+ return ASCIILiteral("auto");
+ case Notification::Direction::Ltr:
+ return ASCIILiteral("ltr");
+ case Notification::Direction::Rtl:
+ return ASCIILiteral("rtl");
+ }
+ ASSERT_NOT_REACHED();
+ return { };
+}
+
+Ref<Notification> Notification::create(Document& context, const String& title, const Options& options)
+{
auto notification = adoptRef(*new Notification(context, title));
- String argument;
- if (options.get("body", argument))
- notification.get().setBody(argument);
- if (options.get("tag", argument))
- notification.get().setTag(argument);
- if (options.get("lang", argument))
- notification.get().setLang(argument);
- if (options.get("dir", argument))
- notification.get().setDir(argument);
- if (options.get("icon", argument)) {
- URL iconURI = argument.isEmpty() ? URL() : context.completeURL(argument);
- if (!iconURI.isEmpty() && iconURI.isValid())
- notification.get().setIconURL(iconURI);
+ notification.get().m_body = options.body;
+ notification.get().m_tag = options.tag;
+ notification.get().m_lang = options.lang;
+ notification.get().m_direction = directionString(options.dir);
+ if (!options.icon.isEmpty()) {
+ auto iconURL = context.completeURL(options.icon);
+ if (iconURL.isValid())
+ notification.get().m_icon = iconURL;
}
-
notification.get().suspendIfNeeded();
return notification;
}
+
#endif
void Notification::show()
@@ -135,9 +143,10 @@
// prevent double-showing
if (m_state == Idle && m_notificationCenter->client()) {
#if ENABLE(NOTIFICATIONS)
- if (!downcast<Document>(*scriptExecutionContext()).page())
+ auto* page = downcast<Document>(*scriptExecutionContext()).page();
+ if (!page)
return;
- if (NotificationController::from(downcast<Document>(*scriptExecutionContext()).page())->client()->checkPermission(scriptExecutionContext()) != NotificationClient::PermissionAllowed) {
+ if (NotificationController::from(page)->client()->checkPermission(scriptExecutionContext()) != NotificationClient::PermissionAllowed) {
dispatchErrorEvent();
return;
}
@@ -212,21 +221,13 @@
}
#if ENABLE(NOTIFICATIONS)
-void Notification::taskTimerFired()
-{
- ASSERT(scriptExecutionContext()->isDocument());
- show();
-}
-#endif
-
-#if ENABLE(NOTIFICATIONS)
-const String Notification::permission(Document& document)
+String Notification::permission(Document& document)
{
return permissionString(NotificationController::from(document.page())->client()->checkPermission(&document));
}
-const String Notification::permissionString(NotificationClient::Permission permission)
+String Notification::permissionString(NotificationClient::Permission permission)
{
switch (permission) {
case NotificationClient::PermissionAllowed:
@@ -236,15 +237,15 @@
case NotificationClient::PermissionNotAllowed:
return ASCIILiteral("default");
}
-
ASSERT_NOT_REACHED();
- return String();
+ return { };
}
void Notification::requestPermission(Document& document, RefPtr<NotificationPermissionCallback>&& callback)
{
NotificationController::from(document.page())->client()->requestPermission(&document, WTFMove(callback));
}
+
#endif
} // namespace WebCore
Modified: trunk/Source/WebCore/Modules/notifications/Notification.h (200606 => 200607)
--- trunk/Source/WebCore/Modules/notifications/Notification.h 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/Modules/notifications/Notification.h 2016-05-10 02:31:03 UTC (rev 200607)
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2009 Google Inc. All rights reserved.
- * Copyright (C) 2009, 2011, 2012 Apple Inc. All rights reserved.
+ * Copyright (C) 2009, 2011, 2012, 2016 Apple Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -29,131 +29,106 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef Notification_h
-#define Notification_h
+#pragma once
+#if ENABLE(NOTIFICATIONS) || ENABLE(LEGACY_NOTIFICATIONS)
+
#include "ActiveDOMObject.h"
-#include "EventNames.h"
#include "EventTarget.h"
#include "NotificationClient.h"
-#include "ThreadableLoaderClient.h"
#include "URL.h"
#include "WritingMode.h"
-#include <wtf/PassRefPtr.h>
-#include <wtf/RefCounted.h>
-#include <wtf/RefPtr.h>
-#include <wtf/text/AtomicStringHash.h>
#if ENABLE(NOTIFICATIONS)
#include "Timer.h"
#endif
-#if ENABLE(NOTIFICATIONS) || ENABLE(LEGACY_NOTIFICATIONS)
namespace WebCore {
-class Dictionary;
class Document;
class NotificationCenter;
class NotificationPermissionCallback;
-class ResourceError;
-class ResourceResponse;
-class ThreadableLoader;
typedef int ExceptionCode;
class Notification final : public RefCounted<Notification>, public ActiveDOMObject, public EventTargetWithInlineData {
WTF_MAKE_FAST_ALLOCATED;
public:
- WEBCORE_EXPORT Notification();
#if ENABLE(LEGACY_NOTIFICATIONS)
- static Ref<Notification> create(const String& title, const String& body, const String& iconURI, ScriptExecutionContext&, ExceptionCode&, PassRefPtr<NotificationCenter> provider);
+ static Ref<Notification> create(const String& title, const String& body, const String& iconURL, ScriptExecutionContext&, ExceptionCode&, NotificationCenter&);
#endif
+
#if ENABLE(NOTIFICATIONS)
- static Ref<Notification> create(Document&, const String& title, const Dictionary& options);
+ enum class Direction { Auto, Ltr, Rtl };
+ struct Options {
+ Direction dir;
+ String lang;
+ String body;
+ String tag;
+ String icon;
+ };
+ static Ref<Notification> create(Document&, const String& title, const Options&);
#endif
- WEBCORE_EXPORT virtual ~Notification();
+ virtual ~Notification();
void show();
-#if ENABLE(LEGACY_NOTIFICATIONS)
- void cancel() { close(); }
-#endif
void close();
- URL iconURL() const { return m_icon; }
- void setIconURL(const URL& url) { m_icon = url; }
+ const URL& iconURL() const { return m_icon; }
+ const String& title() const { return m_title; }
+ const String& body() const { return m_body; }
+ const String& lang() const { return m_lang; }
- String title() const { return m_title; }
- String body() const { return m_body; }
-
- String lang() const { return m_lang; }
- void setLang(const String& lang) { m_lang = lang; }
-
- String dir() const { return m_direction; }
+#if ENABLE(LEGACY_NOTIFICATIONS)
+ const String& dir() const { return m_direction; }
void setDir(const String& dir) { m_direction = dir; }
-#if ENABLE(LEGACY_NOTIFICATIONS)
- String replaceId() const { return tag(); }
- void setReplaceId(const String& replaceId) { setTag(replaceId); }
+ const String& replaceId() const { return m_tag; }
+ void setReplaceId(const String& replaceId) { m_tag = replaceId; }
#endif
- String tag() const { return m_tag; }
+ const String& tag() const { return m_tag; }
void setTag(const String& tag) { m_tag = tag; }
- TextDirection direction() const { return dir() == "rtl" ? RTL : LTR; }
+ TextDirection direction() const { return m_direction == "rtl" ? RTL : LTR; }
WEBCORE_EXPORT void dispatchClickEvent();
WEBCORE_EXPORT void dispatchCloseEvent();
WEBCORE_EXPORT void dispatchErrorEvent();
WEBCORE_EXPORT void dispatchShowEvent();
- using RefCounted<Notification>::ref;
- using RefCounted<Notification>::deref;
-
- // EventTarget interface
- EventTargetInterface eventTargetInterface() const override { return NotificationEventTargetInterfaceType; }
- ScriptExecutionContext* scriptExecutionContext() const override { return ActiveDOMObject::scriptExecutionContext(); }
-
- void stopLoadingIcon();
-
- // Deprecated. Use functions from NotificationCenter.
- void detachPresenter() { }
-
WEBCORE_EXPORT void finalize();
#if ENABLE(NOTIFICATIONS)
- static const String permission(Document&);
- WEBCORE_EXPORT static const String permissionString(NotificationClient::Permission);
+ static String permission(Document&);
+ WEBCORE_EXPORT static String permissionString(NotificationClient::Permission);
static void requestPermission(Document&, RefPtr<NotificationPermissionCallback>&&);
#endif
+ ScriptExecutionContext* scriptExecutionContext() const final { return ActiveDOMObject::scriptExecutionContext(); }
+
+ using RefCounted::ref;
+ using RefCounted::deref;
+
private:
#if ENABLE(LEGACY_NOTIFICATIONS)
- Notification(const String& title, const String& body, const String& iconURI, ScriptExecutionContext&, ExceptionCode&, PassRefPtr<NotificationCenter>);
+ Notification(const String& title, const String& body, const String& iconURL, ScriptExecutionContext&, ExceptionCode&, NotificationCenter&);
#endif
+
#if ENABLE(NOTIFICATIONS)
- Notification(ScriptExecutionContext&, const String& title);
+ Notification(Document&, const String& title);
#endif
- void setBody(const String& body) { m_body = body; }
+ EventTargetInterface eventTargetInterface() const final { return NotificationEventTargetInterfaceType; }
- // ActiveDOMObject API.
- void contextDestroyed() override;
- const char* activeDOMObjectName() const override;
- bool canSuspendForDocumentSuspension() const override;
+ void contextDestroyed() final;
+ const char* activeDOMObjectName() const final;
+ bool canSuspendForDocumentSuspension() const final;
- // EventTarget API.
- void refEventTarget() override { ref(); }
- void derefEventTarget() override { deref(); }
+ void refEventTarget() final { ref(); }
+ void derefEventTarget() final { deref(); }
- void startLoadingIcon();
- void finishLoadingIcon();
-
-#if ENABLE(NOTIFICATIONS)
- void taskTimerFired();
-#endif
-
- // Text notifications.
URL m_icon;
String m_title;
String m_body;
@@ -161,14 +136,9 @@
String m_lang;
String m_tag;
- enum NotificationState {
- Idle = 0,
- Showing = 1,
- Closed = 2,
- };
+ enum State { Idle, Showing, Closed };
+ State m_state { Idle };
- NotificationState m_state;
-
RefPtr<NotificationCenter> m_notificationCenter;
#if ENABLE(NOTIFICATIONS)
@@ -179,5 +149,3 @@
} // namespace WebCore
#endif // ENABLE(NOTIFICATIONS) || ENABLE(LEGACY_NOTIFICATIONS)
-
-#endif // Notifications_h
Modified: trunk/Source/WebCore/Modules/notifications/Notification.idl (200606 => 200607)
--- trunk/Source/WebCore/Modules/notifications/Notification.idl 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/Modules/notifications/Notification.idl 2016-05-10 02:31:03 UTC (rev 200607)
@@ -34,12 +34,12 @@
ActiveDOMObject,
ExportMacro=WEBCORE_EXPORT,
#if defined(ENABLE_NOTIFICATIONS) && ENABLE_NOTIFICATIONS
- Constructor(DOMString title, optional Dictionary options),
+ Constructor(DOMString title, optional NotificationOptions options),
ConstructorCallWith=Document,
#endif
] interface Notification : EventTarget {
void show();
- [Conditional=LEGACY_NOTIFICATIONS] void cancel();
+ [Conditional=LEGACY_NOTIFICATIONS, ImplementedAs=close] void cancel();
[Conditional=NOTIFICATIONS] void close();
[Conditional=NOTIFICATIONS, CallWith=Document] static readonly attribute DOMString permission;
@@ -53,6 +53,16 @@
[Conditional=LEGACY_NOTIFICATIONS] attribute DOMString dir;
[Conditional=LEGACY_NOTIFICATIONS] attribute DOMString replaceId;
+
[Conditional=NOTIFICATIONS] attribute DOMString tag;
};
+[Conditional=NOTIFICATIONS] enum NotificationDirection { "auto", "ltr", "rtl" };
+
+[Conditional=NOTIFICATIONS] dictionary NotificationOptions {
+ NotificationDirection dir = "auto";
+ DOMString lang = "";
+ DOMString body = "";
+ DOMString tag = "";
+ DOMString icon;
+};
Modified: trunk/Source/WebCore/Modules/notifications/NotificationCenter.cpp (200606 => 200607)
--- trunk/Source/WebCore/Modules/notifications/NotificationCenter.cpp 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/Modules/notifications/NotificationCenter.cpp 2016-05-10 02:31:03 UTC (rev 200607)
@@ -38,6 +38,7 @@
#include "Notification.h"
#include "ScriptExecutionContext.h"
#include "SecurityOrigin.h"
+#include "VoidCallback.h"
namespace WebCore {
@@ -63,7 +64,7 @@
ec = INVALID_STATE_ERR;
return nullptr;
}
- return Notification::create(title, body, iconURI, *scriptExecutionContext(), ec, this);
+ return Notification::create(title, body, iconURI, *scriptExecutionContext(), ec, *this);
}
int NotificationCenter::checkPermission()
Modified: trunk/Source/WebCore/Modules/notifications/NotificationClient.h (200606 => 200607)
--- trunk/Source/WebCore/Modules/notifications/NotificationClient.h 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/Modules/notifications/NotificationClient.h 2016-05-10 02:31:03 UTC (rev 200607)
@@ -29,23 +29,19 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#ifndef NotificationClient_h
-#define NotificationClient_h
+#pragma once
-#include "NotificationPermissionCallback.h"
-#include "VoidCallback.h"
-#include <wtf/PassRefPtr.h>
+#include <wtf/Forward.h>
namespace WebCore {
-class Document;
-class URL;
class Notification;
+class NotificationPermissionCallback;
class Page;
class ScriptExecutionContext;
+class VoidCallback;
class NotificationClient {
-
public:
enum Permission {
PermissionAllowed, // User has allowed notifications
@@ -71,10 +67,10 @@
// Informs the presenter the controller attached to the page has been destroyed.
virtual void notificationControllerDestroyed() = 0;
-#if ENABLE(LEGACY_NOTIFICATIONS)
// Requests user permission to show desktop notifications from a particular
// script context. The callback parameter should be run when the user has
// made a decision.
+#if ENABLE(LEGACY_NOTIFICATIONS)
virtual void requestPermission(ScriptExecutionContext*, RefPtr<VoidCallback>&&) = 0;
#endif
#if ENABLE(NOTIFICATIONS)
@@ -96,5 +92,3 @@
WEBCORE_EXPORT void provideNotification(Page*, NotificationClient*);
} // namespace WebCore
-
-#endif // NotificationClient_h
Modified: trunk/Source/WebCore/bindings/js/JSDOMConvert.h (200606 => 200607)
--- trunk/Source/WebCore/bindings/js/JSDOMConvert.h 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/js/JSDOMConvert.h 2016-05-10 02:31:03 UTC (rev 200607)
@@ -32,156 +32,200 @@
enum class ShouldAllowNonFinite { No, Yes };
+template<typename T> struct Converter;
+
template<typename T> T convert(JSC::ExecState&, JSC::JSValue);
+template<typename T> T convert(JSC::ExecState&, JSC::JSValue, IntegerConversionConfiguration);
template<typename T> T convert(JSC::ExecState&, JSC::JSValue, ShouldAllowNonFinite);
-template<typename T> T convert(JSC::ExecState&, JSC::JSValue, IntegerConversionConfiguration);
-template<typename T> Optional<T> convertOptional(JSC::ExecState&, JSC::JSValue);
+template<typename T> typename Converter<T>::OptionalValue convertOptional(JSC::ExecState&, JSC::JSValue);
template<typename T, typename U> T convertOptional(JSC::ExecState&, JSC::JSValue, U&& defaultValue);
-template<typename T> Optional<T> inline convertOptional(JSC::ExecState& state, JSC::JSValue value)
-{
- return value.isUndefined() ? Optional<T>() : convert<T>(state, value);
-}
+// This is where the implementation of the things declared above begins:
-template<typename T, typename U> inline T convertOptional(JSC::ExecState& state, JSC::JSValue value, U&& defaultValue)
+template<typename T> T convert(JSC::ExecState& state, JSC::JSValue value)
{
- return value.isUndefined() ? std::forward<U>(defaultValue) : convert<T>(state, value);
+ return Converter<T>::convert(state, value);
}
-template<> inline bool convert<bool>(JSC::ExecState& state, JSC::JSValue value)
+template<typename T> T convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
{
- return value.toBoolean(&state);
+ return Converter<T>::convert(state, value, configuration);
}
-template<> inline String convert<String>(JSC::ExecState& state, JSC::JSValue value)
+template<typename T> inline T convert(JSC::ExecState& state, JSC::JSValue value, ShouldAllowNonFinite allow)
{
- return value.toWTFString(&state);
-}
-
-template<typename T> inline T convert(JSC::ExecState& state, JSC::JSValue value, ShouldAllowNonFinite allowNonFinite)
-{
- static_assert(std::is_same<T, float>::value || std::is_same<T, double>::value, "Should be called with converting to float or double");
+ static_assert(std::is_same<T, float>::value || std::is_same<T, double>::value, "ShouldAllowNonFinite can only be used with float or double");
double number = value.toNumber(&state);
- if (allowNonFinite == ShouldAllowNonFinite::No && UNLIKELY(!std::isfinite(number)))
+ if (allow == ShouldAllowNonFinite::No && UNLIKELY(!std::isfinite(number)))
throwNonFiniteTypeError(state);
return static_cast<T>(number);
}
-template<> inline Vector<String> convert<Vector<String>>(JSC::ExecState& state, JSC::JSValue value)
+template<typename T> typename Converter<T>::OptionalValue inline convertOptional(JSC::ExecState& state, JSC::JSValue value)
{
- // FIXME: The toNativeArray function doesn't throw a type error if the value is not an object. Is that really OK?
- return toNativeArray<String>(&state, value);
+ return value.isUndefined() ? typename Converter<T>::OptionalValue() : convert<T>(state, value);
}
-template<> inline int8_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+template<typename T, typename U> inline T convertOptional(JSC::ExecState& state, JSC::JSValue value, U&& defaultValue)
{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toInt8EnforceRange(state, value);
- case Clamp:
- return toInt8Clamp(state, value);
- }
- return toInt8(state, value);
+ return value.isUndefined() ? std::forward<U>(defaultValue) : convert<T>(state, value);
}
-template<> inline uint8_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toUInt8EnforceRange(state, value);
- case Clamp:
- return toUInt8Clamp(state, value);
+template<typename T> struct DefaultConverter {
+ using OptionalValue = Optional<T>;
+};
+
+template<typename T> struct Converter : DefaultConverter<T> {
+};
+
+template<> struct Converter<bool> : DefaultConverter<bool> {
+ static bool convert(JSC::ExecState& state, JSC::JSValue value)
+ {
+ return value.toBoolean(&state);
}
- return toUInt8(state, value);
-}
+};
-template<> inline int16_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toInt16EnforceRange(state, value);
- case Clamp:
- return toInt16Clamp(state, value);
+template<> struct Converter<String> : DefaultConverter<String> {
+ using OptionalValue = String; // Use null string to mean an optional value was not present.
+ static String convert(JSC::ExecState& state, JSC::JSValue value)
+ {
+ return value.toWTFString(&state);
}
- return toInt16(state, value);
-}
+};
-template<> inline uint16_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toUInt16EnforceRange(state, value);
- case Clamp:
- return toUInt16Clamp(state, value);
+template<typename T> struct Converter<Vector<T>> : DefaultConverter<Vector<T>> {
+ static Vector<T> convert(JSC::ExecState& state, JSC::JSValue value)
+ {
+ // FIXME: The toNativeArray function doesn't throw a type error if the value is not an object. Is that OK?
+ return toNativeArray<T>(&state, value);
}
- return toUInt16(state, value);
-}
+};
-template<> inline int32_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toInt32EnforceRange(state, value);
- case Clamp:
- return toInt32Clamp(state, value);
+template<> struct Converter<int8_t> : DefaultConverter<int8_t> {
+ static int8_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toInt8EnforceRange(state, value);
+ case Clamp:
+ return toInt8Clamp(state, value);
+ }
+ return toInt8(state, value);
}
- return value.toInt32(&state);
-}
+};
-template<> inline uint32_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toUInt32EnforceRange(state, value);
- case Clamp:
- return toUInt32Clamp(state, value);
+template<> struct Converter<uint8_t> : DefaultConverter<uint8_t> {
+ static uint8_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toUInt8EnforceRange(state, value);
+ case Clamp:
+ return toUInt8Clamp(state, value);
+ }
+ return toUInt8(state, value);
}
- return value.toUInt32(&state);
-}
+};
-template<> inline int64_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- if (value.isInt32())
- return value.asInt32();
+template<> struct Converter<int16_t> : DefaultConverter<int16_t> {
+ static int16_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toInt16EnforceRange(state, value);
+ case Clamp:
+ return toInt16Clamp(state, value);
+ }
+ return toInt16(state, value);
+ }
+};
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toInt64EnforceRange(state, value);
- case Clamp:
- return toInt64Clamp(state, value);
+template<> struct Converter<uint16_t> : DefaultConverter<uint16_t> {
+ static uint16_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toUInt16EnforceRange(state, value);
+ case Clamp:
+ return toUInt16Clamp(state, value);
+ }
+ return toUInt16(state, value);
}
- return toInt64(state, value);
-}
+};
-template<> inline uint64_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
-{
- if (value.isUInt32())
- return value.asUInt32();
+template<> struct Converter<int32_t> : DefaultConverter<int32_t> {
+ static int32_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toInt32EnforceRange(state, value);
+ case Clamp:
+ return toInt32Clamp(state, value);
+ }
+ return value.toInt32(&state);
+ }
+};
- switch (configuration) {
- case NormalConversion:
- break;
- case EnforceRange:
- return toUInt64EnforceRange(state, value);
- case Clamp:
- return toUInt64Clamp(state, value);
+template<> struct Converter<uint32_t> : DefaultConverter<uint32_t> {
+ static uint32_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toUInt32EnforceRange(state, value);
+ case Clamp:
+ return toUInt32Clamp(state, value);
+ }
+ return value.toUInt32(&state);
}
- return toUInt64(state, value);
-}
+};
+template<> struct Converter<int64_t> : DefaultConverter<int64_t> {
+ static int64_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ if (value.isInt32())
+ return value.asInt32();
+
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toInt64EnforceRange(state, value);
+ case Clamp:
+ return toInt64Clamp(state, value);
+ }
+ return toInt64(state, value);
+ }
+};
+
+template<> struct Converter<uint64_t> : DefaultConverter<uint64_t> {
+ static uint64_t convert(JSC::ExecState& state, JSC::JSValue value, IntegerConversionConfiguration configuration)
+ {
+ if (value.isUInt32())
+ return value.asUInt32();
+
+ switch (configuration) {
+ case NormalConversion:
+ break;
+ case EnforceRange:
+ return toUInt64EnforceRange(state, value);
+ case Clamp:
+ return toUInt64Clamp(state, value);
+ }
+ return toUInt64(state, value);
+ }
+};
+
} // namespace WebCore
Modified: trunk/Source/WebCore/bindings/scripts/CodeGeneratorJS.pm (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/CodeGeneratorJS.pm 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/CodeGeneratorJS.pm 2016-05-10 02:31:03 UTC (rev 200607)
@@ -3,7 +3,7 @@
# Copyright (C) 2006 Anders Carlsson <ander...@mac.com>
# Copyright (C) 2006, 2007 Samuel Weinig <s...@webkit.org>
# Copyright (C) 2006 Alexey Proskuryakov <a...@webkit.org>
-# Copyright (C) 2006, 2007-2010, 2013-2016 Apple Inc. All rights reserved.
+# Copyright (C) 2006-2010, 2013-2016 Apple Inc. All rights reserved.
# Copyright (C) 2009 Cameron McCormack <c...@mcc.id.au>
# Copyright (C) Research In Motion Limited 2010. All rights reserved.
# Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
@@ -861,16 +861,15 @@
my $conditionalString = $codeGenerator->GenerateConditionalString($enumeration);
$result .= "#if ${conditionalString}\n\n" if $conditionalString;
- # Declare this instead of using "static" because it may be unused and we don't
- # want to get warnings about it.
- $result .= "JSString* jsStringWithCache(ExecState*, $className);\n";
+ # Declare this instead of using "static" because it may be unused and we don't want warnings about that.
+ $result .= "JSString* jsStringWithCache(ExecState*, $className);\n\n";
# Take an ExecState* instead of an ExecState& to match the jsStringWithCache from JSString.h.
# FIXME: Change to take VM& instead of ExecState*.
$result .= "JSString* jsStringWithCache(ExecState* state, $className enumerationValue)\n";
$result .= "{\n";
# FIXME: Might be nice to make this global be "const", but NeverDestroyed does not currently support that.
- # FIXME: Might be nice to make the entire array be NeverDestroyed instead of each value, but not sure the syntax for that.
+ # FIXME: Might be nice to make the entire array be NeverDestroyed instead of each value, but not sure what the syntax for that is.
$result .= " static NeverDestroyed<const String> values[] = {\n";
foreach my $value (@{$enumeration->values}) {
if ($value eq "") {
@@ -942,6 +941,31 @@
return GetNestedClassName($interface, $name);
}
+sub GenerateDefaultValue
+{
+ my ($interface, $member) = @_;
+
+ my $value = $member->default;
+
+ if ($codeGenerator->IsEnumType($member->type)) {
+ # FIXME: Would be nice to report an error if the value does not have quote marks around it.
+ # FIXME: Would be nice to report an error if the value is not one of the enumeration values.
+ my $className = GetEnumerationClassName($interface, $member->type);
+ my $enumerationValueName = GetEnumerationValueName(substr($value, 1, -1));
+ $value = $className . "::" . $enumerationValueName;
+ }
+
+ return $value;
+}
+
+sub GenerateDefaultValueWithLeadingComma
+{
+ my ($interface, $member) = @_;
+
+ return "" unless $member->isOptional && defined $member->default;
+ return ", " . GenerateDefaultValue($interface, $member);
+}
+
sub GenerateDictionaryImplementationContent
{
my ($interface, $dictionaries) = @_;
@@ -965,7 +989,7 @@
$defaultValues = "";
last;
}
- $defaultValues .= $comma . (defined $member->default ? $member->default : "Nullopt");
+ $defaultValues .= $comma . (defined $member->default ? GenerateDefaultValue($interface, $member) : "{ }");
$comma = ", ";
}
@@ -985,11 +1009,12 @@
$result .= " if (UNLIKELY(state.hadException()))\n";
$result .= " return { };\n";
}
- # FIXME: Eventually we will want this to call JSValueToNative.
+ # FIXME: Eventually we will want this to share a lot more code with JSValueToNative.
my $function = $member->isOptional ? "convertOptional" : "convert";
my $defaultValueWithLeadingComma = $member->isOptional && defined $member->default ? ", " . $member->default : "";
$result .= " auto " . $member->name . " = " . $function . "<" . GetNativeTypeFromSignature($interface, $member) . ">"
- . "(state, object->get(&state, Identifier::fromString(&state, \"" . $member->name . "\"))" . $defaultValueWithLeadingComma . ");\n";
+ . "(state, object->get(&state, Identifier::fromString(&state, \"" . $member->name . "\"))"
+ . GenerateDefaultValueWithLeadingComma($interface, $member) . ");\n";
$needExceptionCheck = 1;
}
@@ -3716,12 +3741,13 @@
push(@$outputArray, " $nativeType $name;\n");
if ($parameter->isOptional) {
- push(@$outputArray, " if (${name}Value.isUndefined()) {\n");
- if (defined($parameter->default)) {
- my $enumerationValueName = GetEnumerationValueName(substr($parameter->default, 1, -1));
- push(@$outputArray, " $name = ${className}::${enumerationValueName};\n");
+ if (!defined $parameter->default) {
+ push(@$outputArray, " if (!${name}Value.isUndefined()) {\n");
+ } else {
+ push(@$outputArray, " if (${name}Value.isUndefined()) {\n");
+ push(@$outputArray, " $name = " . GenerateDefaultValue($interface, $parameter) . ";\n");
+ push(@$outputArray, " } else {\n");
}
- push(@$outputArray, " } else {\n");
$indent = " ";
}
Modified: trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.cpp (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.cpp 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.cpp 2016-05-10 02:31:03 UTC (rev 200607)
@@ -34,7 +34,7 @@
#include "WebKitDOMNodePrivate.h"
#include "WebKitDOMPrivate.h"
#include "WebKitDOMSVGPointPrivate.h"
-#include "WebKitDOMShadowRootInitPrivate.h"
+#include "WebKitDOMTestDictionaryPrivate.h"
#include "WebKitDOMTestEnumTypePrivate.h"
#include "WebKitDOMTestNodePrivate.h"
#include "WebKitDOMTestObjPrivate.h"
@@ -1413,6 +1413,16 @@
item->methodWithEnumArg(convertedEnumArg);
}
+void webkit_dom_test_obj_method_with_optional_enum_arg(WebKitDOMTestObj* self, WebKitDOMTestEnumType* enumArg)
+{
+ WebCore::JSMainThreadNullState state;
+ g_return_if_fail(WEBKIT_DOM_IS_TEST_OBJ(self));
+ g_return_if_fail(WEBKIT_DOM_IS_TEST_ENUM_TYPE(enumArg));
+ WebCore::TestObj* item = WebKit::core(self);
+ WebCore::TestEnumType* convertedEnumArg = WebKit::core(enumArg);
+ item->methodWithOptionalEnumArg(convertedEnumArg);
+}
+
void webkit_dom_test_obj_method_with_optional_enum_arg_and_default_value(WebKitDOMTestObj* self, WebKitDOMTestEnumType* enumArg)
{
WebCore::JSMainThreadNullState state;
@@ -2022,13 +2032,13 @@
item->any(a, b);
}
-void webkit_dom_test_obj_attach_shadow_root(WebKitDOMTestObj* self, WebKitDOMShadowRootInit* init)
+void webkit_dom_test_obj_attach_shadow_root(WebKitDOMTestObj* self, WebKitDOMTestDictionary* init)
{
WebCore::JSMainThreadNullState state;
g_return_if_fail(WEBKIT_DOM_IS_TEST_OBJ(self));
- g_return_if_fail(WEBKIT_DOM_IS_SHADOW_ROOT_INIT(init));
+ g_return_if_fail(WEBKIT_DOM_IS_TEST_DICTIONARY(init));
WebCore::TestObj* item = WebKit::core(self);
- WebCore::ShadowRootInit* convertedInit = WebKit::core(init);
+ WebCore::TestDictionary* convertedInit = WebKit::core(init);
item->attachShadowRoot(convertedInit);
}
Modified: trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.h (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.h 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/GObject/WebKitDOMTestObj.h 2016-05-10 02:31:03 UTC (rev 200607)
@@ -320,6 +320,16 @@
webkit_dom_test_obj_method_with_enum_arg(WebKitDOMTestObj* self, WebKitDOMTestEnumType* enumArg);
/**
+ * webkit_dom_test_obj_method_with_optional_enum_arg:
+ * @self: A #WebKitDOMTestObj
+ * @enumArg: A #WebKitDOMTestEnumType
+ *
+ * Stability: Unstable
+**/
+WEBKIT_API void
+webkit_dom_test_obj_method_with_optional_enum_arg(WebKitDOMTestObj* self, WebKitDOMTestEnumType* enumArg);
+
+/**
* webkit_dom_test_obj_method_with_optional_enum_arg_and_default_value:
* @self: A #WebKitDOMTestObj
* @enumArg: A #WebKitDOMTestEnumType
@@ -935,12 +945,12 @@
/**
* webkit_dom_test_obj_attach_shadow_root:
* @self: A #WebKitDOMTestObj
- * @init: A #WebKitDOMShadowRootInit
+ * @init: A #WebKitDOMTestDictionary
*
* Stability: Unstable
**/
WEBKIT_API void
-webkit_dom_test_obj_attach_shadow_root(WebKitDOMTestObj* self, WebKitDOMShadowRootInit* init);
+webkit_dom_test_obj_attach_shadow_root(WebKitDOMTestObj* self, WebKitDOMTestDictionary* init);
/**
* webkit_dom_test_obj_get_read_only_long_attr:
Modified: trunk/Source/WebCore/bindings/scripts/test/JS/JSTestObj.cpp (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/JS/JSTestObj.cpp 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/JS/JSTestObj.cpp 2016-05-10 02:31:03 UTC (rev 200607)
@@ -93,11 +93,12 @@
template<typename T> const char* expectedEnumerationValues();
JSString* jsStringWithCache(ExecState*, TestObj::EnumType);
+
JSString* jsStringWithCache(ExecState* state, TestObj::EnumType enumerationValue)
{
static NeverDestroyed<const String> values[] = {
emptyString(),
- ASCIILiteral("EnumValue1"),
+ ASCIILiteral("enumValue1"),
ASCIILiteral("EnumValue2"),
ASCIILiteral("EnumValue3"),
};
@@ -118,7 +119,7 @@
auto stringValue = value.toWTFString(&state);
if (stringValue.isEmpty())
return TestObj::EnumType::EmptyString;
- if (stringValue == "EnumValue1")
+ if (stringValue == "enumValue1")
return TestObj::EnumType::EnumValue1;
if (stringValue == "EnumValue2")
return TestObj::EnumType::EnumValue2;
@@ -139,10 +140,11 @@
template<> inline const char* expectedEnumerationValues<TestObj::EnumType>()
{
- return "\"\", \"EnumValue1\", \"EnumValue2\", \"EnumValue3\"";
+ return "\"\", \"enumValue1\", \"EnumValue2\", \"EnumValue3\"";
}
JSString* jsStringWithCache(ExecState*, TestObj::Optional);
+
JSString* jsStringWithCache(ExecState* state, TestObj::Optional enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -195,6 +197,7 @@
#if ENABLE(Condition1)
JSString* jsStringWithCache(ExecState*, TestObj::EnumA);
+
JSString* jsStringWithCache(ExecState* state, TestObj::EnumA enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -237,6 +240,7 @@
#if ENABLE(Condition1) && ENABLE(Condition2)
JSString* jsStringWithCache(ExecState*, TestObj::EnumB);
+
JSString* jsStringWithCache(ExecState* state, TestObj::EnumB enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -279,6 +283,7 @@
#if ENABLE(Condition1) || ENABLE(Condition2)
JSString* jsStringWithCache(ExecState*, TestObj::EnumC);
+
JSString* jsStringWithCache(ExecState* state, TestObj::EnumC enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -319,6 +324,7 @@
#endif
JSString* jsStringWithCache(ExecState*, TestObj::Kind);
+
JSString* jsStringWithCache(ExecState* state, TestObj::Kind enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -361,6 +367,7 @@
}
JSString* jsStringWithCache(ExecState*, TestObj::Size);
+
JSString* jsStringWithCache(ExecState* state, TestObj::Size enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -403,6 +410,7 @@
}
JSString* jsStringWithCache(ExecState*, TestObj::Confidence);
+
JSString* jsStringWithCache(ExecState* state, TestObj::Confidence enumerationValue)
{
static NeverDestroyed<const String> values[] = {
@@ -444,92 +452,68 @@
return "\"high\", \"kinda-low\"";
}
-JSString* jsStringWithCache(ExecState*, TestObj::ShadowRootMode);
-JSString* jsStringWithCache(ExecState* state, TestObj::ShadowRootMode enumerationValue)
+template<> TestObj::Dictionary convert<TestObj::Dictionary>(ExecState& state, JSValue value)
{
- static NeverDestroyed<const String> values[] = {
- ASCIILiteral("open"),
- ASCIILiteral("closed"),
- };
- static_assert(static_cast<size_t>(TestObj::ShadowRootMode::Open) == 0, "TestObj::ShadowRootMode::Open is not 0 as expected");
- static_assert(static_cast<size_t>(TestObj::ShadowRootMode::Closed) == 1, "TestObj::ShadowRootMode::Closed is not 1 as expected");
- ASSERT(static_cast<size_t>(enumerationValue) < WTF_ARRAY_LENGTH(values));
- return jsStringWithCache(state, values[static_cast<size_t>(enumerationValue)]);
-}
-
-template<> struct JSValueTraits<TestObj::ShadowRootMode> {
- static JSString* arrayJSValue(ExecState* state, JSDOMGlobalObject*, TestObj::ShadowRootMode value) { return jsStringWithCache(state, value); }
-};
-
-template<> Optional<TestObj::ShadowRootMode> parse<TestObj::ShadowRootMode>(ExecState& state, JSValue value)
-{
- auto stringValue = value.toWTFString(&state);
- if (stringValue == "open")
- return TestObj::ShadowRootMode::Open;
- if (stringValue == "closed")
- return TestObj::ShadowRootMode::Closed;
- return Nullopt;
-}
-
-template<> TestObj::ShadowRootMode convert<TestObj::ShadowRootMode>(ExecState& state, JSValue value)
-{
- auto result = parse<TestObj::ShadowRootMode>(state, value);
- if (UNLIKELY(!result)) {
- throwTypeError(&state);
- return { };
- }
- return result.value();
-}
-
-template<> inline const char* expectedEnumerationValues<TestObj::ShadowRootMode>()
-{
- return "\"open\", \"closed\"";
-}
-
-template<> TestObj::ShadowRootInit convert<TestObj::ShadowRootInit>(ExecState& state, JSValue value)
-{
+ if (value.isUndefinedOrNull())
+ return { { }, TestObj::EnumType::EnumValue1, TestObj::EnumType::EmptyString, "defaultString", { }, false, { }, { } };
auto* object = value.getObject();
if (UNLIKELY(!object || object->type() == RegExpObjectType)) {
throwTypeError(&state);
return { };
}
- auto mode = convert<TestObj::ShadowRootMode>(state, object->get(&state, Identifier::fromString(&state, "mode")));
- return { WTFMove(mode) };
+ auto enumerationValueWithoutDefault = convertOptional<TestObj::EnumType>(state, object->get(&state, Identifier::fromString(&state, "enumerationValueWithoutDefault")));
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto enumerationValueWithDefault = convertOptional<TestObj::EnumType>(state, object->get(&state, Identifier::fromString(&state, "enumerationValueWithDefault")), TestObj::EnumType::EnumValue1);
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto enumerationValueWithEmptyStringDefault = convertOptional<TestObj::EnumType>(state, object->get(&state, Identifier::fromString(&state, "enumerationValueWithEmptyStringDefault")), TestObj::EnumType::EmptyString);
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto stringWithDefault = convertOptional<String>(state, object->get(&state, Identifier::fromString(&state, "stringWithDefault")), "defaultString");
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto stringWithoutDefault = convertOptional<String>(state, object->get(&state, Identifier::fromString(&state, "stringWithoutDefault")));
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto booleanWithDefault = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "booleanWithDefault")), false);
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto booleanWithoutDefault = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "booleanWithoutDefault")));
+ if (UNLIKELY(state.hadException()))
+ return { };
+ auto sequenceOfStrings = convertOptional<Vector<String>>(state, object->get(&state, Identifier::fromString(&state, "sequenceOfStrings")));
+ return { WTFMove(enumerationValueWithoutDefault), WTFMove(enumerationValueWithDefault), WTFMove(enumerationValueWithEmptyStringDefault), WTFMove(stringWithDefault), WTFMove(stringWithoutDefault), WTFMove(booleanWithDefault), WTFMove(booleanWithoutDefault), WTFMove(sequenceOfStrings) };
}
-template<> TestObj::FontFaceDescriptors convert<TestObj::FontFaceDescriptors>(ExecState& state, JSValue value)
+template<> TestObj::DictionaryThatShouldNotTolerateNull convert<TestObj::DictionaryThatShouldNotTolerateNull>(ExecState& state, JSValue value)
{
- if (value.isUndefinedOrNull())
- return { "normal", "U+0-10FFFF" };
auto* object = value.getObject();
if (UNLIKELY(!object || object->type() == RegExpObjectType)) {
throwTypeError(&state);
return { };
}
- auto style = convertOptional<String>(state, object->get(&state, Identifier::fromString(&state, "style")), "normal");
+ auto requiredEnumerationValue = convert<TestObj::EnumType>(state, object->get(&state, Identifier::fromString(&state, "requiredEnumerationValue")));
if (UNLIKELY(state.hadException()))
return { };
- auto unicodeRange = convertOptional<String>(state, object->get(&state, Identifier::fromString(&state, "unicodeRange")), "U+0-10FFFF");
- return { WTFMove(style), WTFMove(unicodeRange) };
+ auto booleanWithoutDefault = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "booleanWithoutDefault")));
+ return { WTFMove(requiredEnumerationValue), WTFMove(booleanWithoutDefault) };
}
-template<> TestObj::MutationObserverInit convert<TestObj::MutationObserverInit>(ExecState& state, JSValue value)
+template<> TestObj::DictionaryThatShouldTolerateNull convert<TestObj::DictionaryThatShouldTolerateNull>(ExecState& state, JSValue value)
{
if (value.isUndefinedOrNull())
- return { false, Nullopt, Nullopt };
+ return { { }, { } };
auto* object = value.getObject();
if (UNLIKELY(!object || object->type() == RegExpObjectType)) {
throwTypeError(&state);
return { };
}
- auto childList = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "childList")), false);
+ auto enumerationValue = convertOptional<TestObj::EnumType>(state, object->get(&state, Identifier::fromString(&state, "enumerationValue")));
if (UNLIKELY(state.hadException()))
return { };
- auto attributes = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "attributes")));
- if (UNLIKELY(state.hadException()))
- return { };
- auto attributeFilter = convertOptional<Vector<String>>(state, object->get(&state, Identifier::fromString(&state, "attributeFilter")));
- return { WTFMove(childList), WTFMove(attributes), WTFMove(attributeFilter) };
+ auto booleanWithoutDefault = convertOptional<bool>(state, object->get(&state, Identifier::fromString(&state, "booleanWithoutDefault")));
+ return { WTFMove(enumerationValue), WTFMove(booleanWithoutDefault) };
}
// Functions
@@ -556,6 +540,7 @@
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithSequenceArg(JSC::ExecState*);
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodReturningSequence(JSC::ExecState*);
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithEnumArg(JSC::ExecState*);
+JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithOptionalEnumArg(JSC::ExecState*);
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithOptionalEnumArgAndDefaultValue(JSC::ExecState*);
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodThatRequiresAllArgsAndThrows(JSC::ExecState*);
JSC::EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionSerializedValue(JSC::ExecState*);
@@ -1127,6 +1112,7 @@
{ "methodWithSequenceArg", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodWithSequenceArg), (intptr_t) (1) } },
{ "methodReturningSequence", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodReturningSequence), (intptr_t) (1) } },
{ "methodWithEnumArg", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodWithEnumArg), (intptr_t) (1) } },
+ { "methodWithOptionalEnumArg", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodWithOptionalEnumArg), (intptr_t) (0) } },
{ "methodWithOptionalEnumArgAndDefaultValue", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodWithOptionalEnumArgAndDefaultValue), (intptr_t) (0) } },
{ "methodThatRequiresAllArgsAndThrows", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionMethodThatRequiresAllArgsAndThrows), (intptr_t) (2) } },
{ "serializedValue", JSC::Function, NoIntrinsic, { (intptr_t)static_cast<NativeFunction>(jsTestObjPrototypeFunctionSerializedValue), (intptr_t) (1) } },
@@ -4210,6 +4196,27 @@
return JSValue::encode(jsUndefined());
}
+EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithOptionalEnumArg(ExecState* state)
+{
+ JSValue thisValue = state->thisValue();
+ auto castedThis = jsDynamicCast<JSTestObj*>(thisValue);
+ if (UNLIKELY(!castedThis))
+ return throwThisTypeError(*state, "TestObj", "methodWithOptionalEnumArg");
+ ASSERT_GC_OBJECT_INHERITS(castedThis, JSTestObj::info());
+ auto& impl = castedThis->wrapped();
+ auto enumArgValue = state->argument(0);
+ Optional<TestObj::EnumType> enumArg;
+ if (!enumArgValue.isUndefined()) {
+ enumArg = parse<TestObj::EnumType>(*state, enumArgValue);
+ if (UNLIKELY(state->hadException()))
+ return JSValue::encode(jsUndefined());
+ if (UNLIKELY(!enumArg))
+ return throwArgumentMustBeEnumError(*state, 0, "enumArg", "TestObj", "methodWithOptionalEnumArg", expectedEnumerationValues<TestObj::EnumType>());
+ }
+ impl.methodWithOptionalEnumArg(enumArg);
+ return JSValue::encode(jsUndefined());
+}
+
EncodedJSValue JSC_HOST_CALL jsTestObjPrototypeFunctionMethodWithOptionalEnumArgAndDefaultValue(ExecState* state)
{
JSValue thisValue = state->thisValue();
@@ -6127,7 +6134,7 @@
auto& impl = castedThis->wrapped();
if (UNLIKELY(state->argumentCount() < 1))
return throwVMError(state, createNotEnoughArgumentsError(state));
- auto init = convert<TestObj::ShadowRootInit>(*state, state->argument(0));
+ auto init = convert<TestObj::Dictionary>(*state, state->argument(0));
if (UNLIKELY(state->hadException()))
return JSValue::encode(jsUndefined());
impl.attachShadowRoot(WTFMove(init));
Modified: trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.h (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.h 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.h 2016-05-10 02:31:03 UTC (rev 200607)
@@ -31,7 +31,7 @@
@class DOMNode;
@class DOMSVGDocument;
@class DOMSVGPoint;
-@class DOMShadowRootInit;
+@class DOMTestDictionary;
@class DOMTestEnumType;
@class DOMTestNode;
@class DOMTestObj;
@@ -155,6 +155,7 @@
- (NSString *)nullableStringStaticMethod;
- (NSString *)nullableStringSpecialMethod:(unsigned)index;
- (void)methodWithEnumArg:(DOMTestEnumType *)enumArg;
+- (void)methodWithOptionalEnumArg:(DOMTestEnumType *)enumArg;
- (void)methodWithOptionalEnumArgAndDefaultValue:(DOMTestEnumType *)enumArg;
- (DOMTestObj *)methodThatRequiresAllArgsAndThrows:(NSString *)strArg objArg:(DOMTestObj *)objArg;
- (void)serializedValue:(NSString *)serializedArg;
@@ -217,5 +218,5 @@
- (void)variadicDoubleMethod:(double)head tail:(double)tail;
- (void)variadicNodeMethod:(DOMNode *)head tail:(DOMNode *)tail;
- (void)any:(float)a b:(int)b;
-- (void)attachShadowRoot:(DOMShadowRootInit *)init;
+- (void)attachShadowRoot:(DOMTestDictionary *)init;
@end
Modified: trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.mm (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.mm 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/ObjC/DOMTestObj.mm 2016-05-10 02:31:03 UTC (rev 200607)
@@ -35,7 +35,7 @@
#import "DOMNodeInternal.h"
#import "DOMSVGDocumentInternal.h"
#import "DOMSVGPointInternal.h"
-#import "DOMShadowRootInitInternal.h"
+#import "DOMTestDictionaryInternal.h"
#import "DOMTestEnumTypeInternal.h"
#import "DOMTestNodeInternal.h"
#import "DOMTestObjInternal.h"
@@ -55,7 +55,7 @@
#import "SVGDocument.h"
#import "SVGPoint.h"
#import "SerializedScriptValue.h"
-#import "ShadowRootInit.h"
+#import "TestDictionary.h"
#import "TestEnumType.h"
#import "TestNode.h"
#import "TestObj.h"
@@ -1154,6 +1154,12 @@
IMPL->methodWithEnumArg(core(enumArg));
}
+- (void)methodWithOptionalEnumArg:(DOMTestEnumType *)enumArg
+{
+ WebCore::JSMainThreadNullState state;
+ IMPL->methodWithOptionalEnumArg(core(enumArg));
+}
+
- (void)methodWithOptionalEnumArgAndDefaultValue:(DOMTestEnumType *)enumArg
{
WebCore::JSMainThreadNullState state;
@@ -1641,7 +1647,7 @@
IMPL->any(a, b);
}
-- (void)attachShadowRoot:(DOMShadowRootInit *)init
+- (void)attachShadowRoot:(DOMTestDictionary *)init
{
WebCore::JSMainThreadNullState state;
IMPL->attachShadowRoot(core(init));
Modified: trunk/Source/WebCore/bindings/scripts/test/TestObj.idl (200606 => 200607)
--- trunk/Source/WebCore/bindings/scripts/test/TestObj.idl 2016-05-10 02:01:28 UTC (rev 200606)
+++ trunk/Source/WebCore/bindings/scripts/test/TestObj.idl 2016-05-10 02:31:03 UTC (rev 200607)
@@ -30,7 +30,7 @@
// This IDL file is for testing the bindings code generator and for tracking
// changes in its ouput.
-enum TestEnumType { "", "EnumValue1", "EnumValue2", "EnumValue3" };
+enum TestEnumType { "", "enumValue1", "EnumValue2", "EnumValue3" };
// Leading underscore on an enum should be removed.
enum _optional { "", "OptionalValue1", "OptionalValue2", "OptionalValue3" };
@@ -121,6 +121,7 @@
sequence<ScriptProfile> methodReturningSequence(long longArg);
void methodWithEnumArg(TestEnumType enumArg);
+ void methodWithOptionalEnumArg(optional TestEnumType enumArg);
void methodWithOptionalEnumArgAndDefaultValue(optional TestEnumType enumArg = "EnumValue1");
[RaisesException] TestObj methodThatRequiresAllArgsAndThrows(DOMString strArg, TestObj objArg);
@@ -375,24 +376,29 @@
[InvokesCustomElementLifecycleCallbacks] void methodWithNeedsLifecycleProcessingStack();
#endif
- void attachShadowRoot(ShadowRootInit init);
+ void attachShadowRoot(TestDictionary init);
};
// The following comment should not generate any code.
// TestObj implements TestImplements;
-enum ShadowRootMode { "open", "closed" };
-dictionary ShadowRootInit {
- required ShadowRootMode mode;
+dictionary TestDictionary {
+ TestEnumType enumerationValueWithoutDefault;
+ TestEnumType enumerationValueWithDefault = "enumValue1";
+ TestEnumType enumerationValueWithEmptyStringDefault = "";
+ DOMString stringWithDefault = "defaultString";
+ DOMString stringWithoutDefault;
+ boolean booleanWithDefault = false;
+ boolean booleanWithoutDefault;
+ sequence<DOMString> sequenceOfStrings;
};
-dictionary FontFaceDescriptors {
- DOMString style = "normal";
- DOMString unicodeRange = "U+0-10FFFF";
+dictionary TestDictionaryThatShouldNotTolerateNull {
+ required TestEnumType requiredEnumerationValue;
+ boolean booleanWithoutDefault;
};
-dictionary MutationObserverInit {
- boolean childList = false;
- boolean attributes;
- sequence<DOMString> attributeFilter;
+dictionary TestDictionaryThatShouldTolerateNull {
+ TestEnumType enumerationValue;
+ boolean booleanWithoutDefault;
};