/*
 * Copyright (C) 2008 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 met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
 */

#include "config.h"
#include "AccessibilityUIElement.h"

#include "AccessibilityController.h"
#include "DumpRenderTree.h"
#include "FrameLoadDelegate.h"
#include <JavaScriptCore/JSStringRef.h>
#include <tchar.h>
#include <string>

using std::wstring;

static COMPtr<IAccessibleComparable> comparableObject(IAccessible* accessible)
{
    COMPtr<IServiceProvider> serviceProvider(Query, accessible);
    if (!serviceProvider)
        return 0;
    COMPtr<IAccessibleComparable> comparable;
    serviceProvider->QueryService(SID_AccessibleComparable, __uuidof(IAccessibleComparable), reinterpret_cast<void**>(&comparable));
    return comparable;
}

AccessibilityUIElement::AccessibilityUIElement(PlatformUIElement element)
    : m_element(element)
{
}

AccessibilityUIElement::AccessibilityUIElement(const AccessibilityUIElement& other)
    : m_element(other.m_element)
{
}

AccessibilityUIElement::~AccessibilityUIElement()
{
}

bool AccessibilityUIElement::isEqual(AccessibilityUIElement* otherElement)
{
    COMPtr<IAccessibleComparable> comparable = comparableObject(m_element.get());
    COMPtr<IAccessibleComparable> otherComparable = comparableObject(otherElement->m_element.get());
    if (!comparable || !otherComparable)
        return false;
    BOOL isSame = FALSE;
    if (FAILED(comparable->isSameObject(otherComparable.get(), &isSame)))
        return false;
    return isSame;
}

void AccessibilityUIElement::getLinkedUIElements(Vector<AccessibilityUIElement>&)
{
}

void AccessibilityUIElement::getDocumentLinks(Vector<AccessibilityUIElement>&)
{
}

void AccessibilityUIElement::getChildren(Vector<AccessibilityUIElement>& children)
{
    long childCount;
    if (FAILED(m_element->get_accChildCount(&childCount)))
        return;
    for (long i = 0; i < childCount; ++i)
        children.append(getChildAtIndex(i));
}

void AccessibilityUIElement::getChildrenWithRange(Vector<AccessibilityUIElement>& elementVector, unsigned location, unsigned length)
{
    long childCount;
    unsigned appendedCount = 0;
    if (FAILED(m_element->get_accChildCount(&childCount)))
        return;
    for (long i = location; i < childCount && appendedCount < length; ++i, ++appendedCount)
        elementVector.append(getChildAtIndex(i));
}

int AccessibilityUIElement::childrenCount()
{
    long childCount;
    m_element->get_accChildCount(&childCount);
    return childCount;
}

int AccessibilityUIElement::rowCount()
{
    // FIXME: implement
    return 0;
}
 
