image.go 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176
  1. // Copyright 2018 visualfc. All rights reserved.
  2. package tk
  3. import (
  4. "errors"
  5. "fmt"
  6. "image"
  7. "image/color"
  8. _ "image/png"
  9. "os"
  10. "path/filepath"
  11. "strings"
  12. "github.com/visualfc/atk/tk/interp"
  13. )
  14. type Image struct {
  15. id string
  16. photo *interp.Photo
  17. tk85alpha color.Color
  18. }
  19. func (i *Image) Id() string {
  20. return i.id
  21. }
  22. type ImageAttr struct {
  23. key string
  24. value interface{}
  25. }
  26. func ImageAttrGamma(gamma float64) *ImageAttr {
  27. return &ImageAttr{"gamma", gamma}
  28. }
  29. func ImageAttrTk85AlphaColor(color color.Color) *ImageAttr {
  30. return &ImageAttr{"tk85alphacolor", color}
  31. }
  32. func LoadImage(file string, attributes ...*ImageAttr) (*Image, error) {
  33. if file == "" {
  34. return nil, ErrInvalid
  35. }
  36. var fileImage image.Image
  37. if filepath.Ext(file) == ".gif" {
  38. attributes = append(attributes, &ImageAttr{"file", file})
  39. } else {
  40. file, err := os.Open(file)
  41. if err != nil {
  42. return nil, err
  43. }
  44. im, _, err := image.Decode(file)
  45. file.Close()
  46. if err != nil {
  47. return nil, err
  48. }
  49. fileImage = im
  50. }
  51. im := NewImage(attributes...)
  52. if im == nil {
  53. return nil, errors.New("NewImage failed")
  54. }
  55. if fileImage != nil {
  56. im.SetImage(fileImage)
  57. }
  58. return im, nil
  59. }
  60. func NewImage(attributes ...*ImageAttr) *Image {
  61. var attrList []string
  62. var tk85alphacolor color.Color
  63. for _, attr := range attributes {
  64. if attr == nil {
  65. continue
  66. }
  67. if attr.key == "tk85alphacolor" {
  68. if clr, ok := attr.value.(color.Color); ok {
  69. tk85alphacolor = clr
  70. }
  71. continue
  72. }
  73. if s, ok := attr.value.(string); ok {
  74. pname := "atk_tmp_" + attr.key
  75. setObjText(pname, s)
  76. attrList = append(attrList, fmt.Sprintf("-%v $%v", attr.key, pname))
  77. continue
  78. }
  79. attrList = append(attrList, fmt.Sprintf("-%v {%v}", attr.key, attr.value))
  80. }
  81. iid := makeNamedId("atk_image")
  82. script := fmt.Sprintf("image create photo %v", iid)
  83. if len(attrList) > 0 {
  84. script += " " + strings.Join(attrList, " ")
  85. }
  86. err := eval(script)
  87. if err != nil {
  88. return nil
  89. }
  90. photo := interp.FindPhoto(mainInterp, iid)
  91. if photo == nil {
  92. return nil
  93. }
  94. return &Image{iid, photo, tk85alphacolor}
  95. }
  96. func (i *Image) IsValid() bool {
  97. return i.id != "" && i.photo != nil
  98. }
  99. func (i *Image) SetImage(img image.Image) *Image {
  100. err := i.photo.PutImage(img, i.tk85alpha)
  101. if err != nil {
  102. dumpError(err)
  103. }
  104. return i
  105. }
  106. func (i *Image) SetZoomedImage(img image.Image, zoomX, zoomY, subsampleX, subsampleY int) *Image {
  107. err := i.photo.PutZoomedImage(img, zoomX, zoomY, subsampleX, subsampleY, i.tk85alpha)
  108. if err != nil {
  109. dumpError(err)
  110. }
  111. return i
  112. }
  113. func (i *Image) ToImage() image.Image {
  114. return i.photo.ToImage()
  115. }
  116. func (i *Image) Blank() *Image {
  117. i.photo.Blank()
  118. return i
  119. }
  120. func (i *Image) SizeN() (width int, height int) {
  121. return i.photo.Size()
  122. }
  123. func (i *Image) Size() Size {
  124. w, h := i.SizeN()
  125. return Size{w, h}
  126. }
  127. func (i *Image) SetSizeN(width int, height int) *Image {
  128. err := i.photo.SetSize(width, height)
  129. if err != nil {
  130. dumpError(err)
  131. }
  132. return i
  133. }
  134. func (i *Image) SetSize(sz Size) *Image {
  135. return i.SetSizeN(sz.Width, sz.Height)
  136. }
  137. func (i *Image) Gamma() float64 {
  138. v, _ := evalAsFloat64(fmt.Sprintf("%v cget -gamma", i.id))
  139. return v
  140. }
  141. func (i *Image) SetGamma(v float64) *Image {
  142. eval(fmt.Sprintf("%v configure -gamma {%v}", i.id, v))
  143. return i
  144. }
  145. func parserImageResult(id string, err error) *Image {
  146. if err != nil {
  147. return nil
  148. }
  149. photo := interp.FindPhoto(mainInterp, id)
  150. if photo == nil {
  151. return nil
  152. }
  153. return &Image{id, photo, nil}
  154. }