_stateFromProps = props => {
   let selectedIndex = 0;
   const items = React.Children.map(props.children, (child, index) => {
     if (child.props.value === props.selectedValue) {
       selectedIndex = index;
     }
     const childProps = {
       value: child.props.value,
       label: child.props.label,
     };
     if (child.props.color) {
       /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was
        * found when making Flow check .android.js files. */
       childProps.color = processColor(child.props.color);
     }
     return childProps;
   });
   return {selectedIndex, items};
 };
 _childrenWithOverridenStyle = (): Array => {
   // Override styles so that each page will fill the parent. Native component
   // will handle positioning of elements, so it's not important to offset
   // them correctly.
   /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was found
    * when making Flow check .android.js files. */
   return React.Children.map(this.props.children, function(child) {
     if (!child) {
       return null;
     }
     const newProps = {
       ...child.props,
       style: [
         child.props.style,
         {
           position: 'absolute',
           left: 0,
           top: 0,
           right: 0,
           bottom: 0,
           width: undefined,
           height: undefined,
         },
       ],
       collapsable: false,
     };
     if (
       child.type &&
       child.type.displayName &&
       child.type.displayName !== 'RCTView' &&
       child.type.displayName !== 'View'
     ) {
       console.warn(
         'Each ViewPager child must be a <View>. Was ' +
           child.type.displayName,
       );
     }
     return React.createElement(child.type, newProps);
   });
 };
 render: function render() {
   var child = React.Children.only(this.props.children);
   var children = child.props.children;
   warning(!child.type || child.type.displayName !== 'Text', 'TouchableWithoutFeedback does not work well with Text children. Wrap children in a View instead. See ' + (child._owner && child._owner.getName && child._owner.getName() || '<unknown>'));
   if (Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'View') {
     children = React.Children.toArray(children);
     children.push(Touchable.renderDebugView({ color: 'red', hitSlop: this.props.hitSlop }));
   }
   var style = Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'Text' ? [child.props.style, { color: 'red' }] : child.props.style;
   return React.cloneElement(child, {
     accessible: this.props.accessible !== false,
     accessibilityLabel: this.props.accessibilityLabel,
     accessibilityComponentType: this.props.accessibilityComponentType,
     accessibilityTraits: this.props.accessibilityTraits,
     testID: this.props.testID,
     onLayout: this.props.onLayout,
     hitSlop: this.props.hitSlop,
     onStartShouldSetResponder: this.touchableHandleStartShouldSetResponder,
     onResponderTerminationRequest: this.touchableHandleResponderTerminationRequest,
     onResponderGrant: this.touchableHandleResponderGrant,
     onResponderMove: this.touchableHandleResponderMove,
     onResponderRelease: this.touchableHandleResponderRelease,
     onResponderTerminate: this.touchableHandleResponderTerminate,
     style: style,
     children: children
   });
 }
示例#4
0
  renderContent(): ?ReactElement {
    if (React.Children.count(this.props.children) === 0) {
      return null;
    }
    const content = React.Children.only(this.props.children);

    const {minHeight, maxHeight, offset} = this.props;
    const length = maxHeight - minHeight;
    const opacity = offset.interpolate({
      inputRange: [0, length - 40],
      outputRange: [1, 0],
      extrapolate: 'clamp',
    });
    const translateY = offset.interpolate({
      inputRange: [0, length],
      outputRange: [-32, -(length / 2) - 32],
      extrapolate: 'clamp',
    });
    const transforms = { opacity, transform: [{translateY}] };
    return (
      <Animated.View style={[styles.contentContainer, transforms]}>
        {content}
      </Animated.View>
    );
  }
  _onChange = (event: PickerAndroidChangeEvent) => {
    if (this.props.onValueChange) {
      const position = event.nativeEvent.position;
      if (position >= 0) {
        const children = React.Children.toArray(this.props.children);
        const value = children[position].props.value;
        /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was
         * found when making Flow check .android.js files. */
        this.props.onValueChange(value, position);
      } else {
        this.props.onValueChange(null, position);
      }
    }

    // The picker is a controlled component. This means we expect the
    // on*Change handlers to be in charge of updating our
    // `selectedValue` prop. That way they can also
    // disallow/undo/mutate the selection of certain values. In other
    // words, the embedder of this component should be the source of
    // truth, not the native component.
    if (
      this.refs[REF_PICKER] &&
      this.state.selectedIndex !== event.nativeEvent.position
    ) {
      this.refs[REF_PICKER].setNativeProps({
        selected: this.state.selectedIndex,
      });
    }
  };
