]> git.saurik.com Git - wxWidgets.git/blame_incremental - src/msw/ole/access.cpp
Back to previous call with -1 replacement.
[wxWidgets.git] / src / msw / ole / access.cpp
... / ...
CommitLineData
1///////////////////////////////////////////////////////////////////////////////
2// Name: src/msw/ole/access.cpp
3// Purpose: implementation of wxIAccessible and wxAccessible
4// Author: Julian Smart
5// Modified by:
6// Created: 2003-02-12
7// RCS-ID: $Id$
8// Copyright: (c) 2003 Julian Smart
9// Licence: wxWindows licence
10///////////////////////////////////////////////////////////////////////////////
11
12// ============================================================================
13// declarations
14// ============================================================================
15
16// ----------------------------------------------------------------------------
17// headers
18// ----------------------------------------------------------------------------
19
20// For compilers that support precompilation, includes "wx.h".
21#include "wx/wxprec.h"
22
23#if defined(__BORLANDC__)
24 #pragma hdrstop
25#endif
26
27#if wxUSE_OLE && wxUSE_ACCESSIBILITY
28
29#include "wx/access.h"
30
31#ifndef WX_PRECOMP
32 #include "wx/msw/wrapwin.h"
33 #include "wx/window.h"
34 #include "wx/log.h"
35#endif
36
37// for some compilers, the entire ole2.h must be included, not only oleauto.h
38#if wxUSE_NORLANDER_HEADERS || defined(__WATCOMC__)
39 #include <ole2.h>
40#endif
41
42#include <oleauto.h>
43#include <oleacc.h>
44#include <winable.h>
45
46#include "wx/msw/ole/oleutils.h"
47
48#ifndef CHILDID_SELF
49#define CHILDID_SELF 0
50#endif
51
52#ifndef OBJID_CLIENT
53#define OBJID_CLIENT 0xFFFFFFFC
54#endif
55
56// Convert to Windows role
57int wxConvertToWindowsRole(wxAccRole wxrole);
58
59// Convert to Windows state
60long wxConvertToWindowsState(long wxstate);
61
62// Convert to Windows selection flag
63int wxConvertToWindowsSelFlag(wxAccSelectionFlags sel);
64
65// Convert from Windows selection flag
66wxAccSelectionFlags wxConvertFromWindowsSelFlag(int sel);
67
68#if wxUSE_VARIANT
69// ----------------------------------------------------------------------------
70// wxIEnumVARIANT interface implementation
71// ----------------------------------------------------------------------------
72
73class wxIEnumVARIANT : public IEnumVARIANT
74{
75public:
76 wxIEnumVARIANT(const wxVariant& variant);
77 virtual ~wxIEnumVARIANT() { }
78
79 DECLARE_IUNKNOWN_METHODS;
80
81 // IEnumVARIANT
82 STDMETHODIMP Next(ULONG celt, VARIANT *rgelt, ULONG *pceltFetched);
83 STDMETHODIMP Skip(ULONG celt);
84 STDMETHODIMP Reset();
85 STDMETHODIMP Clone(IEnumVARIANT **ppenum);
86
87private:
88 wxVariant m_variant; // List of further variants
89 int m_nCurrent; // Current enum position
90
91 DECLARE_NO_COPY_CLASS(wxIEnumVARIANT)
92};
93
94// ----------------------------------------------------------------------------
95// wxIEnumVARIANT
96// ----------------------------------------------------------------------------
97
98BEGIN_IID_TABLE(wxIEnumVARIANT)
99 ADD_IID(Unknown)
100 ADD_IID(EnumVARIANT)
101END_IID_TABLE;
102
103IMPLEMENT_IUNKNOWN_METHODS(wxIEnumVARIANT)
104
105// wxVariant contains a list of further variants.
106wxIEnumVARIANT::wxIEnumVARIANT(const wxVariant& variant)
107{
108 m_variant = variant;
109}
110
111STDMETHODIMP wxIEnumVARIANT::Next(ULONG celt,
112 VARIANT *rgelt,
113 ULONG *pceltFetched)
114{
115 wxLogTrace(wxTRACE_OleCalls, wxT("wxIEnumVARIANT::Next"));
116
117 if ( celt > 1 ) {
118 // we only return 1 element at a time - mainly because I'm too lazy to
119 // implement something which you're never asked for anyhow
120 return S_FALSE;
121 }
122
123 if (m_variant.GetType() != wxT("list"))
124 return S_FALSE;
125
126 if ( m_nCurrent < (int) m_variant.GetList().GetCount() ) {
127 if (!wxConvertVariantToOle(m_variant[m_nCurrent++], rgelt[0]))
128 {
129 return S_FALSE;
130 }
131
132 // TODO: should we AddRef if this is an object?
133
134 * pceltFetched = 1;
135 return S_OK;
136 }
137 else {
138 // bad index
139 return S_FALSE;
140 }
141}
142
143STDMETHODIMP wxIEnumVARIANT::Skip(ULONG celt)
144{
145 wxLogTrace(wxTRACE_OleCalls, wxT("wxIEnumVARIANT::Skip"));
146
147 if (m_variant.GetType() != wxT("list"))
148 return S_FALSE;
149
150 m_nCurrent += celt;
151 if ( m_nCurrent < (int) m_variant.GetList().GetCount() )
152 return S_OK;
153
154 // no, can't skip this many elements
155 m_nCurrent -= celt;
156
157 return S_FALSE;
158}
159
160STDMETHODIMP wxIEnumVARIANT::Reset()
161{
162 wxLogTrace(wxTRACE_OleCalls, wxT("wxIEnumVARIANT::Reset"));
163
164 m_nCurrent = 0;
165
166 return S_OK;
167}
168
169STDMETHODIMP wxIEnumVARIANT::Clone(IEnumVARIANT **ppenum)
170{
171 wxLogTrace(wxTRACE_OleCalls, wxT("wxIEnumVARIANT::Clone"));
172
173 wxIEnumVARIANT *pNew = new wxIEnumVARIANT(m_variant);
174 pNew->AddRef();
175 *ppenum = pNew;
176
177 return S_OK;
178}
179
180#endif // wxUSE_VARIANT
181
182// ----------------------------------------------------------------------------
183// wxIAccessible implementation of IAccessible interface
184// ----------------------------------------------------------------------------
185
186class wxIAccessible : public IAccessible
187{
188public:
189 wxIAccessible(wxAccessible *pAccessible);
190
191 DECLARE_IUNKNOWN_METHODS;
192
193// IAccessible
194
195// Navigation and Hierarchy
196
197 // Retrieves the child element or child object at a given point on the screen.
198 // All visual objects support this method; sound objects do not support it.
199
200 STDMETHODIMP accHitTest(long xLeft, long yLeft, VARIANT* pVarID);
201
202 // Retrieves the specified object's current screen location. All visual objects must
203 // support this method; sound objects do not support it.
204
205 STDMETHODIMP accLocation ( long* pxLeft, long* pyTop, long* pcxWidth, long* pcyHeight, VARIANT varID);
206
207 // Traverses to another user interface element within a container and retrieves the object.
208 // All visual objects must support this method.
209
210 STDMETHODIMP accNavigate ( long navDir, VARIANT varStart, VARIANT* pVarEnd);
211
212 // Retrieves the address of an IDispatch interface for the specified child.
213 // All objects must support this property.
214
215 STDMETHODIMP get_accChild ( VARIANT varChildID, IDispatch** ppDispChild);
216
217 // Retrieves the number of children that belong to this object.
218 // All objects must support this property.
219
220 STDMETHODIMP get_accChildCount ( long* pCountChildren);
221
222 // Retrieves the IDispatch interface of the object's parent.
223 // All objects support this property.
224
225 STDMETHODIMP get_accParent ( IDispatch** ppDispParent);
226
227// Descriptive Properties and Methods
228
229 // Performs the object's default action. Not all objects have a default
230 // action.
231
232 STDMETHODIMP accDoDefaultAction(VARIANT varID);
233
234 // Retrieves a string that describes the object's default action.
235 // Not all objects have a default action.
236
237 STDMETHODIMP get_accDefaultAction ( VARIANT varID, BSTR* pszDefaultAction);
238
239 // Retrieves a string that describes the visual appearance of the specified object.
240 // Not all objects have a description.
241
242 STDMETHODIMP get_accDescription ( VARIANT varID, BSTR* pszDescription);
243
244 // Retrieves an object's Help property string.
245 // Not all objects support this property.
246
247 STDMETHODIMP get_accHelp ( VARIANT varID, BSTR* pszHelp);
248
249 // Retrieves the full path of the WinHelp file associated with the specified
250 // object and the identifier of the appropriate topic within that file.
251 // Not all objects support this property.
252
253 STDMETHODIMP get_accHelpTopic ( BSTR* pszHelpFile, VARIANT varChild, long* pidTopic);
254
255 // Retrieves the specified object's shortcut key or access key, also known as
256 // the mnemonic. All objects that have a shortcut key or access key support
257 // this property.
258
259 STDMETHODIMP get_accKeyboardShortcut ( VARIANT varID, BSTR* pszKeyboardShortcut);
260
261 // Retrieves the name of the specified object.
262 // All objects support this property.
263
264 STDMETHODIMP get_accName ( VARIANT varID, BSTR* pszName);
265
266 // Retrieves information that describes the role of the specified object.
267 // All objects support this property.
268
269 STDMETHODIMP get_accRole ( VARIANT varID, VARIANT* pVarRole);
270
271 // Retrieves the current state of the specified object.
272 // All objects support this property.
273
274 STDMETHODIMP get_accState ( VARIANT varID, VARIANT* pVarState);
275
276 // Retrieves the value of the specified object.
277 // Not all objects have a value.
278
279 STDMETHODIMP get_accValue ( VARIANT varID, BSTR* pszValue);
280
281// Selection and Focus
282
283 // Modifies the selection or moves the keyboard focus of the
284 // specified object. All objects that select or receive the
285 // keyboard focus must support this method.
286
287 STDMETHODIMP accSelect ( long flagsSelect, VARIANT varID );
288
289 // Retrieves the object that has the keyboard focus. All objects
290 // that receive the keyboard focus must support this property.
291
292 STDMETHODIMP get_accFocus ( VARIANT* pVarID);
293
294 // Retrieves the selected children of this object. All objects
295 // selected must support this property.
296
297 STDMETHODIMP get_accSelection ( VARIANT * pVarChildren);
298
299// Obsolete
300
301 STDMETHODIMP put_accName(VARIANT WXUNUSED(varChild), BSTR WXUNUSED(szName)) { return E_FAIL; }
302 STDMETHODIMP put_accValue(VARIANT WXUNUSED(varChild), BSTR WXUNUSED(szName)) { return E_FAIL; }
303
304// IDispatch
305
306 // Get type info
307
308 STDMETHODIMP GetTypeInfo(unsigned int typeInfo, LCID lcid, ITypeInfo** ppTypeInfo);
309
310 // Get type info count
311
312 STDMETHODIMP GetTypeInfoCount(unsigned int* typeInfoCount);
313
314 // Get ids of names
315
316 STDMETHODIMP GetIDsOfNames(REFIID riid, OLECHAR** names, unsigned int cNames,
317 LCID lcid, DISPID* dispId);
318
319 // Invoke
320
321 STDMETHODIMP Invoke(DISPID dispIdMember, REFIID riid, LCID lcid,
322 WORD wFlags, DISPPARAMS *pDispParams,
323 VARIANT *pVarResult, EXCEPINFO *pExcepInfo,
324 unsigned int *puArgErr );
325
326// Helpers
327
328 // Gets the standard IAccessible interface for the given child or object.
329 // Call Release if this is non-NULL.
330 IAccessible* GetChildStdAccessible(int id);
331
332 // Gets the IAccessible interface for the given child or object.
333 // Call Release if this is non-NULL.
334 IAccessible* GetChildAccessible(int id);
335
336private:
337 wxAccessible *m_pAccessible; // pointer to C++ class we belong to
338
339 DECLARE_NO_COPY_CLASS(wxIAccessible)
340};
341
342// ============================================================================
343// Implementation
344// ============================================================================
345
346// ----------------------------------------------------------------------------
347// wxIAccessible implementation
348// ----------------------------------------------------------------------------
349BEGIN_IID_TABLE(wxIAccessible)
350 ADD_IID(Unknown)
351 ADD_IID(Accessible)
352 ADD_IID(Dispatch)
353END_IID_TABLE;
354
355IMPLEMENT_IUNKNOWN_METHODS(wxIAccessible)
356
357wxIAccessible::wxIAccessible(wxAccessible *pAccessible)
358{
359 wxASSERT( pAccessible != NULL );
360
361 m_pAccessible = pAccessible;
362}
363
364// Retrieves the child element or child object at a given point on the screen.
365// All visual objects support this method; sound objects do not support it.
366
367STDMETHODIMP wxIAccessible::accHitTest(long xLeft, long yLeft, VARIANT* pVarID)
368{
369 wxLogTrace(wxT("access"), wxT("accHitTest"));
370 wxASSERT (m_pAccessible != NULL);
371 if (!m_pAccessible)
372 return E_FAIL;
373
374 wxAccessible* childObject = NULL;
375 int childId = 0;
376 VariantInit(pVarID);
377
378 wxAccStatus status = m_pAccessible->HitTest(wxPoint(xLeft, yLeft), & childId, & childObject);
379
380 if (status == wxACC_FAIL)
381 return E_FAIL;
382
383 if (status == wxACC_NOT_IMPLEMENTED)
384 {
385 // Use standard interface instead.
386 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
387 if (!stdInterface)
388 return E_NOTIMPL;
389 else
390 return stdInterface->accHitTest(xLeft, yLeft, pVarID);
391 }
392
393 if (childObject)
394 {
395 if (childObject == m_pAccessible)
396 {
397 pVarID->vt = VT_I4;
398 pVarID->lVal = CHILDID_SELF;
399 return S_OK;
400 }
401 else
402 {
403 wxIAccessible* childIA = childObject->GetIAccessible();
404 if (!childIA)
405 return E_NOTIMPL;
406
407 if (childIA->QueryInterface(IID_IDispatch, (LPVOID*) & pVarID->pdispVal) != S_OK)
408 return E_FAIL;
409
410 pVarID->vt = VT_DISPATCH;
411 return S_OK;
412 }
413 }
414 else if (childId > 0)
415 {
416 pVarID->vt = VT_I4;
417 pVarID->lVal = childId;
418 return S_OK;
419 }
420 else
421 {
422 pVarID->vt = VT_EMPTY;
423 return S_FALSE;
424 }
425
426 #if 0
427 // all cases above already cause some return action so below line
428 // is unreachable and cause unnecessary warning
429 return E_NOTIMPL;
430 #endif
431}
432
433// Retrieves the specified object's current screen location. All visual objects must
434// support this method; sound objects do not support it.
435
436STDMETHODIMP wxIAccessible::accLocation ( long* pxLeft, long* pyTop, long* pcxWidth, long* pcyHeight, VARIANT varID)
437{
438 wxLogTrace(wxT("access"), wxT("accLocation"));
439 wxASSERT (m_pAccessible != NULL);
440 if (!m_pAccessible)
441 return E_FAIL;
442
443 wxRect rect;
444
445 wxAccStatus status = m_pAccessible->GetLocation(rect, varID.lVal);
446 if (status == wxACC_FAIL)
447 return E_FAIL;
448
449 if (status == wxACC_NOT_IMPLEMENTED)
450 {
451 // Try to use child object directly.
452 if (varID.lVal > 0)
453 {
454 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
455 if (childAccessible)
456 {
457 varID.lVal = 0;
458 HRESULT hResult = childAccessible->accLocation(pxLeft, pyTop, pcxWidth, pcyHeight, varID);
459 childAccessible->Release();
460 return hResult;
461 }
462 else if (m_pAccessible->GetIAccessibleStd())
463 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accLocation(pxLeft, pyTop, pcxWidth, pcyHeight, varID);
464 }
465 else if (m_pAccessible->GetIAccessibleStd())
466 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accLocation(pxLeft, pyTop, pcxWidth, pcyHeight, varID);
467 }
468 else
469 {
470 *pxLeft = rect.x;
471 *pyTop = rect.y;
472 *pcxWidth = rect.width;
473 *pcyHeight = rect.height;
474 return S_OK;
475 }
476
477 return E_NOTIMPL;
478}
479
480// Traverses to another user interface element within a container and retrieves the object.
481// All visual objects must support this method.
482
483STDMETHODIMP wxIAccessible::accNavigate ( long navDir, VARIANT varStart, VARIANT* pVarEnd)
484{
485 wxASSERT (m_pAccessible != NULL);
486 if (!m_pAccessible)
487 return E_FAIL;
488 wxLogTrace(wxT("access"), wxString(wxT("accNavigate for ")) + m_pAccessible->GetWindow()->GetClassInfo()->GetClassName());
489
490 if ((varStart.vt != VT_I4 && varStart.vt != VT_EMPTY)
491 #if 0
492 // according to MSDN and sources varStart.vt is unsigned
493 // so below line cause warning "Condition is always false"
494 || varStart.vt < 0
495 #endif
496 )
497 {
498 wxLogTrace(wxT("access"), wxT("Invalid arg for accNavigate"));
499 return E_INVALIDARG;
500 }
501
502 wxAccessible* elementObject = NULL;
503 int elementId = 0;
504 VariantInit(pVarEnd);
505 wxNavDir navDirWX = wxNAVDIR_FIRSTCHILD;
506
507 wxString navStr;
508
509 switch (navDir)
510 {
511 case NAVDIR_DOWN:
512 navDirWX = wxNAVDIR_DOWN;
513 navStr = wxT("wxNAVDIR_DOWN");
514 break;
515
516 case NAVDIR_FIRSTCHILD:
517 navDirWX = wxNAVDIR_FIRSTCHILD;
518 navStr = wxT("wxNAVDIR_FIRSTCHILD");
519 break;
520
521 case NAVDIR_LASTCHILD:
522 navDirWX = wxNAVDIR_LASTCHILD;
523 navStr = wxT("wxNAVDIR_LASTCHILD");
524 break;
525
526 case NAVDIR_LEFT:
527 navDirWX = wxNAVDIR_LEFT;
528 navStr = wxT("wxNAVDIR_LEFT");
529 break;
530
531 case NAVDIR_NEXT:
532 navDirWX = wxNAVDIR_NEXT;
533 navStr = wxT("wxNAVDIR_NEXT");
534 break;
535
536 case NAVDIR_PREVIOUS:
537 navDirWX = wxNAVDIR_PREVIOUS;
538 navStr = wxT("wxNAVDIR_PREVIOUS");
539 break;
540
541 case NAVDIR_RIGHT:
542 navDirWX = wxNAVDIR_RIGHT;
543 navStr = wxT("wxNAVDIR_RIGHT");
544 break;
545
546 case NAVDIR_UP:
547 navDirWX = wxNAVDIR_UP;
548 navStr = wxT("wxNAVDIR_UP");
549 break;
550 default:
551 {
552 wxLogTrace(wxT("access"), wxT("Unknown NAVDIR symbol"));
553 break;
554 }
555 }
556 wxLogTrace(wxT("access"), navStr);
557
558 wxAccStatus status = m_pAccessible->Navigate(navDirWX, varStart.lVal, & elementId,
559 & elementObject);
560
561 if (status == wxACC_FAIL)
562 {
563 wxLogTrace(wxT("access"), wxT("wxAccessible::Navigate failed"));
564 return E_FAIL;
565 }
566
567 if (status == wxACC_FALSE)
568 {
569 wxLogTrace(wxT("access"), wxT("wxAccessible::Navigate found no object in this direction"));
570 return S_FALSE;
571 }
572
573 if (status == wxACC_NOT_IMPLEMENTED)
574 {
575 wxLogTrace(wxT("access"), wxT("Navigate not implemented"));
576
577 // Try to use child object directly.
578 if (varStart.vt == VT_I4 && varStart.lVal > 0)
579 {
580 IAccessible* childAccessible = GetChildAccessible(varStart.lVal);
581 if (childAccessible)
582 {
583 varStart.lVal = 0;
584 HRESULT hResult = childAccessible->accNavigate(navDir, varStart, pVarEnd);
585 childAccessible->Release();
586 return hResult;
587 }
588 else if (m_pAccessible->GetIAccessibleStd())
589 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accNavigate(navDir, varStart, pVarEnd);
590 }
591 else if (m_pAccessible->GetIAccessibleStd())
592 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accNavigate(navDir, varStart, pVarEnd);
593 }
594 else
595 {
596 if (elementObject)
597 {
598 wxLogTrace(wxT("access"), wxT("Getting wxIAccessible and calling QueryInterface for Navigate"));
599 wxIAccessible* objectIA = elementObject->GetIAccessible();
600 if (!objectIA)
601 {
602 wxLogTrace(wxT("access"), wxT("No wxIAccessible"));
603 return E_FAIL;
604 }
605
606 HRESULT hResult = objectIA->QueryInterface(IID_IDispatch, (LPVOID*) & pVarEnd->pdispVal);
607 if (hResult != S_OK)
608 {
609 wxLogTrace(wxT("access"), wxT("QueryInterface failed"));
610 return E_FAIL;
611 }
612
613 wxLogTrace(wxT("access"), wxT("Called QueryInterface for Navigate"));
614 pVarEnd->vt = VT_DISPATCH;
615 return S_OK;
616 }
617 else if (elementId > 0)
618 {
619 wxLogTrace(wxT("access"), wxT("Returning element id from Navigate"));
620 pVarEnd->vt = VT_I4;
621 pVarEnd->lVal = elementId;
622 return S_OK;
623 }
624 else
625 {
626 wxLogTrace(wxT("access"), wxT("No object in accNavigate"));
627 pVarEnd->vt = VT_EMPTY;
628 return S_FALSE;
629 }
630 }
631
632 wxLogTrace(wxT("access"), wxT("Failing Navigate"));
633 return E_NOTIMPL;
634}
635
636// Retrieves the address of an IDispatch interface for the specified child.
637// All objects must support this property.
638
639STDMETHODIMP wxIAccessible::get_accChild ( VARIANT varChildID, IDispatch** ppDispChild)
640{
641 wxLogTrace(wxT("access"), wxT("get_accChild"));
642 wxASSERT (m_pAccessible != NULL);
643 if (!m_pAccessible)
644 return E_FAIL;
645
646 if (varChildID.vt != VT_I4)
647 {
648 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accChild"));
649 return E_INVALIDARG;
650 }
651
652 if (varChildID.lVal == CHILDID_SELF)
653 {
654 *ppDispChild = this;
655 AddRef();
656 return S_OK;
657 }
658
659 wxAccessible* child = NULL;
660
661 wxAccStatus status = m_pAccessible->GetChild(varChildID.lVal, & child);
662 if (status == wxACC_FAIL)
663 {
664 wxLogTrace(wxT("access"), wxT("GetChild failed"));
665 return E_FAIL;
666 }
667
668 if (status == wxACC_NOT_IMPLEMENTED)
669 {
670 // Use standard interface instead.
671 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
672 if (!stdInterface)
673 return E_NOTIMPL;
674 else
675 {
676 wxLogTrace(wxT("access"), wxT("Using standard interface for get_accChild"));
677 return stdInterface->get_accChild (varChildID, ppDispChild);
678 }
679 }
680 else
681 {
682 if (child)
683 {
684 wxIAccessible* objectIA = child->GetIAccessible();
685 if (!objectIA)
686 return E_NOTIMPL;
687
688 if (objectIA->QueryInterface(IID_IDispatch, (LPVOID*) ppDispChild) != S_OK)
689 {
690 wxLogTrace(wxT("access"), wxT("QueryInterface failed in get_accChild"));
691 return E_FAIL;
692 }
693
694 return S_OK;
695 }
696 else
697 {
698 wxLogTrace(wxT("access"), wxT("Not an accessible object"));
699 return S_FALSE; // Indicates it's not an accessible object
700 }
701 }
702
703 #if 0
704 // all cases above already cause some return action so below line
705 // is unreachable and cause unnecessary warning
706 return E_NOTIMPL;
707 #endif
708}
709
710// Retrieves the number of children that belong to this object.
711// All objects must support this property.
712
713STDMETHODIMP wxIAccessible::get_accChildCount ( long* pCountChildren)
714{
715 wxLogTrace(wxT("access"), wxT("get_accChildCount"));
716 wxASSERT (m_pAccessible != NULL);
717 if (!m_pAccessible)
718 return E_FAIL;
719
720 int childCount = 0;
721 wxAccStatus status = m_pAccessible->GetChildCount(& childCount);
722 if (status == wxACC_FAIL)
723 return E_FAIL;
724
725 if (status == wxACC_NOT_IMPLEMENTED)
726 {
727 // Use standard interface instead.
728 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
729 if (!stdInterface)
730 return E_NOTIMPL;
731 else
732 {
733 wxLogTrace(wxT("access"), wxT("Using standard interface for get_accChildCount"));
734 HRESULT res = stdInterface->get_accChildCount (pCountChildren);
735 wxString str;
736 str.Printf(wxT("Number of children was %d"), (int) (*pCountChildren));
737 wxLogTrace(wxT("access"), str);
738 return res;
739 }
740 }
741 else
742 {
743 * pCountChildren = (long) childCount;
744 return S_OK;
745 }
746
747 #if 0
748 // all cases above already cause some return action so below line
749 // is unreachable and cause unnecessary warning
750 return E_NOTIMPL;
751 #endif
752}
753
754// Retrieves the IDispatch interface of the object's parent.
755// All objects support this property.
756
757STDMETHODIMP wxIAccessible::get_accParent ( IDispatch** ppDispParent)
758{
759 wxLogTrace(wxT("access"), wxT("get_accParent"));
760 wxASSERT (m_pAccessible != NULL);
761 if (!m_pAccessible)
762 return E_FAIL;
763
764 wxAccessible* parent = NULL;
765 wxAccStatus status = m_pAccessible->GetParent(& parent);
766
767 if (status == wxACC_FAIL)
768 return E_FAIL;
769
770 // It doesn't seem acceptable to return S_FALSE with a NULL
771 // ppDispParent, so if we have no wxWidgets parent, we leave
772 // it to the standard interface.
773 if (status == wxACC_NOT_IMPLEMENTED || !parent)
774 {
775 wxLogTrace(wxT("access"), wxT("Using standard interface to get the parent."));
776 // Use standard interface instead.
777 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
778 if (!stdInterface)
779 return E_NOTIMPL;
780 else
781 return stdInterface->get_accParent (ppDispParent);
782 }
783 else
784 {
785 if (parent)
786 {
787 wxIAccessible* objectIA = parent->GetIAccessible();
788 if (!objectIA)
789 return E_FAIL;
790
791 wxLogTrace(wxT("access"), wxT("About to call QueryInterface"));
792 if (objectIA->QueryInterface(IID_IDispatch, (LPVOID*) ppDispParent) != S_OK)
793 {
794 wxLogTrace(wxT("access"), wxT("Failed QueryInterface"));
795 return E_FAIL;
796 }
797
798 wxLogTrace(wxT("access"), wxT("Returning S_OK for get_accParent"));
799 return S_OK;
800 }
801 else
802 {
803 // This doesn't seem to be allowed, despite the documentation,
804 // so we handle it higher up by using the standard interface.
805 wxLogTrace(wxT("access"), wxT("Returning NULL parent because there was none"));
806 *ppDispParent = NULL;
807 return S_FALSE;
808 }
809 }
810
811 #if 0
812 // all cases above already cause some return action so below line
813 // is unreachable and cause unnecessary warning
814 return E_NOTIMPL;
815 #endif
816}
817
818// Performs the object's default action. Not all objects have a default
819// action.
820
821STDMETHODIMP wxIAccessible::accDoDefaultAction(VARIANT varID)
822{
823 wxLogTrace(wxT("access"), wxT("accDoDefaultAction"));
824 wxASSERT (m_pAccessible != NULL);
825 if (!m_pAccessible)
826 return E_FAIL;
827
828 if (varID.vt != VT_I4)
829 {
830 wxLogTrace(wxT("access"), wxT("Invalid arg for accDoDefaultAction"));
831 return E_INVALIDARG;
832 }
833
834 wxAccStatus status = m_pAccessible->DoDefaultAction(varID.lVal);
835 if (status == wxACC_FAIL)
836 return E_FAIL;
837
838 if (status == wxACC_NOT_SUPPORTED)
839 return DISP_E_MEMBERNOTFOUND;
840
841 if (status == wxACC_NOT_IMPLEMENTED)
842 {
843 // Try to use child object directly.
844 if (varID.lVal > 0)
845 {
846 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
847 if (childAccessible)
848 {
849 varID.lVal = 0;
850 HRESULT hResult = childAccessible->accDoDefaultAction(varID);
851 childAccessible->Release();
852 return hResult;
853 }
854 else if (m_pAccessible->GetIAccessibleStd())
855 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accDoDefaultAction(varID);
856 }
857 else if (m_pAccessible->GetIAccessibleStd())
858 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accDoDefaultAction(varID);
859 }
860 return E_FAIL;
861}
862
863// Retrieves a string that describes the object's default action.
864// Not all objects have a default action.
865
866STDMETHODIMP wxIAccessible::get_accDefaultAction ( VARIANT varID, BSTR* pszDefaultAction)
867{
868 wxLogTrace(wxT("access"), wxT("get_accDefaultAction"));
869 wxASSERT (m_pAccessible != NULL);
870 if (!m_pAccessible)
871 return E_FAIL;
872
873 if (varID.vt != VT_I4)
874 {
875 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accDefaultAction"));
876 return E_INVALIDARG;
877 }
878
879 wxString defaultAction;
880 wxAccStatus status = m_pAccessible->GetDefaultAction(varID.lVal, & defaultAction);
881 if (status == wxACC_FAIL)
882 return E_FAIL;
883
884 if (status == wxACC_NOT_SUPPORTED)
885 return DISP_E_MEMBERNOTFOUND;
886
887 if (status == wxACC_NOT_IMPLEMENTED)
888 {
889 // Try to use child object directly.
890 if (varID.lVal > 0)
891 {
892 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
893 if (childAccessible)
894 {
895 varID.lVal = 0;
896 HRESULT hResult = childAccessible->get_accDefaultAction(varID, pszDefaultAction);
897 childAccessible->Release();
898 return hResult;
899 }
900 else if (m_pAccessible->GetIAccessibleStd())
901 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accDefaultAction(varID, pszDefaultAction);
902 }
903 else if (m_pAccessible->GetIAccessibleStd())
904 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accDefaultAction(varID, pszDefaultAction);
905 }
906 else
907 {
908 if (defaultAction.IsEmpty())
909 {
910 * pszDefaultAction = NULL;
911 return S_FALSE;
912 }
913 else
914 {
915 wxBasicString basicString(defaultAction);
916 * pszDefaultAction = basicString.Get();
917 return S_OK;
918 }
919 }
920 return E_FAIL;
921}
922
923// Retrieves a string that describes the visual appearance of the specified object.
924// Not all objects have a description.
925
926STDMETHODIMP wxIAccessible::get_accDescription ( VARIANT varID, BSTR* pszDescription)
927{
928 wxLogTrace(wxT("access"), wxT("get_accDescription"));
929 wxASSERT (m_pAccessible != NULL);
930 if (!m_pAccessible)
931 return E_FAIL;
932
933 if (varID.vt != VT_I4)
934 {
935 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accDescription"));
936 return E_INVALIDARG;
937 }
938
939 wxString description;
940 wxAccStatus status = m_pAccessible->GetDescription(varID.lVal, & description);
941 if (status == wxACC_FAIL)
942 return E_FAIL;
943
944 if (status == wxACC_NOT_IMPLEMENTED)
945 {
946 // Try to use child object directly.
947 if (varID.lVal > 0)
948 {
949 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
950 if (childAccessible)
951 {
952 varID.lVal = 0;
953 HRESULT hResult = childAccessible->get_accDescription(varID, pszDescription);
954 childAccessible->Release();
955 return hResult;
956 }
957 else if (m_pAccessible->GetIAccessibleStd())
958 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accDescription(varID, pszDescription);
959 }
960 else if (m_pAccessible->GetIAccessibleStd())
961 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accDescription(varID, pszDescription);
962 }
963 else
964 {
965 if (description.empty())
966 {
967 * pszDescription = NULL;
968 return S_FALSE;
969 }
970 else
971 {
972 wxBasicString basicString(description);
973 * pszDescription = basicString.Get();
974 return S_OK;
975 }
976 }
977 return E_NOTIMPL;
978}
979
980// Retrieves an object's Help property string.
981// Not all objects support this property.
982
983STDMETHODIMP wxIAccessible::get_accHelp ( VARIANT varID, BSTR* pszHelp)
984{
985 wxLogTrace(wxT("access"), wxT("get_accHelp"));
986 wxASSERT (m_pAccessible != NULL);
987 if (!m_pAccessible)
988 return E_FAIL;
989
990 if (varID.vt != VT_I4)
991 {
992 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accHelp"));
993 return E_INVALIDARG;
994 }
995
996 wxString helpString;
997 wxAccStatus status = m_pAccessible->GetHelpText(varID.lVal, & helpString);
998 if (status == wxACC_FAIL)
999 return E_FAIL;
1000
1001 if (status == wxACC_NOT_IMPLEMENTED)
1002 {
1003 // Try to use child object directly.
1004 if (varID.lVal > 0)
1005 {
1006 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1007 if (childAccessible)
1008 {
1009 varID.lVal = 0;
1010 HRESULT hResult = childAccessible->get_accHelp(varID, pszHelp);
1011 childAccessible->Release();
1012 return hResult;
1013 }
1014 else if (m_pAccessible->GetIAccessibleStd())
1015 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accHelp(varID, pszHelp);
1016 }
1017 else if (m_pAccessible->GetIAccessibleStd())
1018 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accHelp (varID, pszHelp);
1019 }
1020 else
1021 {
1022 if (helpString.empty())
1023 {
1024 * pszHelp = NULL;
1025 return S_FALSE;
1026 }
1027 else
1028 {
1029 wxBasicString basicString(helpString);
1030 * pszHelp = basicString.Get();
1031 return S_OK;
1032 }
1033 }
1034 return E_NOTIMPL;
1035}
1036
1037// Retrieves the full path of the WinHelp file associated with the specified
1038// object and the identifier of the appropriate topic within that file.
1039// Not all objects support this property.
1040// NOTE: not supported by wxWidgets at this time. Use
1041// GetHelpText instead.
1042
1043STDMETHODIMP wxIAccessible::get_accHelpTopic ( BSTR* pszHelpFile, VARIANT varChild, long* pidTopic)
1044{
1045 wxLogTrace(wxT("access"), wxT("get_accHelpTopic"));
1046 wxASSERT (m_pAccessible != NULL);
1047 if (!m_pAccessible)
1048 return E_FAIL;
1049
1050 if (varChild.vt != VT_I4)
1051 {
1052 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accHelpTopic"));
1053 return E_INVALIDARG;
1054 }
1055
1056 wxAccStatus status = wxACC_NOT_IMPLEMENTED;
1057 if (status == wxACC_FAIL)
1058 return E_FAIL;
1059
1060 if (status == wxACC_NOT_IMPLEMENTED)
1061 {
1062 // Try to use child object directly.
1063 if (varChild.lVal > 0)
1064 {
1065 IAccessible* childAccessible = GetChildAccessible(varChild.lVal);
1066 if (childAccessible)
1067 {
1068 varChild.lVal = 0;
1069 HRESULT hResult = childAccessible->get_accHelpTopic(pszHelpFile, varChild, pidTopic);
1070 childAccessible->Release();
1071 return hResult;
1072 }
1073 else if (m_pAccessible->GetIAccessibleStd())
1074 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accHelpTopic(pszHelpFile, varChild, pidTopic);
1075 }
1076 else if (m_pAccessible->GetIAccessibleStd())
1077 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accHelpTopic (pszHelpFile, varChild, pidTopic);
1078 }
1079 return E_NOTIMPL;
1080}
1081
1082// Retrieves the specified object's shortcut key or access key, also known as
1083// the mnemonic. All objects that have a shortcut key or access key support
1084// this property.
1085
1086STDMETHODIMP wxIAccessible::get_accKeyboardShortcut ( VARIANT varID, BSTR* pszKeyboardShortcut)
1087{
1088 wxLogTrace(wxT("access"), wxT("get_accKeyboardShortcut"));
1089 *pszKeyboardShortcut = NULL;
1090
1091 wxASSERT (m_pAccessible != NULL);
1092 if (!m_pAccessible)
1093 return E_FAIL;
1094
1095 if (varID.vt != VT_I4)
1096 {
1097 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accKeyboardShortcut"));
1098 return E_INVALIDARG;
1099 }
1100
1101 wxString keyboardShortcut;
1102 wxAccStatus status = m_pAccessible->GetKeyboardShortcut(varID.lVal, & keyboardShortcut);
1103 if (status == wxACC_FAIL)
1104 return E_FAIL;
1105
1106 if (status == wxACC_NOT_IMPLEMENTED)
1107 {
1108 // Try to use child object directly.
1109 if (varID.lVal > 0)
1110 {
1111 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1112 if (childAccessible)
1113 {
1114 varID.lVal = 0;
1115 HRESULT hResult = childAccessible->get_accKeyboardShortcut(varID, pszKeyboardShortcut);
1116 childAccessible->Release();
1117 return hResult;
1118 }
1119 else if (m_pAccessible->GetIAccessibleStd())
1120 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accKeyboardShortcut(varID, pszKeyboardShortcut);
1121 }
1122 else if (m_pAccessible->GetIAccessibleStd())
1123 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accKeyboardShortcut (varID, pszKeyboardShortcut);
1124 }
1125 else
1126 {
1127 if (keyboardShortcut.empty())
1128 {
1129 * pszKeyboardShortcut = NULL;
1130 return S_FALSE;
1131 }
1132 else
1133 {
1134 wxBasicString basicString(keyboardShortcut);
1135 * pszKeyboardShortcut = basicString.Get();
1136 return S_OK;
1137 }
1138 }
1139 return E_NOTIMPL;
1140}
1141
1142// Retrieves the name of the specified object.
1143// All objects support this property.
1144
1145STDMETHODIMP wxIAccessible::get_accName ( VARIANT varID, BSTR* pszName)
1146{
1147 wxLogTrace(wxT("access"), wxT("get_accName"));
1148 *pszName = NULL;
1149
1150 wxASSERT (m_pAccessible != NULL);
1151 if (!m_pAccessible)
1152 return E_FAIL;
1153
1154 if (varID.vt != VT_I4)
1155 {
1156 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accName"));
1157 return E_INVALIDARG;
1158 }
1159
1160 wxString name;
1161
1162 wxAccStatus status = m_pAccessible->GetName(varID.lVal, & name);
1163
1164 if (status == wxACC_FAIL)
1165 return E_FAIL;
1166
1167 if (status == wxACC_NOT_IMPLEMENTED)
1168 {
1169 // Try to use child object directly.
1170 if (varID.lVal > 0)
1171 {
1172 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1173 if (childAccessible)
1174 {
1175 varID.lVal = 0;
1176 HRESULT hResult = childAccessible->get_accName(varID, pszName);
1177 childAccessible->Release();
1178 return hResult;
1179 }
1180 else if (m_pAccessible->GetIAccessibleStd())
1181 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accName(varID, pszName);
1182 }
1183 else if (m_pAccessible->GetIAccessibleStd())
1184 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accName (varID, pszName);
1185 }
1186 else
1187 {
1188 wxBasicString basicString(name);
1189 *pszName = basicString.Get();
1190 return S_OK;
1191 }
1192 return E_NOTIMPL;
1193}
1194
1195// Retrieves information that describes the role of the specified object.
1196// All objects support this property.
1197
1198STDMETHODIMP wxIAccessible::get_accRole ( VARIANT varID, VARIANT* pVarRole)
1199{
1200 wxLogTrace(wxT("access"), wxT("get_accRole"));
1201 wxASSERT (m_pAccessible != NULL);
1202 if (!m_pAccessible)
1203 return E_FAIL;
1204
1205 if (varID.vt != VT_I4)
1206 {
1207 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accRole"));
1208 return E_INVALIDARG;
1209 }
1210
1211 VariantInit(pVarRole);
1212
1213 wxAccRole role = wxROLE_NONE;
1214
1215 wxAccStatus status = m_pAccessible->GetRole(varID.lVal, & role);
1216
1217 if (status == wxACC_FAIL)
1218 return E_FAIL;
1219
1220 if (status == wxACC_NOT_IMPLEMENTED)
1221 {
1222 // Try to use child object directly.
1223 if (varID.lVal > 0)
1224 {
1225 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1226 if (childAccessible)
1227 {
1228 varID.lVal = 0;
1229 HRESULT hResult = childAccessible->get_accRole(varID, pVarRole);
1230 childAccessible->Release();
1231 return hResult;
1232 }
1233 else if (m_pAccessible->GetIAccessibleStd())
1234 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accRole(varID, pVarRole);
1235 }
1236 else if (m_pAccessible->GetIAccessibleStd())
1237 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accRole (varID, pVarRole);
1238 }
1239 else
1240 {
1241 if (role == wxROLE_NONE)
1242 {
1243 pVarRole->vt = VT_EMPTY;
1244 return S_OK;
1245 }
1246
1247 pVarRole->lVal = wxConvertToWindowsRole(role);
1248 pVarRole->vt = VT_I4;
1249
1250 return S_OK;
1251 }
1252 return E_NOTIMPL;
1253}
1254
1255// Retrieves the current state of the specified object.
1256// All objects support this property.
1257
1258STDMETHODIMP wxIAccessible::get_accState ( VARIANT varID, VARIANT* pVarState)
1259{
1260 wxLogTrace(wxT("access"), wxT("get_accState"));
1261 wxASSERT (m_pAccessible != NULL);
1262 if (!m_pAccessible)
1263 return E_FAIL;
1264
1265 if (varID.vt != VT_I4 && varID.vt != VT_EMPTY)
1266 {
1267 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accState"));
1268 return E_INVALIDARG;
1269 }
1270
1271 long wxstate = 0;
1272
1273 wxAccStatus status = m_pAccessible->GetState(varID.lVal, & wxstate);
1274 if (status == wxACC_FAIL)
1275 return E_FAIL;
1276
1277 if (status == wxACC_NOT_IMPLEMENTED)
1278 {
1279 // Try to use child object directly.
1280 if (varID.lVal > 0)
1281 {
1282 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1283 if (childAccessible)
1284 {
1285 varID.lVal = 0;
1286 HRESULT hResult = childAccessible->get_accState(varID, pVarState);
1287 childAccessible->Release();
1288 return hResult;
1289 }
1290 else if (m_pAccessible->GetIAccessibleStd())
1291 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accState(varID, pVarState);
1292 }
1293 else if (m_pAccessible->GetIAccessibleStd())
1294 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accState (varID, pVarState);
1295 }
1296 else
1297 {
1298 long state = wxConvertToWindowsState(wxstate);
1299 pVarState->lVal = state;
1300 pVarState->vt = VT_I4;
1301 return S_OK;
1302 }
1303 return E_NOTIMPL;
1304}
1305
1306// Retrieves the value of the specified object.
1307// Not all objects have a value.
1308
1309STDMETHODIMP wxIAccessible::get_accValue ( VARIANT varID, BSTR* pszValue)
1310{
1311 wxLogTrace(wxT("access"), wxT("get_accValue"));
1312 wxASSERT (m_pAccessible != NULL);
1313 if (!m_pAccessible)
1314 return E_FAIL;
1315
1316 if (varID.vt != VT_I4)
1317 {
1318 wxLogTrace(wxT("access"), wxT("Invalid arg for get_accValue"));
1319 return E_INVALIDARG;
1320 }
1321
1322 wxString strValue;
1323
1324 wxAccStatus status = m_pAccessible->GetValue(varID.lVal, & strValue);
1325
1326 if (status == wxACC_FAIL)
1327 return E_FAIL;
1328
1329 if (status == wxACC_NOT_IMPLEMENTED)
1330 {
1331 // Try to use child object directly.
1332 if (varID.lVal > 0)
1333 {
1334 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1335 if (childAccessible)
1336 {
1337 varID.lVal = 0;
1338 HRESULT hResult = childAccessible->get_accValue(varID, pszValue);
1339 childAccessible->Release();
1340 return hResult;
1341 }
1342 else if (m_pAccessible->GetIAccessibleStd())
1343 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accValue(varID, pszValue);
1344 }
1345 else if (m_pAccessible->GetIAccessibleStd())
1346 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->get_accValue (varID, pszValue);
1347 }
1348 else
1349 {
1350 wxBasicString basicString(strValue);
1351 * pszValue = basicString.Get();
1352 return S_OK;
1353 }
1354 return E_NOTIMPL;
1355}
1356
1357// Modifies the selection or moves the keyboard focus of the
1358// specified object. All objects that select or receive the
1359// keyboard focus must support this method.
1360
1361STDMETHODIMP wxIAccessible::accSelect ( long flagsSelect, VARIANT varID )
1362{
1363 wxLogTrace(wxT("access"), wxT("get_accSelect"));
1364 wxASSERT (m_pAccessible != NULL);
1365 if (!m_pAccessible)
1366 return E_FAIL;
1367
1368 if (varID.vt != VT_I4 && varID.vt != VT_EMPTY)
1369 {
1370 wxLogTrace(wxT("access"), wxT("Invalid arg for accSelect"));
1371 return E_INVALIDARG;
1372 }
1373
1374 wxAccSelectionFlags wxsel = wxConvertFromWindowsSelFlag(flagsSelect);
1375
1376 wxAccStatus status = m_pAccessible->Select(varID.lVal, wxsel);
1377 if (status == wxACC_FAIL)
1378 return E_FAIL;
1379
1380 if (status == wxACC_NOT_IMPLEMENTED)
1381 {
1382 // Try to use child object directly.
1383 if (varID.lVal > 0 && varID.lVal > 0)
1384 {
1385 IAccessible* childAccessible = GetChildAccessible(varID.lVal);
1386 if (childAccessible)
1387 {
1388 varID.lVal = 0;
1389 HRESULT hResult = childAccessible->accSelect(flagsSelect, varID);
1390 childAccessible->Release();
1391 return hResult;
1392 }
1393 else if (m_pAccessible->GetIAccessibleStd())
1394 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accSelect(flagsSelect, varID);
1395 }
1396 else if (m_pAccessible->GetIAccessibleStd())
1397 return ((IAccessible*) m_pAccessible->GetIAccessibleStd())->accSelect(flagsSelect, varID);
1398 }
1399 else
1400 return S_OK;
1401
1402 return E_NOTIMPL;
1403}
1404
1405// Retrieves the object that has the keyboard focus. All objects
1406// that receive the keyboard focus must support this property.
1407
1408STDMETHODIMP wxIAccessible::get_accFocus ( VARIANT* pVarID)
1409{
1410 wxLogTrace(wxT("access"), wxT("get_accFocus"));
1411 wxASSERT (m_pAccessible != NULL);
1412 if (!m_pAccessible)
1413 return E_FAIL;
1414
1415 wxAccessible* childObject = NULL;
1416 int childId = 0;
1417 VariantInit(pVarID);
1418
1419 wxAccStatus status = m_pAccessible->GetFocus(& childId, & childObject);
1420 if (status == wxACC_FAIL)
1421 return E_FAIL;
1422
1423 if (status == wxACC_NOT_IMPLEMENTED)
1424 {
1425 // Use standard interface instead.
1426 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
1427 if (!stdInterface)
1428 return E_NOTIMPL;
1429 else
1430 return stdInterface->get_accFocus (pVarID);
1431 }
1432 if (childObject)
1433 {
1434 if (childObject == m_pAccessible)
1435 {
1436 pVarID->vt = VT_I4;
1437 pVarID->lVal = CHILDID_SELF;
1438 return S_OK; }
1439 else
1440 {
1441 wxIAccessible* childIA = childObject->GetIAccessible();
1442 if (!childIA)
1443 return E_NOTIMPL;
1444
1445 if (childIA->QueryInterface(IID_IDispatch, (LPVOID*) & pVarID->pdispVal) != S_OK)
1446 return E_FAIL;
1447
1448 pVarID->vt = VT_DISPATCH;
1449 return S_OK;
1450 }
1451 }
1452 else if (childId > 0)
1453 {
1454 pVarID->vt = VT_I4;
1455 pVarID->lVal = childId;
1456 return S_OK;
1457 }
1458 else
1459 {
1460 pVarID->vt = VT_EMPTY;
1461 return S_FALSE;
1462 }
1463
1464 #if 0
1465 // all cases above already cause some return action so below line
1466 // is unreachable and cause unnecessary warning
1467 return E_NOTIMPL;
1468 #endif
1469}
1470
1471// Retrieves the selected children of this object. All objects
1472// selected must support this property.
1473
1474STDMETHODIMP wxIAccessible::get_accSelection ( VARIANT * pVarChildren)
1475{
1476#if wxUSE_VARIANT
1477 wxLogTrace(wxT("access"), wxT("get_accSelection"));
1478 wxASSERT (m_pAccessible != NULL);
1479 if (!m_pAccessible)
1480 return E_FAIL;
1481
1482 VariantInit(pVarChildren);
1483
1484 wxVariant selections;
1485 wxAccStatus status = m_pAccessible->GetSelections(& selections);
1486 if (status == wxACC_FAIL)
1487 return E_FAIL;
1488
1489 if (status == wxACC_NOT_IMPLEMENTED)
1490 {
1491 // Use standard interface instead.
1492 IAccessible* stdInterface = (IAccessible*)m_pAccessible->GetIAccessibleStd();
1493 if (!stdInterface)
1494 return E_NOTIMPL;
1495 else
1496 return stdInterface->get_accSelection (pVarChildren);
1497 }
1498 else
1499 {
1500 if (selections.GetType() == wxT("long"))
1501 {
1502 pVarChildren->vt = VT_I4;
1503 pVarChildren->lVal = selections.GetLong();
1504
1505 return S_OK;
1506 }
1507 else if (selections.GetType() == wxT("void*"))
1508 {
1509 wxAccessible* childObject = (wxAccessible*) selections.GetVoidPtr();
1510 wxIAccessible* childIA = childObject->GetIAccessible();
1511 if (!childIA)
1512 return E_NOTIMPL;
1513
1514 if (childIA->QueryInterface(IID_IDispatch, (LPVOID*) & pVarChildren->pdispVal) != S_OK)
1515 return E_FAIL;
1516
1517 pVarChildren->vt = VT_DISPATCH;
1518
1519 return S_OK;
1520 }
1521 else if (selections.GetType() == wxT("list"))
1522 {
1523 // TODO: should we AddRef for every "void*" member??
1524
1525 wxIEnumVARIANT* enumVariant = new wxIEnumVARIANT(selections);
1526 enumVariant->AddRef();
1527
1528 pVarChildren->vt = VT_UNKNOWN;
1529 pVarChildren->punkVal = enumVariant;
1530
1531 return S_OK;
1532 }
1533 }
1534#else
1535 wxUnusedVar(pVarChildren);
1536#endif // wxUSE_VARIANT
1537
1538 return E_NOTIMPL;
1539}
1540
1541// Get type info
1542
1543STDMETHODIMP wxIAccessible::GetTypeInfo(unsigned int WXUNUSED(typeInfo), LCID WXUNUSED(lcid), ITypeInfo** ppTypeInfo)
1544{
1545 *ppTypeInfo = NULL;
1546 return E_NOTIMPL;
1547}
1548
1549// Get type info count
1550
1551STDMETHODIMP wxIAccessible::GetTypeInfoCount(unsigned int* typeInfoCount)
1552{
1553 *typeInfoCount = 0;
1554 return E_NOTIMPL;
1555}
1556
1557// Get ids of names
1558
1559STDMETHODIMP wxIAccessible::GetIDsOfNames(REFIID WXUNUSED(riid), OLECHAR** WXUNUSED(names), unsigned int WXUNUSED(cNames),
1560 LCID WXUNUSED(lcid), DISPID* WXUNUSED(dispId))
1561{
1562 return E_NOTIMPL;
1563}
1564
1565// Invoke
1566
1567STDMETHODIMP wxIAccessible::Invoke(DISPID WXUNUSED(dispIdMember), REFIID WXUNUSED(riid), LCID WXUNUSED(lcid),
1568 WORD WXUNUSED(wFlags), DISPPARAMS *WXUNUSED(pDispParams),
1569 VARIANT *WXUNUSED(pVarResult), EXCEPINFO *WXUNUSED(pExcepInfo),
1570 unsigned int *WXUNUSED(puArgErr) )
1571{
1572 return E_NOTIMPL;
1573}
1574
1575// Gets the standard IAccessible interface for the given child or object.
1576// Call Release if this is non-NULL.
1577IAccessible* wxIAccessible::GetChildStdAccessible(int id)
1578{
1579 if (id == 0)
1580 {
1581 IAccessible* obj = (IAccessible*)m_pAccessible->GetIAccessibleStd();
1582
1583 obj->AddRef();
1584 return obj;
1585 }
1586 else
1587 {
1588 VARIANT var;
1589 VariantInit(& var);
1590 var.vt = VT_I4;
1591 var.lVal = id;
1592 IDispatch* pDispatch = NULL;
1593 if (S_OK == get_accChild ( var, & pDispatch))
1594 {
1595 IAccessible* childAccessible = NULL;
1596 if (pDispatch->QueryInterface(IID_IAccessible, (LPVOID*) & childAccessible) == S_OK)
1597 {
1598 pDispatch->Release();
1599 wxIAccessible* c = (wxIAccessible*) childAccessible;
1600 IAccessible* stdChildAccessible = (IAccessible*) c->m_pAccessible->GetIAccessibleStd();
1601 stdChildAccessible->AddRef();
1602 childAccessible->Release();
1603 return stdChildAccessible;
1604 }
1605 else
1606 {
1607 pDispatch->Release();
1608 }
1609 }
1610 }
1611
1612#if 0
1613 {
1614 // Loop until we find the right id
1615 long nChildren = 0;
1616 this->get_accChildCount(& nChildren);
1617
1618 int i;
1619 for (i = 0; i < nChildren; i++)
1620 {
1621 long obtained = 0;
1622 VARIANT var;
1623 VariantInit(& var);
1624 var.vt = VT_I4;
1625 if (S_OK == AccessibleChildren(this, i, 1, & var, &obtained))
1626 {
1627 if (var.lVal == id)
1628 {
1629 VariantInit(& var);
1630 var.vt = VT_DISPATCH;
1631 if (S_OK == AccessibleChildren(this, i, 1, & var, &obtained))
1632 {
1633 IAccessible* childAccessible = NULL;
1634 if (var.pdispVal->QueryInterface(IID_IAccessible, (LPVOID*) & childAccessible) == S_OK)
1635 {
1636 var.pdispVal->Release();
1637 return childAccessible;
1638 }
1639 else
1640 {
1641 var.pdispVal->Release();
1642 }
1643 }
1644 }
1645 break;
1646 }
1647 }
1648 }
1649#endif
1650 return NULL;
1651}
1652
1653// Gets the IAccessible interface for the given child or object.
1654// Call Release if this is non-NULL.
1655IAccessible* wxIAccessible::GetChildAccessible(int id)
1656{
1657 if (id == 0)
1658 {
1659 IAccessible* obj = this;
1660
1661 obj->AddRef();
1662 return obj;
1663 }
1664 else
1665 {
1666 VARIANT var;
1667 VariantInit(& var);
1668 var.vt = VT_I4;
1669 var.lVal = id;
1670 IDispatch* pDispatch = NULL;
1671 if (S_OK == get_accChild ( var, & pDispatch))
1672 {
1673 IAccessible* childAccessible = NULL;
1674 if (pDispatch->QueryInterface(IID_IAccessible, (LPVOID*) & childAccessible) == S_OK)
1675 {
1676 pDispatch->Release();
1677 return childAccessible;
1678 }
1679 else
1680 {
1681 pDispatch->Release();
1682 }
1683 }
1684 }
1685 return NULL;
1686}
1687
1688// ----------------------------------------------------------------------------
1689// wxAccessible implementation
1690// ----------------------------------------------------------------------------
1691
1692// ctors
1693
1694// common part of all ctors
1695void wxAccessible::Init()
1696{
1697 m_pIAccessibleStd = NULL;
1698 m_pIAccessible = new wxIAccessible(this);
1699 m_pIAccessible->AddRef();
1700}
1701
1702wxAccessible::wxAccessible(wxWindow* win)
1703 : wxAccessibleBase(win)
1704{
1705 Init();
1706}
1707
1708wxAccessible::~wxAccessible()
1709{
1710 m_pIAccessible->Release();
1711 if (m_pIAccessibleStd)
1712 ((IAccessible*)m_pIAccessibleStd)->Release();
1713}
1714
1715// Gets or creates a standard interface for this object.
1716void* wxAccessible::GetIAccessibleStd()
1717{
1718 if (m_pIAccessibleStd)
1719 return m_pIAccessibleStd;
1720
1721 if (GetWindow())
1722 {
1723 HRESULT retCode = ::CreateStdAccessibleObject((HWND) GetWindow()->GetHWND(),
1724 OBJID_CLIENT, IID_IAccessible, (void**) & m_pIAccessibleStd);
1725 if (retCode == S_OK)
1726 return m_pIAccessibleStd;
1727 else
1728 {
1729 m_pIAccessibleStd = NULL;
1730 return NULL;
1731 }
1732 }
1733 return NULL;
1734}
1735
1736// Sends an event when something changes in an accessible object.
1737void wxAccessible::NotifyEvent(int eventType, wxWindow* window, wxAccObject objectType,
1738 int objectId)
1739{
1740 ::NotifyWinEvent((DWORD) eventType, (HWND) window->GetHWND(),
1741 (LONG) objectType, (LONG) objectId);
1742}
1743
1744// Utilities
1745
1746// Convert to Windows role
1747int wxConvertToWindowsRole(wxAccRole wxrole)
1748{
1749 switch (wxrole)
1750 {
1751 case wxROLE_SYSTEM_ALERT:
1752 return ROLE_SYSTEM_ALERT;
1753 case wxROLE_SYSTEM_ANIMATION:
1754 return ROLE_SYSTEM_ANIMATION;
1755 case wxROLE_SYSTEM_APPLICATION:
1756 return ROLE_SYSTEM_APPLICATION;
1757 case wxROLE_SYSTEM_BORDER:
1758 return ROLE_SYSTEM_BORDER;
1759 case wxROLE_SYSTEM_BUTTONDROPDOWN:
1760 return ROLE_SYSTEM_BUTTONDROPDOWN;
1761 case wxROLE_SYSTEM_BUTTONDROPDOWNGRID:
1762 return ROLE_SYSTEM_BUTTONDROPDOWNGRID;
1763 case wxROLE_SYSTEM_BUTTONMENU:
1764 return ROLE_SYSTEM_BUTTONMENU;
1765 case wxROLE_SYSTEM_CARET:
1766 return ROLE_SYSTEM_CARET;
1767 case wxROLE_SYSTEM_CELL:
1768 return ROLE_SYSTEM_CELL;
1769 case wxROLE_SYSTEM_CHARACTER:
1770 return ROLE_SYSTEM_CHARACTER;
1771 case wxROLE_SYSTEM_CHART:
1772 return ROLE_SYSTEM_CHART;
1773 case wxROLE_SYSTEM_CHECKBUTTON:
1774 return ROLE_SYSTEM_CHECKBUTTON;
1775 case wxROLE_SYSTEM_CLIENT:
1776 return ROLE_SYSTEM_CLIENT;
1777 case wxROLE_SYSTEM_CLOCK:
1778 return ROLE_SYSTEM_CLOCK;
1779 case wxROLE_SYSTEM_COLUMN:
1780 return ROLE_SYSTEM_COLUMN;
1781 case wxROLE_SYSTEM_COLUMNHEADER:
1782 return ROLE_SYSTEM_COLUMNHEADER;
1783 case wxROLE_SYSTEM_COMBOBOX:
1784 return ROLE_SYSTEM_COMBOBOX;
1785 case wxROLE_SYSTEM_CURSOR:
1786 return ROLE_SYSTEM_CURSOR;
1787 case wxROLE_SYSTEM_DIAGRAM:
1788 return ROLE_SYSTEM_DIAGRAM;
1789 case wxROLE_SYSTEM_DIAL:
1790 return ROLE_SYSTEM_DIAL;
1791 case wxROLE_SYSTEM_DIALOG:
1792 return ROLE_SYSTEM_DIALOG;
1793 case wxROLE_SYSTEM_DOCUMENT:
1794 return ROLE_SYSTEM_DOCUMENT;
1795 case wxROLE_SYSTEM_DROPLIST:
1796 return ROLE_SYSTEM_DROPLIST;
1797 case wxROLE_SYSTEM_EQUATION:
1798 return ROLE_SYSTEM_EQUATION;
1799 case wxROLE_SYSTEM_GRAPHIC:
1800 return ROLE_SYSTEM_GRAPHIC;
1801 case wxROLE_SYSTEM_GRIP:
1802 return ROLE_SYSTEM_GRIP;
1803 case wxROLE_SYSTEM_GROUPING:
1804 return ROLE_SYSTEM_GROUPING;
1805 case wxROLE_SYSTEM_HELPBALLOON:
1806 return ROLE_SYSTEM_HELPBALLOON;
1807 case wxROLE_SYSTEM_HOTKEYFIELD:
1808 return ROLE_SYSTEM_HOTKEYFIELD;
1809 case wxROLE_SYSTEM_INDICATOR:
1810 return ROLE_SYSTEM_INDICATOR;
1811 case wxROLE_SYSTEM_LINK:
1812 return ROLE_SYSTEM_LINK;
1813 case wxROLE_SYSTEM_LIST:
1814 return ROLE_SYSTEM_LIST;
1815 case wxROLE_SYSTEM_LISTITEM:
1816 return ROLE_SYSTEM_LISTITEM;
1817 case wxROLE_SYSTEM_MENUBAR:
1818 return ROLE_SYSTEM_MENUBAR;
1819 case wxROLE_SYSTEM_MENUITEM:
1820 return ROLE_SYSTEM_MENUITEM;
1821 case wxROLE_SYSTEM_MENUPOPUP:
1822 return ROLE_SYSTEM_MENUPOPUP;
1823 case wxROLE_SYSTEM_OUTLINE:
1824 return ROLE_SYSTEM_OUTLINE;
1825 case wxROLE_SYSTEM_OUTLINEITEM:
1826 return ROLE_SYSTEM_OUTLINEITEM;
1827 case wxROLE_SYSTEM_PAGETAB:
1828 return ROLE_SYSTEM_PAGETAB;
1829 case wxROLE_SYSTEM_PAGETABLIST:
1830 return ROLE_SYSTEM_PAGETABLIST;
1831 case wxROLE_SYSTEM_PANE:
1832 return ROLE_SYSTEM_PANE;
1833 case wxROLE_SYSTEM_PROGRESSBAR:
1834 return ROLE_SYSTEM_PROGRESSBAR;
1835 case wxROLE_SYSTEM_PROPERTYPAGE:
1836 return ROLE_SYSTEM_PROPERTYPAGE;
1837 case wxROLE_SYSTEM_PUSHBUTTON:
1838 return ROLE_SYSTEM_PUSHBUTTON;
1839 case wxROLE_SYSTEM_RADIOBUTTON:
1840 return ROLE_SYSTEM_RADIOBUTTON;
1841 case wxROLE_SYSTEM_ROW:
1842 return ROLE_SYSTEM_ROW;
1843 case wxROLE_SYSTEM_ROWHEADER:
1844 return ROLE_SYSTEM_ROWHEADER;
1845 case wxROLE_SYSTEM_SCROLLBAR:
1846 return ROLE_SYSTEM_SCROLLBAR;
1847 case wxROLE_SYSTEM_SEPARATOR:
1848 return ROLE_SYSTEM_SEPARATOR;
1849 case wxROLE_SYSTEM_SLIDER:
1850 return ROLE_SYSTEM_SLIDER;
1851 case wxROLE_SYSTEM_SOUND:
1852 return ROLE_SYSTEM_SOUND;
1853 case wxROLE_SYSTEM_SPINBUTTON:
1854 return ROLE_SYSTEM_SPINBUTTON;
1855 case wxROLE_SYSTEM_STATICTEXT:
1856 return ROLE_SYSTEM_STATICTEXT;
1857 case wxROLE_SYSTEM_STATUSBAR:
1858 return ROLE_SYSTEM_STATUSBAR;
1859 case wxROLE_SYSTEM_TABLE:
1860 return ROLE_SYSTEM_TABLE;
1861 case wxROLE_SYSTEM_TEXT:
1862 return ROLE_SYSTEM_TEXT;
1863 case wxROLE_SYSTEM_TITLEBAR:
1864 return ROLE_SYSTEM_TITLEBAR;
1865 case wxROLE_SYSTEM_TOOLBAR:
1866 return ROLE_SYSTEM_TOOLBAR;
1867 case wxROLE_SYSTEM_TOOLTIP:
1868 return ROLE_SYSTEM_TOOLTIP;
1869 case wxROLE_SYSTEM_WHITESPACE:
1870 return ROLE_SYSTEM_WHITESPACE;
1871 case wxROLE_SYSTEM_WINDOW:
1872 return ROLE_SYSTEM_WINDOW;
1873 }
1874 return 0;
1875}
1876
1877// Convert to Windows state
1878long wxConvertToWindowsState(long wxstate)
1879{
1880 long state = 0;
1881 if (wxstate & wxACC_STATE_SYSTEM_ALERT_HIGH)
1882 state |= STATE_SYSTEM_ALERT_HIGH;
1883
1884 if (wxstate & wxACC_STATE_SYSTEM_ALERT_MEDIUM)
1885 state |= STATE_SYSTEM_ALERT_MEDIUM;
1886
1887 if (wxstate & wxACC_STATE_SYSTEM_ALERT_LOW)
1888 state |= STATE_SYSTEM_ALERT_LOW;
1889
1890 if (wxstate & wxACC_STATE_SYSTEM_ANIMATED)
1891 state |= STATE_SYSTEM_ANIMATED;
1892
1893 if (wxstate & wxACC_STATE_SYSTEM_BUSY)
1894 state |= STATE_SYSTEM_BUSY;
1895
1896 if (wxstate & wxACC_STATE_SYSTEM_CHECKED)
1897 state |= STATE_SYSTEM_CHECKED;
1898
1899 if (wxstate & wxACC_STATE_SYSTEM_COLLAPSED)
1900 state |= STATE_SYSTEM_COLLAPSED;
1901
1902 if (wxstate & wxACC_STATE_SYSTEM_DEFAULT)
1903 state |= STATE_SYSTEM_DEFAULT;
1904
1905 if (wxstate & wxACC_STATE_SYSTEM_EXPANDED)
1906 state |= STATE_SYSTEM_EXPANDED;
1907
1908 if (wxstate & wxACC_STATE_SYSTEM_EXTSELECTABLE)
1909 state |= STATE_SYSTEM_EXTSELECTABLE;
1910
1911 if (wxstate & wxACC_STATE_SYSTEM_FLOATING)
1912 state |= STATE_SYSTEM_FLOATING;
1913
1914 if (wxstate & wxACC_STATE_SYSTEM_FOCUSABLE)
1915 state |= STATE_SYSTEM_FOCUSABLE;
1916
1917 if (wxstate & wxACC_STATE_SYSTEM_FOCUSED)
1918 state |= STATE_SYSTEM_FOCUSED;
1919
1920 if (wxstate & wxACC_STATE_SYSTEM_HOTTRACKED)
1921 state |= STATE_SYSTEM_HOTTRACKED;
1922
1923 if (wxstate & wxACC_STATE_SYSTEM_INVISIBLE)
1924 state |= STATE_SYSTEM_INVISIBLE;
1925
1926 if (wxstate & wxACC_STATE_SYSTEM_INVISIBLE)
1927 state |= STATE_SYSTEM_INVISIBLE;
1928
1929 if (wxstate & wxACC_STATE_SYSTEM_MIXED)
1930 state |= STATE_SYSTEM_MIXED;
1931
1932 if (wxstate & wxACC_STATE_SYSTEM_MULTISELECTABLE)
1933 state |= STATE_SYSTEM_MULTISELECTABLE;
1934
1935 if (wxstate & wxACC_STATE_SYSTEM_OFFSCREEN)
1936 state |= STATE_SYSTEM_OFFSCREEN;
1937
1938 if (wxstate & wxACC_STATE_SYSTEM_PRESSED)
1939 state |= STATE_SYSTEM_PRESSED;
1940
1941// if (wxstate & wxACC_STATE_SYSTEM_PROTECTED)
1942// state |= STATE_SYSTEM_PROTECTED;
1943
1944 if (wxstate & wxACC_STATE_SYSTEM_READONLY)
1945 state |= STATE_SYSTEM_READONLY;
1946
1947 if (wxstate & wxACC_STATE_SYSTEM_SELECTABLE)
1948 state |= STATE_SYSTEM_SELECTABLE;
1949
1950 if (wxstate & wxACC_STATE_SYSTEM_SELECTED)
1951 state |= STATE_SYSTEM_SELECTED;
1952
1953 if (wxstate & wxACC_STATE_SYSTEM_SELFVOICING)
1954 state |= STATE_SYSTEM_SELFVOICING;
1955
1956 if (wxstate & wxACC_STATE_SYSTEM_UNAVAILABLE)
1957 state |= STATE_SYSTEM_UNAVAILABLE;
1958
1959 return state;
1960}
1961
1962// Convert to Windows selection flag
1963int wxConvertToWindowsSelFlag(wxAccSelectionFlags wxsel)
1964{
1965 int sel = 0;
1966
1967 if (wxsel & wxACC_SEL_TAKEFOCUS)
1968 sel |= SELFLAG_TAKEFOCUS;
1969 if (wxsel & wxACC_SEL_TAKESELECTION)
1970 sel |= SELFLAG_TAKESELECTION;
1971 if (wxsel & wxACC_SEL_EXTENDSELECTION)
1972 sel |= SELFLAG_EXTENDSELECTION;
1973 if (wxsel & wxACC_SEL_ADDSELECTION)
1974 sel |= SELFLAG_ADDSELECTION;
1975 if (wxsel & wxACC_SEL_REMOVESELECTION)
1976 sel |= SELFLAG_REMOVESELECTION;
1977 return sel;
1978}
1979
1980// Convert from Windows selection flag
1981wxAccSelectionFlags wxConvertFromWindowsSelFlag(int sel)
1982{
1983 int wxsel = 0;
1984
1985 if (sel & SELFLAG_TAKEFOCUS)
1986 wxsel |= wxACC_SEL_TAKEFOCUS;
1987 if (sel & SELFLAG_TAKESELECTION)
1988 wxsel |= wxACC_SEL_TAKESELECTION;
1989 if (sel & SELFLAG_EXTENDSELECTION)
1990 wxsel |= wxACC_SEL_EXTENDSELECTION;
1991 if (sel & SELFLAG_ADDSELECTION)
1992 wxsel |= wxACC_SEL_ADDSELECTION;
1993 if (sel & SELFLAG_REMOVESELECTION)
1994 wxsel |= wxACC_SEL_REMOVESELECTION;
1995 return (wxAccSelectionFlags) wxsel;
1996}
1997
1998
1999#endif // wxUSE_OLE && wxUSE_ACCESSIBILITY