Plugin.js 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. const yo = require('yo-yo')
  2. const nanoraf = require('nanoraf')
  3. const { findDOMElement } = require('../core/Utils')
  4. const getFormData = require('get-form-data')
  5. /**
  6. * Boilerplate that all Plugins share - and should not be used
  7. * directly. It also shows which methods final plugins should implement/override,
  8. * this deciding on structure.
  9. *
  10. * @param {object} main Uppy core object
  11. * @param {object} object with plugin options
  12. * @return {array | string} files or success/fail message
  13. */
  14. module.exports = class Plugin {
  15. constructor (core, opts) {
  16. this.core = core
  17. this.opts = opts || {}
  18. // clear everything inside the target selector
  19. this.opts.replaceTargetContent === this.opts.replaceTargetContent || true
  20. this.update = this.update.bind(this)
  21. this.mount = this.mount.bind(this)
  22. this.install = this.install.bind(this)
  23. this.uninstall = this.uninstall.bind(this)
  24. }
  25. update (state) {
  26. if (typeof this.el === 'undefined') {
  27. return
  28. }
  29. if (this.updateUI) {
  30. this.updateUI(state)
  31. }
  32. }
  33. /**
  34. * Check if supplied `target` is a DOM element or an `object`.
  35. * If it’s an object — target is a plugin, and we search `plugins`
  36. * for a plugin with same name and return its target.
  37. *
  38. * @param {String|Object} target
  39. *
  40. */
  41. mount (target, plugin) {
  42. const callerPluginName = plugin.id
  43. const targetElement = findDOMElement(target)
  44. // Set up nanoraf.
  45. this.updateUI = nanoraf((state) => {
  46. this.el = yo.update(this.el, this.render(state))
  47. })
  48. if (targetElement) {
  49. this.core.log(`Installing ${callerPluginName} to a DOM element`)
  50. // attempt to extract meta from form element
  51. if (this.opts.getMetaFromForm && targetElement.nodeName === 'FORM') {
  52. const formMeta = getFormData(targetElement)
  53. this.core.setMeta(formMeta)
  54. }
  55. // clear everything inside the target container
  56. if (this.opts.replaceTargetContent) {
  57. targetElement.innerHTML = ''
  58. }
  59. this.el = plugin.render(this.core.state)
  60. targetElement.appendChild(this.el)
  61. return targetElement
  62. }
  63. const Target = target
  64. // Find the target plugin instance.
  65. let targetPlugin
  66. this.core.iteratePlugins((plugin) => {
  67. if (plugin instanceof Target) {
  68. targetPlugin = plugin
  69. return false
  70. }
  71. })
  72. if (targetPlugin) {
  73. const targetPluginName = targetPlugin.id
  74. this.core.log(`Installing ${callerPluginName} to ${targetPluginName}`)
  75. return targetPlugin.addTarget(plugin)
  76. }
  77. this.core.log(`Not installing ${callerPluginName}`)
  78. return null
  79. }
  80. unmount () {
  81. if (this.el && this.el.parentNode) {
  82. this.el.parentNode.removeChild(this.el)
  83. }
  84. }
  85. install () {
  86. return
  87. }
  88. uninstall () {
  89. this.unmount()
  90. }
  91. }