示例#6
0
  render() {
    const {leftItem, title, rightItem, foreground} = this.props;
    const titleColor = foreground === 'dark' ? globalStyles.darkText : 'white';
    const itemsColor = foreground === 'dark' ? globalStyles.lightText : 'white';

    const content = React.Children.count(this.props.children) === 0
      ? <Text style={[styles.titleText, {color: titleColor}]}>
          {title}
        </Text>
      : this.props.children;
    return (
      <View style={[styles.header, this.props.style]} >
        <View style={styles.leftItem}>
          <ItemWrapperIOS color={itemsColor} item={leftItem} />
        </View>
        <View
          accessible={true}
          accessibilityLabel={title}
          accessibilityTraits="header"
          style={styles.centerItem}>
          {content}
        </View>
        <View style={styles.rightItem}>
          <ItemWrapperIOS color={itemsColor} item={rightItem} />
        </View>
      </View>
    );
  }
示例#7
0
  _renderAndroid: function() {
    const props = Object.assign({}, this.props);
    props.style = [this.props.style];
    props.autoCapitalize = UIManager.getViewManagerConfig(
      'AndroidTextInput',
    ).Constants.AutoCapitalizationType[props.autoCapitalize || 'sentences'];
    /* $FlowFixMe(>=0.53.0 site=react_native_fb,react_native_oss) This comment
     * suppresses an error when upgrading Flow's support for React. To see the
     * error delete this comment and run Flow. */
    let children = this.props.children;
    let childCount = 0;
    React.Children.forEach(children, () => ++childCount);
    invariant(
      !(this.props.value && childCount),
      'Cannot specify both value and children.',
    );
    if (childCount > 1) {
      children = <Text>{children}</Text>;
    }

    if (props.selection && props.selection.end == null) {
      props.selection = {
        start: props.selection.start,
        end: props.selection.start,
      };
    }

    const textContainer = (
      <AndroidTextInput
        ref={this._setNativeRef}
        {...props}
        mostRecentEventCount={0}
        onFocus={this._onFocus}
        onBlur={this._onBlur}
        onChange={this._onChange}
        onSelectionChange={this._onSelectionChange}
        onTextInput={this._onTextInput}
        text={this._getText()}
        children={children}
        disableFullscreenUI={this.props.disableFullscreenUI}
        textBreakStrategy={this.props.textBreakStrategy}
        onScroll={this._onScroll}
      />
    );

    return (
      <TouchableWithoutFeedback
        onLayout={props.onLayout}
        onPress={this._onPress}
        accessible={this.props.accessible}
        accessibilityLabel={this.props.accessibilityLabel}
        accessibilityRole={this.props.accessibilityRole}
        accessibilityStates={this.props.accessibilityStates}
        nativeID={this.props.nativeID}
        testID={this.props.testID}>
        {textContainer}
      </TouchableWithoutFeedback>
    );
  },
  _onLayout = event => {
    this.setState({
      measured: true,
      layoutY: event.nativeEvent.layout.y,
      layoutHeight: event.nativeEvent.layout.height,
    });

    this.props.onLayout(event);
    const child = React.Children.only(this.props.children);
    if (child.props.onLayout) {
      child.props.onLayout(event);
    }
  };
 render: function() {
   const child = React.Children.only(this.props.children);
   return (
     <View
       accessible={this.props.accessible !== false}
       accessibilityLabel={this.props.accessibilityLabel}
       accessibilityHint={this.props.accessibilityHint}
       accessibilityRole={this.props.accessibilityRole}
       accessibilityStates={this.props.accessibilityStates}
       style={StyleSheet.compose(
         this.props.style,
         this.state.extraUnderlayStyle,
       )}
       onLayout={this.props.onLayout}
       hitSlop={this.props.hitSlop}
       isTVSelectable={true}
       tvParallaxProperties={this.props.tvParallaxProperties}
       hasTVPreferredFocus={this.props.hasTVPreferredFocus}
       nextFocusDown={this.props.nextFocusDown}
       nextFocusForward={this.props.nextFocusForward}
       nextFocusLeft={this.props.nextFocusLeft}
       nextFocusRight={this.props.nextFocusRight}
       nextFocusUp={this.props.nextFocusUp}
       clickable={
         this.props.clickable !== false && this.props.onPress !== undefined
       }
       onClick={this.touchableHandlePress}
       onStartShouldSetResponder={this.touchableHandleStartShouldSetResponder}
       onResponderTerminationRequest={
         this.touchableHandleResponderTerminationRequest
       }
       onResponderGrant={this.touchableHandleResponderGrant}
       onResponderMove={this.touchableHandleResponderMove}
       onResponderRelease={this.touchableHandleResponderRelease}
       onResponderTerminate={this.touchableHandleResponderTerminate}
       nativeID={this.props.nativeID}
       testID={this.props.testID}>
       {React.cloneElement(child, {
         style: StyleSheet.compose(
           child.props.style,
           this.state.extraChildStyle,
         ),
       })}
       {Touchable.renderDebugView({
         color: 'green',
         hitSlop: this.props.hitSlop,
       })}
     </View>
   );
 },
 render: function(): React.Element<any> {
   // Note(avik): remove dynamic typecast once Flow has been upgraded
   // $FlowFixMe(>=0.41.0)
   const child = React.Children.only(this.props.children);
   let children = child.props.children;
   warning(
     !child.type || child.type.displayName !== 'Text',
     'TouchableWithoutFeedback does not work well with Text children. Wrap children in a View instead. See ' +
       ((child._owner && child._owner.getName && child._owner.getName()) || '<unknown>')
   );
   if (Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'View') {
     children = React.Children.toArray(children);
     children.push(Touchable.renderDebugView({color: 'red', hitSlop: this.props.hitSlop}));
   }
   const style = (Touchable.TOUCH_TARGET_DEBUG && child.type && child.type.displayName === 'Text') ?
     [child.props.style, {color: 'red'}] :
     child.props.style;
   return (React: any).cloneElement(child, {
     accessible: this.props.accessible !== false,
     accessibilityLabel: this.props.accessibilityLabel,
     accessibilityComponentType: this.props.accessibilityComponentType,
     accessibilityTraits: this.props.accessibilityTraits,
     nativeID: this.props.nativeID,
     testID: this.props.testID,
     onLayout: this.props.onLayout,
     hitSlop: this.props.hitSlop,
     onStartShouldSetResponder: this.touchableHandleStartShouldSetResponder,
     onResponderTerminationRequest: this.touchableHandleResponderTerminationRequest,
     onResponderGrant: this.touchableHandleResponderGrant,
     onResponderMove: this.touchableHandleResponderMove,
     onResponderRelease: this.touchableHandleResponderRelease,
     onResponderTerminate: this.touchableHandleResponderTerminate,
     style,
     children,
   });
 }
 _onChange = (event: Event) => {
   if (this.props.onValueChange) {
     const position = event.nativeEvent.position;
     if (position >= 0) {
       /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was
        * found when making Flow check .android.js files. */
       const children = React.Children.toArray(this.props.children);
       const value = children[position].props.value;
       /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was
        * found when making Flow check .android.js files. */
       this.props.onValueChange(value, position);
     } else {
       this.props.onValueChange(null, position);
     }
   }
   /* $FlowFixMe(>=0.78.0 site=react_native_android_fb) This issue was found
    * when making Flow check .android.js files. */
   this._lastNativePosition = event.nativeEvent.position;
   this.forceUpdate();
 };
