font.go 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272
  1. // Copyright 2018 visualfc. All rights reserved.
  2. package tk
  3. import (
  4. "fmt"
  5. "strings"
  6. )
  7. type Font interface {
  8. Id() string
  9. IsValid() bool
  10. String() string
  11. Description() string
  12. Family() string
  13. Size() int
  14. IsBold() bool
  15. IsItalic() bool
  16. IsUnderline() bool
  17. IsOverstrike() bool
  18. }
  19. type FontAttr struct {
  20. key string
  21. value interface{}
  22. }
  23. func FontAttrBold() *FontAttr {
  24. return &FontAttr{"weight", "bold"}
  25. }
  26. func FontAttrItalic() *FontAttr {
  27. return &FontAttr{"slant", "italic"}
  28. }
  29. func FontAttrUnderline() *FontAttr {
  30. return &FontAttr{"underline", 1}
  31. }
  32. func FontAttrOverstrike() *FontAttr {
  33. return &FontAttr{"overstrike", 1}
  34. }
  35. type BaseFont struct {
  36. id string
  37. }
  38. func (f *BaseFont) Id() string {
  39. return f.id
  40. }
  41. func (f *BaseFont) IsValid() bool {
  42. return f.id != ""
  43. }
  44. func (w *BaseFont) String() string {
  45. return fmt.Sprintf("Font{%v}", w.id)
  46. }
  47. func (w *BaseFont) Description() string {
  48. if w.id == "" {
  49. return ""
  50. }
  51. r, _ := evalAsString(fmt.Sprintf("font actual %v", w.id))
  52. return r
  53. }
  54. func (w *BaseFont) Family() string {
  55. r, _ := evalAsString(fmt.Sprintf("font actual %v -family", w.id))
  56. return r
  57. }
  58. func (w *BaseFont) Size() int {
  59. r, _ := evalAsInt(fmt.Sprintf("font actual %v -size", w.id))
  60. return r
  61. }
  62. func (w *BaseFont) IsBold() bool {
  63. r, _ := evalAsString(fmt.Sprintf("font actual %v -weight", w.id))
  64. return r == "bold"
  65. }
  66. func (w *BaseFont) IsItalic() bool {
  67. r, _ := evalAsString(fmt.Sprintf("font actual %v -slant", w.id))
  68. return r == "italic"
  69. }
  70. func (w *BaseFont) IsUnderline() bool {
  71. r, _ := evalAsBool(fmt.Sprintf("font actual %v -underline", w.id))
  72. return r
  73. }
  74. func (w *BaseFont) IsOverstrike() bool {
  75. r, _ := evalAsBool(fmt.Sprintf("font actual %v -overstrike", w.id))
  76. return r
  77. }
  78. func (w *BaseFont) MeasureTextWidth(text string) int {
  79. setObjText("atk_tmp_text", text)
  80. r, _ := evalAsInt(fmt.Sprintf("font measure %v $atk_tmp_text", w.id))
  81. return r
  82. }
  83. func (w *BaseFont) Ascent() int {
  84. r, _ := evalAsInt(fmt.Sprintf("font metrics %v -ascent", w.id))
  85. return r
  86. }
  87. func (w *BaseFont) Descent() int {
  88. r, _ := evalAsInt(fmt.Sprintf("font metrics %v -descent", w.id))
  89. return r
  90. }
  91. func (w *BaseFont) Clone() *UserFont {
  92. iid := makeNamedId("atk_font")
  93. script := fmt.Sprintf("font create %v %v", iid, w.Description())
  94. if eval(script) != nil {
  95. return nil
  96. }
  97. return &UserFont{BaseFont{iid}}
  98. }
  99. type UserFont struct {
  100. BaseFont
  101. }
  102. func (f *UserFont) Destroy() error {
  103. if f.id == "" {
  104. return ErrInvalid
  105. }
  106. eval(fmt.Sprintf("font delete %v", f.id))
  107. f.id = ""
  108. return nil
  109. }
  110. func NewUserFont(family string, size int, attributes ...*FontAttr) *UserFont {
  111. var attrList []string
  112. for _, attr := range attributes {
  113. if attr == nil {
  114. continue
  115. }
  116. attrList = append(attrList, fmt.Sprintf("-%v {%v}", attr.key, attr.value))
  117. }
  118. iid := makeNamedId("atk_font")
  119. setObjText("atk_tmp_family", family)
  120. script := fmt.Sprintf("font create %v -family $atk_tmp_family -size %v", iid, size)
  121. if len(attrList) > 0 {
  122. script += " " + strings.Join(attrList, " ")
  123. }
  124. err := eval(script)
  125. if err != nil {
  126. return nil
  127. }
  128. return &UserFont{BaseFont{iid}}
  129. }
  130. func NewUserFontFromClone(font Font) *UserFont {
  131. if font == nil {
  132. return nil
  133. }
  134. iid := makeNamedId("atk_font")
  135. script := fmt.Sprintf("font create %v", iid)
  136. if font != nil {
  137. script += " " + font.Description()
  138. }
  139. err := eval(script)
  140. if err != nil {
  141. return nil
  142. }
  143. return &UserFont{BaseFont{iid}}
  144. }
  145. func (w *UserFont) SetFamily(family string) error {
  146. setObjText("atk_tmp_family", family)
  147. return eval(fmt.Sprintf("font configure %v -family $atk_tmp_family", w.id))
  148. }
  149. func (w *UserFont) SetSize(size int) error {
  150. return eval(fmt.Sprintf("font configure %v -size {%v}", w.id, size))
  151. }
  152. func (w *UserFont) SetBold(bold bool) error {
  153. var v string
  154. if bold {
  155. v = "bold"
  156. } else {
  157. v = "normal"
  158. }
  159. return eval(fmt.Sprintf("font configure %v -weight {%v}", w.id, v))
  160. }
  161. func (w *UserFont) SetItalic(italic bool) error {
  162. var v string
  163. if italic {
  164. v = "italic"
  165. } else {
  166. v = "roman"
  167. }
  168. return eval(fmt.Sprintf("font configure %v -slant {%v}", w.id, v))
  169. }
  170. func (w *UserFont) SetUnderline(underline bool) error {
  171. return eval(fmt.Sprintf("font configure %v -underline {%v}", w.id, boolToInt(underline)))
  172. }
  173. func (w *UserFont) SetOverstrike(overstrike bool) error {
  174. return eval(fmt.Sprintf("font configure %v -overstrike {%v}", w.id, boolToInt(overstrike)))
  175. }
  176. func FontFamilieList() []string {
  177. r, _ := evalAsStringList("font families")
  178. return r
  179. }
  180. //tk system default font
  181. type SysFont struct {
  182. BaseFont
  183. }
  184. type SysFontType int
  185. const (
  186. SysDefaultFont SysFontType = 0
  187. SysTextFont
  188. SysFixedFont
  189. SysMenuFont
  190. SysHeadingFont
  191. SysCaptionFont
  192. SysSmallCaptionFont
  193. SysIconFont
  194. SysTooltipFont
  195. )
  196. var (
  197. sysFontNameList = []string{
  198. "TKDefaultFont",
  199. "TKTextFont",
  200. "TKFixedFont",
  201. "TKMenuFont",
  202. "TKHeadingFont",
  203. "TKCaptionFont",
  204. "TKSmallCaptionFont",
  205. "TKIconFont",
  206. "TKTooltipFont",
  207. }
  208. sysFontList []*SysFont
  209. )
  210. func init() {
  211. for _, name := range sysFontNameList {
  212. sysFontList = append(sysFontList, &SysFont{BaseFont{name}})
  213. }
  214. }
  215. func LoadSysFont(typ SysFontType) *SysFont {
  216. if int(typ) >= 0 && int(typ) < len(sysFontList) {
  217. return sysFontList[typ]
  218. }
  219. return nil
  220. }
  221. func parserFontResult(r string, err error) Font {
  222. if err != nil || r == "" {
  223. return nil
  224. }
  225. for _, f := range sysFontList {
  226. if f.Id() == r {
  227. return f
  228. }
  229. }
  230. return &UserFont{BaseFont{r}}
  231. }