Home | History | Annotate | Download | only in web
      1 /*
      2  * Copyright (C) 2009 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 are
      6  * met:
      7  *
      8  *     * Redistributions of source code must retain the above copyright
      9  * notice, this list of conditions and the following disclaimer.
     10  *     * Redistributions in binary form must reproduce the above
     11  * copyright notice, this list of conditions and the following disclaimer
     12  * in the documentation and/or other materials provided with the
     13  * distribution.
     14  *     * Neither the name of Google Inc. nor the names of its
     15  * contributors may be used to endorse or promote products derived from
     16  * this software without specific prior written permission.
     17  *
     18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     19  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     20  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     21  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     22  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
     23  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
     24  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
     25  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
     26  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
     27  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
     28  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     29  */
     30 
     31 #include "config.h"
     32 
     33 #include "core/dom/DataTransferItem.h"
     34 #include "core/platform/chromium/ChromiumDataObject.h"
     35 #include "core/platform/chromium/ClipboardMimeTypes.h"
     36 #include "modules/filesystem/DraggedIsolatedFileSystem.h"
     37 #include "public/platform/WebData.h"
     38 #include "public/platform/WebDragData.h"
     39 #include "public/platform/WebString.h"
     40 #include "public/platform/WebURL.h"
     41 #include "public/platform/WebVector.h"
     42 #include "wtf/HashMap.h"
     43 #include "wtf/PassRefPtr.h"
     44 
     45 using namespace WebCore;
     46 
     47 namespace WebKit {
     48 
     49 class WebDragDataPrivate : public ChromiumDataObject {
     50 };
     51 
     52 void WebDragData::initialize()
     53 {
     54     assign(static_cast<WebDragDataPrivate*>(ChromiumDataObject::create().leakRef()));
     55 }
     56 
     57 void WebDragData::reset()
     58 {
     59     assign(0);
     60 }
     61 
     62 void WebDragData::assign(const WebDragData& other)
     63 {
     64     WebDragDataPrivate* p = const_cast<WebDragDataPrivate*>(other.m_private);
     65     if (p)
     66         p->ref();
     67     assign(p);
     68 }
     69 
     70 WebVector<WebDragData::Item> WebDragData::items() const
     71 {
     72     Vector<Item> itemList;
     73     for (size_t i = 0; i < m_private->length(); ++i) {
     74         ChromiumDataObjectItem* originalItem = m_private->item(i).get();
     75         WebDragData::Item item;
     76         if (originalItem->kind() == DataTransferItem::kindString) {
     77             item.storageType = Item::StorageTypeString;
     78             item.stringType = originalItem->type();
     79             item.stringData = originalItem->internalGetAsString();
     80         } else if (originalItem->kind() == DataTransferItem::kindFile) {
     81             if (originalItem->sharedBuffer()) {
     82                 item.storageType = Item::StorageTypeBinaryData;
     83                 item.binaryData = originalItem->sharedBuffer();
     84             } else if (originalItem->isFilename()) {
     85                 item.storageType = Item::StorageTypeFilename;
     86                 RefPtr<WebCore::Blob> blob = originalItem->getAsFile();
     87                 if (blob->isFile()) {
     88                     File* file = toFile(blob.get());
     89                     item.filenameData = file->path();
     90                     item.displayNameData = file->name();
     91                 } else
     92                     ASSERT_NOT_REACHED();
     93             } else
     94                 ASSERT_NOT_REACHED();
     95         } else
     96             ASSERT_NOT_REACHED();
     97         item.title = originalItem->title();
     98         item.baseURL = originalItem->baseURL();
     99         itemList.append(item);
    100     }
    101     return itemList;
    102 }
    103 
    104 void WebDragData::setItems(const WebVector<Item>& itemList)
    105 {
    106     m_private->clearAll();
    107     for (size_t i = 0; i < itemList.size(); ++i)
    108         addItem(itemList[i]);
    109 }
    110 
    111 void WebDragData::addItem(const Item& item)
    112 {
    113     ensureMutable();
    114     switch (item.storageType) {
    115     case Item::StorageTypeString:
    116         if (String(item.stringType) == mimeTypeTextURIList)
    117             m_private->setURLAndTitle(item.stringData, item.title);
    118         else if (String(item.stringType) == mimeTypeTextHTML)
    119             m_private->setHTMLAndBaseURL(item.stringData, item.baseURL);
    120         else
    121             m_private->setData(item.stringType, item.stringData);
    122         return;
    123     case Item::StorageTypeFilename:
    124         m_private->addFilename(item.filenameData, item.displayNameData);
    125         return;
    126     case Item::StorageTypeBinaryData:
    127         // This should never happen when dragging in.
    128         ASSERT_NOT_REACHED();
    129     }
    130 }
    131 
    132 WebString WebDragData::filesystemId() const
    133 {
    134     ASSERT(!isNull());
    135     DraggedIsolatedFileSystem* filesystem = DraggedIsolatedFileSystem::from(m_private);
    136     if (filesystem)
    137         return filesystem->filesystemId();
    138     return WebString();
    139 }
    140 
    141 void WebDragData::setFilesystemId(const WebString& filesystemId)
    142 {
    143     // The ID is an opaque string, given by and validated by chromium port.
    144     ensureMutable();
    145     DraggedIsolatedFileSystem::provideTo(m_private, DraggedIsolatedFileSystem::supplementName(), DraggedIsolatedFileSystem::create(filesystemId));
    146 }
    147 
    148 WebDragData::WebDragData(const WTF::PassRefPtr<WebCore::ChromiumDataObject>& data)
    149     : m_private(static_cast<WebDragDataPrivate*>(data.leakRef()))
    150 {
    151 }
    152 
    153 WebDragData& WebDragData::operator=(const WTF::PassRefPtr<WebCore::ChromiumDataObject>& data)
    154 {
    155     assign(static_cast<WebDragDataPrivate*>(data.leakRef()));
    156     return *this;
    157 }
    158 
    159 WebDragData::operator WTF::PassRefPtr<WebCore::ChromiumDataObject>() const
    160 {
    161     return PassRefPtr<ChromiumDataObject>(const_cast<WebDragDataPrivate*>(m_private));
    162 }
    163 
    164 void WebDragData::assign(WebDragDataPrivate* p)
    165 {
    166     // p is already ref'd for us by the caller
    167     if (m_private)
    168         m_private->deref();
    169     m_private = p;
    170 }
    171 
    172 void WebDragData::ensureMutable()
    173 {
    174     ASSERT(!isNull());
    175     ASSERT(m_private->hasOneRef());
    176 }
    177 
    178 } // namespace WebKit
    179