示例#12
0
  _onStickyHeaderLayout: function(index, event, key) {
    if (!this.props.stickyHeaderIndices) {
      return;
    }
    const childArray = React.Children.toArray(this.props.children);
    if (key !== this._getKeyForIndex(index, childArray)) {
      // ignore stale layout update
      return;
    }

    const layoutY = event.nativeEvent.layout.y;
    this._headerLayoutYs.set(key, layoutY);

    const indexOfIndex = this.props.stickyHeaderIndices.indexOf(index);
    const previousHeaderIndex = this.props.stickyHeaderIndices[indexOfIndex - 1];
    if (previousHeaderIndex != null) {
      const previousHeader = this._stickyHeaderRefs.get(
        this._getKeyForIndex(previousHeaderIndex, childArray)
      );
      previousHeader && previousHeader.setNextHeaderY(layoutY);
    }
  },
 }, _this._childrenWithOverridenStyle = function () {
   return React.Children.map(_this.props.children, function (child) {
     if (!child) {
       return null;
     }
     var newProps = babelHelpers.extends({}, child.props, {
       style: [child.props.style, {
         position: 'absolute',
         left: 0,
         top: 0,
         right: 0,
         bottom: 0,
         width: undefined,
         height: undefined
       }],
       collapsable: false
     });
     if (child.type && child.type.displayName && child.type.displayName !== 'RCTView' && child.type.displayName !== 'View') {
       console.warn('Each ViewPager child must be a <View>. Was ' + child.type.displayName);
     }
     return React.createElement(child.type, newProps);
   });
 }, _this._onPageScroll = function (e) {
示例#14
0
export const findChild = (children, iteratee) => _.find(Children.toArray(children), iteratee)
示例#15
0
export const Body = ({ hidePrint, children }) =>
  <BodyContainer hidePrint={hidePrint}>
    {React.Children.map(children, c => emojify(`${c}`, { output: 'unicode' }))}
  </BodyContainer>
示例#16
0
  render() {
    const {
      ariaLabel,
      ButtonProps,
      children: childrenProp,
      classes,
      className: classNameProp,
      hidden,
      icon: iconProp,
      onClick,
      onClose,
      onKeyDown,
      open,
      direction,
      openIcon,
      TransitionComponent,
      transitionDuration,
      TransitionProps,
      ...other
    } = this.props;

    // Filter the label for valid id characters.
    const id = ariaLabel.replace(/^[^a-z]+|[^\w:.-]+/gi, '');

    let totalValidChildren = 0;
    React.Children.forEach(childrenProp, child => {
      if (React.isValidElement(child)) totalValidChildren += 1;
    });

    let validChildCount = 0;
    const children = React.Children.map(childrenProp, child => {
      if (!React.isValidElement(child)) {
        return null;
      }

      warning(
        child.type !== React.Fragment,
        [
          "Material-UI: the SpeedDial component doesn't accept a Fragment as a child.",
          'Consider providing an array instead.',
        ].join('\n'),
      );

      const delay = 30 * (open ? validChildCount : totalValidChildren - validChildCount);
      validChildCount += 1;
      return React.cloneElement(child, {
        delay,
        open,
        onKeyDown: this.handleKeyDown,
        id: `${id}-item-${validChildCount}`,
      });
    });

    const icon = () => {
      if (!React.isValidElement(iconProp)) {
        return iconProp;
      }
      if (isMuiElement(iconProp, ['SpeedDialIcon'])) {
        return React.cloneElement(iconProp, { open });
      }
      return icon;
    };

    const actionsPlacementClass = {
      [classes.directionUp]: direction === 'up',
      [classes.directionDown]: direction === 'down',
      [classes.directionLeft]: direction === 'left',
      [classes.directionRight]: direction === 'right',
    };

    let clickProp = { onClick };

    if (typeof document !== 'undefined' && 'ontouchstart' in document.documentElement) {
      clickProp = { onTouchEnd: onClick };
    }

    return (
      <div className={classNames(classes.root, actionsPlacementClass, classNameProp)} {...other}>
        <TransitionComponent
          in={!hidden}
          timeout={transitionDuration}
          unmountOnExit
          {...TransitionProps}
        >
          <Button
            variant="fab"
            color="primary"
            onKeyDown={this.handleKeyDown}
            aria-label={ariaLabel}
            aria-haspopup="true"
            aria-expanded={open ? 'true' : 'false'}
            aria-controls={`${id}-actions`}
            ref={ref => {
              this.fabRef = ref;
            }}
            className={classes.fab}
            {...clickProp}
            {...ButtonProps}
          >
            {icon()}
          </Button>
        </TransitionComponent>
        <div
          id={`${id}-actions`}
          role="menu"
          className={classNames(
            classes.actions,
            { [classes.actionsClosed]: !open },
            actionsPlacementClass,
          )}
          ref={ref => {
            this.actionsRef = ref;
          }}
        >
          {children}
        </div>
      </div>
    );
  }
示例#17
0
 render() {
   return Children.only(this.props.children)
 }
示例#18
0
    value: function render() {
      var _this2 = this;

      var _props = this.props,
          children = _props.children,
          className = _props.className,
          disableHeader = _props.disableHeader,
          gridClassName = _props.gridClassName,
          gridStyle = _props.gridStyle,
          headerHeight = _props.headerHeight,
          headerRowRenderer = _props.headerRowRenderer,
          height = _props.height,
          id = _props.id,
          noRowsRenderer = _props.noRowsRenderer,
          rowClassName = _props.rowClassName,
          rowStyle = _props.rowStyle,
          scrollToIndex = _props.scrollToIndex,
          style = _props.style,
          width = _props.width;
      var scrollbarWidth = this.state.scrollbarWidth;


      var availableRowsHeight = disableHeader ? height : height - headerHeight;

      var rowClass = typeof rowClassName === 'function' ? rowClassName({ index: -1 }) : rowClassName;
      var rowStyleObject = typeof rowStyle === 'function' ? rowStyle({ index: -1 }) : rowStyle;

      // Precompute and cache column styles before rendering rows and columns to speed things up
      this._cachedColumnStyles = [];
      React.Children.toArray(children).forEach(function (column, index) {
        var flexStyles = _this2._getFlexStyleForColumn(column, column.props.style);

        _this2._cachedColumnStyles[index] = _extends({}, flexStyles, {
          overflow: 'hidden'
        });
      });

      // Note that we specify :rowCount, :scrollbarWidth, :sortBy, and :sortDirection as properties on Grid even though these have nothing to do with Grid.
      // This is done because Grid is a pure component and won't update unless its properties or state has changed.
      // Any property that should trigger a re-render of Grid then is specified here to avoid a stale display.
      return React.createElement(
        'div',
        {
          className: cn('ReactVirtualized__Table', className),
          id: id,
          role: 'grid',
          style: style },
        !disableHeader && headerRowRenderer({
          className: cn('ReactVirtualized__Table__headerRow', rowClass),
          columns: this._getHeaderColumns(),
          style: _extends({}, rowStyleObject, {
            height: headerHeight,
            overflow: 'hidden',
            paddingRight: scrollbarWidth,
            width: width
          })
        }),
        React.createElement(Grid, _extends({}, this.props, {
          autoContainerWidth: true,
          className: cn('ReactVirtualized__Table__Grid', gridClassName),
          cellRenderer: this._createRow,
          columnWidth: width,
          columnCount: 1,
          height: availableRowsHeight,
          id: undefined,
          noContentRenderer: noRowsRenderer,
          onScroll: this._onScroll,
          onSectionRendered: this._onSectionRendered,
          ref: this._setRef,
          role: 'rowgroup',
          scrollbarWidth: scrollbarWidth,
          scrollToRow: scrollToIndex,
          style: _extends({}, gridStyle, {
            overflowX: 'hidden'
          })
        }))
      );
    }
示例#19
0
 render() {
   // `Children.only` enables us not to add a <div /> for nothing
   return Children.only(this.props.children);
 }
示例#20
0
文件: Steps.js 项目: weutils/utils
    value: function render() {
      var _classNames;

      var _props = this.props,
          prefixCls = _props.prefixCls,
          _props$style = _props.style,
          style = _props$style === undefined ? {} : _props$style,
          className = _props.className,
          children = _props.children,
          direction = _props.direction,
          labelPlacement = _props.labelPlacement,
          iconPrefix = _props.iconPrefix,
          status = _props.status,
          size = _props.size,
          current = _props.current,
          progressDot = _props.progressDot,
          restProps = (0, _objectWithoutProperties3['default'])(_props, ['prefixCls', 'style', 'className', 'children', 'direction', 'labelPlacement', 'iconPrefix', 'status', 'size', 'current', 'progressDot']);
      var _state = this.state,
          lastStepOffsetWidth = _state.lastStepOffsetWidth,
          flexSupported = _state.flexSupported;

      var filteredChildren = _react2['default'].Children.toArray(children).filter(function (c) {
        return !!c;
      });
      var lastIndex = filteredChildren.length - 1;
      var adjustedlabelPlacement = !!progressDot ? 'vertical' : labelPlacement;
      var classString = (0, _classnames2['default'])(prefixCls, prefixCls + '-' + direction, className, (_classNames = {}, (0, _defineProperty3['default'])(_classNames, prefixCls + '-' + size, size), (0, _defineProperty3['default'])(_classNames, prefixCls + '-label-' + adjustedlabelPlacement, direction === 'horizontal'), (0, _defineProperty3['default'])(_classNames, prefixCls + '-dot', !!progressDot), _classNames));

      return _react2['default'].createElement(
        'div',
        (0, _extends3['default'])({ className: classString, style: style }, restProps),
        _react.Children.map(filteredChildren, function (child, index) {
          if (!child) {
            return null;
          }
          var childProps = (0, _extends3['default'])({
            stepNumber: '' + (index + 1),
            prefixCls: prefixCls,
            iconPrefix: iconPrefix,
            wrapperStyle: style,
            progressDot: progressDot
          }, child.props);
          if (!flexSupported && direction !== 'vertical' && index !== lastIndex) {
            childProps.itemWidth = 100 / lastIndex + '%';
            childProps.adjustMarginRight = -Math.round(lastStepOffsetWidth / lastIndex + 1);
          }
          // fix tail color
          if (status === 'error' && index === current - 1) {
            childProps.className = prefixCls + '-next-error';
          }
          if (!child.props.status) {
            if (index === current) {
              childProps.status = status;
            } else if (index < current) {
              childProps.status = 'finish';
            } else {
              childProps.status = 'wait';
            }
          }
          return (0, _react.cloneElement)(child, childProps);
        })
      );
    }
示例#21
0
    React.Children.forEach(props.children, (child, index) => {
      var name = child.props.name;

      if (child.type.prototype.className() == 'Schema') {
        this.schemas[name] = Object.assign({}, this.schemas[name], child.props);
        if (name === 'default') {
          this.schemas.tabs = Object.assign({}, this.schemas.tabs, {
            footer: child.props.tabBar,
          });

          Object.keys(this.schemas).forEach(key => {
            this.schemas[key] = Object.assign(
              {}, this.schemas.default, this.schemas[key]);
          });
        }
      } else if (child.type.prototype.className() == 'TabRoute') {
        const tabBarName = child.props.name;
        this.routes[tabBarName] = {};
        this.tabStyles[tabBarName] = {
          barTint: child.props.barTint,
          tint: child.props.tint,
        };
        actions.routes[tabBarName] = {};
        React.Children.forEach(child.props.children, (tabChild, tabIndex) => {
          const tabName = tabChild.props.name;
          this.routes[tabBarName][tabName] = tabChild.props;
          this.routes[tabName] = tabChild.props;
          if (tabChild.props.initial || !this.initial.name) {
            this.initial.name = tabName;
            this.initial.tabBarName = tabBarName;
          }
          if (props.initial === tabName) {
            this.initial.tabBarName = tabBarName;
          }
          actions.routes[tabBarName][tabName] = (data = {}) => e => {
            if (typeof(data) !== 'object') {
              data = { data }
            }

            dispatch({
              type: actionMap[data.type || tabChild.props.type] || 'ROUTER_PUSH',
              payload: { name: tabName, tabBarName, data }
            });
          };
        });
      } else if (child.type.prototype.className() == 'Route') {
        if (child.props.initial || !this.initial.name) {
          this.initial.name = name;
        }

        actions.routes[name] = (data = {}) => e => {
          if (typeof(data) !== 'object') {
            data = { data }
          }

          dispatch({
            type: actionMap[data.type || child.props.type] || 'ROUTER_PUSH',
            payload: { name, data },
          });
        };

        this.routes[name] = child.props;

        if (!child.props.component && !child.props.children) {
          console.error('No route component is defined for name: ' + name);
          return;
        }
      }
    });
示例#22
0
  render() {
    const buttonEventHandlers = {
      onBlur: this.handleBlur,
      onFocus: this.handleFocus,
      onKeyDown: this.handleKeyDown,
      onMouseDown: this.handleMouseDown,
      onMouseEnter: this.handleMouseEnter,
      onMouseLeave: this.handleMouseLeave,
      onMouseUp: this.handleMouseUp,
      onTouchEnd: this.handleTouchEnd,
      onTouchStart: this.handleTouchStart,
      onKeyboardFocus: this.handleKeyboardFocus,
    };

    const {prepareStyles} = this.context.muiTheme;
    const styles = getStyles(this.props, this.context, this.state);

    const {
      children: childrenProp,
      containerElement,
      style,
      className,
      deleteIconStyle,
      labelStyle,
      labelColor, // eslint-disable-line no-unused-vars,prefer-const
      backgroundColor, // eslint-disable-line no-unused-vars,prefer-const
      onRequestDelete, // eslint-disable-line no-unused-vars,prefer-const
      ...other
    } = this.props;

    const deletable = this.props.onRequestDelete;
    let avatar = null;

    const deleteIcon = deletable ? (
      <DeleteIcon
        color={styles.deleteIcon.color}
        style={Object.assign(styles.deleteIcon, deleteIconStyle)}
        onTouchTap={this.handleTouchTapDeleteIcon}
        onMouseEnter={this.handleMouseEnterDeleteIcon}
        onMouseLeave={this.handleMouseLeaveDeleteIcon}
      />
    ) : null;

    let children = childrenProp;
    const childCount = React.Children.count(children);

    // If the first child is an avatar, extract it and style it
    if (childCount > 1) {
      children = React.Children.toArray(children);

      if (React.isValidElement(children[0]) && children[0].type.muiName === 'Avatar') {
        avatar = children.shift();

        avatar = React.cloneElement(avatar, {
          style: Object.assign(styles.avatar, avatar.props.style),
          size: 32,
        });
      }
    }

    return (
      <EnhancedButton
        {...other}
        {...buttonEventHandlers}
        className={className}
        containerElement={containerElement}
        disableTouchRipple={true}
        disableFocusRipple={true}
        style={Object.assign(styles.root, style)}
      >
        {avatar}
        <span style={prepareStyles(Object.assign(styles.label, labelStyle))}>
          {children}
        </span>
        {deleteIcon}
      </EnhancedButton>
    );
  }
  render() {
    const {inverted, scrollViewHeight} = this.props;
    const {measured, layoutHeight, layoutY, nextHeaderLayoutY} = this.state;
    const inputRange: Array<number> = [-1, 0];
    const outputRange: Array<number> = [0, 0];

    if (measured) {
      if (inverted) {
        // The interpolation looks like:
        // - Negative scroll: no translation
        // - `stickStartPoint` is the point at which the header will start sticking.
        //   It is calculated using the ScrollView viewport height so it is a the bottom.
        // - Headers that are in the initial viewport will never stick, `stickStartPoint`
        //   will be negative.
        // - From 0 to `stickStartPoint` no translation. This will cause the header
        //   to scroll normally until it reaches the top of the scroll view.
        // - From `stickStartPoint` to when the next header y hits the bottom edge of the header: translate
        //   equally to scroll. This will cause the header to stay at the top of the scroll view.
        // - Past the collision with the next header y: no more translation. This will cause the
        //   header to continue scrolling up and make room for the next sticky header.
        //   In the case that there is no next header just translate equally to
        //   scroll indefinitely.
        if (scrollViewHeight != null) {
          const stickStartPoint = layoutY + layoutHeight - scrollViewHeight;
          if (stickStartPoint > 0) {
            inputRange.push(stickStartPoint);
            outputRange.push(0);
            inputRange.push(stickStartPoint + 1);
            outputRange.push(1);
            // If the next sticky header has not loaded yet (probably windowing) or is the last
            // we can just keep it sticked forever.
            const collisionPoint =
              (nextHeaderLayoutY || 0) - layoutHeight - scrollViewHeight;
            if (collisionPoint > stickStartPoint) {
              inputRange.push(collisionPoint, collisionPoint + 1);
              outputRange.push(
                collisionPoint - stickStartPoint,
                collisionPoint - stickStartPoint,
              );
            }
          }
        }
      } else {
        // The interpolation looks like:
        // - Negative scroll: no translation
        // - From 0 to the y of the header: no translation. This will cause the header
        //   to scroll normally until it reaches the top of the scroll view.
        // - From header y to when the next header y hits the bottom edge of the header: translate
        //   equally to scroll. This will cause the header to stay at the top of the scroll view.
        // - Past the collision with the next header y: no more translation. This will cause the
        //   header to continue scrolling up and make room for the next sticky header.
        //   In the case that there is no next header just translate equally to
        //   scroll indefinitely.
        inputRange.push(layoutY);
        outputRange.push(0);
        // If the next sticky header has not loaded yet (probably windowing) or is the last
        // we can just keep it sticked forever.
        const collisionPoint = (nextHeaderLayoutY || 0) - layoutHeight;
        if (collisionPoint >= layoutY) {
          inputRange.push(collisionPoint, collisionPoint + 1);
          outputRange.push(collisionPoint - layoutY, collisionPoint - layoutY);
        } else {
          inputRange.push(layoutY + 1);
          outputRange.push(1);
        }
      }
    }

    const translateY = this.props.scrollAnimatedValue.interpolate({
      inputRange,
      outputRange,
    });
    const child = React.Children.only(this.props.children);

    return (
      <Animated.View
        collapsable={false}
        onLayout={this._onLayout}
        style={[child.props.style, styles.header, {transform: [{translateY}]}]}>
        {React.cloneElement(child, {
          style: styles.fill, // We transfer the child style to the wrapper.
          onLayout: undefined, // we call this manually through our this._onLayout
        })}
      </Animated.View>
    );
  }
示例#24
0
 it('Address should consist of details', (done) => {
   Expect(React.Children.count(output.props.children)).toBe(1);
   done();
 });
示例#25
0
  render: function() {
    let ScrollViewClass;
    let ScrollContentContainerViewClass;
    if (Platform.OS === 'ios') {
      ScrollViewClass = RCTScrollView;
      ScrollContentContainerViewClass = RCTScrollContentView;
    } else if (Platform.OS === 'android') {
      if (this.props.horizontal) {
        ScrollViewClass = AndroidHorizontalScrollView;
      } else {
        ScrollViewClass = AndroidScrollView;
      }
      ScrollContentContainerViewClass = View;
    }

    invariant(
      ScrollViewClass !== undefined,
      'ScrollViewClass must not be undefined'
    );

    invariant(
      ScrollContentContainerViewClass !== undefined,
      'ScrollContentContainerViewClass must not be undefined'
    );

    const contentContainerStyle = [
      this.props.horizontal && styles.contentContainerHorizontal,
      this.props.contentContainerStyle,
    ];
    let style, childLayoutProps;
    if (__DEV__ && this.props.style) {
      style = flattenStyle(this.props.style);
      childLayoutProps = ['alignItems', 'justifyContent']
        .filter((prop) => style && style[prop] !== undefined);
      invariant(
        childLayoutProps.length === 0,
        'ScrollView child layout (' + JSON.stringify(childLayoutProps) +
          ') must be applied through the contentContainerStyle prop.'
      );
    }

    let contentSizeChangeProps = {};
    if (this.props.onContentSizeChange) {
      contentSizeChangeProps = {
        onLayout: this._handleContentOnLayout,
      };
    }

    const {stickyHeaderIndices} = this.props;
    const hasStickyHeaders = stickyHeaderIndices && stickyHeaderIndices.length > 0;
    const childArray = hasStickyHeaders && React.Children.toArray(this.props.children);
    const children = hasStickyHeaders ?
      childArray.map((child, index) => {
        const indexOfIndex = child ? stickyHeaderIndices.indexOf(index) : -1;
        if (indexOfIndex > -1) {
          const key = child.key;
          const nextIndex = stickyHeaderIndices[indexOfIndex + 1];
          return (
            <ScrollViewStickyHeader
              key={key}
              ref={(ref) => this._setStickyHeaderRef(key, ref)}
              nextHeaderLayoutY={
                this._headerLayoutYs.get(this._getKeyForIndex(nextIndex, childArray))
              }
              onLayout={(event) => this._onStickyHeaderLayout(index, event, key)}
              scrollAnimatedValue={this._scrollAnimatedValue}>
              {child}
            </ScrollViewStickyHeader>
          );
        } else {
          return child;
        }
      }) :
      this.props.children;
    const contentContainer =
      <ScrollContentContainerViewClass
        {...contentSizeChangeProps}
        ref={this._setInnerViewRef}
        style={contentContainerStyle}
        removeClippedSubviews={this.props.removeClippedSubviews}
        collapsable={false}>
        {children}
      </ScrollContentContainerViewClass>;

    const alwaysBounceHorizontal =
      this.props.alwaysBounceHorizontal !== undefined ?
        this.props.alwaysBounceHorizontal :
        this.props.horizontal;

    const alwaysBounceVertical =
      this.props.alwaysBounceVertical !== undefined ?
        this.props.alwaysBounceVertical :
        !this.props.horizontal;

    const baseStyle = this.props.horizontal ? styles.baseHorizontal : styles.baseVertical;
    const props = {
      ...this.props,
      alwaysBounceHorizontal,
      alwaysBounceVertical,
      style: ([baseStyle, this.props.style]: ?Array<any>),
      // Override the onContentSizeChange from props, since this event can
      // bubble up from TextInputs
      onContentSizeChange: null,
      onMomentumScrollBegin: this.scrollResponderHandleMomentumScrollBegin,
      onMomentumScrollEnd: this.scrollResponderHandleMomentumScrollEnd,
      onResponderGrant: this.scrollResponderHandleResponderGrant,
      onResponderReject: this.scrollResponderHandleResponderReject,
      onResponderRelease: this.scrollResponderHandleResponderRelease,
      onResponderTerminate: this.scrollResponderHandleTerminate,
      onResponderTerminationRequest: this.scrollResponderHandleTerminationRequest,
      onScroll: this._handleScroll,
      onScrollBeginDrag: this.scrollResponderHandleScrollBeginDrag,
      onScrollEndDrag: this.scrollResponderHandleScrollEndDrag,
      onScrollShouldSetResponder: this.scrollResponderHandleScrollShouldSetResponder,
      onStartShouldSetResponder: this.scrollResponderHandleStartShouldSetResponder,
      onStartShouldSetResponderCapture: this.scrollResponderHandleStartShouldSetResponderCapture,
      onTouchEnd: this.scrollResponderHandleTouchEnd,
      onTouchMove: this.scrollResponderHandleTouchMove,
      onTouchStart: this.scrollResponderHandleTouchStart,
      scrollEventThrottle: hasStickyHeaders ? 1 : this.props.scrollEventThrottle,
      sendMomentumEvents: (this.props.onMomentumScrollBegin || this.props.onMomentumScrollEnd) ?
        true : false,
    };

    const { decelerationRate } = this.props;
    if (decelerationRate) {
      props.decelerationRate = processDecelerationRate(decelerationRate);
    }

    const refreshControl = this.props.refreshControl;

    if (refreshControl) {
      if (Platform.OS === 'ios') {
        // On iOS the RefreshControl is a child of the ScrollView.
        // tvOS lacks native support for RefreshControl, so don't include it in that case
        return (
          <ScrollViewClass {...props} ref={this._setScrollViewRef}>
            {Platform.isTVOS ? null : refreshControl}
            {contentContainer}
          </ScrollViewClass>
        );
      } else if (Platform.OS === 'android') {
        // On Android wrap the ScrollView with a AndroidSwipeRefreshLayout.
        // Since the ScrollView is wrapped add the style props to the
        // AndroidSwipeRefreshLayout and use flex: 1 for the ScrollView.
        // Note: we should only apply props.style on the wrapper
        // however, the ScrollView still needs the baseStyle to be scrollable

        return React.cloneElement(
          refreshControl,
          {style: props.style},
          <ScrollViewClass {...props} style={baseStyle} ref={this._setScrollViewRef}>
            {contentContainer}
          </ScrollViewClass>
        );
      }
    }
    return (
      <ScrollViewClass {...props} ref={this._setScrollViewRef}>
        {contentContainer}
      </ScrollViewClass>
    );
  }
示例#26
0
    return {
      activeKey: defaultActiveKey,
      previousActiveKey: null
    };
  },

  componentWillReceiveProps(nextProps) {
    if (nextProps.activeKey != null && nextProps.activeKey !== this.props.activeKey) {
      // check if the 'previousActiveKey' child still exists
      let previousActiveKey = this.props.activeKey;
      React.Children.forEach(nextProps.children, (child) => {
        if (React.isValidElement(child)) {
          if (child.props.eventKey === previousActiveKey) {
            this.setState({
              previousActiveKey
            });
            return;
          }
        }
      });
    }
  },

  componentDidUpdate() {
    let tabs = this._tabs;
    let tabIdx = this._eventKeys().indexOf(this.getActiveKey());

    if (this._needsRefocus) {
      this._needsRefocus = false;
      if (tabs && tabIdx !== -1) {
        let tabNode = ReactDOM.findDOMNode(tabs[tabIdx]);
示例#27
0
 getTabsCount: function() {
     return this.props.children && this.props.children[0] ?
         React.Children.count(this.props.children[0].props.children) :
         0;
 },
示例#28
0
export const someChild = (children, iteratee) => _.some(Children.toArray(children), iteratee)
示例#29
0
 _getOptions() {
   return React.Children.toArray(this.props.children).find(isMenuOptions);
 }
示例#30
0
const countChildren = c =>
  React.Children.toArray(c).filter(React.isValidElement).length;