michael@0: michael@0: /* michael@0: * Copyright 2006 The Android Open Source Project michael@0: * michael@0: * Use of this source code is governed by a BSD-style license that can be michael@0: * found in the LICENSE file. michael@0: */ michael@0: michael@0: michael@0: #ifndef SkWidgetViews_DEFINED michael@0: #define SkWidgetViews_DEFINED michael@0: michael@0: #include "SkView.h" michael@0: michael@0: michael@0: enum SkWidgetEnum { michael@0: kBorder_WidgetEnum, //!< michael@0: kButton_WidgetEnum, //!< michael@0: kImage_WidgetEnum, //!< michael@0: kList_WidgetEnum, //!< michael@0: kProgress_WidgetEnum, //!< michael@0: kScroll_WidgetEnum, //!< michael@0: kText_WidgetEnum, //!< michael@0: michael@0: kWidgetEnumCount michael@0: }; michael@0: michael@0: //determines which skin to use michael@0: enum SkinEnum { michael@0: kBorder_SkinEnum, michael@0: kButton_SkinEnum, michael@0: kProgress_SkinEnum, michael@0: kScroll_SkinEnum, michael@0: kStaticText_SkinEnum, michael@0: michael@0: kSkinEnumCount michael@0: }; michael@0: michael@0: #include "SkAnimator.h" michael@0: //used for inflates michael@0: const char* get_skin_enum_path(SkinEnum se); michael@0: void init_skin_anim(const char path[], SkAnimator* anim); michael@0: void init_skin_anim(SkinEnum se, SkAnimator* anim); michael@0: void init_skin_paint(SkinEnum se, SkPaint* paint); michael@0: void inflate_paint(const SkDOM& dom, const SkDOM::Node* node, SkPaint* paint); michael@0: michael@0: /** Given an enum value, return an instance of the specified widget. michael@0: If the enum is out of range, returns null michael@0: */ michael@0: SkView* SkWidgetFactory(SkWidgetEnum); michael@0: /** Given the inflate/element name of a widget, return an instance of michael@0: the specified widget, or null if name does not match any known michael@0: widget type. michael@0: */ michael@0: SkView* SkWidgetFactory(const char name[]); michael@0: michael@0: //////////////////////////////////////////////////////////////////////////////////////////////// michael@0: michael@0: class SkWidgetView : public SkView { michael@0: public: michael@0: SkWidgetView(); michael@0: michael@0: const char* getLabel() const; michael@0: void getLabel(SkString* label) const; michael@0: michael@0: void setLabel(const char[]); michael@0: void setLabel(const char[], size_t len); michael@0: void setLabel(const SkString&); michael@0: michael@0: SkEvent& event() { return fEvent; } michael@0: const SkEvent& event() const { return fEvent; } michael@0: michael@0: /** Returns true if the widget can post its event to its listeners. michael@0: */ michael@0: bool postWidgetEvent(); michael@0: michael@0: /** Returns the sinkID of the widgetview that posted the event, or 0 michael@0: */ michael@0: static SkEventSinkID GetWidgetEventSinkID(const SkEvent&); michael@0: michael@0: protected: michael@0: /** called when the label changes. override in subclasses. default action invals the view's bounds. michael@0: called with the old and new labels, before the label has actually changed. michael@0: */ michael@0: virtual void onLabelChange(const char oldLabel[], const char newLabel[]); michael@0: /** called before posting the event to our listeners. Override to add slots to the event michael@0: before posting. Return true to proceed with posting, or false to not post the event to any michael@0: listener. Note: the event passed in may not be the same as calling this->event(). michael@0: Be sure to call your INHERITED method as well, so that all classes in the hierarchy get a shot michael@0: at modifying the event (and possibly returning false to abort). michael@0: */ michael@0: virtual bool onPrepareWidgetEvent(SkEvent* evt); michael@0: michael@0: // overrides michael@0: virtual void onInflate(const SkDOM& dom, const SkDOM::Node*); michael@0: michael@0: private: michael@0: SkString fLabel; michael@0: SkEvent fEvent; michael@0: michael@0: typedef SkView INHERITED; michael@0: }; michael@0: michael@0: //////////////////////////////////////////////////////////////////////////////////////////////// michael@0: michael@0: class SkButtonView : public SkWidgetView { michael@0: public: michael@0: // inflate: "sk-button" michael@0: michael@0: protected: michael@0: // overrides michael@0: virtual bool onEvent(const SkEvent&); michael@0: private: michael@0: typedef SkWidgetView INHERITED; michael@0: }; michael@0: michael@0: //////////////////////////////////////////////////////////////////////////////////////////////// michael@0: michael@0: class SkCheckButtonView : public SkWidgetView { michael@0: public: michael@0: SkCheckButtonView(); michael@0: michael@0: // inflate: "sk-checkbutton" michael@0: michael@0: enum CheckState { michael@0: kOff_CheckState, //!< inflate: check-state="off" michael@0: kOn_CheckState, //!< inflate: check-state="on" michael@0: kUnknown_CheckState //!< inflate: check-state="unknown" michael@0: }; michael@0: CheckState getCheckState() const { return (CheckState)fCheckState; } michael@0: void setCheckState(CheckState); michael@0: michael@0: /** use this to extract the CheckState from an event (i.e. one that as posted michael@0: by a SkCheckButtonView). Returns true if the proper slot was present in the event, michael@0: and sets state to that value. If no proper slot is found, returns false and does not michael@0: modify state. michael@0: */ michael@0: static bool GetWidgetEventCheckState(const SkEvent&, CheckState* state); michael@0: michael@0: protected: michael@0: // called when the check-state is about to change, but before it actually has michael@0: virtual void onCheckStateChange(CheckState oldState, CheckState newState); michael@0: michael@0: // overrides michael@0: virtual void onInflate(const SkDOM& dom, const SkDOM::Node*); michael@0: virtual bool onPrepareWidgetEvent(SkEvent* evt); michael@0: michael@0: private: michael@0: uint8_t fCheckState; michael@0: michael@0: typedef SkWidgetView INHERITED; michael@0: }; michael@0: michael@0: //////////////////////////////////////////////////////////////////////////////////////////////// michael@0: #include "SkTextBox.h" michael@0: michael@0: class SkStaticTextView : public SkView { michael@0: public: michael@0: SkStaticTextView(); michael@0: virtual ~SkStaticTextView(); michael@0: michael@0: enum Mode { michael@0: kFixedSize_Mode, michael@0: kAutoWidth_Mode, michael@0: kAutoHeight_Mode, michael@0: michael@0: kModeCount michael@0: }; michael@0: Mode getMode() const { return (Mode)fMode; } michael@0: void setMode(Mode); michael@0: michael@0: SkTextBox::SpacingAlign getSpacingAlign() const { return (SkTextBox::SpacingAlign)fSpacingAlign; } michael@0: void setSpacingAlign(SkTextBox::SpacingAlign); michael@0: michael@0: void getMargin(SkPoint* margin) const; michael@0: void setMargin(SkScalar dx, SkScalar dy); michael@0: michael@0: size_t getText(SkString* text = NULL) const; michael@0: size_t getText(char text[] = NULL) const; michael@0: void setText(const SkString&); michael@0: void setText(const char text[]); michael@0: void setText(const char text[], size_t len); michael@0: michael@0: void getPaint(SkPaint*) const; michael@0: void setPaint(const SkPaint&); michael@0: michael@0: protected: michael@0: // overrides michael@0: virtual void onDraw(SkCanvas*); michael@0: virtual void onInflate(const SkDOM& dom, const SkDOM::Node*); michael@0: michael@0: private: michael@0: SkPoint fMargin; michael@0: SkString fText; michael@0: SkPaint fPaint; michael@0: uint8_t fMode; michael@0: uint8_t fSpacingAlign; michael@0: michael@0: void computeSize(); michael@0: michael@0: typedef SkView INHERITED; michael@0: }; michael@0: michael@0: //////////////////////////////////////////////////////////////////////////////////////////////// michael@0: michael@0: class SkAnimator; michael@0: class SkListSource; michael@0: class SkScrollBarView; michael@0: michael@0: class SkListView : public SkWidgetView { michael@0: public: michael@0: SkListView(); michael@0: virtual ~SkListView(); michael@0: michael@0: bool hasScrollBar() const { return fScrollBar != NULL; } michael@0: void setHasScrollBar(bool); michael@0: michael@0: /** Return the number of visible rows michael@0: */ michael@0: int getVisibleRowCount() const { return fVisibleRowCount; } michael@0: /** Return the index of the selected row, or -1 if none michael@0: */ michael@0: int getSelection() const { return fCurrIndex; } michael@0: /** Set the index of the selected row, or -1 for none michael@0: */ michael@0: void setSelection(int); michael@0: /** If possible, move the selection up and return true, michael@0: else do nothing and return false michael@0: If nothing is selected, select the last item (unless there are no items). michael@0: */ michael@0: bool moveSelectionUp(); michael@0: /** If possible, move the selection down and return true, michael@0: else do nothing and return false. michael@0: If nothing is selected, select the first item (unless there are no items). michael@0: */ michael@0: bool moveSelectionDown(); michael@0: michael@0: SkListSource* getListSource() const { return fSource; } michael@0: SkListSource* setListSource(SkListSource*); michael@0: michael@0: /** Call this in your event handler. If the specified event is from a SkListView, michael@0: then it returns the index of the selected item in this list, otherwise it michael@0: returns -1 michael@0: */ michael@0: static int GetWidgetEventListIndex(const SkEvent&); michael@0: michael@0: protected: michael@0: // overrides michael@0: virtual void onDraw(SkCanvas*); michael@0: virtual void onSizeChange(); michael@0: virtual bool onEvent(const SkEvent&); michael@0: virtual void onInflate(const SkDOM& dom, const SkDOM::Node* node); michael@0: virtual bool onPrepareWidgetEvent(SkEvent*); michael@0: michael@0: private: michael@0: enum DirtyFlags { michael@0: kAnimCount_DirtyFlag = 0x01, michael@0: kAnimContent_DirtyFlag = 0x02 michael@0: }; michael@0: void dirtyCache(unsigned dirtyFlags); michael@0: bool ensureCache(); michael@0: michael@0: int logicalToVisualIndex(int index) const { return index - fScrollIndex; } michael@0: void invalSelection(); michael@0: SkScalar getContentWidth() const; michael@0: bool getRowRect(int index, SkRect*) const; michael@0: void ensureSelectionIsVisible(); michael@0: void ensureVisibleRowCount(); michael@0: michael@0: struct BindingRec; michael@0: michael@0: enum Heights { michael@0: kNormal_Height, michael@0: kSelected_Height michael@0: }; michael@0: SkListSource* fSource; michael@0: SkScrollBarView* fScrollBar; michael@0: SkAnimator* fAnims; michael@0: BindingRec* fBindings; michael@0: SkString fSkinName; michael@0: SkScalar fHeights[2]; michael@0: int16_t fScrollIndex, fCurrIndex; michael@0: uint16_t fVisibleRowCount, fBindingCount; michael@0: SkBool8 fAnimContentDirty; michael@0: SkBool8 fAnimFocusDirty; michael@0: michael@0: typedef SkWidgetView INHERITED; michael@0: }; michael@0: michael@0: class SkListSource : public SkRefCnt { michael@0: public: michael@0: SK_DECLARE_INST_COUNT(SkListSource) michael@0: michael@0: virtual int countFields(); michael@0: virtual void getFieldName(int index, SkString* field); michael@0: /** Return the index of the named field, or -1 if not found */ michael@0: virtual int findFieldIndex(const char field[]); michael@0: michael@0: virtual int countRecords(); michael@0: virtual void getRecord(int rowIndex, int fieldIndex, SkString* data); michael@0: michael@0: virtual bool prepareWidgetEvent(SkEvent*, int rowIndex); michael@0: michael@0: static SkListSource* Factory(const char name[]); michael@0: private: michael@0: typedef SkRefCnt INHERITED; michael@0: }; michael@0: michael@0: #endif