events.spec.ts 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. import { patch } from 'web/runtime/patch'
  2. import VNode from 'core/vdom/vnode'
  3. describe('vdom events module', () => {
  4. it('should attach event handler to element', () => {
  5. const click = vi.fn()
  6. const vnode = new VNode('a', { on: { click } })
  7. const elm = patch(null, vnode)
  8. document.body.appendChild(elm)
  9. global.triggerEvent(elm, 'click')
  10. expect(click.mock.calls.length).toBe(1)
  11. })
  12. it('should not duplicate the same listener', () => {
  13. const click = vi.fn()
  14. const vnode1 = new VNode('a', { on: { click } })
  15. const vnode2 = new VNode('a', { on: { click } })
  16. const elm = patch(null, vnode1)
  17. patch(vnode1, vnode2)
  18. document.body.appendChild(elm)
  19. global.triggerEvent(elm, 'click')
  20. expect(click.mock.calls.length).toBe(1)
  21. })
  22. it('should update different listener', () => {
  23. const click = vi.fn()
  24. const click2 = vi.fn()
  25. const vnode1 = new VNode('a', { on: { click } })
  26. const vnode2 = new VNode('a', { on: { click: click2 } })
  27. const elm = patch(null, vnode1)
  28. document.body.appendChild(elm)
  29. global.triggerEvent(elm, 'click')
  30. expect(click.mock.calls.length).toBe(1)
  31. expect(click2.mock.calls.length).toBe(0)
  32. patch(vnode1, vnode2)
  33. global.triggerEvent(elm, 'click')
  34. expect(click.mock.calls.length).toBe(1)
  35. expect(click2.mock.calls.length).toBe(1)
  36. })
  37. it('should attach Array of multiple handlers', () => {
  38. const click = vi.fn()
  39. const vnode = new VNode('a', { on: { click: [click, click] } })
  40. const elm = patch(null, vnode)
  41. document.body.appendChild(elm)
  42. global.triggerEvent(elm, 'click')
  43. expect(click.mock.calls.length).toBe(2)
  44. })
  45. it('should update Array of multiple handlers', () => {
  46. const click = vi.fn()
  47. const click2 = vi.fn()
  48. const vnode1 = new VNode('a', { on: { click: [click, click2] } })
  49. const vnode2 = new VNode('a', { on: { click: [click] } })
  50. const elm = patch(null, vnode1)
  51. document.body.appendChild(elm)
  52. global.triggerEvent(elm, 'click')
  53. expect(click.mock.calls.length).toBe(1)
  54. expect(click2.mock.calls.length).toBe(1)
  55. patch(vnode1, vnode2)
  56. global.triggerEvent(elm, 'click')
  57. expect(click.mock.calls.length).toBe(2)
  58. expect(click2.mock.calls.length).toBe(1)
  59. })
  60. it('should remove handlers that are no longer present', () => {
  61. const click = vi.fn()
  62. const vnode1 = new VNode('a', { on: { click } })
  63. const vnode2 = new VNode('a', {})
  64. const elm = patch(null, vnode1)
  65. document.body.appendChild(elm)
  66. global.triggerEvent(elm, 'click')
  67. expect(click.mock.calls.length).toBe(1)
  68. patch(vnode1, vnode2)
  69. global.triggerEvent(elm, 'click')
  70. expect(click.mock.calls.length).toBe(1)
  71. })
  72. it('should remove Array handlers that are no longer present', () => {
  73. const click = vi.fn()
  74. const vnode1 = new VNode('a', { on: { click: [click, click] } })
  75. const vnode2 = new VNode('a', {})
  76. const elm = patch(null, vnode1)
  77. document.body.appendChild(elm)
  78. global.triggerEvent(elm, 'click')
  79. expect(click.mock.calls.length).toBe(2)
  80. patch(vnode1, vnode2)
  81. global.triggerEvent(elm, 'click')
  82. expect(click.mock.calls.length).toBe(2)
  83. })
  84. // #4650
  85. it('should handle single -> array or array -> single handler changes', () => {
  86. const click = vi.fn()
  87. const click2 = vi.fn()
  88. const click3 = vi.fn()
  89. const vnode0 = new VNode('a', { on: { click: click } })
  90. const vnode1 = new VNode('a', { on: { click: [click, click2] } })
  91. const vnode2 = new VNode('a', { on: { click: click } })
  92. const vnode3 = new VNode('a', { on: { click: [click2, click3] } })
  93. const elm = patch(null, vnode0)
  94. document.body.appendChild(elm)
  95. global.triggerEvent(elm, 'click')
  96. expect(click.mock.calls.length).toBe(1)
  97. expect(click2.mock.calls.length).toBe(0)
  98. patch(vnode0, vnode1)
  99. global.triggerEvent(elm, 'click')
  100. expect(click.mock.calls.length).toBe(2)
  101. expect(click2.mock.calls.length).toBe(1)
  102. patch(vnode1, vnode2)
  103. global.triggerEvent(elm, 'click')
  104. expect(click.mock.calls.length).toBe(3)
  105. expect(click2.mock.calls.length).toBe(1)
  106. patch(vnode2, vnode3)
  107. global.triggerEvent(elm, 'click')
  108. expect(click.mock.calls.length).toBe(3)
  109. expect(click2.mock.calls.length).toBe(2)
  110. expect(click3.mock.calls.length).toBe(1)
  111. })
  112. })