InfoWindow.vue 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. <template>
  2. <div v-show="show">
  3. <slot></slot>
  4. </div>
  5. </template>
  6. <script>
  7. import commonMixin from '../base/mixins/common.js'
  8. import bindEvents from '../base/bindEvent.js'
  9. import {createPoint, createSize} from '../base/factory.js'
  10. export default {
  11. name: 'bm-info-window',
  12. mixins: [commonMixin('overlay')],
  13. props: {
  14. show: {
  15. type: Boolean
  16. },
  17. position: {
  18. type: Object
  19. },
  20. title: {
  21. type: String
  22. },
  23. width: {
  24. type: Number
  25. },
  26. height: {
  27. type: Number
  28. },
  29. maxWidth: {
  30. type: Number
  31. },
  32. offset: {
  33. type: Object
  34. },
  35. maximize: {
  36. type: Boolean
  37. },
  38. autoPan: {
  39. type: Boolean
  40. },
  41. closeOnClick: {
  42. type: Boolean,
  43. default: true
  44. },
  45. message: {
  46. type: String
  47. }
  48. },
  49. watch: {
  50. show (val) {
  51. val ? this.openInfoWindow() : this.closeInfoWindow()
  52. },
  53. 'position.lng' (val, oldVal) {
  54. this.reload()
  55. },
  56. 'position.lat' (val, oldVal) {
  57. this.reload()
  58. },
  59. 'offset.width' (val, oldVal) {
  60. this.reload()
  61. },
  62. 'offset.height' (val) {
  63. this.reload()
  64. },
  65. maxWidth () {
  66. this.reload()
  67. },
  68. width (val) {
  69. this.originInstance.setWidth(val)
  70. },
  71. height (val) {
  72. this.originInstance.setHeight(val)
  73. },
  74. title (val) {
  75. this.originInstance.setTitle(val)
  76. },
  77. maximize (val) {
  78. val ? this.originInstance.enableMaximize() : this.originInstance.disableMaximize()
  79. },
  80. autoPan (val) {
  81. val ? this.originInstance.enableAutoPan() : this.originInstance.disableAutoPan()
  82. },
  83. closeOnClick (val) {
  84. val ? this.originInstance.enableCloseOnClick() : this.originInstance.disableCloseOnClick()
  85. }
  86. },
  87. methods: {
  88. redraw () {
  89. this.originInstance.redraw()
  90. },
  91. load () {
  92. const {BMap, map, show, title, width, height, maxWidth, offset, autoPan, closeOnClick, message, maximize, bindObserver, $parent} = this
  93. const $content = this.$el
  94. const overlay = new BMap.InfoWindow($content, {
  95. width,
  96. height,
  97. title,
  98. maxWidth,
  99. offset: createSize(BMap, offset),
  100. enableAutoPan: autoPan,
  101. enableCloseOnClick: closeOnClick,
  102. enableMessage: typeof message === 'undefined',
  103. message
  104. })
  105. maximize ? overlay.enableMaximize() : overlay.disableMaximize()
  106. bindEvents.call(this, overlay)
  107. this.originInstance = overlay
  108. overlay.redraw()
  109. ;[].forEach.call($content.querySelectorAll('img'), $img => {
  110. $img.onload = () => overlay.redraw()
  111. })
  112. bindObserver()
  113. this.$container = $parent.originInstance && $parent.originInstance.openInfoWindow ? $parent.originInstance : map
  114. show && this.openInfoWindow()
  115. },
  116. bindObserver () {
  117. const MutationObserver = global.MutationObserver
  118. if (!MutationObserver) {
  119. return
  120. }
  121. const {$el, originInstance} = this
  122. this.observer = new MutationObserver(mutations => originInstance.redraw())
  123. this.observer.observe($el, {attributes: true, childList: true, characterData: true, subtree: true})
  124. },
  125. openInfoWindow () {
  126. const {BMap, $container, position, originInstance} = this
  127. $container.openInfoWindow(originInstance, createPoint(BMap, position))
  128. },
  129. closeInfoWindow () {
  130. this.$container.closeInfoWindow(this.originInstance)
  131. }
  132. }
  133. }
  134. </script>