Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

506 lines
16 KiB

  1. //+------------------------------------------------------------------
  2. //
  3. // Microsoft IEPEERS
  4. // Copyright (C) Microsoft Corporation, 1999.
  5. //
  6. // File: iextags\select.hxx
  7. //
  8. // Contents: The SELECT control.
  9. //
  10. // Classes: CIESelectElement
  11. //
  12. // Interfaces: IHTMLSelectElement3
  13. // IPrivateSelect
  14. //
  15. //-------------------------------------------------------------------
  16. #ifndef __SELECT_HXX_
  17. #define __SELECT_HXX_
  18. #include "basectl.hxx"
  19. #include "resource.h" // main symbols
  20. // Uncomment this line to turn on the new GetSize features
  21. #define SELECT_GETSIZE
  22. #define SELECT_TIMERVL
  23. //
  24. // These are properties and flavors for the control.
  25. // The numbers are setup so that we only need one flavor bitfield.
  26. // The flavor will be equal something from the flavor enumeration.
  27. // The flavor can be "&"ed with a property to determine if that
  28. // property is active. This allows us to minimize the book-keeping
  29. // on the flavor bitfield.
  30. //
  31. enum // Properties
  32. {
  33. SELECT_DROPBOX = 1,
  34. SELECT_MULTIPLE = 2,
  35. SELECT_INPOPUP = 4,
  36. };
  37. #define SELECT_ISLISTBOX(flag) (!(flag & SELECT_DROPBOX))
  38. #define SELECT_ISDROPBOX(flag) (flag & SELECT_DROPBOX)
  39. #define SELECT_ISMULTIPLE(flag) (flag & SELECT_MULTIPLE)
  40. #define SELECT_ISINPOPUP(flag) (flag & SELECT_INPOPUP)
  41. enum
  42. {
  43. SELECT_SHIFT = 1,
  44. SELECT_CTRL = 2,
  45. SELECT_ALT = 4,
  46. SELECT_CLEARPREV = 8,
  47. SELECT_EXTEND = 16,
  48. SELECT_TOGGLE = 32,
  49. SELECT_FIREEVENT = 64,
  50. };
  51. enum
  52. {
  53. SELECTES_POPUP = 1,
  54. SELECTES_VIEWLINK = 2,
  55. SELECTES_BUTTON = 4,
  56. SELECTES_INPOPUP = 8,
  57. };
  58. interface IPrivateOption;
  59. typedef interface IPrivateOption IPrivateOption;
  60. /////////////////////////////////////////////////////////////////////////////
  61. //
  62. // IPrivateSelect
  63. //
  64. /////////////////////////////////////////////////////////////////////////////
  65. /* {3050f6a2-98b5-11cf-bb82-00aa00bdce0b} */
  66. DEFINE_GUID(IID_IPrivateSelect,
  67. 0x3050f6a2, 0x98b5, 0x11cf, 0xbb, 0x82, 0x0, 0xaa, 0x0, 0xbd, 0xce, 0x0b);
  68. interface IPrivateSelect : public IUnknown
  69. {
  70. STDMETHOD(OnOptionClicked)(long lIndex, DWORD dwFlags) PURE;
  71. STDMETHOD(OnOptionSelected)(VARIANT_BOOL bSelected, long lIndex, DWORD dwFlags) PURE;
  72. STDMETHOD(OnOptionHighlighted)(long lIndex) PURE;
  73. STDMETHOD(OnOptionFocus)(long lIndex, VARIANT_BOOL bRequireRefresh = VARIANT_TRUE) PURE;
  74. STDMETHOD(InitOptions)() PURE;
  75. #ifdef SELECT_GETSIZE
  76. STDMETHOD(OnOptionSized)(SIZE* psizeOption, BOOL bNew, BOOL bAdjust) PURE;
  77. #else
  78. STDMETHOD(SetDimensions)() PURE;
  79. #endif
  80. STDMETHOD(GetDisabled)(VARIANT_BOOL *pbDisabled) PURE;
  81. STDMETHOD(GetSelectedIndex)(long *plIndex) PURE;
  82. STDMETHOD(SelectCurrentOption)(DWORD dwFlags) PURE;
  83. STDMETHOD(MoveFocusByOne)(BOOL bUp, DWORD dwFlags) PURE;
  84. STDMETHOD(SetInPopup)(IHTMLPopup *pPopup) PURE;
  85. STDMETHOD(CommitSelection)(BOOL *pbChanged) PURE;
  86. STDMETHOD(SetWritingMode)(BSTR bstrName) PURE;
  87. STDMETHOD(GetFlavor)(DWORD *pdwFlavor)
  88. {
  89. Assert(pdwFlavor);
  90. *pdwFlavor = _fFlavor;
  91. return S_OK;
  92. }
  93. unsigned _fFlavor:5;
  94. };
  95. typedef interface IPrivateSelect IPrivateSelect;
  96. /////////////////////////////////////////////////////////////////////////////
  97. //
  98. // CIESelectElement
  99. //
  100. /////////////////////////////////////////////////////////////////////////////
  101. class ATL_NO_VTABLE CIESelectElement :
  102. public CBaseCtl,
  103. public CComCoClass<CIESelectElement, &CLSID_CIESelectElement>,
  104. public IDispatchImpl<IHTMLSelectElement3, &IID_IHTMLSelectElement3, &LIBID_IEXTagLib>,
  105. public IElementBehaviorSubmit,
  106. public IElementBehaviorFocus,
  107. #ifdef SELECT_GETSIZE
  108. public IElementBehaviorLayout,
  109. #endif
  110. protected IPrivateSelect
  111. {
  112. friend class CIEOptionElement;
  113. private:
  114. class CEventSink;
  115. friend class CIESelectElement::CEventSink;
  116. public:
  117. CIESelectElement();
  118. ~CIESelectElement();
  119. //
  120. // IElementBehavior overrides
  121. //
  122. STDMETHOD(Detach)();
  123. //
  124. // IElementBehaviorSubmit overrides
  125. //
  126. STDMETHOD(Reset)();
  127. STDMETHOD(GetSubmitInfo)(IHTMLSubmitData * pSubmitData);
  128. //
  129. // IElementBehaviorFocus overrides
  130. //
  131. STDMETHOD(GetFocusRect)(RECT * pRect);
  132. #ifdef SELECT_GETSIZE
  133. //
  134. // IElementBehaviorLayout
  135. //
  136. STDMETHOD(GetLayoutInfo)(LONG *plLayoutInfo);
  137. STDMETHOD(GetSize)(LONG dwFlags,
  138. SIZE sizeContent,
  139. POINT * pptTranslate,
  140. POINT *pptTopLeft,
  141. SIZE *psizeProposed);
  142. STDMETHOD(GetPosition)(LONG lFlags, POINT * ppt) { return E_NOTIMPL; };
  143. STDMETHOD(MapSize)(SIZE *psizeIn, RECT *prcOut) { return E_NOTIMPL; };
  144. #endif
  145. //
  146. // CBaseCtl overrides
  147. //
  148. virtual HRESULT Init();
  149. //
  150. // CBaseCtl Event Methods
  151. //
  152. virtual HRESULT OnContentReady();
  153. virtual HRESULT OnFocus(CEventObjectAccess *pEvent);
  154. virtual HRESULT OnBlur(CEventObjectAccess *pEvent);
  155. virtual HRESULT OnMouseDown(CEventObjectAccess *pEvent);
  156. virtual HRESULT OnMouseUp(CEventObjectAccess *pEvent);
  157. virtual HRESULT OnMouseOver(CEventObjectAccess *pEvent);
  158. virtual HRESULT OnMouseOut(CEventObjectAccess *pEvent);
  159. virtual HRESULT OnMouseMove(CEventObjectAccess *pEvent);
  160. virtual HRESULT OnKeyDown(CEventObjectAccess *pEvent);
  161. virtual HRESULT OnSelectStart(CEventObjectAccess *pEvent);
  162. virtual HRESULT OnScroll(CEventObjectAccess *pEvent);
  163. virtual HRESULT OnContextMenu(CEventObjectAccess *pEvent);
  164. virtual HRESULT OnPropertyChange(CEventObjectAccess *pEvent, BSTR bstr);
  165. //
  166. // IHTMLSelectElement3 overrides
  167. //
  168. STDMETHOD(put_name)(BSTR bstrName);
  169. STDMETHOD(get_name)(BSTR *pbstrName);
  170. STDMETHOD(put_size)(long lSize);
  171. STDMETHOD(get_size)(long *plSize);
  172. STDMETHOD(put_selectedIndex)(long lIndex);
  173. STDMETHOD(get_selectedIndex)(long *plIndex);
  174. STDMETHOD(put_multiple)(VARIANT_BOOL bMultiple);
  175. STDMETHOD(get_multiple)(VARIANT_BOOL *bMultiple);
  176. STDMETHOD(clearSelection)();
  177. STDMETHOD(selectAll)();
  178. STDMETHOD(add)(IDispatch *pElement, VARIANT varIndex);
  179. STDMETHOD(remove)(long lIndex);
  180. STDMETHOD(get_length)(long *plLength);
  181. STDMETHOD(get_type)(BSTR *pbstrType);
  182. STDMETHOD(get_options)(IDispatch ** ppOptions);
  183. STDMETHOD(get__newEnum)(IUnknown ** p);
  184. STDMETHOD(item)(VARIANT name, VARIANT index, IDispatch ** pdisp);
  185. STDMETHOD(tags)(VARIANT tagName, IDispatch ** pdisp);
  186. STDMETHOD(urns)(VARIANT urn, IDispatch ** pdisp);
  187. //
  188. // Wiring
  189. //
  190. DECLARE_REGISTRY_RESOURCEID(IDR_SELECT)
  191. DECLARE_NOT_AGGREGATABLE(CIESelectElement)
  192. BEGIN_COM_MAP(CIESelectElement)
  193. COM_INTERFACE_ENTRY2(IDispatch,IHTMLSelectElement3)
  194. COM_INTERFACE_ENTRY(IAccessible)
  195. COM_INTERFACE_ENTRY(IElementBehavior)
  196. COM_INTERFACE_ENTRY(IElementBehaviorSubmit)
  197. COM_INTERFACE_ENTRY(IElementBehaviorFocus)
  198. #ifdef SELECT_GETSIZE
  199. COM_INTERFACE_ENTRY(IElementBehaviorLayout)
  200. #endif
  201. COM_INTERFACE_ENTRY(IPersistPropertyBag2)
  202. COM_INTERFACE_ENTRY(IHTMLSelectElement3)
  203. COM_INTERFACE_ENTRY(IPrivateSelect)
  204. END_COM_MAP()
  205. private:
  206. //
  207. // IElementBehaviorSubmit Helpers
  208. //
  209. HRESULT GetSingleSubmitInfo(IHTMLSubmitData *pSubmitData, CComBSTR bstrName);
  210. HRESULT GetMultipleSubmitInfo(IHTMLSubmitData *pSubmitData, CComBSTR bstrName);
  211. //
  212. // IElementBehaviorFocus Helpers
  213. //
  214. HRESULT RefreshFocusRect();
  215. //
  216. // CBaseCtl Helpers
  217. //
  218. HRESULT SetupDefaultStyle();
  219. HRESULT MakeVisible(BOOL bShow = TRUE);
  220. HRESULT InitContent();
  221. HRESULT StartDrag();
  222. HRESULT FinishDrag();
  223. HRESULT HandleDownXY(POINT pt, BOOL bCtrlKey);
  224. HRESULT GetOptionIndexFromY(long lY, long *plIndex, BOOL *pbNeedTimer);
  225. HRESULT SelectByKey(long lKey);
  226. HRESULT SearchForKey(long lKey, long lStart, long lEnd, long *plIndex);
  227. HRESULT CancelEvent(CEventObjectAccess *pEvent);
  228. HRESULT OnButtonMouseDown(CEventObjectAccess *pEvent);
  229. HRESULT PressButton(BOOL bDown);
  230. #ifdef SELECT_GETSIZE
  231. HRESULT IsWidthHeightSet(BOOL *pbWidthSet, BOOL *pbHeightSet);
  232. HRESULT BecomeDropBox();
  233. HRESULT BecomeListBox();
  234. HRESULT RefreshListBox();
  235. #else
  236. HRESULT SetDimensions(long lSize);
  237. #endif
  238. HRESULT SetAllSelected(VARIANT_BOOL bSelected, DWORD dwFlags);
  239. HRESULT GetNumOptions(long *plItems);
  240. HRESULT GetIndex(long lIndex, IHTMLOptionElement2 **ppOption);
  241. HRESULT GetIndex(long lIndex, IPrivateOption **ppOption);
  242. HRESULT GetIndex(long lIndex, IHTMLElement **ppElem);
  243. HRESULT GetIndex(long lIndex, IDispatch **ppOption);
  244. HRESULT SelectRange(long lAnchor, long lLast, long lNew);
  245. HRESULT AddOptionHelper(IHTMLOptionElement2 *pOption, long lIndex);
  246. HRESULT RemoveOptionHelper(long lIndex);
  247. HRESULT ResetIndexes();
  248. HRESULT ParseChildren();
  249. HRESULT GetScrollTopBottom(long *plScrollTop, long *plScrollBottom);
  250. HRESULT PushFocusToExtreme(BOOL bTop);
  251. HRESULT MakeOptionVisible(IPrivateOption *pOption);
  252. HRESULT SelectVisibleIndex(long lIndex);
  253. HRESULT GetTopVisibleOptionIndex(long *plIndex);
  254. HRESULT GetBottomVisibleOptionIndex(long *plIndex);
  255. HRESULT GetFirstSelected(long *plIndex);
  256. HRESULT Select(long lIndex);
  257. HRESULT CommitSingleSelection(BOOL *pbChanged);
  258. HRESULT CommitMultipleSelection(BOOL *pbChanged);
  259. HRESULT FireOnChange();
  260. void AdjustChangedRange(long lIndex);
  261. //
  262. // DropBox Helpers
  263. //
  264. HRESULT SetupDropBox();
  265. HRESULT SetupDropControl();
  266. #ifdef SELECT_GETSIZE
  267. HRESULT InitViewLink();
  268. HRESULT DeInitViewLink();
  269. HRESULT EngageViewLink();
  270. HRESULT SetupButton(IHTMLElement *pButton);
  271. HRESULT SetupDisplay(IHTMLElement *pDisplay);
  272. HRESULT SetupDropControlDimensions();
  273. #endif
  274. HRESULT SetupPopup();
  275. HRESULT UpdatePopup();
  276. HRESULT SetDisplayHighlight(BOOL bOn);
  277. HRESULT ShowPopup();
  278. HRESULT HidePopup();
  279. HRESULT TogglePopup();
  280. HRESULT AttachEventToSink(IHTMLElement2 *pElem, CComBSTR& bstr, CEventSink* pSink);
  281. HRESULT AttachEventToSink(IHTMLDocument3 *pDoc, CComBSTR& bstr, CEventSink* pSink);
  282. HRESULT DropDownSelect(IPrivateOption *pOption);
  283. HRESULT SynchSelWithPopup();
  284. HRESULT RefreshView();
  285. HRESULT SetPixelHeightWidth();
  286. HRESULT SetWritingModeFlag();
  287. //
  288. // ListBox Helpers
  289. //
  290. HRESULT SetupListBox();
  291. //
  292. // IPrivateSelect overrides
  293. //
  294. STDMETHOD(OnOptionClicked)(long lIndex, DWORD dwFlags);
  295. STDMETHOD(OnOptionSelected)(VARIANT_BOOL bSelected, long lIndex, DWORD dwFlags);
  296. STDMETHOD(OnOptionHighlighted)(long lIndex);
  297. STDMETHOD(OnOptionFocus)(long lIndex, VARIANT_BOOL bRequireRefresh = VARIANT_TRUE);
  298. STDMETHOD(InitOptions)();
  299. STDMETHOD(GetSelectedIndex)(long *plIndex);
  300. STDMETHOD(GetDisabled)(VARIANT_BOOL *pbDisabled);
  301. #ifdef SELECT_GETSIZE
  302. STDMETHOD(OnOptionSized)(SIZE* psizeOption, BOOL bNew, BOOL bAdjust);
  303. VOID AdjustSizeForScrollbar(SIZE *pSize);
  304. #else
  305. STDMETHOD(SetDimensions)();
  306. #endif
  307. STDMETHOD(MoveFocusByOne)(BOOL bUp, DWORD dwFlags);
  308. STDMETHOD(SelectCurrentOption)(DWORD dwFlags);
  309. STDMETHOD(CommitSelection)(BOOL *pbChanged);
  310. STDMETHOD(SetWritingMode)(BSTR bstrName);
  311. STDMETHOD(SetInPopup)(IHTMLPopup *pPopup)
  312. {
  313. _fFlavor |= SELECT_INPOPUP;
  314. _pPopup = pPopup;
  315. return S_OK;
  316. };
  317. //
  318. // Called by the event sink
  319. //
  320. HRESULT OnChangeInPopup();
  321. //
  322. // Attributes
  323. //
  324. private:
  325. long _lFocusIndex;
  326. IPrivateOption *_pLastSelected;
  327. IPrivateOption *_pLastHighlight;
  328. long _lShiftAnchor;
  329. //
  330. // _lMaxHeight is for all the places where we
  331. // assume we have fixed height options (all options
  332. // are the same height).
  333. //
  334. // When we want to support different height options,
  335. // then we need to change each location where
  336. // this is used.
  337. //
  338. long _lMaxHeight;
  339. IHTMLPopup *_pPopup;
  340. VARIANT_BOOL _bPopupOpen;
  341. CEventSink *_pSinkPopup;
  342. CEventSink *_pSinkVL;
  343. CEventSink *_pSinkButton;
  344. IHTMLElement *_pElemDisplay;
  345. IDispatch *_pDispDocLink;
  346. IHTMLStyle *_pStyleButton;
  347. IPrivateSelect *_pSelectInPopup;
  348. unsigned _fDragMode:1;
  349. unsigned _fButtonHit:1;
  350. #ifdef SELECT_GETSIZE
  351. unsigned _fLayoutDirty:1;
  352. unsigned _fContentReady:1;
  353. unsigned _fAllOptionsSized:1;
  354. unsigned _fVLEngaged:1;
  355. unsigned _fNeedScrollBar:1;
  356. SIZE _sizeSelect;
  357. SIZE _sizeContent;
  358. SIZE _sizeOption;
  359. // We need _sizeOptionReported since _sizeOption can get overwritten in GetSize
  360. SIZE _sizeOptionReported;
  361. long _lNumOptionsReported;
  362. #else
  363. SIZE _lPopupSize;
  364. #endif
  365. long _lOnChangeCookie;
  366. long _lOnMouseDownCookie;
  367. long _lOnMouseUpCookie;
  368. long _lOnClickCookie;
  369. long _lOnKeyDownCookie;
  370. long _lOnKeyUpCookie;
  371. long _lOnKeyPressedCookie;
  372. long _fWritingModeTBRL;
  373. long _lTopChanged;
  374. long _lBottomChanged;
  375. //
  376. // Timer related
  377. //
  378. HRESULT SetScrollTimeout(POINT pt, BOOL bCtrl);
  379. HRESULT ClearScrollTimeout();
  380. static VOID CALLBACK TimerProc(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime);
  381. static CIESelectElement *_pTimerSelect;
  382. static UINT_PTR _iTimerID;
  383. static POINT _ptSavedPoint;
  384. static BOOL _bSavedCtrl;
  385. #ifdef SELECT_TIMERVL
  386. static VOID InitTimerVLServices();
  387. static VOID DeInitTimerVLServices();
  388. static VOID SetTimerVL();
  389. static VOID ClearTimerVL();
  390. static VOID AddSelectToTimerVLQueue(CIESelectElement *pSelect);
  391. static VOID CALLBACK TimerVLProc(HWND hwnd, UINT uMsg, UINT_PTR idEvent, DWORD dwTime);
  392. struct SELECT_TIMERVL_LINKELEM
  393. {
  394. CIESelectElement *pSelect;
  395. struct SELECT_TIMERVL_LINKELEM *pNext;
  396. };
  397. static UINT_PTR _iTimerVL;
  398. static LONG _lTimerVLRef;
  399. static CRITICAL_SECTION _lockTimerVL;
  400. static struct SELECT_TIMERVL_LINKELEM *_queueTimerVL;
  401. #endif
  402. public:
  403. DECLARE_PROPDESC_MEMBERS(6);
  404. private:
  405. class CEventSink : public IDispatch
  406. {
  407. public:
  408. CEventSink (CIESelectElement *pParent, DWORD dwFlags);
  409. //
  410. // IUnknown
  411. //
  412. STDMETHODIMP QueryInterface(REFIID, void **);
  413. STDMETHODIMP_(ULONG) AddRef(void);
  414. STDMETHODIMP_(ULONG) Release(void);
  415. //
  416. // IDispatch
  417. //
  418. STDMETHODIMP GetTypeInfoCount(UINT* pctinfo);
  419. STDMETHODIMP GetTypeInfo(UINT iTInfo, LCID lcid, ITypeInfo** ppTInfo);
  420. STDMETHODIMP GetIDsOfNames( REFIID riid,
  421. LPOLESTR *rgszNames,
  422. UINT cNames,
  423. LCID lcid,
  424. DISPID *rgDispId);
  425. STDMETHODIMP Invoke(DISPID dispIdMember,
  426. REFIID riid,
  427. LCID lcid,
  428. WORD wFlags,
  429. DISPPARAMS *pDispParams,
  430. VARIANT *pVarResult,
  431. EXCEPINFO *pExcepInfo,
  432. UINT *puArgErr);
  433. private:
  434. CIESelectElement *_pParent;
  435. DWORD _dwFlags;
  436. };
  437. };
  438. #endif // __SELECT_HXX_