accessible/src/generic/ImageAccessible.cpp

Wed, 31 Dec 2014 07:16:47 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 07:16:47 +0100
branch
TOR_BUG_9701
changeset 3
141e0f1194b1
permissions
-rw-r--r--

Revert simplistic fix pending revisit of Mozilla integration attempt.

michael@0 1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
michael@0 2 /* This Source Code Form is subject to the terms of the Mozilla Public
michael@0 3 * License, v. 2.0. If a copy of the MPL was not distributed with this
michael@0 4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
michael@0 5
michael@0 6 #include "ImageAccessible.h"
michael@0 7
michael@0 8 #include "nsAccUtils.h"
michael@0 9 #include "Role.h"
michael@0 10 #include "AccIterator.h"
michael@0 11 #include "States.h"
michael@0 12
michael@0 13 #include "imgIContainer.h"
michael@0 14 #include "imgIRequest.h"
michael@0 15 #include "nsGenericHTMLElement.h"
michael@0 16 #include "nsIDocument.h"
michael@0 17 #include "nsIImageLoadingContent.h"
michael@0 18 #include "nsIPresShell.h"
michael@0 19 #include "nsIServiceManager.h"
michael@0 20 #include "nsIDOMHTMLImageElement.h"
michael@0 21 #include "nsIPersistentProperties2.h"
michael@0 22 #include "nsPIDOMWindow.h"
michael@0 23 #include "nsIURI.h"
michael@0 24
michael@0 25 using namespace mozilla::a11y;
michael@0 26
michael@0 27 ////////////////////////////////////////////////////////////////////////////////
michael@0 28 // ImageAccessible
michael@0 29 ////////////////////////////////////////////////////////////////////////////////
michael@0 30
michael@0 31 ImageAccessible::
michael@0 32 ImageAccessible(nsIContent* aContent, DocAccessible* aDoc) :
michael@0 33 LinkableAccessible(aContent, aDoc)
michael@0 34 {
michael@0 35 mType = eImageType;
michael@0 36 }
michael@0 37
michael@0 38 NS_IMPL_ISUPPORTS_INHERITED(ImageAccessible, Accessible,
michael@0 39 nsIAccessibleImage)
michael@0 40
michael@0 41 ////////////////////////////////////////////////////////////////////////////////
michael@0 42 // Accessible public
michael@0 43
michael@0 44 uint64_t
michael@0 45 ImageAccessible::NativeState()
michael@0 46 {
michael@0 47 // The state is a bitfield, get our inherited state, then logically OR it with
michael@0 48 // states::ANIMATED if this is an animated image.
michael@0 49
michael@0 50 uint64_t state = LinkableAccessible::NativeState();
michael@0 51
michael@0 52 nsCOMPtr<nsIImageLoadingContent> content(do_QueryInterface(mContent));
michael@0 53 nsCOMPtr<imgIRequest> imageRequest;
michael@0 54
michael@0 55 if (content)
michael@0 56 content->GetRequest(nsIImageLoadingContent::CURRENT_REQUEST,
michael@0 57 getter_AddRefs(imageRequest));
michael@0 58
michael@0 59 nsCOMPtr<imgIContainer> imgContainer;
michael@0 60 if (imageRequest)
michael@0 61 imageRequest->GetImage(getter_AddRefs(imgContainer));
michael@0 62
michael@0 63 if (imgContainer) {
michael@0 64 bool animated;
michael@0 65 imgContainer->GetAnimated(&animated);
michael@0 66 if (animated)
michael@0 67 state |= states::ANIMATED;
michael@0 68 }
michael@0 69
michael@0 70 return state;
michael@0 71 }
michael@0 72
michael@0 73 ENameValueFlag
michael@0 74 ImageAccessible::NativeName(nsString& aName)
michael@0 75 {
michael@0 76 bool hasAltAttrib =
michael@0 77 mContent->GetAttr(kNameSpaceID_None, nsGkAtoms::alt, aName);
michael@0 78 if (!aName.IsEmpty())
michael@0 79 return eNameOK;
michael@0 80
michael@0 81 ENameValueFlag nameFlag = Accessible::NativeName(aName);
michael@0 82 if (!aName.IsEmpty())
michael@0 83 return nameFlag;
michael@0 84
michael@0 85 // No accessible name but empty 'alt' attribute is present. If further name
michael@0 86 // computation algorithm doesn't provide non empty name then it means
michael@0 87 // an empty 'alt' attribute was used to indicate a decorative image (see
michael@0 88 // Accessible::Name() method for details).
michael@0 89 return hasAltAttrib ? eNoNameOnPurpose : eNameOK;
michael@0 90 }
michael@0 91
michael@0 92 role
michael@0 93 ImageAccessible::NativeRole()
michael@0 94 {
michael@0 95 return roles::GRAPHIC;
michael@0 96 }
michael@0 97
michael@0 98 ////////////////////////////////////////////////////////////////////////////////
michael@0 99 // nsIAccessible
michael@0 100
michael@0 101 uint8_t
michael@0 102 ImageAccessible::ActionCount()
michael@0 103 {
michael@0 104 uint8_t actionCount = LinkableAccessible::ActionCount();
michael@0 105 return HasLongDesc() ? actionCount + 1 : actionCount;
michael@0 106 }
michael@0 107
michael@0 108 NS_IMETHODIMP
michael@0 109 ImageAccessible::GetActionName(uint8_t aIndex, nsAString& aName)
michael@0 110 {
michael@0 111 aName.Truncate();
michael@0 112
michael@0 113 if (IsDefunct())
michael@0 114 return NS_ERROR_FAILURE;
michael@0 115
michael@0 116 if (IsLongDescIndex(aIndex) && HasLongDesc()) {
michael@0 117 aName.AssignLiteral("showlongdesc");
michael@0 118 return NS_OK;
michael@0 119 }
michael@0 120 return LinkableAccessible::GetActionName(aIndex, aName);
michael@0 121 }
michael@0 122
michael@0 123 NS_IMETHODIMP
michael@0 124 ImageAccessible::DoAction(uint8_t aIndex)
michael@0 125 {
michael@0 126 if (IsDefunct())
michael@0 127 return NS_ERROR_FAILURE;
michael@0 128
michael@0 129 // Get the long description uri and open in a new window.
michael@0 130 if (!IsLongDescIndex(aIndex))
michael@0 131 return LinkableAccessible::DoAction(aIndex);
michael@0 132
michael@0 133 nsCOMPtr<nsIURI> uri = GetLongDescURI();
michael@0 134 if (!uri)
michael@0 135 return NS_ERROR_INVALID_ARG;
michael@0 136
michael@0 137 nsAutoCString utf8spec;
michael@0 138 uri->GetSpec(utf8spec);
michael@0 139 NS_ConvertUTF8toUTF16 spec(utf8spec);
michael@0 140
michael@0 141 nsIDocument* document = mContent->OwnerDoc();
michael@0 142 nsCOMPtr<nsPIDOMWindow> piWindow = document->GetWindow();
michael@0 143 nsCOMPtr<nsIDOMWindow> win = do_QueryInterface(piWindow);
michael@0 144 NS_ENSURE_STATE(win);
michael@0 145
michael@0 146 nsCOMPtr<nsIDOMWindow> tmp;
michael@0 147 return win->Open(spec, EmptyString(), EmptyString(),
michael@0 148 getter_AddRefs(tmp));
michael@0 149 }
michael@0 150
michael@0 151 ////////////////////////////////////////////////////////////////////////////////
michael@0 152 // nsIAccessibleImage
michael@0 153
michael@0 154 NS_IMETHODIMP
michael@0 155 ImageAccessible::GetImagePosition(uint32_t aCoordType, int32_t* aX, int32_t* aY)
michael@0 156 {
michael@0 157 int32_t width, height;
michael@0 158 nsresult rv = GetBounds(aX, aY, &width, &height);
michael@0 159 if (NS_FAILED(rv))
michael@0 160 return rv;
michael@0 161
michael@0 162 nsAccUtils::ConvertScreenCoordsTo(aX, aY, aCoordType, this);
michael@0 163 return NS_OK;
michael@0 164 }
michael@0 165
michael@0 166 NS_IMETHODIMP
michael@0 167 ImageAccessible::GetImageSize(int32_t* aWidth, int32_t* aHeight)
michael@0 168 {
michael@0 169 int32_t x, y;
michael@0 170 return GetBounds(&x, &y, aWidth, aHeight);
michael@0 171 }
michael@0 172
michael@0 173 // Accessible
michael@0 174 already_AddRefed<nsIPersistentProperties>
michael@0 175 ImageAccessible::NativeAttributes()
michael@0 176 {
michael@0 177 nsCOMPtr<nsIPersistentProperties> attributes =
michael@0 178 LinkableAccessible::NativeAttributes();
michael@0 179
michael@0 180 nsAutoString src;
michael@0 181 mContent->GetAttr(kNameSpaceID_None, nsGkAtoms::src, src);
michael@0 182 if (!src.IsEmpty())
michael@0 183 nsAccUtils::SetAccAttr(attributes, nsGkAtoms::src, src);
michael@0 184
michael@0 185 return attributes.forget();
michael@0 186 }
michael@0 187
michael@0 188 ////////////////////////////////////////////////////////////////////////////////
michael@0 189 // Private methods
michael@0 190
michael@0 191 already_AddRefed<nsIURI>
michael@0 192 ImageAccessible::GetLongDescURI() const
michael@0 193 {
michael@0 194 if (mContent->HasAttr(kNameSpaceID_None, nsGkAtoms::longdesc)) {
michael@0 195 nsGenericHTMLElement* element =
michael@0 196 nsGenericHTMLElement::FromContent(mContent);
michael@0 197 if (element) {
michael@0 198 nsCOMPtr<nsIURI> uri;
michael@0 199 element->GetURIAttr(nsGkAtoms::longdesc, nullptr, getter_AddRefs(uri));
michael@0 200 return uri.forget();
michael@0 201 }
michael@0 202 }
michael@0 203
michael@0 204 DocAccessible* document = Document();
michael@0 205 if (document) {
michael@0 206 IDRefsIterator iter(document, mContent, nsGkAtoms::aria_describedby);
michael@0 207 while (nsIContent* target = iter.NextElem()) {
michael@0 208 if ((target->IsHTML(nsGkAtoms::a) || target->IsHTML(nsGkAtoms::area)) &&
michael@0 209 target->HasAttr(kNameSpaceID_None, nsGkAtoms::href)) {
michael@0 210 nsGenericHTMLElement* element =
michael@0 211 nsGenericHTMLElement::FromContent(target);
michael@0 212
michael@0 213 nsCOMPtr<nsIURI> uri;
michael@0 214 element->GetURIAttr(nsGkAtoms::href, nullptr, getter_AddRefs(uri));
michael@0 215 return uri.forget();
michael@0 216 }
michael@0 217 }
michael@0 218 }
michael@0 219
michael@0 220 return nullptr;
michael@0 221 }
michael@0 222
michael@0 223 bool
michael@0 224 ImageAccessible::IsLongDescIndex(uint8_t aIndex)
michael@0 225 {
michael@0 226 return aIndex == LinkableAccessible::ActionCount();
michael@0 227 }
michael@0 228

mercurial