Dialog.js 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. import { use } from '../utils';
  2. import { PopupMixin } from '../mixins/popup';
  3. import Button from '../button';
  4. const [sfc, bem, t] = use('dialog');
  5. export default sfc({
  6. mixins: [PopupMixin],
  7. props: {
  8. title: String,
  9. message: String,
  10. className: null,
  11. callback: Function,
  12. beforeClose: Function,
  13. messageAlign: String,
  14. cancelButtonText: String,
  15. cancelButtonColor: String,
  16. confirmButtonText: String,
  17. confirmButtonColor: String,
  18. showCancelButton: Boolean,
  19. showConfirmButton: {
  20. type: Boolean,
  21. default: true
  22. },
  23. overlay: {
  24. type: Boolean,
  25. default: true
  26. },
  27. closeOnClickOverlay: {
  28. type: Boolean,
  29. default: false
  30. }
  31. },
  32. data() {
  33. return {
  34. loading: {
  35. confirm: false,
  36. cancel: false
  37. }
  38. };
  39. },
  40. methods: {
  41. onClickOverlay() {
  42. this.handleAction('overlay');
  43. },
  44. handleAction(action) {
  45. this.$emit(action);
  46. if (this.beforeClose) {
  47. this.loading[action] = true;
  48. this.beforeClose(action, state => {
  49. if (state !== false) {
  50. this.onClose(action);
  51. }
  52. this.loading[action] = false;
  53. });
  54. } else {
  55. this.onClose(action);
  56. }
  57. },
  58. onClose(action) {
  59. this.close();
  60. if (this.callback) {
  61. this.callback(action);
  62. }
  63. }
  64. },
  65. render(h) {
  66. if (!this.shouldRender) {
  67. return;
  68. }
  69. const { title, message, messageAlign } = this;
  70. const children = this.slots();
  71. const Title = title && (
  72. <div class={bem('header', { isolated: !message && !children })}>{title}</div>
  73. );
  74. const Content = (children || message) && (
  75. <div class={bem('content')}>
  76. {children || (
  77. <div
  78. domPropsInnerHTML={message}
  79. class={bem('message', { 'has-title': title, [messageAlign]: messageAlign })}
  80. />
  81. )}
  82. </div>
  83. );
  84. const hasButtons = this.showCancelButton && this.showConfirmButton;
  85. const ButtonGroup = (
  86. <div class={['van-hairline--top', bem('footer', { buttons: hasButtons })]}>
  87. {this.showCancelButton && (
  88. <Button
  89. size="large"
  90. class={bem('cancel')}
  91. loading={this.loading.cancel}
  92. text={this.cancelButtonText || t('cancel')}
  93. style={{ color: this.cancelButtonColor }}
  94. onClick={() => {
  95. this.handleAction('cancel');
  96. }}
  97. />
  98. )}
  99. {this.showConfirmButton && (
  100. <Button
  101. size="large"
  102. class={[bem('confirm'), { 'van-hairline--left': hasButtons }]}
  103. loading={this.loading.confirm}
  104. text={this.confirmButtonText || t('confirm')}
  105. style={{ color: this.confirmButtonColor }}
  106. onClick={() => {
  107. this.handleAction('confirm');
  108. }}
  109. />
  110. )}
  111. </div>
  112. );
  113. return (
  114. <transition name="van-dialog-bounce">
  115. <div vShow={this.value} class={[bem(), this.className]}>
  116. {Title}
  117. {Content}
  118. {ButtonGroup}
  119. </div>
  120. </transition>
  121. );
  122. }
  123. });