tabbar.go 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220
  1. // Copyright 2016 The G3N Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style
  3. // license that can be found in the LICENSE file.
  4. package gui
  5. import "github.com/g3n/engine/math32"
  6. // TabBar is a panel which can contain other panels contained in Tabs.
  7. // Only one panel is visible at one time.
  8. // To show another panel the corresponding Tab must be selected.
  9. type TabBar struct {
  10. Panel // Embedded panel
  11. styles *TabBarStyles // Pointer to current styles
  12. tabs []*Tab // Array of tabs
  13. selected int // Index of the selected tab
  14. cursorOver bool // Cursor over flag
  15. }
  16. // Tab describes an individual tab from the TabBar
  17. type Tab struct {
  18. header Panel // Tab header
  19. label *Label // Tab optional label
  20. icon *Label // Tab optional icon
  21. img *Image // Tab optional image
  22. content Panel // User content panel
  23. }
  24. // TabBarStyle describes the style
  25. type TabBarStyle struct {
  26. Border BorderSizes
  27. Paddings BorderSizes
  28. BorderColor math32.Color4
  29. BgColor math32.Color4
  30. FgColor math32.Color
  31. }
  32. type TabBarStyles struct {
  33. Normal TabBarStyle
  34. Over TabBarStyle
  35. Focus TabBarStyle
  36. Disabled TabBarStyle
  37. }
  38. // NewTabBar creates and returns a pointer to a new TabBar widget
  39. // with the specified width and height
  40. func NewTabBar(width, height float32) *TabBar {
  41. // Creates new TabBar
  42. tb := new(TabBar)
  43. tb.Initialize(width, height)
  44. tb.styles = &StyleDefault().TabBar
  45. tb.tabs = make([]*Tab, 0)
  46. tb.selected = -1
  47. // Subscribe to panel events
  48. tb.Subscribe(OnCursorEnter, tb.onCursor)
  49. tb.Subscribe(OnCursorLeave, tb.onCursor)
  50. tb.Subscribe(OnEnable, func(name string, ev interface{}) { tb.update() })
  51. tb.Subscribe(OnResize, func(name string, ev interface{}) { tb.recalc() })
  52. tb.recalc()
  53. tb.update()
  54. return tb
  55. }
  56. // AddTab creates and adds a new Tab panel with the specified header text
  57. // at end of this TabBar list of tabs.
  58. // Returns the pointer to thew new Tab.
  59. func (tb *TabBar) AddTab(text string) *Tab {
  60. return tb.InsertTab(text, len(tb.tabs))
  61. }
  62. // InsertTab creates and inserts a new Tab panel with the specified header text
  63. // at the specified position in the TabBar from left to right.
  64. // Returns the pointer to the new Tab or nil if the position is invalid.
  65. func (tb *TabBar) InsertTab(text string, pos int) *Tab {
  66. // Checks position to insert into
  67. if pos < 0 || pos > len(tb.tabs) {
  68. return nil
  69. }
  70. // Creates and initializes the new Tab
  71. tab := new(Tab)
  72. if text != "" {
  73. tab.label = NewLabel(text)
  74. }
  75. tab.content.Initialize(0, 0)
  76. // Inserts created Tab at the specified position
  77. tb.tabs = append(tb.tabs, nil)
  78. copy(tb.tabs[pos+1:], tb.tabs[pos:])
  79. tb.tabs[pos] = tab
  80. tb.update()
  81. tb.recalc()
  82. return tab
  83. }
  84. // RemoveTab removes the tab at the specified position in the TabBar.
  85. // Returns the pointer of the removed tab or nil if the position is invalid.
  86. func (tb *TabBar) RemoveTab(pos int) *Tab {
  87. if pos < 0 || pos >= len(tb.tabs) {
  88. return nil
  89. }
  90. tab := tb.tabs[pos]
  91. // Remove tab from array
  92. copy(tb.tabs[pos:], tb.tabs[pos+1:])
  93. tb.tabs[len(tb.tabs)-1] = nil
  94. tb.tabs = tb.tabs[:len(tb.tabs)-1]
  95. // Checks if tab was selected
  96. if tb.selected == pos {
  97. }
  98. return tab
  99. }
  100. // TabCount returns the current number of tabs
  101. func (tb *TabBar) TabCount() int {
  102. return len(tb.tabs)
  103. }
  104. // TabAt returns the pointer of the Tab object at the specified index.
  105. // Return nil if the index is invalid
  106. func (tb *TabBar) TabAt(idx int) *Tab {
  107. if idx < 0 || idx >= len(tb.tabs) {
  108. return nil
  109. }
  110. return tb.tabs[idx]
  111. }
  112. // SetSelected sets the selected tab of the TabBar to the tab with the specified position.
  113. // Returns the pointer of the selected tab or nil if the position is invalid.
  114. func (tb *TabBar) SetSelected(pos int) *Tab {
  115. if pos < 0 || pos >= len(tb.tabs) {
  116. return nil
  117. }
  118. tb.selected = pos
  119. return tb.tabs[pos]
  120. }
  121. // onCursor process subscribed cursor events
  122. func (tb *TabBar) onCursor(evname string, ev interface{}) {
  123. switch evname {
  124. case OnCursorEnter:
  125. tb.cursorOver = true
  126. tb.update()
  127. case OnCursorLeave:
  128. tb.cursorOver = false
  129. tb.update()
  130. default:
  131. return
  132. }
  133. tb.root.StopPropagation(StopAll)
  134. }
  135. // applyStyle applies the specified TabBar style
  136. func (tb *TabBar) applyStyle(s *TabBarStyle) {
  137. tb.SetBordersFrom(&s.Border)
  138. tb.SetBordersColor4(&s.BorderColor)
  139. tb.SetPaddingsFrom(&s.Paddings)
  140. tb.SetColor4(&s.BgColor)
  141. }
  142. // recalc recalculates and updates the positions of all tabs
  143. func (tb *TabBar) recalc() {
  144. }
  145. // update...
  146. func (tb *TabBar) update() {
  147. if !tb.Enabled() {
  148. tb.applyStyle(&tb.styles.Disabled)
  149. return
  150. }
  151. if tb.cursorOver {
  152. tb.applyStyle(&tb.styles.Over)
  153. return
  154. }
  155. tb.applyStyle(&tb.styles.Normal)
  156. }
  157. //
  158. // Tab methods
  159. //
  160. // SetText sets the text of the tab header
  161. func (tab *Tab) SetText(text string) *Tab {
  162. return tab
  163. }
  164. // SetIcon sets the icon of the tab header
  165. func (tab *Tab) SetIcon(icon string) *Tab {
  166. return tab
  167. }
  168. // Panel returns a pointer to the specified tab content panel
  169. func (tab *Tab) Panel() *Panel {
  170. return &tab.content
  171. }
  172. // recalc recalculates the positions of the Tab header internal panels
  173. func (tab *Tab) recalc() {
  174. width := tab.header.Width()
  175. }