97104805245e61111613f52134c932a6d8462597
[WebKit-https.git] / Source / WebCore / html / track / LoadableTextTrack.cpp
1 /*
2  * Copyright (C) 2011 Google Inc.  All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
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.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, 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 COMPUTER, 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.
24  */
25
26 #include "config.h"
27
28 #if ENABLE(VIDEO_TRACK)
29
30 #include "LoadableTextTrack.h"
31
32 #include "Event.h"
33 #include "HTMLTrackElement.h"
34 #include "ScriptExecutionContext.h"
35 #include "TextTrackCueList.h"
36
37 namespace WebCore {
38
39 LoadableTextTrack::LoadableTextTrack(HTMLTrackElement* track, const String& kind, const String& label, const String& language)
40     : TextTrack(&track->document(), track, kind, emptyString(), label, language, TrackElement)
41     , m_trackElement(track)
42     , m_loadTimer(this, &LoadableTextTrack::loadTimerFired)
43     , m_isDefault(false)
44 {
45 }
46
47 LoadableTextTrack::~LoadableTextTrack()
48 {
49 }
50
51 void LoadableTextTrack::clearClient()
52 {
53     m_trackElement = 0;
54     TextTrack::clearClient();
55 }
56
57 void LoadableTextTrack::scheduleLoad(const URL& url)
58 {
59     if (url == m_url)
60         return;
61
62     // 4.8.10.12.3 Sourcing out-of-band text tracks (continued)
63
64     // 2. Let URL be the track URL of the track element.
65     m_url = url;
66     
67     // 3. Asynchronously run the remaining steps, while continuing with whatever task 
68     // was responsible for creating the text track or changing the text track mode.
69     if (!m_loadTimer.isActive())
70         m_loadTimer.startOneShot(0);
71 }
72
73 Element* LoadableTextTrack::element()
74 {
75     return m_trackElement;
76 }
77     
78 void LoadableTextTrack::setTrackElement(HTMLTrackElement* element)
79 {
80     ASSERT(!m_trackElement || m_trackElement == element);
81     m_trackElement = element;
82 }
83
84 void LoadableTextTrack::loadTimerFired(Timer<LoadableTextTrack>&)
85 {
86     if (m_loader)
87         m_loader->cancelLoad();
88
89     if (!m_trackElement)
90         return;
91
92     // 4.8.10.12.3 Sourcing out-of-band text tracks (continued)
93
94     // 4. Download: If URL is not the empty string, perform a potentially CORS-enabled fetch of URL, with the
95     // mode being the state of the media element's crossorigin content attribute, the origin being the
96     // origin of the media element's Document, and the default origin behaviour set to fail.
97     m_loader = std::make_unique<TextTrackLoader>(static_cast<TextTrackLoaderClient&>(*this), static_cast<ScriptExecutionContext*>(&m_trackElement->document()));
98     if (!m_loader->load(m_url, m_trackElement->mediaElementCrossOriginAttribute()))
99         m_trackElement->didCompleteLoad(HTMLTrackElement::Failure);
100 }
101
102 void LoadableTextTrack::newCuesAvailable(TextTrackLoader* loader)
103 {
104     ASSERT_UNUSED(loader, m_loader.get() == loader);
105
106     Vector<RefPtr<TextTrackCue>> newCues;
107     m_loader->getNewCues(newCues);
108
109     if (!m_cues)
110         m_cues = TextTrackCueList::create();    
111
112     for (size_t i = 0; i < newCues.size(); ++i) {
113         newCues[i]->setTrack(this);
114         m_cues->add(newCues[i]);
115     }
116
117     if (client())
118         client()->textTrackAddCues(this, m_cues.get());
119 }
120
121 void LoadableTextTrack::cueLoadingCompleted(TextTrackLoader* loader, bool loadingFailed)
122 {
123     ASSERT_UNUSED(loader, m_loader.get() == loader);
124
125     if (!m_trackElement)
126         return;
127
128     m_trackElement->didCompleteLoad(loadingFailed ? HTMLTrackElement::Failure : HTMLTrackElement::Success);
129 }
130
131 #if ENABLE(WEBVTT_REGIONS)
132 void LoadableTextTrack::newRegionsAvailable(TextTrackLoader* loader)
133 {
134     ASSERT_UNUSED(loader, m_loader.get() == loader);
135
136     Vector<RefPtr<TextTrackRegion>> newRegions;
137     m_loader->getNewRegions(newRegions);
138
139     for (size_t i = 0; i < newRegions.size(); ++i) {
140         newRegions[i]->setTrack(this);
141         regionList()->add(newRegions[i]);
142     }
143 }
144 #endif
145
146 AtomicString LoadableTextTrack::id() const
147 {
148     if (m_trackElement)
149         return m_trackElement->getAttribute("id");
150     return emptyString();
151 }
152
153 size_t LoadableTextTrack::trackElementIndex()
154 {
155     ASSERT(m_trackElement);
156     ASSERT(m_trackElement->parentNode());
157
158     size_t index = 0;
159     for (Node* node = m_trackElement->parentNode()->firstChild(); node; node = node->nextSibling()) {
160         if (!node->hasTagName(trackTag) || !node->parentNode())
161             continue;
162         if (node == m_trackElement)
163             return index;
164         ++index;
165     }
166     ASSERT_NOT_REACHED();
167
168     return 0;
169 }
170
171 } // namespace WebCore
172
173 #endif