dddb44ca7b46d577d6e651ee62bf37c1cf0d636b
[WebKit-https.git] / Source / WebKit / win / WebBackForwardList.cpp
1 /*
2  * Copyright (C) 2006-2007, 2015 Apple 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 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. 
24  */
25
26 #include "WebKitDLL.h"
27 #include "WebBackForwardList.h"
28
29 #include "WebFrame.h"
30 #include "WebKit.h"
31 #include "WebPreferences.h"
32
33 #include <WebCore/BackForwardList.h>
34 #include <WebCore/COMPtr.h>
35 #include <WebCore/HistoryItem.h>
36
37 using std::min;
38 using namespace WebCore;
39
40 // WebBackForwardList ----------------------------------------------------------------
41
42 // FIXME: Instead of this we could just create a class derived from BackForwardList
43 // with a pointer to a WebBackForwardList in it.
44 static HashMap<BackForwardList*, WebBackForwardList*>& backForwardListWrappers()
45 {
46     static HashMap<BackForwardList*, WebBackForwardList*> staticBackForwardListWrappers;
47     return staticBackForwardListWrappers;
48 }
49
50 WebBackForwardList::WebBackForwardList(PassRefPtr<BackForwardList> backForwardList)
51     : m_backForwardList(backForwardList)
52 {
53     ASSERT(!backForwardListWrappers().contains(m_backForwardList.get()));
54     backForwardListWrappers().set(m_backForwardList.get(), this);
55
56     gClassCount++;
57     gClassNameCount().add("WebBackForwardList");
58 }
59
60 WebBackForwardList::~WebBackForwardList()
61 {
62     ASSERT(m_backForwardList->closed());
63
64     ASSERT(backForwardListWrappers().contains(m_backForwardList.get()));
65     backForwardListWrappers().remove(m_backForwardList.get());
66
67     gClassCount--;
68     gClassNameCount().remove("WebBackForwardList");
69 }
70
71 WebBackForwardList* WebBackForwardList::createInstance(PassRefPtr<BackForwardList> backForwardList)
72 {
73     WebBackForwardList* instance = backForwardListWrappers().get(backForwardList.get());
74
75     if (!instance)
76         instance = new WebBackForwardList(backForwardList);
77
78     instance->AddRef();
79     return instance;
80 }
81
82 // IUnknown -------------------------------------------------------------------
83
84 HRESULT WebBackForwardList::QueryInterface(_In_ REFIID riid, _COM_Outptr_ void** ppvObject)
85 {
86     if (!ppvObject)
87         return E_POINTER;
88     *ppvObject = nullptr;
89     if (IsEqualGUID(riid, IID_IUnknown))
90         *ppvObject = static_cast<IWebBackForwardList*>(this);
91     else if (IsEqualGUID(riid, IID_IWebBackForwardList))
92         *ppvObject = static_cast<IWebBackForwardList*>(this);
93     else if (IsEqualGUID(riid, IID_IWebBackForwardListPrivate))
94         *ppvObject = static_cast<IWebBackForwardListPrivate*>(this);
95     else
96         return E_NOINTERFACE;
97
98     AddRef();
99     return S_OK;
100 }
101
102 ULONG WebBackForwardList::AddRef()
103 {
104     return ++m_refCount;
105 }
106
107 ULONG WebBackForwardList::Release()
108 {
109     ULONG newRef = --m_refCount;
110     if (!newRef)
111         delete(this);
112
113     return newRef;
114 }
115
116 // IWebBackForwardList ---------------------------------------------------------
117
118 HRESULT WebBackForwardList::addItem(_In_opt_ IWebHistoryItem* item)
119 {
120     COMPtr<WebHistoryItem> webHistoryItem;
121  
122     if (!item || FAILED(item->QueryInterface(&webHistoryItem)))
123         return E_FAIL;
124  
125     m_backForwardList->addItem(*webHistoryItem->historyItem());
126     return S_OK;
127 }
128
129 HRESULT WebBackForwardList::goBack()
130 {
131     m_backForwardList->goBack();
132     return S_OK;
133 }
134
135 HRESULT WebBackForwardList::goForward()
136 {
137     m_backForwardList->goForward();
138     return S_OK;
139 }
140
141 HRESULT WebBackForwardList::goToItem(_In_opt_ IWebHistoryItem* item)
142 {
143     COMPtr<WebHistoryItem> webHistoryItem;
144  
145     if (!item || FAILED(item->QueryInterface(&webHistoryItem)))
146         return E_FAIL;
147
148     m_backForwardList->goToItem(webHistoryItem->historyItem());
149     return S_OK;
150 }
151
152 HRESULT WebBackForwardList::backItem(_COM_Outptr_opt_ IWebHistoryItem** item)
153 {
154     if (!item)
155         return E_POINTER;
156     *item = nullptr;
157     HistoryItem* historyItem = m_backForwardList->backItem();
158
159     if (!historyItem)
160         return E_FAIL;
161
162     *item = WebHistoryItem::createInstance(historyItem);
163     return S_OK;
164 }
165
166 HRESULT WebBackForwardList::currentItem(_COM_Outptr_opt_ IWebHistoryItem** item)
167 {
168     if (!item)
169         return E_POINTER;
170     *item = nullptr;
171
172     HistoryItem* historyItem = m_backForwardList->currentItem();
173     if (!historyItem)
174         return E_FAIL;
175
176     *item = WebHistoryItem::createInstance(historyItem);
177     return S_OK;
178 }
179
180 HRESULT WebBackForwardList::forwardItem(_COM_Outptr_opt_ IWebHistoryItem** item)
181 {
182     if (!item)
183         return E_POINTER;
184     *item = nullptr;
185
186     HistoryItem* historyItem = m_backForwardList->forwardItem();
187     if (!historyItem)
188         return E_FAIL;
189
190     *item = WebHistoryItem::createInstance(historyItem);
191     return S_OK;
192 }
193
194 HRESULT WebBackForwardList::backListWithLimit(int limit, _Out_ int* listCount,
195     __deref_inout_opt IWebHistoryItem** list)
196 {
197     HistoryItemVector historyItemVector;
198     m_backForwardList->backListWithLimit(limit, historyItemVector);
199
200     *listCount = static_cast<int>(historyItemVector.size());
201
202     if (!list)
203         return E_NOT_SUFFICIENT_BUFFER;
204
205     for (unsigned i = 0; i < historyItemVector.size(); i++)
206         list[i] = WebHistoryItem::createInstance(historyItemVector[i].ptr());
207
208     return S_OK;
209 }
210
211 HRESULT WebBackForwardList::forwardListWithLimit(int limit, _Out_ int* listCount,
212     __deref_inout_opt IWebHistoryItem** list)
213 {
214     HistoryItemVector historyItemVector;
215     m_backForwardList->forwardListWithLimit(limit, historyItemVector);
216
217     *listCount = static_cast<int>(historyItemVector.size());
218
219     if (!list)
220         return E_NOT_SUFFICIENT_BUFFER;
221     
222     for (unsigned i = 0; i < historyItemVector.size(); i++)
223         list[i] = WebHistoryItem::createInstance(historyItemVector[i].ptr());
224
225     return S_OK;
226 }
227
228 HRESULT WebBackForwardList::capacity(_Out_ int* result)
229 {
230     if (!result)
231         return E_POINTER;
232
233     *result = m_backForwardList->capacity();
234     return S_OK;
235 }
236
237 HRESULT WebBackForwardList::setCapacity(int size)
238 {
239     if (size < 0)
240         return E_FAIL;
241     
242     m_backForwardList->setCapacity(size);
243     return S_OK;
244 }
245
246 HRESULT WebBackForwardList::backListCount(_Out_ int* count)
247 {
248     if (!count)
249         return E_POINTER;
250
251     *count = m_backForwardList->backListCount();
252     return S_OK;
253 }
254
255 HRESULT WebBackForwardList::forwardListCount(_Out_ int* count)
256 {
257     if (!count)
258         return E_POINTER;
259
260     *count = m_backForwardList->forwardListCount();
261     return S_OK;
262 }
263
264 HRESULT WebBackForwardList::containsItem(_In_opt_ IWebHistoryItem* item, _Out_ BOOL* result)
265 {
266     if (!result)
267         return E_POINTER;
268
269     COMPtr<WebHistoryItem> webHistoryItem;
270
271     if (!item || FAILED(item->QueryInterface(&webHistoryItem)))
272         return E_FAIL;
273
274     *result = m_backForwardList->containsItem(webHistoryItem->historyItem());
275     return S_OK;
276 }
277
278 HRESULT WebBackForwardList::itemAtIndex(int index, _COM_Outptr_opt_ IWebHistoryItem** item)
279 {
280     if (!item)
281         return E_POINTER;
282     *item = nullptr;
283
284     HistoryItem* historyItem = m_backForwardList->itemAtIndex(index);
285     if (!historyItem)
286         return E_FAIL;
287  
288     *item = WebHistoryItem::createInstance(historyItem);
289     return S_OK;
290 }
291
292 // IWebBackForwardListPrivate --------------------------------------------------------
293
294 HRESULT WebBackForwardList::removeItem(_In_opt_ IWebHistoryItem* item)
295 {
296     COMPtr<WebHistoryItem> webHistoryItem;
297  
298     if (!item || FAILED(item->QueryInterface(&webHistoryItem)))
299         return E_FAIL;
300  
301     m_backForwardList->removeItem(webHistoryItem->historyItem());
302     return S_OK;
303 }