1. import React from 'react'
  2. import PropTypes from 'prop-types'
  3. import Component from '../utils/Component'
  4. import classnames from 'classnames'
  5. import Animate from '../animate/'
  6. import Logger from '../utils/logger'
  7.  
  8. import '../style'
  9. import 'phoenix-styles/less/modules/popup.less'
  10.  
  11. /**
  12. * 弹层组件<br/>
  13. * - 由于弹层的显示操作在组件以外, 所以需要在使用时自定义visible、onShow、closeCallback函数。
  14. * - 通过align设置碳层弹出的位置, 可选top/bottom。
  15. * - 可通过closeCallback配置点击弹层阴影部分来关闭弹层。
  16. *
  17. * 主要属性和接口:
  18. * - visible:弹层是否显示标识, 默认false不可见
  19. * - closeCallback:关闭弹层的功能函数
  20. * - align:弹层的位置, 默认top
  21. *
  22. * 示例:
  23. * ```code
  24. * <Popup align='top' visible={this.state.visible} closeCallback={::this.closeCallback}>
  25. * <ul className='ph-popup-list'>
  26. * <li className='ph-popup-item'>未上线单店</li>
  27. * <li className='ph-popup-item'>未上线连锁店</li>
  28. * </ul>
  29. * </Popup>
  30. * ```
  31. * ```code
  32. * onShow(){
  33. * this.setState({
  34. * visible: true
  35. * });
  36. * }
  37. * closeCallback(){
  38. * this.setState({
  39. * visible: false
  40. * });
  41. * }
  42. * ```
  43. *
  44. * @class Popup
  45. * @module 操作类组件
  46. * @extends Component
  47. * @constructor
  48. * @since 0.4.0
  49. * @demo popup|popup.js {展示}
  50. * @show true
  51. * */
  52.  
  53. export default class Popup extends Component{
  54.  
  55. static propTypes = {
  56. /**
  57. * 样式前缀
  58. * @property classPrefix
  59. * @type String
  60. * @default 'popup'
  61. * */
  62. classPrefix: PropTypes.string,
  63. /**
  64. * 标签tagName
  65. * @property componentTag
  66. * @type String
  67. * */
  68. componentTag: PropTypes.string,
  69. /**
  70. * 是否可见标识
  71. * @property visible
  72. * @type Boolean
  73. * */
  74. visible: PropTypes.bool,
  75. /**
  76. * 弹层的位置,默认top
  77. * @property align
  78. * @type String
  79. * */
  80. align: PropTypes.string,
  81. /**
  82. * 关闭的执行函数
  83. * @method closeCallback
  84. * @type Function
  85. * */
  86. closeCallback: PropTypes.func
  87. };
  88.  
  89. static defaultProps = {
  90. visible: false,
  91. align: 'top',
  92. classPrefix:'popup',
  93. componentTag:'div',
  94. classMapping : {
  95. 'top': 'top',
  96. 'bottom': 'bottom'
  97. }
  98. };
  99.  
  100. constructor(props, context) {
  101. super(props, context)
  102. new Logger('Popup')
  103. }
  104.  
  105. renderShadow(){
  106. let {visible, closeCallback} = this.props;
  107.  
  108. if(visible){
  109. return <div className={classnames(this.setPhPrefix('shadow'),'animated')} onClick={closeCallback}></div>;
  110. }else{
  111. return '';
  112. }
  113. }
  114.  
  115. renderContent(){
  116. let {visible,children,className} = this.props;
  117.  
  118. if(visible){
  119. return <div {...this.otherProps} className={classnames(this.setPhPrefix('content'), 'animated', className)}>{children}</div>;
  120. }else{
  121. return '';
  122. }
  123. }
  124.  
  125. renderPopup(){
  126. let {componentTag:Component, className} = this.props;
  127.  
  128. return (
  129. <Component {...this.otherProps} className={classnames(
  130. this.getProperty(true),
  131. className
  132. )}>
  133. <Animate>
  134. {this.renderShadow()}
  135. </Animate>
  136. <Animate className={this.setPhPrefix('main')} transitionName={`slide-${this.props.align}`}>
  137. {this.renderContent()}
  138. </Animate>
  139. </Component>
  140. )
  141. }
  142.  
  143. render(){
  144. return this.renderPopup()
  145. }
  146. }
  147.