2 * Copyright (C) 2016 Apple Inc. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 #include "ActiveDOMObject.h"
30 #include "CSSFontFaceSet.h"
31 #include "DOMCoreException.h"
32 #include "EventTarget.h"
33 #include "JSDOMPromise.h"
34 #include <wtf/HashTraits.h>
35 #include <wtf/Optional.h>
37 #include <wtf/RefCounted.h>
38 #include <wtf/RefPtr.h>
39 #include <wtf/Vector.h>
40 #include <wtf/text/WTFString.h>
51 class FontFaceSet final : public RefCounted<FontFaceSet>, public CSSFontFaceSetClient, public EventTargetWithInlineData, public ActiveDOMObject {
53 static Ref<FontFaceSet> create(Document&, const Vector<RefPtr<FontFace>>& initialFaces);
54 static Ref<FontFaceSet> create(Document&, CSSFontFaceSet& backing);
55 virtual ~FontFaceSet();
57 bool has(RefPtr<WebCore::FontFace>) const;
59 FontFaceSet& add(RefPtr<WebCore::FontFace>);
60 bool remove(RefPtr<WebCore::FontFace>);
63 void load(JSC::ExecState& execState, const String& font, DeferredWrapper&& promise, ExceptionCode& ec) { load(execState, font, String(" ", String::ConstructFromLiteral), WTFMove(promise), ec); }
64 void load(JSC::ExecState&, const String& font, const String& text, DeferredWrapper&& promise, ExceptionCode&);
65 bool check(const String& font, ExceptionCode& ec) { return check(font, String(" ", String::ConstructFromLiteral), ec); }
66 bool check(const String& font, const String& text, ExceptionCode&);
68 String status() const;
70 typedef DOMPromise<FontFaceSet&, DOMCoreException&> Promise;
71 Promise& promise(JSC::ExecState&);
73 CSSFontFaceSet& backing() { return m_backing; }
77 explicit Iterator(FontFaceSet&);
78 Optional<WTF::KeyValuePair<RefPtr<FontFace>, RefPtr<FontFace>>> next(JSC::ExecState&);
81 Ref<FontFaceSet> m_target;
82 size_t m_index { 0 }; // FIXME: There needs to be a mechanism to handle when fonts are added or removed from the middle of the FontFaceSet.
84 Iterator createIterator() { return Iterator(*this); }
86 using RefCounted<FontFaceSet>::ref;
87 using RefCounted<FontFaceSet>::deref;
90 struct PendingPromise : public RefCounted<PendingPromise> {
91 typedef DOMPromise<Vector<RefPtr<FontFace>>&, DOMCoreException&> Promise;
92 static Ref<PendingPromise> create(Promise&& promise)
94 return adoptRef(*new PendingPromise(WTFMove(promise)));
99 PendingPromise(Promise&&);
102 Vector<RefPtr<FontFace>> faces;
106 FontFaceSet(Document&, const Vector<RefPtr<FontFace>>&);
107 FontFaceSet(Document&, CSSFontFaceSet&);
109 void fulfillPromise();
111 // CSSFontFaceSetClient
112 void startedLoading() override;
113 void completedLoading() override;
114 void faceFinished(CSSFontFace&, CSSFontFace::Status) override;
117 const char* activeDOMObjectName() const override { return "FontFaceSet"; }
118 bool canSuspendForDocumentSuspension() const override;
121 EventTargetInterface eventTargetInterface() const override { return FontFaceSetEventTargetInterfaceType; }
122 ScriptExecutionContext* scriptExecutionContext() const override { return ActiveDOMObject::scriptExecutionContext(); }
123 void refEventTarget() override { ref(); }
124 void derefEventTarget() override { deref(); }
126 Ref<CSSFontFaceSet> m_backing;
127 HashMap<RefPtr<CSSFontFace>, Vector<Ref<PendingPromise>>> m_pendingPromises;
128 Optional<Promise> m_promise;