int AccessibilityUIElement::columnCount()
{
    // FIXME: implement
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::elementAtPoint(int x, int y)
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::linkedUIElementAtIndex(unsigned index)
{
    // FIXME: implement
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::getChildAtIndex(unsigned index)
{
    COMPtr<IDispatch> child;
    VARIANT vChild;
    ::VariantInit(&vChild);
    V_VT(&vChild) = VT_I4;
    // In MSAA, index 0 is the object itself.
    V_I4(&vChild) = index + 1;
    if (FAILED(m_element->get_accChild(vChild, &child)))
        return 0;
    return COMPtr<IAccessible>(Query, child);
}

unsigned AccessibilityUIElement::indexOfChild(AccessibilityUIElement* element)
{ 
    // FIXME: implement
    return 0;
}

JSStringRef AccessibilityUIElement::allAttributes()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfLinkedUIElements()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfDocumentLinks()
{
    return JSStringCreateWithCharacters(0, 0);
}

AccessibilityUIElement AccessibilityUIElement::titleUIElement()
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::parentElement()
{
    COMPtr<IDispatch> parent;
    m_element->get_accParent(&parent);

    COMPtr<IAccessible> parentAccessible(Query, parent);
    return parentAccessible;
}

JSStringRef AccessibilityUIElement::attributesOfChildren()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::parameterizedAttributeNames()
{
    return JSStringCreateWithCharacters(0, 0);
}

static VARIANT& self()
{
    static VARIANT vSelf;
    static bool haveInitialized;

    if (!haveInitialized) {
        ::VariantInit(&vSelf);
        V_VT(&vSelf) = VT_I4;
        V_I4(&vSelf) = CHILDID_SELF;
    }
    return vSelf;
}

JSStringRef AccessibilityUIElement::role()
{
    VARIANT vRole;
    if (FAILED(m_element->get_accRole(self(), &vRole)))
        return JSStringCreateWithCharacters(0, 0);

    ASSERT(V_VT(&vRole) == VT_I4 || V_VT(&vRole) == VT_BSTR);

    wstring result;
    if (V_VT(&vRole) == VT_I4) {
        unsigned roleTextLength = ::GetRoleText(V_I4(&vRole), 0, 0) + 1;

        Vector<TCHAR> roleText(roleTextLength);

        ::GetRoleText(V_I4(&vRole), roleText.data(), roleTextLength);

        result = roleText.data();
    } else if (V_VT(&vRole) == VT_BSTR)
        result = wstring(V_BSTR(&vRole), ::SysStringLen(V_BSTR(&vRole)));

    ::VariantClear(&vRole);

    return JSStringCreateWithCharacters(result.data(), result.length());
}

JSStringRef AccessibilityUIElement::subrole()
{
    return 0;
}

JSStringRef AccessibilityUIElement::roleDescription()
{
    return 0;
}

JSStringRef AccessibilityUIElement::title()
{
    BSTR titleBSTR;
    if (FAILED(m_element->get_accName(self(), &titleBSTR)) || !titleBSTR)
        return JSStringCreateWithCharacters(0, 0);
    wstring title(titleBSTR, SysStringLen(titleBSTR));
    ::SysFreeString(titleBSTR);
    return JSStringCreateWithCharacters(title.data(), title.length());
}

JSStringRef AccessibilityUIElement::description()
{
    BSTR descriptionBSTR;
    if (FAILED(m_element->get_accDescription(self(), &descriptionBSTR)) || !descriptionBSTR)
        return JSStringCreateWithCharacters(0, 0);
    wstring description(descriptionBSTR, SysStringLen(descriptionBSTR));
    ::SysFreeString(descriptionBSTR);
    return JSStringCreateWithCharacters(description.data(), description.length());
}

JSStringRef AccessibilityUIElement::stringValue()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::language()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::helpText() const
{
    return 0;
}

double AccessibilityUIElement::x()
{
    long x, y, width, height;
    if (FAILED(m_element->accLocation(&x, &y, &width, &height, self())))
        return 0;
    return x;
}

double AccessibilityUIElement::y()
{
    long x, y, width, height;
    if (FAILED(m_element->accLocation(&x, &y, &width, &height, self())))
        return 0;
    return y;
}

double AccessibilityUIElement::width()
{
    long x, y, width, height;
    if (FAILED(m_element->accLocation(&x, &y, &width, &height, self())))
        return 0;
    return width;
}

double AccessibilityUIElement::height()
{
    long x, y, width, height;
    if (FAILED(m_element->accLocation(&x, &y, &width, &height, self())))
        return 0;
    return height;
}

double AccessibilityUIElement::clickPointX()
{
    return 0;
}

double AccessibilityUIElement::clickPointY()
{
    return 0;
}

JSStringRef AccessibilityUIElement::valueDescription()
{
    return 0;
}

static DWORD accessibilityState(COMPtr<IAccessible> element)
{
    VARIANT state;
    element->get_accState(self(), &state);

    ASSERT(V_VT(&state) == VT_I4);

    DWORD result = state.lVal;
    VariantClear(&state);

    return result;
}

bool AccessibilityUIElement::isFocused() const
{
    // FIXME: implement
    return false;
}

bool AccessibilityUIElement::isSelected() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_SELECTED) == STATE_SYSTEM_SELECTED;
}

int AccessibilityUIElement::hierarchicalLevel() const
{
    return 0;
}

bool AccessibilityUIElement::ariaIsGrabbed() const
{
    return false;
}
 
JSStringRef AccessibilityUIElement::ariaDropEffects() const
{
    return 0;
}

bool AccessibilityUIElement::isExpanded() const
{
    return false;
}

bool AccessibilityUIElement::isChecked() const
{
    VARIANT vState;
    if (FAILED(m_element->get_accState(self(), &vState)))
        return false;

    return vState.lVal & STATE_SYSTEM_CHECKED;
}

JSStringRef AccessibilityUIElement::orientation() const
{
    return 0;
}

double AccessibilityUIElement::intValue() const
{
    BSTR valueBSTR;
    if (FAILED(m_element->get_accValue(self(), &valueBSTR)) || !valueBSTR)
        return 0;
    wstring value(valueBSTR, SysStringLen(valueBSTR));
    ::SysFreeString(valueBSTR);
    TCHAR* ignored;
    return _tcstod(value.data(), &ignored);
}

double AccessibilityUIElement::minValue()
{
    return 0;
}

double AccessibilityUIElement::maxValue()
{
    return 0;
}

bool AccessibilityUIElement::isActionSupported(JSStringRef action)
{
    return false;
}

bool AccessibilityUIElement::isEnabled()
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_UNAVAILABLE) != STATE_SYSTEM_UNAVAILABLE;
}

bool AccessibilityUIElement::isRequired() const
{
    return false;
}


int AccessibilityUIElement::insertionPointLineNumber()
{
    return 0;
}

JSStringRef AccessibilityUIElement::attributesOfColumnHeaders()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfRowHeaders()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfColumns()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfRows()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfVisibleCells()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributesOfHeader()
{
    return JSStringCreateWithCharacters(0, 0);
}

int AccessibilityUIElement::indexInTable()
{
    return 0;
}

