{"size": 3451, "ext": "js", "max_stars_repo_path": "src/Button/Button.js", "max_stars_repo_name": "skystebnicki/chameleon", "max_stars_repo_stars_event_min_datetime": "2015-10-08T06:46:30.000Z", "max_stars_repo_stars_event_max_datetime": "2020-05-25T09:11:34.000Z", "max_issues_repo_path": "src/Button/Button.js", "max_issues_repo_name": "skystebnicki/chameleon", "max_issues_repo_issues_event_min_datetime": "2016-04-05T13:50:10.000Z", "max_issues_repo_issues_event_max_datetime": "2017-06-06T17:40:30.000Z", "max_forks_repo_path": "src/Button/Button.js", "max_forks_repo_name": "skystebnicki/chameleon", "max_forks_repo_forks_event_min_datetime": "2020-07-12T02:39:35.000Z", "max_forks_repo_forks_event_max_datetime": "2020-07-12T02:39:35.000Z"}
{"max_stars_count": 16, "max_issues_count": 7, "max_forks_count": 1, "avg_line_length": 20.5416666667, "max_line_length": 70, "alphanum_fraction": 0.6406838598}
import React from 'react';
import PropTypes from 'prop-types';
import TouchRipple from '../ripples/TouchRipple';
import FocusRipple from '../ripples/FocusRipple';
import ThemeService from '../styles/ChamelThemeService';
import classnames from 'classnames';

/**
 * Functional component for any button
 *
 * @param props
 * @param context
 * @returns {ReactDOM}
 * @constructor
 */
const Button = (props, context) => {
  let theme =
    context.chamelTheme && context.chamelTheme.button
      ? context.chamelTheme.button
      : ThemeService.defaultTheme.button;

  // Setup classes
  const className = props.className || null;
  const type = props.type;
  const classes = classnames(
    theme[type],
    {
      [theme[type + 'primary']]: props.primary,
      [theme[type + 'accent']]: props.accent,
      [theme[type + 'disabled']]: props.disabled,
      [theme[type + 'depressed']]: props.depressed,
      [theme[type + 'mini']]: props.mini,
    },
    className,
  );

  // Determine if the selected type of button is a centered ripple
  let centerRipple = type == 'floating' || type == 'icon';
  const label = props.label ? props.label : props.children;

  const onClickHandler = props.onTap || props.onClick;

  if (onClickHandler && !props.disabled) {
    return (
      <button className={classes} onClick={onClickHandler}>
        <FocusRipple />
        <TouchRipple centerRipple={centerRipple}>{label}</TouchRipple>
      </button>
    );
  } else {
    return (
      <button disabled={props.disabled} className={classes}>
        {label}
      </button>
    );
  }
};

/**
 * Set accepted properties
 */
Button.propTypes = {
  /**
   * Secondary accent color
   */
  accent: PropTypes.bool,

  /**
   * Primary button color and behavior
   */
  primary: PropTypes.bool,

  /**
   * Child elements (text and icon)
   */
  children: PropTypes.node,

  /**
   * Optional classname override
   */
  className: PropTypes.string,

  /**
   * Disabled flag - cannot be interacted with
   */
  disabled: PropTypes.bool,

  /**
   * Flat style (looks like a link almost)
   */
  flat: PropTypes.bool,

  /**
   * Floating button like floating action buttons (FAB) in material
   */
  floating: PropTypes.bool,

  /**
   * Link reference to go to
   */
  href: PropTypes.string,

  /**
   * ?
   */
  inverse: PropTypes.bool,

  /**
   * Optional icon to display to the left of the text
   */
  icon: PropTypes.oneOfType([PropTypes.string, PropTypes.element]),

  /**
   * Optional property in place of child text
   */
  label: PropTypes.string,

  /**
   * Small button
   */
  mini: PropTypes.bool,

  /**
   * If true the button should appear pressed or down (think toggle)
   */
  depressed: PropTypes.bool,
  neutral: PropTypes.bool,
  onMouseLeave: PropTypes.func,
  onMouseUp: PropTypes.func,

  /**
   * Event triggered when the user taps/clicks on the button
   */
  onTape: PropTypes.func,

  /**
   * Alias for onTap for backwards compatibility
   */
  onClick: PropTypes.func,

  raised: PropTypes.bool,
  type: PropTypes.oneOf(['raised', 'flat', 'floating', 'icon']),
};

/**
 * Set property defaults
 */
Button.defaultProps = {
  accent: false,
  className: '',
  flat: false,
  floating: false,
  mini: false,
  neutral: true,
  primary: false,
  raised: false,
  type: 'raised',
};

/**
 * An alternate theme may be passed down by a provider
 */
Button.contextTypes = {
  chamelTheme: PropTypes.object,
};

export default Button;
