Line data Source code
1 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 : /* This Source Code Form is subject to the terms of the Mozilla Public
4 : * License, v. 2.0. If a copy of the MPL was not distributed with this
5 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 : #ifndef mozilla_dom_HTMLSelectElement_h
7 : #define mozilla_dom_HTMLSelectElement_h
8 :
9 : #include "mozilla/Attributes.h"
10 : #include "nsGenericHTMLElement.h"
11 : #include "nsIDOMHTMLSelectElement.h"
12 : #include "nsIConstraintValidation.h"
13 :
14 : #include "mozilla/dom/BindingDeclarations.h"
15 : #include "mozilla/dom/HTMLOptionsCollection.h"
16 : #include "mozilla/ErrorResult.h"
17 : #include "nsCheapSets.h"
18 : #include "nsCOMPtr.h"
19 : #include "nsError.h"
20 : #include "mozilla/dom/HTMLFormElement.h"
21 : #include "nsContentUtils.h"
22 :
23 : class nsContentList;
24 : class nsIDOMHTMLOptionElement;
25 : class nsIHTMLCollection;
26 : class nsISelectControlFrame;
27 : class nsPresState;
28 :
29 : namespace mozilla {
30 :
31 : class EventChainPostVisitor;
32 : class EventChainPreVisitor;
33 :
34 : namespace dom {
35 :
36 : class HTMLFormSubmission;
37 : class HTMLSelectElement;
38 :
39 : #define NS_SELECT_STATE_IID \
40 : { /* 4db54c7c-d159-455f-9d8e-f60ee466dbf3 */ \
41 : 0x4db54c7c, \
42 : 0xd159, \
43 : 0x455f, \
44 : {0x9d, 0x8e, 0xf6, 0x0e, 0xe4, 0x66, 0xdb, 0xf3} \
45 : }
46 :
47 : /**
48 : * The restore state used by select
49 : */
50 : class SelectState : public nsISupports
51 : {
52 : public:
53 0 : SelectState()
54 0 : {
55 0 : }
56 : NS_DECLARE_STATIC_IID_ACCESSOR(NS_SELECT_STATE_IID)
57 : NS_DECL_ISUPPORTS
58 :
59 0 : void PutOption(int32_t aIndex, const nsAString& aValue)
60 : {
61 : // If the option is empty, store the index. If not, store the value.
62 0 : if (aValue.IsEmpty()) {
63 0 : mIndices.Put(aIndex);
64 : } else {
65 0 : mValues.Put(aValue);
66 : }
67 0 : }
68 :
69 0 : bool ContainsOption(int32_t aIndex, const nsAString& aValue)
70 : {
71 0 : return mValues.Contains(aValue) || mIndices.Contains(aIndex);
72 : }
73 :
74 : private:
75 0 : virtual ~SelectState()
76 0 : {
77 0 : }
78 :
79 : nsCheapSet<nsStringHashKey> mValues;
80 : nsCheapSet<nsUint32HashKey> mIndices;
81 : };
82 :
83 : NS_DEFINE_STATIC_IID_ACCESSOR(SelectState, NS_SELECT_STATE_IID)
84 :
85 : class MOZ_STACK_CLASS SafeOptionListMutation
86 : {
87 : public:
88 : /**
89 : * @param aSelect The select element which option list is being mutated.
90 : * Can be null.
91 : * @param aParent The content object which is being mutated.
92 : * @param aKid If not null, a new child element is being inserted to
93 : * aParent. Otherwise a child element will be removed.
94 : * @param aIndex The index of the content object in the parent.
95 : */
96 : SafeOptionListMutation(nsIContent* aSelect, nsIContent* aParent,
97 : nsIContent* aKid, uint32_t aIndex, bool aNotify);
98 : ~SafeOptionListMutation();
99 0 : void MutationFailed() { mNeedsRebuild = true; }
100 : private:
101 : static void* operator new(size_t) CPP_THROW_NEW { return 0; }
102 : static void operator delete(void*, size_t) {}
103 : /** The select element which option list is being mutated. */
104 : RefPtr<HTMLSelectElement> mSelect;
105 : /** true if the current mutation is the first one in the stack. */
106 : bool mTopLevelMutation;
107 : /** true if it is known that the option list must be recreated. */
108 : bool mNeedsRebuild;
109 : /** Whether we should be notifying when we make various method calls on
110 : mSelect */
111 : const bool mNotify;
112 : /** The selected index at mutation start. */
113 : int32_t mInitialSelectedIndex;
114 : /** Option list must be recreated if more than one mutation is detected. */
115 : nsMutationGuard mGuard;
116 : };
117 :
118 :
119 : /**
120 : * Implementation of <select>
121 : */
122 : class HTMLSelectElement final : public nsGenericHTMLFormElementWithState,
123 : public nsIDOMHTMLSelectElement,
124 : public nsIConstraintValidation
125 : {
126 : public:
127 : /**
128 : * IS_SELECTED whether to set the option(s) to true or false
129 : *
130 : * CLEAR_ALL whether to clear all other options (for example, if you
131 : * are normal-clicking on the current option)
132 : *
133 : * SET_DISABLED whether it is permissible to set disabled options
134 : * (for JavaScript)
135 : *
136 : * NOTIFY whether to notify frames and such
137 : *
138 : * NO_RESELECT no need to select something after an option is deselected
139 : * (for reset)
140 : */
141 : enum OptionType {
142 : IS_SELECTED = 1 << 0,
143 : CLEAR_ALL = 1 << 1,
144 : SET_DISABLED = 1 << 2,
145 : NOTIFY = 1 << 3,
146 : NO_RESELECT = 1 << 4
147 : };
148 :
149 : using nsIConstraintValidation::GetValidationMessage;
150 :
151 : explicit HTMLSelectElement(already_AddRefed<mozilla::dom::NodeInfo>& aNodeInfo,
152 : FromParser aFromParser = NOT_FROM_PARSER);
153 :
154 0 : NS_IMPL_FROMCONTENT_HTML_WITH_TAG(HTMLSelectElement, select)
155 :
156 : // nsISupports
157 : NS_DECL_ISUPPORTS_INHERITED
158 :
159 : virtual int32_t TabIndexDefault() override;
160 :
161 : // Element
162 0 : virtual bool IsInteractiveHTMLContent(bool aIgnoreTabindex) const override
163 : {
164 0 : return true;
165 : }
166 :
167 : // nsIDOMHTMLSelectElement
168 : NS_DECL_NSIDOMHTMLSELECTELEMENT
169 :
170 : // WebIdl HTMLSelectElement
171 0 : bool Autofocus() const
172 : {
173 0 : return GetBoolAttr(nsGkAtoms::autofocus);
174 : }
175 0 : void SetAutofocus(bool aVal, ErrorResult& aRv)
176 : {
177 0 : SetHTMLBoolAttr(nsGkAtoms::autofocus, aVal, aRv);
178 0 : }
179 : void GetAutocomplete(DOMString& aValue);
180 0 : void SetAutocomplete(const nsAString& aValue, ErrorResult& aRv)
181 : {
182 0 : SetHTMLAttr(nsGkAtoms::autocomplete, aValue, aRv);
183 0 : }
184 :
185 : void GetAutocompleteInfo(AutocompleteInfo& aInfo);
186 :
187 0 : bool Disabled() const
188 : {
189 0 : return GetBoolAttr(nsGkAtoms::disabled);
190 : }
191 0 : void SetDisabled(bool aVal, ErrorResult& aRv)
192 : {
193 0 : SetHTMLBoolAttr(nsGkAtoms::disabled, aVal, aRv);
194 0 : }
195 0 : HTMLFormElement* GetForm() const
196 : {
197 0 : return nsGenericHTMLFormElementWithState::GetForm();
198 : }
199 0 : bool Multiple() const
200 : {
201 0 : return GetBoolAttr(nsGkAtoms::multiple);
202 : }
203 0 : void SetMultiple(bool aVal, ErrorResult& aRv)
204 : {
205 0 : SetHTMLBoolAttr(nsGkAtoms::multiple, aVal, aRv);
206 0 : }
207 : // Uses XPCOM GetName.
208 0 : void SetName(const nsAString& aName, ErrorResult& aRv)
209 : {
210 0 : SetHTMLAttr(nsGkAtoms::name, aName, aRv);
211 0 : }
212 0 : bool Required() const
213 : {
214 0 : return GetBoolAttr(nsGkAtoms::required);
215 : }
216 0 : void SetRequired(bool aVal, ErrorResult& aRv)
217 : {
218 0 : SetHTMLBoolAttr(nsGkAtoms::required, aVal, aRv);
219 0 : }
220 0 : uint32_t Size() const
221 : {
222 0 : return GetUnsignedIntAttr(nsGkAtoms::size, 0);
223 : }
224 0 : void SetSize(uint32_t aSize, ErrorResult& aRv)
225 : {
226 0 : SetUnsignedIntAttr(nsGkAtoms::size, aSize, 0, aRv);
227 0 : }
228 :
229 : // Uses XPCOM GetType.
230 :
231 0 : HTMLOptionsCollection* Options() const
232 : {
233 0 : return mOptions;
234 : }
235 0 : uint32_t Length() const
236 : {
237 0 : return mOptions->Length();
238 : }
239 : void SetLength(uint32_t aLength, ErrorResult& aRv);
240 0 : Element* IndexedGetter(uint32_t aIdx, bool& aFound) const
241 : {
242 0 : return mOptions->IndexedGetter(aIdx, aFound);
243 : }
244 0 : HTMLOptionElement* Item(uint32_t aIdx) const
245 : {
246 0 : return mOptions->ItemAsOption(aIdx);
247 : }
248 0 : HTMLOptionElement* NamedItem(const nsAString& aName) const
249 : {
250 0 : return mOptions->GetNamedItem(aName);
251 : }
252 : void Add(const HTMLOptionElementOrHTMLOptGroupElement& aElement,
253 : const Nullable<HTMLElementOrLong>& aBefore,
254 : ErrorResult& aRv);
255 : // Uses XPCOM Remove.
256 0 : void IndexedSetter(uint32_t aIndex, HTMLOptionElement* aOption,
257 : ErrorResult& aRv)
258 : {
259 0 : mOptions->IndexedSetter(aIndex, aOption, aRv);
260 0 : }
261 :
262 : static bool MatchSelectedOptions(Element* aElement, int32_t, nsIAtom*,
263 : void*);
264 :
265 : nsIHTMLCollection* SelectedOptions();
266 :
267 0 : int32_t SelectedIndex() const
268 : {
269 0 : return mSelectedIndex;
270 : }
271 0 : void SetSelectedIndex(int32_t aIdx, ErrorResult& aRv)
272 : {
273 0 : aRv = SetSelectedIndexInternal(aIdx, true);
274 0 : }
275 : void GetValue(DOMString& aValue);
276 : // Uses XPCOM SetValue.
277 :
278 : // nsIConstraintValidation::WillValidate is fine.
279 : // nsIConstraintValidation::Validity() is fine.
280 : // nsIConstraintValidation::GetValidationMessage() is fine.
281 : // nsIConstraintValidation::CheckValidity() is fine.
282 : using nsIConstraintValidation::CheckValidity;
283 : using nsIConstraintValidation::ReportValidity;
284 : // nsIConstraintValidation::SetCustomValidity() is fine.
285 :
286 : using nsINode::Remove;
287 :
288 : // nsINode
289 : virtual JSObject* WrapNode(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override;
290 :
291 : // nsIContent
292 : virtual nsresult GetEventTargetParent(
293 : EventChainPreVisitor& aVisitor) override;
294 : virtual nsresult PostHandleEvent(
295 : EventChainPostVisitor& aVisitor) override;
296 :
297 : virtual bool IsHTMLFocusable(bool aWithMouse, bool* aIsFocusable, int32_t* aTabIndex) override;
298 : virtual nsresult InsertChildAt(nsIContent* aKid, uint32_t aIndex,
299 : bool aNotify) override;
300 : virtual void RemoveChildAt(uint32_t aIndex, bool aNotify) override;
301 :
302 : // Overriden nsIFormControl methods
303 : NS_IMETHOD Reset() override;
304 : NS_IMETHOD SubmitNamesValues(HTMLFormSubmission* aFormSubmission) override;
305 : NS_IMETHOD SaveState() override;
306 : virtual bool RestoreState(nsPresState* aState) override;
307 : virtual bool IsDisabledForEvents(EventMessage aMessage) override;
308 :
309 : virtual void FieldSetDisabledChanged(bool aNotify) override;
310 :
311 : EventStates IntrinsicState() const override;
312 :
313 : /**
314 : * To be called when stuff is added under a child of the select--but *before*
315 : * they are actually added.
316 : *
317 : * @param aOptions the content that was added (usually just an option, but
318 : * could be an optgroup node with many child options)
319 : * @param aParent the parent the options were added to (could be an optgroup)
320 : * @param aContentIndex the index where the options are being added within the
321 : * parent (if the parent is an optgroup, the index within the optgroup)
322 : */
323 : NS_IMETHOD WillAddOptions(nsIContent* aOptions,
324 : nsIContent* aParent,
325 : int32_t aContentIndex,
326 : bool aNotify);
327 :
328 : /**
329 : * To be called when stuff is removed under a child of the select--but
330 : * *before* they are actually removed.
331 : *
332 : * @param aParent the parent the option(s) are being removed from
333 : * @param aContentIndex the index of the option(s) within the parent (if the
334 : * parent is an optgroup, the index within the optgroup)
335 : */
336 : NS_IMETHOD WillRemoveOptions(nsIContent* aParent,
337 : int32_t aContentIndex,
338 : bool aNotify);
339 :
340 : /**
341 : * Checks whether an option is disabled (even if it's part of an optgroup)
342 : *
343 : * @param aIndex the index of the option to check
344 : * @return whether the option is disabled
345 : */
346 : NS_IMETHOD IsOptionDisabled(int32_t aIndex,
347 : bool* aIsDisabled);
348 : bool IsOptionDisabled(HTMLOptionElement* aOption);
349 :
350 : /**
351 : * Sets multiple options (or just sets startIndex if select is single)
352 : * and handles notifications and cleanup and everything under the sun.
353 : * When this method exits, the select will be in a consistent state. i.e.
354 : * if you set the last option to false, it will select an option anyway.
355 : *
356 : * @param aStartIndex the first index to set
357 : * @param aEndIndex the last index to set (set same as first index for one
358 : * option)
359 : * @param aOptionsMask determines whether to set, clear all or disable
360 : * options and whether frames are to be notified of such.
361 : * @return whether any options were actually changed
362 : */
363 : bool SetOptionsSelectedByIndex(int32_t aStartIndex,
364 : int32_t aEndIndex,
365 : uint32_t aOptionsMask);
366 :
367 : /**
368 : * Finds the index of a given option element
369 : *
370 : * @param aOption the option to get the index of
371 : * @param aStartIndex the index to start looking at
372 : * @param aForward TRUE to look forward, FALSE to look backward
373 : * @return the option index
374 : */
375 : NS_IMETHOD GetOptionIndex(nsIDOMHTMLOptionElement* aOption,
376 : int32_t aStartIndex,
377 : bool aForward,
378 : int32_t* aIndex);
379 :
380 : /**
381 : * Called when an attribute is about to be changed
382 : */
383 : virtual nsresult BindToTree(nsIDocument* aDocument, nsIContent* aParent,
384 : nsIContent* aBindingParent,
385 : bool aCompileEventHandlers) override;
386 : virtual void UnbindFromTree(bool aDeep, bool aNullParent) override;
387 : virtual nsresult BeforeSetAttr(int32_t aNameSpaceID, nsIAtom* aName,
388 : const nsAttrValueOrString* aValue,
389 : bool aNotify) override;
390 : virtual nsresult AfterSetAttr(int32_t aNameSpaceID, nsIAtom* aName,
391 : const nsAttrValue* aValue,
392 : const nsAttrValue* aOldValue,
393 : bool aNotify) override;
394 :
395 : virtual void DoneAddingChildren(bool aHaveNotified) override;
396 0 : virtual bool IsDoneAddingChildren() override {
397 0 : return mIsDoneAddingChildren;
398 : }
399 :
400 : virtual bool ParseAttribute(int32_t aNamespaceID,
401 : nsIAtom* aAttribute,
402 : const nsAString& aValue,
403 : nsAttrValue& aResult) override;
404 : virtual nsMapRuleToAttributesFunc GetAttributeMappingFunction() const override;
405 : virtual nsChangeHint GetAttributeChangeHint(const nsIAtom* aAttribute,
406 : int32_t aModType) const override;
407 : NS_IMETHOD_(bool) IsAttributeMapped(const nsIAtom* aAttribute) const override;
408 :
409 : virtual nsresult Clone(mozilla::dom::NodeInfo* aNodeInfo, nsINode** aResult,
410 : bool aPreallocateChildren) const override;
411 :
412 0 : NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(HTMLSelectElement,
413 : nsGenericHTMLFormElementWithState)
414 :
415 0 : HTMLOptionsCollection* GetOptions()
416 : {
417 0 : return mOptions;
418 : }
419 :
420 : // nsIConstraintValidation
421 : nsresult GetValidationMessage(nsAString& aValidationMessage,
422 : ValidityStateType aType) override;
423 :
424 : void UpdateValueMissingValidityState();
425 : /**
426 : * Insert aElement before the node given by aBefore
427 : */
428 : void Add(nsGenericHTMLElement& aElement, nsGenericHTMLElement* aBefore,
429 : ErrorResult& aError);
430 0 : void Add(nsGenericHTMLElement& aElement, int32_t aIndex, ErrorResult& aError)
431 : {
432 : // If item index is out of range, insert to last.
433 : // (since beforeElement becomes null, it is inserted to last)
434 0 : nsIContent* beforeContent = mOptions->GetElementAt(aIndex);
435 0 : return Add(aElement, nsGenericHTMLElement::FromContentOrNull(beforeContent),
436 0 : aError);
437 : }
438 :
439 : /**
440 : * Is this a combobox?
441 : */
442 0 : bool IsCombobox() const
443 : {
444 0 : return !Multiple() && Size() <= 1;
445 : }
446 :
447 : bool OpenInParentProcess();
448 : void SetOpenInParentProcess(bool aVal);
449 :
450 : void GetPreviewValue(nsAString& aValue);
451 : void SetPreviewValue(const nsAString& aValue);
452 :
453 : protected:
454 : virtual ~HTMLSelectElement();
455 :
456 : friend class SafeOptionListMutation;
457 :
458 : // Helper Methods
459 : /**
460 : * Check whether the option specified by the index is selected
461 : * @param aIndex the index
462 : * @return whether the option at the index is selected
463 : */
464 : bool IsOptionSelectedByIndex(int32_t aIndex);
465 : /**
466 : * Starting with (and including) aStartIndex, find the first selected index
467 : * and set mSelectedIndex to it.
468 : * @param aStartIndex the index to start with
469 : */
470 : void FindSelectedIndex(int32_t aStartIndex, bool aNotify);
471 : /**
472 : * Select some option if possible (generally the first non-disabled option).
473 : * @return true if something was selected, false otherwise
474 : */
475 : bool SelectSomething(bool aNotify);
476 : /**
477 : * Call SelectSomething(), but only if nothing is selected
478 : * @see SelectSomething()
479 : * @return true if something was selected, false otherwise
480 : */
481 : bool CheckSelectSomething(bool aNotify);
482 : /**
483 : * Called to trigger notifications of frames and fixing selected index
484 : *
485 : * @param aSelectFrame the frame for this content (could be null)
486 : * @param aIndex the index that was selected or deselected
487 : * @param aSelected whether the index was selected or deselected
488 : * @param aChangeOptionState if false, don't do anything to the
489 : * HTMLOptionElement at aIndex. If true, change
490 : * its selected state to aSelected.
491 : * @param aNotify whether to notify the style system and such
492 : */
493 : void OnOptionSelected(nsISelectControlFrame* aSelectFrame,
494 : int32_t aIndex,
495 : bool aSelected,
496 : bool aChangeOptionState,
497 : bool aNotify);
498 : /**
499 : * Restore state to a particular state string (representing the options)
500 : * @param aNewSelected the state string to restore to
501 : */
502 : void RestoreStateTo(SelectState* aNewSelected);
503 :
504 : // Adding options
505 : /**
506 : * Insert option(s) into the options[] array and perform notifications
507 : * @param aOptions the option or optgroup being added
508 : * @param aListIndex the index to start adding options into the list at
509 : * @param aDepth the depth of aOptions (1=direct child of select ...)
510 : */
511 : void InsertOptionsIntoList(nsIContent* aOptions,
512 : int32_t aListIndex,
513 : int32_t aDepth,
514 : bool aNotify);
515 : /**
516 : * Remove option(s) from the options[] array
517 : * @param aOptions the option or optgroup being added
518 : * @param aListIndex the index to start removing options from the list at
519 : * @param aDepth the depth of aOptions (1=direct child of select ...)
520 : */
521 : nsresult RemoveOptionsFromList(nsIContent* aOptions,
522 : int32_t aListIndex,
523 : int32_t aDepth,
524 : bool aNotify);
525 :
526 : // nsIConstraintValidation
527 : void UpdateBarredFromConstraintValidation();
528 : bool IsValueMissing();
529 :
530 : /**
531 : * Get the index of the first option at, under or following the content in
532 : * the select, or length of options[] if none are found
533 : * @param aOptions the content
534 : * @return the index of the first option
535 : */
536 : int32_t GetOptionIndexAt(nsIContent* aOptions);
537 : /**
538 : * Get the next option following the content in question (not at or under)
539 : * (this could include siblings of the current content or siblings of the
540 : * parent or children of siblings of the parent).
541 : * @param aOptions the content
542 : * @return the index of the next option after the content
543 : */
544 : int32_t GetOptionIndexAfter(nsIContent* aOptions);
545 : /**
546 : * Get the first option index at or under the content in question.
547 : * @param aOptions the content
548 : * @return the index of the first option at or under the content
549 : */
550 : int32_t GetFirstOptionIndex(nsIContent* aOptions);
551 : /**
552 : * Get the first option index under the content in question, within the
553 : * range specified.
554 : * @param aOptions the content
555 : * @param aStartIndex the first child to look at
556 : * @param aEndIndex the child *after* the last child to look at
557 : * @return the index of the first option at or under the content
558 : */
559 : int32_t GetFirstChildOptionIndex(nsIContent* aOptions,
560 : int32_t aStartIndex,
561 : int32_t aEndIndex);
562 :
563 : /**
564 : * Get the frame as an nsISelectControlFrame (MAY RETURN nullptr)
565 : * @return the select frame, or null
566 : */
567 : nsISelectControlFrame* GetSelectFrame();
568 :
569 : /**
570 : * Helper method for dispatching ContentReset notifications to list
571 : * and combo box frames.
572 : */
573 : void DispatchContentReset();
574 :
575 : /**
576 : * Rebuilds the options array from scratch as a fallback in error cases.
577 : */
578 : void RebuildOptionsArray(bool aNotify);
579 :
580 : #ifdef DEBUG
581 : void VerifyOptionsArray();
582 : #endif
583 :
584 : nsresult SetSelectedIndexInternal(int32_t aIndex, bool aNotify);
585 :
586 : void SetSelectionChanged(bool aValue, bool aNotify);
587 :
588 : /**
589 : * Marks the selectedOptions list as dirty, so that it'll populate itself
590 : * again.
591 : */
592 : void UpdateSelectedOptions();
593 :
594 : /**
595 : * Return whether an element should have a validity UI.
596 : * (with :-moz-ui-invalid and :-moz-ui-valid pseudo-classes).
597 : *
598 : * @return Whether the element should have a validity UI.
599 : */
600 0 : bool ShouldShowValidityUI() const {
601 : /**
602 : * Always show the validity UI if the form has already tried to be submitted
603 : * but was invalid.
604 : *
605 : * Otherwise, show the validity UI if the selection has been changed.
606 : */
607 0 : if (mForm && mForm->HasEverTriedInvalidSubmit()) {
608 0 : return true;
609 : }
610 :
611 0 : return mSelectionHasChanged;
612 : }
613 :
614 : /** The options[] array */
615 : RefPtr<HTMLOptionsCollection> mOptions;
616 : nsContentUtils::AutocompleteAttrState mAutocompleteAttrState;
617 : nsContentUtils::AutocompleteAttrState mAutocompleteInfoState;
618 : /** false if the parser is in the middle of adding children. */
619 : bool mIsDoneAddingChildren;
620 : /** true if our disabled state has changed from the default **/
621 : bool mDisabledChanged;
622 : /** true if child nodes are being added or removed.
623 : * Used by SafeOptionListMutation.
624 : */
625 : bool mMutating;
626 : /**
627 : * True if DoneAddingChildren will get called but shouldn't restore state.
628 : */
629 : bool mInhibitStateRestoration;
630 : /**
631 : * True if the selection has changed since the element's creation.
632 : */
633 : bool mSelectionHasChanged;
634 : /**
635 : * True if the default selected option has been set.
636 : */
637 : bool mDefaultSelectionSet;
638 : /**
639 : * True if :-moz-ui-invalid can be shown.
640 : */
641 : bool mCanShowInvalidUI;
642 : /**
643 : * True if :-moz-ui-valid can be shown.
644 : */
645 : bool mCanShowValidUI;
646 :
647 : /** The number of non-options as children of the select */
648 : uint32_t mNonOptionChildren;
649 : /** The number of optgroups anywhere under the select */
650 : uint32_t mOptGroupCount;
651 : /**
652 : * The current selected index for selectedIndex (will be the first selected
653 : * index if multiple are selected)
654 : */
655 : int32_t mSelectedIndex;
656 : /**
657 : * The temporary restore state in case we try to restore before parser is
658 : * done adding options
659 : */
660 : nsCOMPtr<SelectState> mRestoreState;
661 :
662 : /**
663 : * The live list of selected options.
664 : */
665 : RefPtr<nsContentList> mSelectedOptions;
666 :
667 : private:
668 : static void MapAttributesIntoRule(const nsMappedAttributes* aAttributes,
669 : GenericSpecifiedValues* aGenericData);
670 : };
671 :
672 : } // namespace dom
673 : } // namespace mozilla
674 :
675 : #endif // mozilla_dom_HTMLSelectElement_h
|