JSStringRef AccessibilityUIElement::rowIndexRange()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::columnIndexRange()
{
    return JSStringCreateWithCharacters(0, 0);
}

int AccessibilityUIElement::lineForIndex(int)
{
    return 0;
}

JSStringRef AccessibilityUIElement::boundsForRange(unsigned location, unsigned length)
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::stringForRange(unsigned, unsigned)
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::attributedStringForRange(unsigned, unsigned)
{
    return JSStringCreateWithCharacters(0, 0);
}

bool AccessibilityUIElement::attributedStringRangeIsMisspelled(unsigned, unsigned)
{
    return false;
}

AccessibilityUIElement AccessibilityUIElement::cellForColumnAndRow(unsigned column, unsigned row)
{
    return 0;
}

JSStringRef AccessibilityUIElement::selectedTextRange()
{
    return JSStringCreateWithCharacters(0, 0);    
}

void AccessibilityUIElement::setSelectedTextRange(unsigned location, unsigned length)
{
}

JSStringRef AccessibilityUIElement::stringAttributeValue(JSStringRef attribute)
{
    // FIXME: implement
    return JSStringCreateWithCharacters(0, 0);
}

bool AccessibilityUIElement::boolAttributeValue(JSStringRef attribute)
{
    // FIXME: implement
    return false;
}

bool AccessibilityUIElement::isAttributeSettable(JSStringRef attribute)
{
    return false;
}

bool AccessibilityUIElement::isAttributeSupported(JSStringRef attribute)
{
    return false;
}

void AccessibilityUIElement::increment()
{
}

void AccessibilityUIElement::decrement()
{
}

void AccessibilityUIElement::showMenu()
{
    ASSERT(hasPopup());
    m_element->accDoDefaultAction(self());
}

void AccessibilityUIElement::press()
{
    // FIXME: implement
}

AccessibilityUIElement AccessibilityUIElement::disclosedRowAtIndex(unsigned index)
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::ariaOwnsElementAtIndex(unsigned index)
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::ariaFlowToElementAtIndex(unsigned index)
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::selectedRowAtIndex(unsigned index)
{
    return 0;
}

AccessibilityUIElement AccessibilityUIElement::disclosedByRow()
{
    return 0;
}

JSStringRef AccessibilityUIElement::accessibilityValue() const
{
    BSTR valueBSTR;
    if (FAILED(m_element->get_accValue(self(), &valueBSTR)) || !valueBSTR)
        return JSStringCreateWithCharacters(0, 0);

    wstring value(valueBSTR, SysStringLen(valueBSTR));
    ::SysFreeString(valueBSTR);

    return JSStringCreateWithCharacters(value.data(), value.length());
}


JSStringRef AccessibilityUIElement::documentEncoding()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::documentURI()
{
    return JSStringCreateWithCharacters(0, 0);
}

JSStringRef AccessibilityUIElement::url()
{
    // FIXME: implement
    return JSStringCreateWithCharacters(0, 0);
}

bool AccessibilityUIElement::addNotificationListener(JSObjectRef functionCallback)
{
    if (!functionCallback)
        return false;

    sharedFrameLoadDelegate->accessibilityController()->addNotificationListener(m_element, functionCallback);
    return true;
}

void AccessibilityUIElement::removeNotificationListener()
{
    // FIXME: implement
}

bool AccessibilityUIElement::isFocusable() const
{
    // FIXME: implement
    return false;
}

bool AccessibilityUIElement::isSelectable() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_SELECTABLE) == STATE_SYSTEM_SELECTABLE;
}

bool AccessibilityUIElement::isMultiSelectable() const
{
    DWORD multiSelectable = STATE_SYSTEM_EXTSELECTABLE | STATE_SYSTEM_MULTISELECTABLE;
    DWORD state = accessibilityState(m_element);
    return (state & multiSelectable) == multiSelectable;
}

bool AccessibilityUIElement::isVisible() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_INVISIBLE) != STATE_SYSTEM_INVISIBLE;
}

bool AccessibilityUIElement::isOffScreen() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_OFFSCREEN) == STATE_SYSTEM_OFFSCREEN;
}

bool AccessibilityUIElement::isCollapsed() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_COLLAPSED) == STATE_SYSTEM_COLLAPSED;
}

bool AccessibilityUIElement::isIgnored() const
{
    // FIXME: implement
    return false;
}

bool AccessibilityUIElement::hasPopup() const
{
    DWORD state = accessibilityState(m_element);
    return (state & STATE_SYSTEM_HASPOPUP) == STATE_SYSTEM_HASPOPUP;
}

void AccessibilityUIElement::takeFocus()
{
    m_element->accSelect(SELFLAG_TAKEFOCUS, self());
}

void AccessibilityUIElement::takeSelection()
{
    m_element->accSelect(SELFLAG_TAKESELECTION, self());
}

void AccessibilityUIElement::addSelection()
{
    m_element->accSelect(SELFLAG_ADDSELECTION, self());
}

void AccessibilityUIElement::removeSelection()
{
    m_element->accSelect(SELFLAG_REMOVESELECTION, self());
}
