import React from 'react' import cls from 'classnames' import newEventStores from 'stores/newEvent' import { getEventBlockByBid } from 'stores/funcs/newEvent' import { shallowEqualImmutable } from 'utils/utils' import { EVENT_BLOCK_TYPE, BLOCK_OP_TYPE } from 'const/const' export default class BlockChildren extends React.Component { constructor(props) { super(props) this.state = { subBlockIds: this.getBlockChildren(props.parentBid) } // 加载相关组件 this.blockAction = require('../BlockAction').default this.blockCon = require('../BlockCon').default this.blockLoop = require('../BlockLoop').default this.blockComment = require('../BlockComment').default this.blockGroup = require('../BlockGroup').default // this.blockError = require('./BlockError').default this.onEventChange = this.onEventChange.bind(this) this.getBlockChildren = this.getBlockChildren.bind(this) this.getChild = this.getChild.bind(this) this.isBlockGroupChildren = this.isBlockGroupChildren.bind(this) this.getBlockGroupBg = this.getBlockGroupBg.bind(this) } shouldComponentUpdate(nextProps, nextState) { return ( !shallowEqualImmutable(this.props, nextProps) || !shallowEqualImmutable(this.state, nextState) ) } componentDidUpdate(preProps) { // parentBid改变时需要更新 if (preProps.parentBid !== this.props.parentBid) { let obj = {} let subBlockIds = this.getBlockChildren() if (!shallowEqualImmutable(this.state.subBlockIds, subBlockIds)) { obj.subBlockIds = subBlockIds } if (Object.keys(obj).length > 0) { this.setState(obj) } } } componentDidMount() { this.unsubscribe = newEventStores.listen(this.onEventChange) } componentWillUnmount() { this.unsubscribe() } onEventChange(status) { let obj = {} if (status && status.types) { if ( (status.types.includes('changeBlockChildren') && status.data && status.data.parentBid === this.props.parentBid) || (status.types.includes('reloadBlock') && this.props.parentBid === status.data.affectBlockId) ) { obj.subBlockIds = this.getBlockChildren() } } if (Object.keys(obj).length > 0) { this.setState(obj) } } getBlockChildren() { let childBids = [] let nodeId = this.props.eventNodeId let parentBlock = getEventBlockByBid(this.props.parentBid, nodeId) if (parentBlock) { if (parentBlock.eventId) { if ( parentBlock.ast && parentBlock.ast.args && parentBlock.ast.args.length > 0 ) { parentBlock.ast.args.forEach(child => { if (child.ln) { childBids.push(child.ln) } }) } } else { switch (parentBlock.op) { case BLOCK_OP_TYPE.IF: case BLOCK_OP_TYPE.ELSE: case BLOCK_OP_TYPE.FOR: case BLOCK_OP_TYPE.WHILE: if ( parentBlock.args && parentBlock.args.length > 0 && parentBlock.args[1] ) { if ( parentBlock.args[1].op === 'block' && parentBlock.args[1].args && parentBlock.args[1].args.length > 0 ) { parentBlock.args[1].args.forEach(child => { if (child.ln) { childBids.push(child.ln) } }) } } break case BLOCK_OP_TYPE.BLOCK: if (parentBlock.args && parentBlock.args.length > 0) { parentBlock.args.forEach(child => { if (child.ln) { childBids.push(child.ln) } }) } break } } } return childBids } getChild(bid, index) { let nodeId = this.props.eventNodeId let block = getEventBlockByBid(bid, nodeId) if (block) { switch (block.op) { case BLOCK_OP_TYPE.SET: case BLOCK_OP_TYPE.CALL: case BLOCK_OP_TYPE.LET: case undefined: let BlockAction = this.blockAction return ( ) case BLOCK_OP_TYPE.IF: case BLOCK_OP_TYPE.ELSE: let BlockCon = this.blockCon return ( ) case BLOCK_OP_TYPE.FOR: case BLOCK_OP_TYPE.WHILE: let BlockLoop = this.blockLoop return ( ) case BLOCK_OP_TYPE.NOP: let BlockComment = this.blockComment return ( ) case BLOCK_OP_TYPE.BLOCK: let BlockGroup = this.blockGroup //Group的嵌套处理 return ( ) } } else { // let BlockError = this.blockError // return ( // // ) } return null } isBlockGroupChildren = () => { let nodeId = this.props.eventNodeId let parentBlock = getEventBlockByBid(this.props.parentBid, nodeId) return parentBlock?.op === BLOCK_OP_TYPE.BLOCK } getBlockGroupBg = () => { const leftGap = 18 + (this.props.nestGroupLayer - 1) * 2 const gapping = `${leftGap + (this.props.groupLayer - 1) * 2}px` const left = `${leftGap}px` const style = { width: `calc(100% - ${gapping})`, left: left } return this.isBlockGroupChildren() ? (
) : null } render() { let subBlockIds = this.state.subBlockIds if (this.props.visibleBlockIds) { subBlockIds = subBlockIds.filter(id => { return this.props.visibleBlockIds.indexOf(id) >= 0 }) } return subBlockIds && subBlockIds.length > 0 ? (
{this.getBlockGroupBg()} {subBlockIds.map((subBlockId, index) => { return this.getChild(subBlockId, index) })}
) : null } }