<commit_before>import React from 'react';
import classnames from 'classnames';
import propTypes from 'prop-types';
import SprkIcon from '../../../SprkIcon/SprkIcon';

const SprkInputIconCheck = ({ children, leadingIcon, textIcon }) => {
  if (leadingIcon.length > 0 || textIcon) {
    return (
      <div
        className={classnames({
          'sprk-b-TextInputIconContainer': true,
          'sprk-b-TextInputIconContainer--has-text-icon': textIcon,
          'sprk-b-TextInputIconContainer--has-text-icon-right': textIconRight,
        })}
      >
        {leadingIcon.length > 0 && (
          <SprkIcon
            iconName={leadingIcon}
            additionalClasses="
              sprk-c-Icon--m sprk-c-Icon--stroke-current-color
            "
          />
        )}
        {children}
      </div>
    );
  }
  return <>{children}</>;
};

SprkInputIconCheck.propTypes = {
  leadingIcon: propTypes.string,
  textIcon: propTypes.bool,
};

export default SprkInputIconCheck;
<commit_msg>added textIconRight prop<commit_after>import React from 'react';
import classnames from 'classnames';
import propTypes from 'prop-types';
import SprkIcon from '../../../SprkIcon/SprkIcon';

const SprkInputIconCheck = ({
  children,
  leadingIcon,
  textIcon,
  textIconRight,
}) => {
  if (leadingIcon.length > 0 || textIcon) {
    return (
      <div
        className={classnames({
          'sprk-b-TextInputIconContainer': true,
          'sprk-b-TextInputIconContainer--has-text-icon': textIcon,
          'sprk-b-TextInputIconContainer--has-text-icon-right': textIconRight,
        })}
      >
        {leadingIcon.length > 0 && (
          <SprkIcon
            iconName={leadingIcon}
            additionalClasses="
              sprk-c-Icon--m sprk-c-Icon--stroke-current-color
            "
          />
        )}
        {children}
      </div>
    );
  }
  return <>{children}</>;
};

SprkInputIconCheck.propTypes = {
  leadingIcon: propTypes.string,
  textIcon: propTypes.bool,
};

export default SprkInputIconCheck;
<|endoftext|>


<commit_before>import React from 'react';
import PropTypes from 'prop-types';
import { c } from 'ttag';
import { Button, LinkButton, Icon } from '../../../components';
import { classnames } from '../../../helpers';

const SubscriptionTable = ({
    plans,
    onSelect,
    currentPlanIndex = 0,
    mostPopularIndex = 0,
    currentPlan = c('Title for subscription plan').t`Current plan`,
    selected = c('Info').t`Selected`,
    select = c('Action').t`Select`,
    disabled = false,
    mode = 'radio',
}) => {
    return (

                {plans.map(({ name, title, price, imageSrc, description, features = [], canCustomize }, index) => {
                    return (

                                    {index === currentPlanIndex ? (

                                            {currentPlan}

                                    ) : null}
                                    {index === mostPopularIndex ? (

{c(
                                            'Title for subscription plan'
                                        ).t`Most popular`}

                                    ) : null}

{title}

{price}

{description}

                                    {features.map(({ icon, content }, index) => {
                                        return (

                                                <Icon
                                                    name={icon}
                                                    size="12"
                                                    className="mt0-4 mr0-5 flex-item-noshrink on-rtl-mirror"
                                                />
                                                {content}

                                        );
                                    })}

                                    {mode === 'radio' ? (
                                        <Button
                                            disabled={disabled || index === currentPlanIndex}
                                            className={classnames([index !== currentPlanIndex && 'pm-button--primary'])}
                                            onClick={() => onSelect(index)}
                                        >
                                            {index === currentPlanIndex ? selected : select}
                                        </Button>
                                    ) : null}
                                    {mode === 'button' ? (
                                        <Button className="pm-button--primary" onClick={() => onSelect(index)}>
                                            {select}
                                        </Button>
                                    ) : null}
                                    {canCustomize ? (
                                        <LinkButton
                                            disabled={disabled}
                                            className="subscriptionTable-customize-button"
                                            onClick={() => onSelect(index, true)}
                                        >{c('Action').t`Customize`}</LinkButton>
                                    ) : null}

                    );
                })}

    );
};

SubscriptionTable.propTypes = {
    disabled: PropTypes.bool,
    currentPlan: PropTypes.string,
    plans: PropTypes.arrayOf(
        PropTypes.shape({
            name: PropTypes.string.isRequired,
            title: PropTypes.string.isRequired,
            price: PropTypes.node.isRequired,
            imageSrc: PropTypes.string.isRequired,
            description: PropTypes.node.isRequired,
            features: PropTypes.arrayOf(
                PropTypes.shape({
                    icon: PropTypes.string.isRequired,
                    content: PropTypes.node.isRequired,
                })
            ).isRequired,
        })
    ),
    onSelect: PropTypes.func.isRequired,
    currentPlanIndex: PropTypes.number,
    mostPopularIndex: PropTypes.number,
    selected: PropTypes.string,
    select: PropTypes.string,
    mode: PropTypes.oneOf(['radio', 'button']),
};

export default SubscriptionTable;
<commit_msg>fix plans for tablet in dashboard<commit_after>import React from 'react';
import PropTypes from 'prop-types';
import { c } from 'ttag';
import { Button, LinkButton, Icon } from '../../../components';
import { classnames } from '../../../helpers';

const SubscriptionTable = ({
    plans,
    onSelect,
    currentPlanIndex = 0,
    mostPopularIndex = 0,
    currentPlan = c('Title for subscription plan').t`Current plan`,
    selected = c('Info').t`Selected`,
    select = c('Action').t`Select`,
    disabled = false,
    mode = 'radio',
}) => {
    return (

                {plans.map(({ name, title, price, imageSrc, description, features = [], canCustomize }, index) => {
                    return (

                                    {index === currentPlanIndex ? (

                                            {currentPlan}

                                    ) : null}
                                    {index === mostPopularIndex ? (

{c(
                                            'Title for subscription plan'
                                        ).t`Most popular`}

                                    ) : null}

{title}

{price}

{description}

                                    {features.map(({ icon, content }, index) => {
                                        return (

                                                <Icon
                                                    name={icon}
                                                    size="12"
                                                    className="mt0-4 mr0-5 flex-item-noshrink on-rtl-mirror"
                                                />
                                                {content}

                                        );
                                    })}

                                    {mode === 'radio' ? (
                                        <Button
                                            disabled={disabled || index === currentPlanIndex}
                                            className={classnames([index !== currentPlanIndex && 'pm-button--primary'])}
                                            onClick={() => onSelect(index)}
                                        >
                                            {index === currentPlanIndex ? selected : select}
                                        </Button>
                                    ) : null}
                                    {mode === 'button' ? (
                                        <Button className="pm-button--primary" onClick={() => onSelect(index)}>
                                            {select}
                                        </Button>
                                    ) : null}
                                    {canCustomize ? (
                                        <LinkButton
                                            disabled={disabled}
                                            className="subscriptionTable-customize-button"
                                            onClick={() => onSelect(index, true)}
                                        >{c('Action').t`Customize`}</LinkButton>
                                    ) : null}

                    );
                })}

    );
};

SubscriptionTable.propTypes = {
    disabled: PropTypes.bool,
    currentPlan: PropTypes.string,
    plans: PropTypes.arrayOf(
        PropTypes.shape({
            name: PropTypes.string.isRequired,
            title: PropTypes.string.isRequired,
            price: PropTypes.node.isRequired,
            imageSrc: PropTypes.string.isRequired,
            description: PropTypes.node.isRequired,
            features: PropTypes.arrayOf(
                PropTypes.shape({
                    icon: PropTypes.string.isRequired,
                    content: PropTypes.node.isRequired,
                })
            ).isRequired,
        })
    ),
    onSelect: PropTypes.func.isRequired,
    currentPlanIndex: PropTypes.number,
    mostPopularIndex: PropTypes.number,
    selected: PropTypes.string,
    select: PropTypes.string,
    mode: PropTypes.oneOf(['radio', 'button']),
};

export default SubscriptionTable;
<|endoftext|>


<commit_before>import { filters2cql } from '../lib/FilterGroups';
import { compilePathTemplate } from '@folio/stripes-connect/RESTResource/RESTResource';

// failOnCondition can take values:
//      0: do not fail even if query and filters and empty
//      1: fail if query is empty, whatever the filter state
//      2: fail if both query and filters and empty.
//
// For compatibility, false and true may be used for 0 and 1 respectively.
//
function makeQueryFunction(findAll, queryTemplate, sortMap, filterConfig, failOnCondition) {
  return (queryParams, pathComponents, resourceValues, logger) => {

    const { qindex, filters, query} = queryParams || {};

    if ((query === undefined || query === '') &&
        (failOnCondition === 1 || failOnCondition === true)) {
      return null;
    }
    if ((query === undefined || query === '') &&
        (filters === undefined || filters === '') &&
        (failOnCondition === 2)) {
      return null;
    }

    //This check should remain in place until all uses of the $QUERY syntax have been removed from stripes modules
    if(queryTemplate.includes("$QUERY")) {
      logger.log('mquery', 'Use of "$QUERY" in the queryTemplate is deprecated. Use the "?{query}" syntax instead, as found https://github.com/folio-org/stripes-connect/blob/master/doc/api.md#text-substitution')
      queryTemplate = queryTemplate.replace(/\$QUERY/g, '?{query}');
    }

    let cql = undefined;
    if (query && qindex) {
      const t = qindex.split('/', 2);
      if (t.length === 1) {
        cql = `${qindex}="${query}*"`;
      } else {
        cql = `${t[0]} =\/${t[1]} "${query}*"`;
      }
    } else if (query) {
      cql = compilePathTemplate(queryTemplate, queryParams, pathComponents, resourceValues);
      if (cql === null) {
        // Some part of the template requires something that we don't have.
        return null;
      }
    }

    const filterCql = filters2cql(filterConfig, filters);
    if (filterCql) {
      if (cql) {
        cql = `(${cql}) and ${filterCql}`;
      } else {
        cql = filterCql;
      }
    }

    let { sort } = queryParams || {};
    if (sort) {
      const sortIndexes = sort.split(',').map((sort1) => {
        let reverse = false;
        if (sort1.startsWith('-')) {
          sort1 = sort1.substr(1);
          reverse = true;
        }
        let sortIndex = sortMap[sort1] || sort1;
        if (reverse) {
          sortIndex = sortIndex.replace(' ', '/sort.descending ') + '/sort.descending';
        }
        return sortIndex;
      });

      if (cql === undefined) cql = findAll;
      cql += ` sortby ${sortIndexes.join(' ')}`;
    }

    logger.log('mquery', `query='${query}' filters='${filters}' sort='${sort}' -> ${cql}`);

    return cql;
  };
}

export default makeQueryFunction;
<commit_msg>Extract all queryParams at the same time<commit_after>import { filters2cql } from '../lib/FilterGroups';
import { compilePathTemplate } from '@folio/stripes-connect/RESTResource/RESTResource';

// failOnCondition can take values:
//      0: do not fail even if query and filters and empty
//      1: fail if query is empty, whatever the filter state
//      2: fail if both query and filters and empty.
//
// For compatibility, false and true may be used for 0 and 1 respectively.
//
function makeQueryFunction(findAll, queryTemplate, sortMap, filterConfig, failOnCondition) {
  return (queryParams, pathComponents, resourceValues, logger) => {

    const { qindex, filters, query, sort } = queryParams || {};

    if ((query === undefined || query === '') &&
        (failOnCondition === 1 || failOnCondition === true)) {
      return null;
    }
    if ((query === undefined || query === '') &&
        (filters === undefined || filters === '') &&
        (failOnCondition === 2)) {
      return null;
    }

    //This check should remain in place until all uses of the $QUERY syntax have been removed from stripes modules
    if(queryTemplate.includes("$QUERY")) {
      logger.log('mquery', 'Use of "$QUERY" in the queryTemplate is deprecated. Use the "?{query}" syntax instead, as found https://github.com/folio-org/stripes-connect/blob/master/doc/api.md#text-substitution')
      queryTemplate = queryTemplate.replace(/\$QUERY/g, '?{query}');
    }

    let cql = undefined;
    if (query && qindex) {
      const t = qindex.split('/', 2);
      if (t.length === 1) {
        cql = `${qindex}="${query}*"`;
      } else {
        cql = `${t[0]} =\/${t[1]} "${query}*"`;
      }
    } else if (query) {
      cql = compilePathTemplate(queryTemplate, queryParams, pathComponents, resourceValues);
      if (cql === null) {
        // Some part of the template requires something that we don't have.
        return null;
      }
    }

    const filterCql = filters2cql(filterConfig, filters);
    if (filterCql) {
      if (cql) {
        cql = `(${cql}) and ${filterCql}`;
      } else {
        cql = filterCql;
      }
    }

    if (sort) {
      const sortIndexes = sort.split(',').map((sort1) => {
        let reverse = false;
        if (sort1.startsWith('-')) {
          sort1 = sort1.substr(1);
          reverse = true;
        }
        let sortIndex = sortMap[sort1] || sort1;
        if (reverse) {
          sortIndex = sortIndex.replace(' ', '/sort.descending ') + '/sort.descending';
        }
        return sortIndex;
      });

      if (cql === undefined) cql = findAll;
      cql += ` sortby ${sortIndexes.join(' ')}`;
    }

    logger.log('mquery', `query='${query}' filters='${filters}' sort='${sort}' -> ${cql}`);

    return cql;
  };
}

export default makeQueryFunction;
<|endoftext|>


<commit_before>/**
 * @license
 * Copyright 2018 Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS-IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

const MAX_Z_INDEX = 2147483647;

const Constants = {};

/**
 * Supported environments.
 *
 * @enum {string}
 */
Constants.Environment = {
  LOCAL: 'LOCAL',
  PREPROD: 'PREPROD',
  PRODUCTION: 'PRODUCTION',
  SANDBOX: 'SANDBOX',
  TEST: 'TEST',
  TIN: 'TIN',
};

/**
 * Supported payment methods.
 *
 * @enum {string}
 */
Constants.PaymentMethod = {
  CARD: 'CARD',
  TOKENIZED_CARD: 'TOKENIZED_CARD',
  UPI: 'UPI',
};

/**
 * Auth methods.
 *
 * @enum {string}
 */
Constants.AuthMethod = {
  CRYPTOGRAM_3DS: 'CRYPTOGRAM_3DS',
  PAN_ONLY: 'PAN_ONLY',
};

/**
 * Returned result status.
 *
 * @enum {string}
 */
Constants.ResponseStatus = {
  CANCELED: 'CANCELED',
  DEVELOPER_ERROR: 'DEVELOPER_ERROR',
};

/**
 * Supported total price status.
 *
 * @enum {string}
 */
Constants.TotalPriceStatus = {
  ESTIMATED: 'ESTIMATED',
  FINAL: 'FINAL',
  NOT_CURRENTLY_KNOWN: 'NOT_CURRENTLY_KNOWN',
};

/**
 * Supported Google Pay payment button type.
 *
 * @enum {string}
 */
Constants.ButtonType = {
  SHORT: 'short',
  LONG: 'long',
};

/**
 * Supported button colors.
 *
 * @enum {string}
 */
Constants.ButtonColor = {
  DEFAULT: 'default',  // Currently defaults to black.
  BLACK: 'black',
  WHITE: 'white',
};

/**
 * Id attributes.
 *
 * @enum {string}
 */
Constants.Id = {
  POPUP_WINDOW_CONTAINER: 'popup-window-container',
};

/** @const {string} */
Constants.STORAGE_KEY_PREFIX = 'google.payments.api.storage';

/** @const {string} */
Constants.IS_READY_TO_PAY_RESULT_KEY =
    Constants.STORAGE_KEY_PREFIX + '.isreadytopay.result';

/** @const {string} */
Constants.UPI_CAN_MAKE_PAYMENT_CACHE_KEY =
    Constants.STORAGE_KEY_PREFIX + '.upi.canMakePaymentCache';

Constants.CLASS_PREFIX = 'google-payments-';
Constants.IFRAME_ACTIVE_CONTAINER_CLASS =
    `${Constants.CLASS_PREFIX}activeContainer`;
Constants.IFRAME_CONTAINER_CLASS = `${Constants.CLASS_PREFIX}dialogContainer`;
Constants.IFRAME_STYLE_CENTER_CLASS = `${Constants.CLASS_PREFIX}dialogCenter`;
Constants.IFRAME_STYLE_CLASS = `${Constants.CLASS_PREFIX}dialog`;

Constants.IFRAME_STYLE = `
.${Constants.IFRAME_STYLE_CLASS} {
    animation: none 0s ease 0s 1 normal none running;
    background: none 0 0 / auto repeat scroll padding-box border-box #fff;
    background-blend-mode: normal;
    border: 0 none #333;
    border-radius: 8px 8px 0 0;
    border-collapse: separate;
    bottom: 0;
    box-shadow: #808080 0 3px 0 0, #808080 0 0 22px;
    box-sizing: border-box;
    letter-spacing: normal;
    max-height: 100%;
    overflow: visible;
    position: fixed;
    width: 100%;
    z-index: ${MAX_Z_INDEX};
    -webkit-appearance: none;
    left: 0;
}
@media (min-width: 480px) {
  .${Constants.IFRAME_STYLE_CLASS}{
    width: 480px !important;
    left: -240px !important;
    margin-left: calc(100vw - 100vw / 2) !important;
  }
}
.${Constants.IFRAME_CONTAINER_CLASS} {
  background-color: rgba(0,0,0,0.26);
  bottom: 0;
  height: 100%;
  left: 0;
  position: absolute;
  right: 0;
}
.iframeContainer {
  -webkit-overflow-scrolling: touch;
}
`;

Constants.IFRAME_STYLE_CENTER = `
.${Constants.IFRAME_STYLE_CENTER_CLASS} {
  animation: none 0s ease 0s 1 normal none running;
  background-blend-mode: normal;
  background: none 0 0 / auto repeat scroll padding-box border-box #fff;
  border-collapse: separate;
  border-radius: 8px;
  border: 0px none #333;
  bottom: auto;
  box-shadow: #808080 0 0 22px;
  box-sizing: border-box;
  left: -240px;
  letter-spacing: normal;
  margin-left: calc(100vw - 100vw / 2) !important;
  max-height: 600px;
  overflow: visible;
  position: absolute;
  top: 100%;
  transform: scale(0.8);
  width: 480px;
  z-index: ${MAX_Z_INDEX};
  -webkit-appearance: none;
}
.${Constants.IFRAME_ACTIVE_CONTAINER_CLASS} {
  top: 50%;
  transform: scale(1.0) translateY(-50%);
}
`;

Constants.GPAY_BUTTON_WITH_CARD_INFO_IMAGE =
    'background-image: url(https://pay.google.com/gp/p/generate_gpay_btn_img);';

Constants.BUTTON_LOCALE_TO_MIN_WIDTH = {
  'en': 152,
  'bg': 163,
  'cs': 192,
  'de': 183,
  'es': 183,
  'fr': 183,
  'hr': 157,
  'id': 186,
  'ja': 148,
  'ko': 137,
  'ms': 186,
  'nl': 167,
  'pl': 182,
  'pt': 193,
  'ru': 206,
  'sk': 157,
  'sl': 211,
  'sr': 146,
  'tr': 161,
  'uk': 207,
  'zh': 156,
};

/**
 * Name of the graypane.
 *
 * @const {string}
 */
Constants.GPAY_GRAYPANE = 'gpay-graypane';

/**
 * Class used for the gpay button.
 *
 * @const {string}
 */
Constants.GPAY_BUTTON_CLASS = 'gpay-button';

Constants.BUTTON_STYLE = `
.${Constants.GPAY_BUTTON_CLASS} {
  background-origin: content-box;
  background-position: center center;
  background-repeat: no-repeat;
  background-size: contain;
  border: 0px;
  border-radius: 4px;
  box-shadow: rgba(60, 64, 67, 0.3) 0px 1px 1px 0px, rgba(60, 64, 67, 0.15) 0px 1px 3px 1px;
  cursor: pointer;
  height: 40px;
  min-height: 40px;
  padding: 11px 24px;
}

.${Constants.GPAY_BUTTON_CLASS}.black {
  background-color: #000;
  box-shadow: none;
  padding: 12px 24px 10px;
}

.${Constants.GPAY_BUTTON_CLASS}.white {
  background-color: #fff;
}

.${Constants.GPAY_BUTTON_CLASS}.short {
  min-width: 90px;
  width: 160px;
}

.${Constants.GPAY_BUTTON_CLASS}.black.short {
  background-image: url(https://www.gstatic.com/instantbuy/svg/dark_gpay.svg);
}

.${Constants.GPAY_BUTTON_CLASS}.white.short {
  background-image: url(https://www.gstatic.com/instantbuy/svg/light_gpay.svg);
}

.${Constants.GPAY_BUTTON_CLASS}.black.active {
  background-color: #5f6368;
}

.${Constants.GPAY_BUTTON_CLASS}.black.hover {
  background-color: #3c4043;
}

.${Constants.GPAY_BUTTON_CLASS}.white.active {
  background-color: #fff;
}

.${Constants.GPAY_BUTTON_CLASS}.white.focus {
  box-shadow: #e8e8e8 0 1px 1px 0, #e8e8e8 0 1px 3px;
}

.${Constants.GPAY_BUTTON_CLASS}.white.hover {
  background-color: #f8f8f8;
}
`;

/**
 * Class used for the new gpay button with card info (last 4 digits, card net).
 *
 * @const {string}
 */
Constants.GPAY_BUTTON_CARD_INFO_CLASS = 'gpay-card-info-btn';

Constants.GPAY_BUTTON_CARD_INFO_BUTTON_STYLE = `
  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS} {
    background-origin: content-box;
    background-position: center center;
    background-repeat: no-repeat;
    background-size: contain;
    border: 0px;
    border-radius: 4px;
    box-shadow: rgba(60, 64, 67, 0.3) 0px 1px 1px 0px, rgba(60, 64, 67, 0.15) 0px 1px 3px 1px;
    cursor: pointer;
    height: 40px;
    min-height: 40px;
    padding: 11px 24px;
    background-color: #000;
    box-shadow: none;
    padding: 9px 24px 10px;
    min-width: 190px;
    width: 240px;
  }

  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS}.active {
    background-color: #5f6368;
  }

  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS}.hover {
    background-color: #3c4043;
  }
  `;

/**
 * Trusted domain for secure context validation
 *
 * @const {string}
 */
Constants.TRUSTED_DOMAIN = '.google.com';

export {Constants};

<commit_msg>Copybara migration of following change(s): ---- Change 216624229 Internal change ----<commit_after>/**
 * @license
 * Copyright 2018 Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS-IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

const MAX_Z_INDEX = 2147483647;

const Constants = {};

/**
 * Supported environments.
 *
 * @enum {string}
 */
Constants.Environment = {
  LOCAL: 'LOCAL',
  PREPROD: 'PREPROD',
  PRODUCTION: 'PRODUCTION',
  SANDBOX: 'SANDBOX',
  TEST: 'TEST',
  TIN: 'TIN',
};

/**
 * Supported payment methods.
 *
 * @enum {string}
 */
Constants.PaymentMethod = {
  CARD: 'CARD',
  TOKENIZED_CARD: 'TOKENIZED_CARD',
  UPI: 'UPI',
};

/**
 * Auth methods.
 *
 * @enum {string}
 */
Constants.AuthMethod = {
  CRYPTOGRAM_3DS: 'CRYPTOGRAM_3DS',
  PAN_ONLY: 'PAN_ONLY',
};

/**
 * Returned result status.
 *
 * @enum {string}
 */
Constants.ResponseStatus = {
  CANCELED: 'CANCELED',
  DEVELOPER_ERROR: 'DEVELOPER_ERROR',
};

/**
 * Supported total price status.
 *
 * @enum {string}
 */
Constants.TotalPriceStatus = {
  ESTIMATED: 'ESTIMATED',
  FINAL: 'FINAL',
  NOT_CURRENTLY_KNOWN: 'NOT_CURRENTLY_KNOWN',
};

/**
 * Supported Google Pay payment button type.
 *
 * @enum {string}
 */
Constants.ButtonType = {
  SHORT: 'short',
  LONG: 'long',
};

/**
 * Supported button colors.
 *
 * @enum {string}
 */
Constants.ButtonColor = {
  DEFAULT: 'default',  // Currently defaults to black.
  BLACK: 'black',
  WHITE: 'white',
};

/**
 * Id attributes.
 *
 * @enum {string}
 */
Constants.Id = {
  POPUP_WINDOW_CONTAINER: 'popup-window-container',
};

/** @const {string} */
Constants.STORAGE_KEY_PREFIX = 'google.payments.api.storage';

/** @const {string} */
Constants.IS_READY_TO_PAY_RESULT_KEY =
    Constants.STORAGE_KEY_PREFIX + '.isreadytopay.result';

/** @const {string} */
Constants.UPI_CAN_MAKE_PAYMENT_CACHE_KEY =
    Constants.STORAGE_KEY_PREFIX + '.upi.canMakePaymentCache';

Constants.CLASS_PREFIX = 'google-payments-';
Constants.IFRAME_ACTIVE_CONTAINER_CLASS =
    `${Constants.CLASS_PREFIX}activeContainer`;
Constants.IFRAME_CONTAINER_CLASS = `${Constants.CLASS_PREFIX}dialogContainer`;
Constants.IFRAME_STYLE_CENTER_CLASS = `${Constants.CLASS_PREFIX}dialogCenter`;
Constants.IFRAME_STYLE_CLASS = `${Constants.CLASS_PREFIX}dialog`;

Constants.IFRAME_STYLE = `
.${Constants.IFRAME_STYLE_CLASS} {
    animation: none 0s ease 0s 1 normal none running;
    background: none 0 0 / auto repeat scroll padding-box border-box #fff;
    background-blend-mode: normal;
    border: 0 none #333;
    border-radius: 8px 8px 0 0;
    border-collapse: separate;
    bottom: 0;
    box-shadow: #808080 0 3px 0 0, #808080 0 0 22px;
    box-sizing: border-box;
    letter-spacing: normal;
    max-height: 100%;
    overflow: visible;
    position: fixed;
    width: 100%;
    z-index: ${MAX_Z_INDEX};
    -webkit-appearance: none;
    left: 0;
}
@media (min-width: 480px) {
  .${Constants.IFRAME_STYLE_CLASS} {
    width: 480px !important;
    left: -240px !important;
    margin-left: calc(100vw - 100vw / 2) !important;
  }
}
.${Constants.IFRAME_CONTAINER_CLASS} {
  background-color: rgba(0,0,0,0.26);
  bottom: 0;
  height: 100%;
  left: 0;
  position: absolute;
  right: 0;
}
.iframeContainer {
  -webkit-overflow-scrolling: touch;
}
`;

Constants.IFRAME_STYLE_CENTER = `
.${Constants.IFRAME_STYLE_CENTER_CLASS} {
  animation: none 0s ease 0s 1 normal none running;
  background-blend-mode: normal;
  background: none 0 0 / auto repeat scroll padding-box border-box #fff;
  border-collapse: separate;
  border-radius: 8px;
  border: 0px none #333;
  bottom: auto;
  box-shadow: #808080 0 0 22px;
  box-sizing: border-box;
  left: -240px;
  letter-spacing: normal;
  margin-left: calc(100vw - 100vw / 2) !important;
  max-height: 90%;
  overflow: visible;
  position: absolute;
  top: 100%;
  transform: scale(0.8);
  width: 480px;
  z-index: ${MAX_Z_INDEX};
  -webkit-appearance: none;
}
@media (min-height: 667px) {
  .${Constants.IFRAME_STYLE_CENTER_CLASS} {
    max-height: 600px;
  }
}
.${Constants.IFRAME_ACTIVE_CONTAINER_CLASS} {
  top: 50%;
  transform: scale(1.0) translateY(-50%);
}
`;

Constants.GPAY_BUTTON_WITH_CARD_INFO_IMAGE =
    'background-image: url(https://pay.google.com/gp/p/generate_gpay_btn_img);';

Constants.BUTTON_LOCALE_TO_MIN_WIDTH = {
  'en': 152,
  'bg': 163,
  'cs': 192,
  'de': 183,
  'es': 183,
  'fr': 183,
  'hr': 157,
  'id': 186,
  'ja': 148,
  'ko': 137,
  'ms': 186,
  'nl': 167,
  'pl': 182,
  'pt': 193,
  'ru': 206,
  'sk': 157,
  'sl': 211,
  'sr': 146,
  'tr': 161,
  'uk': 207,
  'zh': 156,
};

/**
 * Name of the graypane.
 *
 * @const {string}
 */
Constants.GPAY_GRAYPANE = 'gpay-graypane';

/**
 * Class used for the gpay button.
 *
 * @const {string}
 */
Constants.GPAY_BUTTON_CLASS = 'gpay-button';

Constants.BUTTON_STYLE = `
.${Constants.GPAY_BUTTON_CLASS} {
  background-origin: content-box;
  background-position: center center;
  background-repeat: no-repeat;
  background-size: contain;
  border: 0px;
  border-radius: 4px;
  box-shadow: rgba(60, 64, 67, 0.3) 0px 1px 1px 0px, rgba(60, 64, 67, 0.15) 0px 1px 3px 1px;
  cursor: pointer;
  height: 40px;
  min-height: 40px;
  padding: 11px 24px;
}

.${Constants.GPAY_BUTTON_CLASS}.black {
  background-color: #000;
  box-shadow: none;
  padding: 12px 24px 10px;
}

.${Constants.GPAY_BUTTON_CLASS}.white {
  background-color: #fff;
}

.${Constants.GPAY_BUTTON_CLASS}.short {
  min-width: 90px;
  width: 160px;
}

.${Constants.GPAY_BUTTON_CLASS}.black.short {
  background-image: url(https://www.gstatic.com/instantbuy/svg/dark_gpay.svg);
}

.${Constants.GPAY_BUTTON_CLASS}.white.short {
  background-image: url(https://www.gstatic.com/instantbuy/svg/light_gpay.svg);
}

.${Constants.GPAY_BUTTON_CLASS}.black.active {
  background-color: #5f6368;
}

.${Constants.GPAY_BUTTON_CLASS}.black.hover {
  background-color: #3c4043;
}

.${Constants.GPAY_BUTTON_CLASS}.white.active {
  background-color: #fff;
}

.${Constants.GPAY_BUTTON_CLASS}.white.focus {
  box-shadow: #e8e8e8 0 1px 1px 0, #e8e8e8 0 1px 3px;
}

.${Constants.GPAY_BUTTON_CLASS}.white.hover {
  background-color: #f8f8f8;
}
`;

/**
 * Class used for the new gpay button with card info (last 4 digits, card net).
 *
 * @const {string}
 */
Constants.GPAY_BUTTON_CARD_INFO_CLASS = 'gpay-card-info-btn';

Constants.GPAY_BUTTON_CARD_INFO_BUTTON_STYLE = `
  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS} {
    background-origin: content-box;
    background-position: center center;
    background-repeat: no-repeat;
    background-size: contain;
    border: 0px;
    border-radius: 4px;
    box-shadow: rgba(60, 64, 67, 0.3) 0px 1px 1px 0px, rgba(60, 64, 67, 0.15) 0px 1px 3px 1px;
    cursor: pointer;
    height: 40px;
    min-height: 40px;
    padding: 11px 24px;
    background-color: #000;
    box-shadow: none;
    padding: 9px 24px 10px;
    min-width: 190px;
    width: 240px;
  }

  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS}.active {
    background-color: #5f6368;
  }

  .${Constants.GPAY_BUTTON_CARD_INFO_CLASS}.hover {
    background-color: #3c4043;
  }
  `;

/**
 * Trusted domain for secure context validation
 *
 * @const {string}
 */
Constants.TRUSTED_DOMAIN = '.google.com';

export {Constants};

<|endoftext|>


<commit_before>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

define([
  'p-promise',
  'client/auth/lightbox/api',
  'client/auth/redirect/api'
], function (p, LightboxUI, RedirectUI) {
  'use strict';

  var UIs = {
    'default': RedirectUI,
    lightbox: LightboxUI,
    redirect: RedirectUI
  };

  function getUI(context, ui, clientId, options) {
    if (context._ui) {
      throw new Error('Firefox Accounts is already open');
    }

    if (typeof ui === 'object') {
      // allow a UI to be passed in for testing.
      context._ui = ui;
    } else {
      ui = ui || 'default';
      var UI = UIs[ui];

      if (! UI) {
        throw new Error('Invalid ui: ' + ui);
      }

      context._ui = new UI(clientId, options);
    }

    return context._ui;
  }

  /**
   * @class FxaRelierClient
   * @constructor
   * @param {string} clientId - the OAuth client ID for the relier
   * @param {Object} [options={}] - configuration
   *   @param {String} [options.contentHost]
   *   Firefox Accounts Content Server host
   *   @param {String} [options.oauthHost]
   *   Firefox Accounts OAuth Server host
   *   @param {Object} [options.window]
   *   window override, used for unit tests
   *   @param {Object} [options.lightbox]
   *   lightbox override, used for unit tests
   *   @param {Object} [options.channel]
   *   channel override, used for unit tests
   */
  function FxaRelierClient(clientId, options) {
    if (! clientId) {
      throw new Error('clientId is required');
    }

    this.auth = {
      /**
       * Sign in an existing user.
       *
       * @method signIn
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} [config.email]
       *   Email address used to pre-fill into the account form,
       *   but the user is free to change it. Set to the string literal
       *   `blank` to ignore any previously signed in email. Default is
       *   the last email address used to sign in.
       *   @param {String} [config.force_email]
       *   Force the user to sign in with the given email
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      signIn: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.signIn(config)
            .fin(function () {
              delete self._ui;
            });
        });
      },

      /**
       * Force a user to sign in as an existing user.
       *
       * @method forceAuth
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} config.email
       *   Email address the user must sign in with. The user
       *   is unable to modify the email address and is unable
       *   to sign up if the address is not registered.
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      forceAuth: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.forceAuth(config)
            .fin(function () {
              delete self._ui;
            });
        });
      },

      /**
       * Sign up a new user
       *
       * @method signUp
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} [config.email]
       *   Email address used to pre-fill into the account form,
       *   but the user is free to change it.
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      signUp: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.signUp(config)
            .fin(function () {
              delete self._ui;
            });
        });
      }
    };
  }

  FxaRelierClient.prototype = {
    /**
     * FxaRelierClient version
     *
     * @property version
     * @type {String}
     */
    version: '0.0.0'
  };

  return FxaRelierClient;
});

<commit_msg>Remove `force_email` from the docs.<commit_after>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

define([
  'p-promise',
  'client/auth/lightbox/api',
  'client/auth/redirect/api'
], function (p, LightboxUI, RedirectUI) {
  'use strict';

  var UIs = {
    'default': RedirectUI,
    lightbox: LightboxUI,
    redirect: RedirectUI
  };

  function getUI(context, ui, clientId, options) {
    if (context._ui) {
      throw new Error('Firefox Accounts is already open');
    }

    if (typeof ui === 'object') {
      // allow a UI to be passed in for testing.
      context._ui = ui;
    } else {
      ui = ui || 'default';
      var UI = UIs[ui];

      if (! UI) {
        throw new Error('Invalid ui: ' + ui);
      }

      context._ui = new UI(clientId, options);
    }

    return context._ui;
  }

  /**
   * @class FxaRelierClient
   * @constructor
   * @param {string} clientId - the OAuth client ID for the relier
   * @param {Object} [options={}] - configuration
   *   @param {String} [options.contentHost]
   *   Firefox Accounts Content Server host
   *   @param {String} [options.oauthHost]
   *   Firefox Accounts OAuth Server host
   *   @param {Object} [options.window]
   *   window override, used for unit tests
   *   @param {Object} [options.lightbox]
   *   lightbox override, used for unit tests
   *   @param {Object} [options.channel]
   *   channel override, used for unit tests
   */
  function FxaRelierClient(clientId, options) {
    if (! clientId) {
      throw new Error('clientId is required');
    }

    this.auth = {
      /**
       * Sign in an existing user.
       *
       * @method signIn
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} [config.email]
       *   Email address used to pre-fill into the account form,
       *   but the user is free to change it. Set to the string literal
       *   `blank` to ignore any previously signed in email. Default is
       *   the last email address used to sign in.
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      signIn: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.signIn(config)
            .fin(function () {
              delete self._ui;
            });
        });
      },

      /**
       * Force a user to sign in as an existing user.
       *
       * @method forceAuth
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} config.email
       *   Email address the user must sign in with. The user
       *   is unable to modify the email address and is unable
       *   to sign up if the address is not registered.
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      forceAuth: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.forceAuth(config)
            .fin(function () {
              delete self._ui;
            });
        });
      },

      /**
       * Sign up a new user
       *
       * @method signUp
       * @param {Object} config - configuration
       *   @param {String} config.state
       *   CSRF/State token
       *   @param {String} config.redirect_uri
       *   URI to redirect to when complete
       *   @param {String} config.scope
       *   OAuth scope
       *   @param {String} [config.email]
       *   Email address used to pre-fill into the account form,
       *   but the user is free to change it.
       *   @param {String} [config.ui]
       *   UI to present - `lightbox` or `redirect` - defaults to `redirect`
       */
      signUp: function (config) {
        var self = this;
        return p().then(function () {
          config = config || {};

          var api = getUI(self, config.ui, clientId, options);
          return api.signUp(config)
            .fin(function () {
              delete self._ui;
            });
        });
      }
    };
  }

  FxaRelierClient.prototype = {
    /**
     * FxaRelierClient version
     *
     * @property version
     * @type {String}
     */
    version: '0.0.0'
  };

  return FxaRelierClient;
});

<|endoftext|>


<commit_before>$(document).ready(function(){

	var svg = d3.select(".donut")
	var margin = {top: 20, right: 30, bottom: 30, left: 40},
		width = 3000 - margin.left - margin.right,
	    height = 500 - margin.top - margin.bottom;

	var data = [];
	var rects;

	// this populates relative position of
	for(var i = 0; i < 200; i++)
		data.push(i)

	var xScale = d3.fisheye.scale(d3.scale.linear).domain([0, data.length]).range([0, width]).focus(width/2);

     svg.on("mousemove", function() {
     	var mouse = d3.mouse(this);
     	xScale.distortion(2.5).focus(mouse[0]);

     	rects.call(position);
	  });

	  // Positions the bars based on data.
	  function position(rect) {
	      rect.attr("x", function(d, i) {
	          return xScale(i);
	      });
	  }

	donut(data);

	$svg = $("svg");

	var left = 171;
	var barRange = 0.5;
	var closestBar = rects[0][0];

	/*
	$("svg").mousemove(function(event){

		fisheye.focus(d3.mouse(this));

		//console.log((event.screenX - left) / 10);
		// get the bar closest to a mouse move
		// then resize the rest of the bars
		// according to which bar we grabbed
		var bar = getClosestBar((event.screenX - left) / 10);

		//console.log(bar);

		d3.select(bar)
			.transition()
			//.attr('width', "30px")
			.attr('fill', 'black')
			.duration(500);

	});
*/

	var donutSliceColor;

	function getClosestBar(mousePosition){
		for(var i = 0; i < rects[0].length; i++){
			if((i - mousePosition) < barRange){
			//if(Math.abs(rects[0][i].__data__ - mousePosition) < barRange) {
				//console.log("square: " + i + "at " + Math.abs(rects[0][i].__data__ - mousePosition));
				closestBar = rects[0][i];
			}
		}
		return closestBar;
	}

function donut(data) {

	var width = 4000,
    height = 1000,
    radius = Math.min(width, height) / 2;

	var color = d3.scale.category20();

	var pie = d3.layout.pie()
	.value(function (d) {return d });

	var arc = d3.svg.arc()
	    .innerRadius(radius - 400)
	    .outerRadius(radius );

	svg.append('rect')
		.attr('width', width)
		.attr('height', height)
		.attr('fill','#D3EDF2')

	svg
		.data([data])
	    .attr("width", width)
	    .attr("height", height)
	    .append("g")
	    .attr("transform", "translate(" + 0 + "," + height / 5 + ")");

	rects = svg.selectAll("rect")
		.data(function(d, i) { return d })
		.enter()
		.append("rect")
		.attr('width', function(d){ return 10 + "px" })
		.attr('height', function(d){ return 200 + "px" })
		.attr('x', function(d, i ){ return 15 * i  })
		.attr('fill', "#3D5C95")
		.on('mouseover', function(){
			var rect = d3.select(this)
			var position = rect[0][0].__data__;

			rect.transition()
				//.attr('y', 300)
				.attr('width', "30px")
				.duration(200);

			//moveSquares(position, rects[0].length, true);
			//moveSquares(position, rects[0].length);
		})
		.on('mouseout',function(){
			/*
			var rect = d3.select(this)
			var position = rect[0][0].__data__;
			*/
			d3.select(this)
				.transition()
				//.attr('y', 0)
				.attr('width', "10px")
				.duration(200)

			//moveSquares(position, rects[0].length, false);

		})
		.call(position);

	function moveSquares(position, length) {
		console.log("position: " + position);

		var scaledPosition;
		/*
		for(var i = 0; i < length; i++){
			otherPosition = i + 1;
			if(otherPosition > position)
				otherPosition = Math.abs(length - otherPosition - position);

			scaledPosition = Math.log(otherPosition)
			console.log(i + " should be " + scaledPosition + " big.");
		}
		/*
		for(var i = position + 1; i < length; i++){
			var current = d3.select(rects[0][i]);
			var oldX = current.attr("x");
			if(forward){
				current
					.transition()
					.attr("x", parseInt(oldX) + 20);
			} else {
				current
					.transition()
					.attr("x", parseInt(oldX) - 20);
			}
		}
		*/
	}

	var mySquare=svg.append("rect")
	  .attr("x",60)
	  .attr("y",400)
	  .attr("width",60)
	  .attr("height",60);

	mySquare.on('mouseover', function(){
		d3.select(this)
		  .transition()
		  .attr("x",320);
	})

	/*
	var path = svg.selectAll("path")
	    .data(pie.value(function(d) { return d }))
	  	.enter().append("path")
	    .attr("fill", function(d, i) { return color(i); })
	    .attr("d", arc)
	    .on('mouseover', function(d){
	    	donutSliceColor = d3.select(this).style('fill');
	    	d3.select(this).transition().style("fill", " #fcfcfa");

	    	//this part is fucked
	    	d3.select(this).tansition()
	    		.attr("d", d3.svg.arc()
				    .innerRadius(radius + 100)
				    .outerRadius(radius + 100));

	    })
	    .on('mouseout', function(d){
	    	d3.select(this).transition().style("fill", donutSliceColor);
	    });
	    */

	}

});

/*
(function chart2() {
  var width = 960,
      height = 180,
      xStepsBig = d3.range(10, width, 16),
      yStepsBig = d3.range(10, height, 16),
      xStepsSmall = d3.range(0, width + 6, 6),
      yStepsSmall = d3.range(0, height + 6, 6);

  var fisheye = d3.fisheye.circular()
      .focus([360, 90])
      .radius(100);

  var line = d3.svg.line();

  var svg = d3.select("#chart2").append("svg")
      .attr("width", width)
      .attr("height", height)
    .append("g")
      .attr("transform", "translate(-.5,-.5)");

  svg.append("rect")
      .attr("class", "background")
      .attr("width", width)
      .attr("height", height);

  svg.selectAll(".x")
      .data(xStepsBig)
    .enter().append("path")
      .attr("class", "x")
      .datum(function(x) { return yStepsSmall.map(function(y) { return [x, y]; }); });

  svg.selectAll(".y")
      .data(yStepsBig)
    .enter().append("path")
      .attr("class", "y")
      .datum(function(y) { return xStepsSmall.map(function(x) { return [x, y]; }); });

  var path = svg.selectAll("path")
      .attr("d", fishline);

  svg.on("mousemove", function() {
    fisheye.focus(d3.mouse(this));
    path.attr("d", fishline);
  });

  function fishline(d) {
    return line(d.map(function(d) {
      d = fisheye({x: d[0], y: d[1]});
      return [d.x, d.y];
    }));
  }
})();
*/

<commit_msg>fixing some sizing<commit_after>$(document).ready(function(){

	var svg = d3.select(".donut")
	var margin = {top: 20, right: 30, bottom: 30, left: 40},
		width = 3000 - margin.left - margin.right,
	    height = 500 - margin.top - margin.bottom;

	var data = [];
	var rects;

	// this populates relative position of
	for(var i = 0; i < 200; i++)
		data.push(i)

	var xScale = d3.fisheye.scale(d3.scale.linear).domain([0, data.length]).range([0, width]).focus(width/2);

     svg.on("mousemove", function() {
     	var mouse = d3.mouse(this);
     	xScale.distortion(2.5).focus(mouse[0]);

     	rects.call(position);
	  });

	  // Positions the bars based on data.
	  function position(rect) {
	      rect.attr("x", function(d, i) {
	          return xScale(i);
	      });
	      rect.attr("width", function(d, i) {
	          return "20px";
	      });
	  }

	donut(data);

	$svg = $("svg");

	var left = 171;
	var barRange = 0.5;
	var closestBar = rects[0][0];

	/*
	$("svg").mousemove(function(event){

		fisheye.focus(d3.mouse(this));

		//console.log((event.screenX - left) / 10);
		// get the bar closest to a mouse move
		// then resize the rest of the bars
		// according to which bar we grabbed
		var bar = getClosestBar((event.screenX - left) / 10);

		//console.log(bar);

		d3.select(bar)
			.transition()
			//.attr('width', "30px")
			.attr('fill', 'black')
			.duration(500);

	});
*/

	var donutSliceColor;

	function getClosestBar(mousePosition){
		for(var i = 0; i < rects[0].length; i++){
			if((i - mousePosition) < barRange){
			//if(Math.abs(rects[0][i].__data__ - mousePosition) < barRange) {
				//console.log("square: " + i + "at " + Math.abs(rects[0][i].__data__ - mousePosition));
				closestBar = rects[0][i];
			}
		}
		return closestBar;
	}

function donut(data) {

	var width = 4000,
    height = 1000,
    radius = Math.min(width, height) / 2;

	var color = d3.scale.category20();

	var pie = d3.layout.pie()
	.value(function (d) {return d });

	var arc = d3.svg.arc()
	    .innerRadius(radius - 400)
	    .outerRadius(radius );

	svg.append('rect')
		.attr('width', width)
		.attr('height', height)
		.attr('fill','#D3EDF2')

	svg
		.data([data])
	    .attr("width", width)
	    .attr("height", height)
	    .append("g")
	    .attr("transform", "translate(" + 0 + "," + height / 5 + ")");

	rects = svg.selectAll("rect")
		.data(function(d, i) { return d })
		.enter()
		.append("rect")
		.attr('width', function(d){ return 10 + "px" })
		.attr('height', function(d){ return 200 + "px" })
		.attr('x', function(d, i ){ return 15 * i  })
		.attr('fill', "#3D5C95")
		/*
		.on('mouseover', function(){
			var rect = d3.select(this)
			var position = rect[0][0].__data__;

			rect.transition()
				//.attr('y', 300)
				.attr('width', "30px")
				.duration(200);

			//moveSquares(position, rects[0].length, true);
			//moveSquares(position, rects[0].length);
		})
		.on('mouseout',function(){
			/*
			var rect = d3.select(this)
			var position = rect[0][0].__data__;

			d3.select(this)
				.transition()
				//.attr('y', 0)
				.attr('width', "10px")
				.duration(200)

			//moveSquares(position, rects[0].length, false);

		})
*/
		.call(position);

	function moveSquares(position, length) {
		console.log("position: " + position);

		var scaledPosition;
		/*
		for(var i = 0; i < length; i++){
			otherPosition = i + 1;
			if(otherPosition > position)
				otherPosition = Math.abs(length - otherPosition - position);

			scaledPosition = Math.log(otherPosition)
			console.log(i + " should be " + scaledPosition + " big.");
		}
		/*
		for(var i = position + 1; i < length; i++){
			var current = d3.select(rects[0][i]);
			var oldX = current.attr("x");
			if(forward){
				current
					.transition()
					.attr("x", parseInt(oldX) + 20);
			} else {
				current
					.transition()
					.attr("x", parseInt(oldX) - 20);
			}
		}
		*/
	}

	var mySquare=svg.append("rect")
	  .attr("x",60)
	  .attr("y",400)
	  .attr("width",60)
	  .attr("height",60);

	mySquare.on('mouseover', function(){
		d3.select(this)
		  .transition()
		  .attr("x",320);
	})

	/*
	var path = svg.selectAll("path")
	    .data(pie.value(function(d) { return d }))
	  	.enter().append("path")
	    .attr("fill", function(d, i) { return color(i); })
	    .attr("d", arc)
	    .on('mouseover', function(d){
	    	donutSliceColor = d3.select(this).style('fill');
	    	d3.select(this).transition().style("fill", " #fcfcfa");

	    	//this part is fucked
	    	d3.select(this).tansition()
	    		.attr("d", d3.svg.arc()
				    .innerRadius(radius + 100)
				    .outerRadius(radius + 100));

	    })
	    .on('mouseout', function(d){
	    	d3.select(this).transition().style("fill", donutSliceColor);
	    });
	    */

	}

});

/*
(function chart2() {
  var width = 960,
      height = 180,
      xStepsBig = d3.range(10, width, 16),
      yStepsBig = d3.range(10, height, 16),
      xStepsSmall = d3.range(0, width + 6, 6),
      yStepsSmall = d3.range(0, height + 6, 6);

  var fisheye = d3.fisheye.circular()
      .focus([360, 90])
      .radius(100);

  var line = d3.svg.line();

  var svg = d3.select("#chart2").append("svg")
      .attr("width", width)
      .attr("height", height)
    .append("g")
      .attr("transform", "translate(-.5,-.5)");

  svg.append("rect")
      .attr("class", "background")
      .attr("width", width)
      .attr("height", height);

  svg.selectAll(".x")
      .data(xStepsBig)
    .enter().append("path")
      .attr("class", "x")
      .datum(function(x) { return yStepsSmall.map(function(y) { return [x, y]; }); });

  svg.selectAll(".y")
      .data(yStepsBig)
    .enter().append("path")
      .attr("class", "y")
      .datum(function(y) { return xStepsSmall.map(function(x) { return [x, y]; }); });

  var path = svg.selectAll("path")
      .attr("d", fishline);

  svg.on("mousemove", function() {
    fisheye.focus(d3.mouse(this));
    path.attr("d", fishline);
  });

  function fishline(d) {
    return line(d.map(function(d) {
      d = fisheye({x: d[0], y: d[1]});
      return [d.x, d.y];
    }));
  }
})();
*/

<|endoftext|>


<commit_before>import Ember from 'ember';
import RedeyeQuestion from '../util/redeye-question';

export default Ember.Controller.extend({

  init() {
    this.setUpdateInterval();
  },

  currentDate: null,

  setDate() {
    Ember.Logger.debug('setDate called');
    this.set('currentDate', new Date());
  },

  setUpdateInterval() {
    Ember.Logger.debug('setUpdateInterval called');
    this.setDate()
    setInterval(() => this.setDate(), 60 * 1000);
  },

  // The date when we first go to sleep, minus one day for waiting period
  initialSleepDateMinusOneDay: new Date('2017-08-24T08:00:00'), // UTC

  hoursOfSleepPer28hrDay: 9,

  // The total duration of this trial in hours (1 week plus one day waiting)
  numberOfHoursOfRedEye: 1 * 7 * 28,

  // One of the following:
  //  - waiting
  //  - awake
  //  - asleep
  //  - done
  redeyeState: Ember.computed('currentDate', function () {
    const currentDate = this.get('currentDate'), initialSleepDateMinusOneDay = this.get('initialSleepDateMinusOneDay');
    Ember.Logger.debug('Received dates', 'currentDate', currentDate, 'initialSleepDateMinusOneDay', initialSleepDateMinusOneDay);
    const difference = (currentDate.getTime() - initialSleepDateMinusOneDay.getTime()) / 1000; // in seconds
    if (currentDate < initialSleepDateMinusOneDay || Math.floor(difference / 60 / 60) < this.get('hoursOfSleepPer28hrDay')) {
      return 'waiting';
    }

    if (difference > this.get('numberOfHoursOfRedEye') * 60 * 60) { return 'done'; }

    const currentHourOf28hrDay = (difference / 60 / 60) % 28;
    if (currentHourOf28hrDay < this.get('hoursOfSleepPer28hrDay')) { return 'asleep'; }

    return 'awake';
  }),

  redeyeStateFormatted: Ember.computed('currentDate', function () {
    const currentDate = this.get('currentDate'), initialSleepDateMinusOneDay = this.get('initialSleepDateMinusOneDay');

    const difference = (currentDate.getTime() - initialSleepDateMinusOneDay.getTime()) / 1000; // in seconds
    const currentHourOf28hrDay = Math.floor(difference / 60 / 60) % 28;
    Ember.Logger.debug('currentHourOf28hrDay', currentHourOf28hrDay);

    switch (this.get('redeyeState')) {
      case 'waiting':
        return 'Hyped to start soon! 🔥';
      case 'awake':
        return `Yep 👍, sleeping in ${Math.ceil(difference / 60) % 60 !== 0 ? 28 - currentHourOf28hrDay - 1 : 28 - currentHourOf28hrDay} hours ${(difference / 60) % 60 === 0 ? 0 : 60 - Math.ceil(difference / 60) % 60} minutes. It's been ${Math.floor(difference / 60 / 60 / 28)} day(s).`;
      case 'asleep':
        return `Sleeping 💤, waking in ${Math.ceil(difference / 60) % 60 !== 0 ? this.get('hoursOfSleepPer28hrDay') - currentHourOf28hrDay - 1 : this.get('hoursOfSleepPer28hrDay') - currentHourOf28hrDay} hours ${(difference / 60) % 60 === 0 ? 0 : 60 - Math.ceil(difference / 60) % 60} minutes. It's been ${Math.floor(difference / 60 / 60 / 28)} day(s).`;
      case 'done':
        return 'Donezos ✅🔥';
    }
  }),

  questions: Ember.computed('hoursOfSleepPer28hrDay', function () {
    const hoursOfSleepPer28hrDay = this.get('hoursOfSleepPer28hrDay');
    return Ember.A([
      RedeyeQuestion.create({
        question: 'What is this?',
        answer: `I'm doing an experiment. Instead of going through a seven-day week as usual, this week will have six 28-hour cycles for me. Each cycle, I will sleep for ${hoursOfSleepPer28hrDay} hours, and be awake for ${28 - hoursOfSleepPer28hrDay}. You can check if I'm awake up there 👆. Check back later if you're curious!`
      }),
      RedeyeQuestion.create({
        question: 'When is this happening?',
        answer: 'August 25 to September 1, 2017, China time.'
      }),
      RedeyeQuestion.create({
        question: 'Why 28-hour cycles?',
        answer: '28 times 6 happens to be 24 times 7, so my schedule will sync up with the world after exactly a week.'
      }),
      RedeyeQuestion.create({
        question: 'But why?',
        answer: Ember.String.htmlSafe('This will give me many more waking hours per week than a normal seven-day week. It\'ll just be a week, so might as well try it 🤷. Google it.')
      })
    ]);
  }),

  containerClassNames: Ember.computed('redeyeState', function () {
    if (this.get('redeyeState') === 'asleep') { return 'redeye-container-asleep'; }
    return 'redeye-container-awake';
  }),

  actions: {
    didClickBackButton() {
      this.transitionToRoute('index');
    }
  }

});
<commit_msg>Disable timer on redeye destroy<commit_after>import Ember from 'ember';
import RedeyeQuestion from '../util/redeye-question';

export default Ember.Controller.extend({

  init() {
    this.setUpdateInterval();
  },

  willDestroy() {
    this._super();
    clearInterval(this.get('timer'));
  },

  currentDate: null,
  timer: null,

  setDate() {
    Ember.Logger.debug('setDate called');
    this.set('currentDate', new Date());
  },

  setUpdateInterval() {
    Ember.Logger.debug('setUpdateInterval called');
    this.setDate()
    this.set('timer', setInterval(() => this.setDate(), 60 * 1000));
  },

  // The date when we first go to sleep, minus one day for waiting period
  initialSleepDateMinusOneDay: new Date('2017-08-24T08:00:00'), // UTC

  hoursOfSleepPer28hrDay: 9,

  // The total duration of this trial in hours (1 week plus one day waiting)
  numberOfHoursOfRedEye: 1 * 7 * 28,

  // One of the following:
  //  - waiting
  //  - awake
  //  - asleep
  //  - done
  redeyeState: Ember.computed('currentDate', function () {
    const currentDate = this.get('currentDate'), initialSleepDateMinusOneDay = this.get('initialSleepDateMinusOneDay');
    Ember.Logger.debug('Received dates', 'currentDate', currentDate, 'initialSleepDateMinusOneDay', initialSleepDateMinusOneDay);
    const difference = (currentDate.getTime() - initialSleepDateMinusOneDay.getTime()) / 1000; // in seconds
    if (currentDate < initialSleepDateMinusOneDay || Math.floor(difference / 60 / 60) < this.get('hoursOfSleepPer28hrDay')) {
      return 'waiting';
    }

    if (difference > this.get('numberOfHoursOfRedEye') * 60 * 60) { return 'done'; }

    const currentHourOf28hrDay = (difference / 60 / 60) % 28;
    if (currentHourOf28hrDay < this.get('hoursOfSleepPer28hrDay')) { return 'asleep'; }

    return 'awake';
  }),

  redeyeStateFormatted: Ember.computed('currentDate', function () {
    const currentDate = this.get('currentDate'), initialSleepDateMinusOneDay = this.get('initialSleepDateMinusOneDay');

    const difference = (currentDate.getTime() - initialSleepDateMinusOneDay.getTime()) / 1000; // in seconds
    const currentHourOf28hrDay = Math.floor(difference / 60 / 60) % 28;
    Ember.Logger.debug('currentHourOf28hrDay', currentHourOf28hrDay);

    switch (this.get('redeyeState')) {
      case 'waiting':
        return 'Hyped to start soon! 🔥';
      case 'awake':
        return `Yep 👍, sleeping in ${Math.ceil(difference / 60) % 60 !== 0 ? 28 - currentHourOf28hrDay - 1 : 28 - currentHourOf28hrDay} hours ${(difference / 60) % 60 === 0 ? 0 : 60 - Math.ceil(difference / 60) % 60} minutes. It's been ${Math.floor(difference / 60 / 60 / 28)} day(s).`;
      case 'asleep':
        return `Sleeping 💤, waking in ${Math.ceil(difference / 60) % 60 !== 0 ? this.get('hoursOfSleepPer28hrDay') - currentHourOf28hrDay - 1 : this.get('hoursOfSleepPer28hrDay') - currentHourOf28hrDay} hours ${(difference / 60) % 60 === 0 ? 0 : 60 - Math.ceil(difference / 60) % 60} minutes. It's been ${Math.floor(difference / 60 / 60 / 28)} day(s).`;
      case 'done':
        return 'Donezos ✅🔥';
    }
  }),

  questions: Ember.computed('hoursOfSleepPer28hrDay', function () {
    const hoursOfSleepPer28hrDay = this.get('hoursOfSleepPer28hrDay');
    return Ember.A([
      RedeyeQuestion.create({
        question: 'What is this?',
        answer: `I'm doing an experiment. Instead of going through a seven-day week as usual, this week will have six 28-hour cycles for me. Each cycle, I will sleep for ${hoursOfSleepPer28hrDay} hours, and be awake for ${28 - hoursOfSleepPer28hrDay}. You can check if I'm awake up there 👆. Check back later if you're curious!`
      }),
      RedeyeQuestion.create({
        question: 'When is this happening?',
        answer: 'August 25 to September 1, 2017, China time.'
      }),
      RedeyeQuestion.create({
        question: 'Why 28-hour cycles?',
        answer: '28 times 6 happens to be 24 times 7, so my schedule will sync up with the world after exactly a week.'
      }),
      RedeyeQuestion.create({
        question: 'But why?',
        answer: Ember.String.htmlSafe('This will give me many more waking hours per week than a normal seven-day week. It\'ll just be a week, so might as well try it 🤷. Google it.')
      })
    ]);
  }),

  containerClassNames: Ember.computed('redeyeState', function () {
    if (this.get('redeyeState') === 'asleep') { return 'redeye-container-asleep'; }
    return 'redeye-container-awake';
  }),

  actions: {
    didClickBackButton() {
      this.transitionToRoute('index');
    }
  }

});
<|endoftext|>


<commit_before>import { HeaderController } from '../HeaderController.js';
import { HomeController } from '../HomeController.js';

export function LogoutController() {
    toastr.success('Logged-out successfully!');
    localStorage.removeItem('elsyser-token');
    localStorage.removeItem('elsyser-username');
    localStorage.removeItem('elsyser-id');
    HeaderController();
    HomeController();
}
<commit_msg>fixed little bug<commit_after>import { HeaderController } from '../HeaderController.js';
import { HomeController } from '../HomeController.js';

export function LogoutController() {
    toastr.success('Logged-out successfully!');
    localStorage.removeItem('elsyser-token');
    localStorage.removeItem('elsyser-username');
    localStorage.removeItem('elsyser-id');
    localStorage.removeItem('elsyser-teachers-subject-id');
    HeaderController();
    HomeController();
}
<|endoftext|>


<commit_before>'use strict';

MCMC.registerAlgorithm('DualAveragingHMC', {

  description: 'Hamiltonian Monte Carlo with Dual Averaging',

  about: function() {
    window.open('https://en.wikipedia.org/wiki/Hybrid_Monte_Carlo');
  },

  init: function(self) {

    self.lambda = 1.6;
    self.delta = 0.65;
    self.M_adapt = 100;

    self.joint = function(theta, r) {
      return Math.exp(self.logDensity(theta) - r.norm2() / 2);
    };

    self.leapFrog = function(theta, r, epsilon) {
      var r_ = r.add(self.gradLogDensity(theta).scale(epsilon / 2));
      var theta_ = theta.add(r_.scale(epsilon));
      r_.increment(self.gradLogDensity(theta_).scale(epsilon / 2));
      return {theta: theta_, r: r_};
    };

    self.findReasonableEpsilon = function(theta) {
      var epsilon = 0.1;
      var r = MultivariateNormal.getSample(self.dim);
      var result = self.leapFrog(theta, r, epsilon);
      var a = 2 * (self.joint(result.theta, result.r) / self.joint(theta, r) > 0.5 ? 1 : 0) - 1;
      while (Math.pow(self.joint(result.theta, result.r) / self.joint(theta, r), a) > Math.pow(2.0, -a)) {
        epsilon = Math.pow(2, a) * epsilon;
        result = self.leapFrog(result.theta, result.r, epsilon);
        if (epsilon < 0.005) {
          return 0.005;
        }
      }
      return epsilon;
    };
  },

  reset: function(self) {
    self.chain = [ MultivariateNormal.getSample(self.dim) ];
    self.epsilon = [ self.findReasonableEpsilon(self.chain.last()) ];
    self.mu = Math.log(10 * self.epsilon[0]);
    self.epsilon_bar = [ 1.0 ];
    self.H_bar = [ 1.0 ];

    self.gamma = 0.2;
    self.t0 = 10;
    self.kappa = 0.75;

    self.accepted = 0;
  },

  attachUI: function(self, folder) {
    folder.add(self, 'lambda', 0.1, 2).step(0.1).name('λ = εL').onChange(function(value) {
      sim.reset();
    });
    folder.add(self, 'delta', 0.1, 1).step(0.1).name('δ').onChange(function(value) {
      sim.reset();
    });
    folder.open();
  },

  step: function(self, visualizer) {
    var r0 = MultivariateNormal.getSample(self.dim);
    var theta = self.chain.last().copy();
    var r = r0.copy();
    var Lm = Math.max(1, Math.round(self.lambda / self.epsilon.last()));
    if (Lm > 100) {
      console.log('Lm > 100', Lm);
      Lm = 100;
    }
    var trajectory = [theta.copy()]
    for (var i = 0; i < Lm; ++i) {
      var result = self.leapFrog(theta, r, self.epsilon.last());
      theta = result.theta;
      r = result.r;
      trajectory.push(theta.copy());
    }
    var epsilon = ((self.epsilon.last() * 1000) | 0) / 1000;
    visualizer.queue.push({type: 'proposal', proposal: theta, trajectory: trajectory, initialMomentum: r0, epsilon: epsilon});
    var alpha = Math.min(1, self.joint(theta, r) / self.joint(self.chain.last(), r0));
    if (Math.random() < alpha) {
      self.chain.push(theta);
      visualizer.queue.push({type: 'accept', proposal: theta});
      self.accepted++;
    } else {
      self.chain.push(self.chain.last().copy());
      visualizer.queue.push({type: 'reject', proposal: theta});
    }
    var m = self.chain.length;
    if (m <= self.M_adapt) {
      self.H_bar.push((1 - 1 / (m + self.t0)) * self.H_bar.last() + (1 / (m + self.t0)) * (self.delta - alpha));
      var log_epsilon = self.mu - Math.sqrt(m) / self.gamma * self.H_bar.last();
      self.epsilon.push(Math.exp(log_epsilon));
      self.epsilon_bar.push(Math.exp(Math.pow(m, -self.kappa) * log_epsilon + (1 - Math.pow(m, -self.kappa)) * Math.log(self.epsilon_bar.last())));
    } else {
      self.epsilon.push(self.epsilon_bar.last());
    }
  }

});<commit_msg>changed delta step size to 0.05<commit_after>'use strict';

MCMC.registerAlgorithm('DualAveragingHMC', {

  description: 'Hamiltonian Monte Carlo with Dual Averaging',

  about: function() {
    window.open('https://en.wikipedia.org/wiki/Hybrid_Monte_Carlo');
  },

  init: function(self) {

    self.lambda = 1.6;
    self.delta = 0.65;
    self.M_adapt = 100;

    self.joint = function(theta, r) {
      return Math.exp(self.logDensity(theta) - r.norm2() / 2);
    };

    self.leapFrog = function(theta, r, epsilon) {
      var r_ = r.add(self.gradLogDensity(theta).scale(epsilon / 2));
      var theta_ = theta.add(r_.scale(epsilon));
      r_.increment(self.gradLogDensity(theta_).scale(epsilon / 2));
      return {theta: theta_, r: r_};
    };

    self.findReasonableEpsilon = function(theta) {
      var epsilon = 0.1;
      var r = MultivariateNormal.getSample(self.dim);
      var result = self.leapFrog(theta, r, epsilon);
      var a = 2 * (self.joint(result.theta, result.r) / self.joint(theta, r) > 0.5 ? 1 : 0) - 1;
      while (Math.pow(self.joint(result.theta, result.r) / self.joint(theta, r), a) > Math.pow(2.0, -a)) {
        epsilon = Math.pow(2, a) * epsilon;
        result = self.leapFrog(result.theta, result.r, epsilon);
        if (epsilon < 0.005) {
          return 0.005;
        }
      }
      return epsilon;
    };
  },

  reset: function(self) {
    self.chain = [ MultivariateNormal.getSample(self.dim) ];
    self.epsilon = [ self.findReasonableEpsilon(self.chain.last()) ];
    self.mu = Math.log(10 * self.epsilon[0]);
    self.epsilon_bar = [ 1.0 ];
    self.H_bar = [ 1.0 ];

    self.gamma = 0.2;
    self.t0 = 10;
    self.kappa = 0.75;

    self.accepted = 0;
  },

  attachUI: function(self, folder) {
    folder.add(self, 'lambda', 0.1, 2).step(0.1).name('λ = εL').onChange(function(value) {
      sim.reset();
    });
    folder.add(self, 'delta', 0.1, 1).step(0.05).name('δ').onChange(function(value) {
      sim.reset();
    });
    folder.open();
  },

  step: function(self, visualizer) {
    var r0 = MultivariateNormal.getSample(self.dim);
    var theta = self.chain.last().copy();
    var r = r0.copy();
    var Lm = Math.max(1, Math.round(self.lambda / self.epsilon.last()));
    if (Lm > 100) {
      console.log('Lm > 100', Lm);
      Lm = 100;
    }
    var trajectory = [theta.copy()]
    for (var i = 0; i < Lm; ++i) {
      var result = self.leapFrog(theta, r, self.epsilon.last());
      theta = result.theta;
      r = result.r;
      trajectory.push(theta.copy());
    }
    var epsilon = ((self.epsilon.last() * 1000) | 0) / 1000;
    visualizer.queue.push({type: 'proposal', proposal: theta, trajectory: trajectory, initialMomentum: r0, epsilon: epsilon});
    var alpha = Math.min(1, self.joint(theta, r) / self.joint(self.chain.last(), r0));
    if (Math.random() < alpha) {
      self.chain.push(theta);
      visualizer.queue.push({type: 'accept', proposal: theta});
      self.accepted++;
    } else {
      self.chain.push(self.chain.last().copy());
      visualizer.queue.push({type: 'reject', proposal: theta});
    }
    var m = self.chain.length;
    if (m <= self.M_adapt) {
      self.H_bar.push((1 - 1 / (m + self.t0)) * self.H_bar.last() + (1 / (m + self.t0)) * (self.delta - alpha));
      var log_epsilon = self.mu - Math.sqrt(m) / self.gamma * self.H_bar.last();
      self.epsilon.push(Math.exp(log_epsilon));
      self.epsilon_bar.push(Math.exp(Math.pow(m, -self.kappa) * log_epsilon + (1 - Math.pow(m, -self.kappa)) * Math.log(self.epsilon_bar.last())));
    } else {
      self.epsilon.push(self.epsilon_bar.last());
    }
  }

});<|endoftext|>


<commit_before>/*jslint indent: 2, plusplus: true*/
"use strict";

module.exports = function (options) {
  var
    MISTAKES_BY_CHAR = 1.0/6, // on 6 chars you may mistype one.
    nonAlphanum = /[^a-zA-Z0-9šđčćžáàâäãæéèêëíîïóôöœúùûüñç ]/g,
    mulSpace = /  +/g,
    trimSpace = /^ | $/g,
    trimParentheses = /\([^)]*\)/g,
    trimSquare = /\[[^\]]*\]/g,
    trimHashtag = /\#([^ ]+)/g,
    replacePairs = [
      ['ć', 'c'],
      ['č', 'c'],
      ['ç', 'c'],
      ['š', 's'],
      ['đ', 'dj'],
      ['ž', 'z'],
      ['á', 'a'],
      ['à', 'a'],
      ['â', 'a'],
      ['ä', 'a'],
      ['ã', 'a'],
      ['æ', 'ae'],
      ['é', 'e'],
      ['è', 'e'],
      ['ê', 'e'],
      ['ë', 'e'],
      ['í', 'i'],
      ['î', 'i'],
      ['ï', 'i'],
      ['ó', 'o'],
      ['ô', 'o'],
      ['ö', 'o'],
      ['œ', 'oe'],
      ['ú', 'u'],
      ['ù', 'u'],
      ['û', 'u'],
      ['ü', 'u'],
      ['ñ', 'n'],
    ];

  // O(n^2) hopefuly.
  function editDistance(a, b) {
    var i, j, matrix = [];
    if(a.length == 0) return b.length;
    if(b.length == 0) return a.length;

    // increment along the first column of each row
    for(i = 0; i <= b.length; i++){
      matrix[i] = [i];
    }

    // increment each column in the first row
    for(j = 0; j <= a.length; j++){
      matrix[0][j] = j;
    }

    // Fill in the rest of the matrix
    for(i = 1; i <= b.length; i++){
      for(j = 1; j <= a.length; j++){
        if(b.charAt(i-1) == a.charAt(j-1)){
          matrix[i][j] = matrix[i-1][j-1];
        } else {
          matrix[i][j] = Math.min(matrix[i-1][j-1] + 1, // substitution
                                  Math.min(matrix[i][j-1] + 1, // insertion
                                           matrix[i-1][j] + 1)); // deletion
        }
      }
    }

    return matrix[b.length][a.length];
  }

  // editDistance(t1, t2) >= editDistanceUnderEstimate(t1, t2)
  // O(1)
  function editDistanceUnderEstimate(t1, t2) {
    return Math.abs(t1.length - t2.length);
  }

  // O(n)
  function editDistanceUnderEstimate2(t1, t2) {
    var chars = {}, it, sol = 0;
    for (it = 0; it < t1.length; chars[t1[it++]] = 0);
    for (it = 0; it < t2.length; chars[t2[it++]] = 0);
    for (it = 0; it < t1.length; ++chars[t1[it++]]);
    for (it = 0; it < t2.length; --chars[t2[it++]]);
    for (it in chars)
      sol += Math.abs(chars[it]);
    return Math.round(sol / 2);
  }

  // this function returns a string.
  //
  // If remove_parenthesis_content is true:
  //  'anton (test)' => 'anton'
  //
  // If remove_parenthesis_content is false:
  // 'anton (test)' => 'anton test'
  function normalize(str, remove_parenthesis_content) {
    var i;
    if (str === null || str === undefined) {
      return "null";
    }
    str = str.toString();
    str = str.toLowerCase();
    str = str.replace(trimHashtag, '');
    if (remove_parenthesis_content) {
      str = str.replace(trimParentheses, '');
      str = str.replace(trimSquare, '');
    }
    str = str.replace(nonAlphanum, ' ');
    str = str.replace(mulSpace, ' ');
    str = str.replace(trimSpace, '');
    for (i = 0; i < replacePairs.length; ++i) {
      // regexp used so all occurences are replaced
      str = str.replace(new RegExp(replacePairs[i][0], 'g'), replacePairs[i][1]);
    }
    return str;
  }

  function checkTitleImpl(correct_title, answer, remove_parenthesis_content) {
    var t1 = normalize(answer, remove_parenthesis_content);
    var t2 = normalize(correct_title, remove_parenthesis_content);
    var allowed_mistakes = Math.floor(t1.length * MISTAKES_BY_CHAR);

    if (t1 === t2) return true;
    if (editDistanceUnderEstimate2(t1, t2) > allowed_mistakes) return false;
    if (editDistanceUnderEstimate(t1, t2) > allowed_mistakes) return false;
    if (editDistance(t1, t2) > allowed_mistakes) return false;
    return true;
  }

  function checkTitle(correct_title, answer) {
    // TODO(ganton): optimization idea, i can omit one call to this function if
    // neither of the strings contains '()[]'.
    return checkTitleImpl(correct_title, answer, true) ||
      checkTitleImpl(correct_title, answer, false);
  }

  function consumePrefixOrFalse(big, small) {
    if (big.substr(0, small.length).toLowerCase() === small.toLowerCase()) {
      return big.substr(small.length);
    }
    return false;
  }

  function maybeStripArtist(title, artist) {
    if (!artist) {
      return title;
    }
    return consumePrefixOrFalse(title, artist + " -") ||
      consumePrefixOrFalse(title, artist + " _") ||
      consumePrefixOrFalse(title, artist + " /") ||
      title;
  }

  // playlistItem is dictionary with 'title', 'title2', ... as a member.
  // answer is a string.
  this.checkAnswer = function (playlistItem, answer) {
    if (playlistItem === undefined) {
      return false;
    }
    var key, artist = playlistItem["artist"];
    // figure out if there is artis
    for (key in playlistItem) {
      // If key has 'title' as a prefix.
      if (key.substr(0, 5) === "title") {
        if (checkTitle(maybeStripArtist(playlistItem[key], artist), answer)) {
          return true;
        }
      }
    }
    return false;
  };
};
<commit_msg>bugfix in answer checker for song 22 from Taylor Swift<commit_after>/*jslint indent: 2, plusplus: true*/
"use strict";

module.exports = function (options) {
  var
    MISTAKES_BY_CHAR = 1.0/6, // on 6 chars you may mistype one.
    nonAlphanum = /[^a-zA-Z0-9šđčćžáàâäãæéèêëíîïóôöœúùûüñç ]/g,
    mulSpace = /  +/g,
    trimSpace = /^ | $/g,
    trimParentheses = /\([^)]*\)/g,
    trimSquare = /\[[^\]]*\]/g,
    trimHashtag = /\#([^ ]+)/g,
    replacePairs = [
      ['ć', 'c'],
      ['č', 'c'],
      ['ç', 'c'],
      ['š', 's'],
      ['đ', 'dj'],
      ['ž', 'z'],
      ['á', 'a'],
      ['à', 'a'],
      ['â', 'a'],
      ['ä', 'a'],
      ['ã', 'a'],
      ['æ', 'ae'],
      ['é', 'e'],
      ['è', 'e'],
      ['ê', 'e'],
      ['ë', 'e'],
      ['í', 'i'],
      ['î', 'i'],
      ['ï', 'i'],
      ['ó', 'o'],
      ['ô', 'o'],
      ['ö', 'o'],
      ['œ', 'oe'],
      ['ú', 'u'],
      ['ù', 'u'],
      ['û', 'u'],
      ['ü', 'u'],
      ['ñ', 'n'],
    ];

  // O(n^2) hopefuly.
  function editDistance(a, b) {
    var i, j, matrix = [];
    if(a.length == 0) return b.length;
    if(b.length == 0) return a.length;

    // increment along the first column of each row
    for(i = 0; i <= b.length; i++){
      matrix[i] = [i];
    }

    // increment each column in the first row
    for(j = 0; j <= a.length; j++){
      matrix[0][j] = j;
    }

    // Fill in the rest of the matrix
    for(i = 1; i <= b.length; i++){
      for(j = 1; j <= a.length; j++){
        if(b.charAt(i-1) == a.charAt(j-1)){
          matrix[i][j] = matrix[i-1][j-1];
        } else {
          matrix[i][j] = Math.min(matrix[i-1][j-1] + 1, // substitution
                                  Math.min(matrix[i][j-1] + 1, // insertion
                                           matrix[i-1][j] + 1)); // deletion
        }
      }
    }

    return matrix[b.length][a.length];
  }

  // editDistance(t1, t2) >= editDistanceUnderEstimate(t1, t2)
  // O(1)
  function editDistanceUnderEstimate(t1, t2) {
    return Math.abs(t1.length - t2.length);
  }

  // O(n)
  function editDistanceUnderEstimate2(t1, t2) {
    var chars = {}, it, sol = 0;
    for (it = 0; it < t1.length; chars[t1[it++]] = 0);
    for (it = 0; it < t2.length; chars[t2[it++]] = 0);
    for (it = 0; it < t1.length; ++chars[t1[it++]]);
    for (it = 0; it < t2.length; --chars[t2[it++]]);
    for (it in chars)
      sol += Math.abs(chars[it]);
    return Math.round(sol / 2);
  }

  // this function returns a string.
  //
  // If remove_parenthesis_content is true:
  //  'anton (test)' => 'anton'
  //
  // If remove_parenthesis_content is false:
  // 'anton (test)' => 'anton test'
  function normalize(str, remove_parenthesis_content) {
    var i;
    if (str === null || str === undefined) {
      return "null";
    }
    str = str.toString();
    str = str.toLowerCase();
    str = str.replace(trimHashtag, '');
    if (remove_parenthesis_content) {
      str = str.replace(trimParentheses, '');
      str = str.replace(trimSquare, '');
    }
    str = str.replace(nonAlphanum, ' ');
    str = str.replace(mulSpace, ' ');
    str = str.replace(trimSpace, '');
    for (i = 0; i < replacePairs.length; ++i) {
      // regexp used so all occurences are replaced
      str = str.replace(new RegExp(replacePairs[i][0], 'g'), replacePairs[i][1]);
    }
    return str;
  }

  function checkTitleImpl(correct_title, answer, remove_parenthesis_content) {
    var t1 = normalize(answer, remove_parenthesis_content);
    var t2 = normalize(correct_title, remove_parenthesis_content);
    var allowed_mistakes = Math.floor(t1.length * MISTAKES_BY_CHAR);

    if (t1 === t2) return true;
    if (editDistanceUnderEstimate2(t1, t2) > allowed_mistakes) return false;
    if (editDistanceUnderEstimate(t1, t2) > allowed_mistakes) return false;
    if (editDistance(t1, t2) > allowed_mistakes) return false;
    return true;
  }

  function checkTitle(correct_title, answer) {
    // TODO(ganton): optimization idea, i can omit one call to this function if
    // neither of the strings contains '()[]'.
    return checkTitleImpl(correct_title, answer, true) ||
      checkTitleImpl(correct_title, answer, false);
  }

  function consumePrefixOrFalse(big, small) {
    if (big.substr(0, small.length).toLowerCase() === small.toLowerCase()) {
      return big.substr(small.length);
    }
    return false;
  }

  // Always returns a string.
  function maybeStripArtist(title, artist) {
    if (!artist) {
      return title;
    }
    artist = String(artist)
    // The song '22' by Taylor Swift for some reason had the Number type as a
    // title..
    title = String(title)
    return consumePrefixOrFalse(title, artist + " -") ||
      consumePrefixOrFalse(title, artist + " _") ||
      consumePrefixOrFalse(title, artist + " /") ||
      title;
  }

  // playlistItem is dictionary with 'title', 'title2', ... as a member.
  // answer is a string.
  this.checkAnswer = function (playlistItem, answer) {
    if (playlistItem === undefined) {
      return false;
    }
    var key, artist = playlistItem["artist"];
    // figure out if there is artis
    for (key in playlistItem) {
      // If key has 'title' as a prefix.
      if (key.substr(0, 5) === "title") {
        if (checkTitle(maybeStripArtist(playlistItem[key], artist), answer)) {
          return true;
        }
      }
    }
    return false;
  };
};
<|endoftext|>


<commit_before>/**
 * @author mrdoob / http://mrdoob.com/
 */

import { LineSegments } from '../objects/LineSegments.js';
import { VertexColors } from '../constants.js';
import { LineBasicMaterial } from '../materials/LineBasicMaterial.js';
import { Float32BufferAttribute } from '../core/BufferAttribute.js';
import { BufferGeometry } from '../core/BufferGeometry.js';
import { Color } from '../math/Color.js';

function GridHelper( size, divisions, color1, color2 ) {

	this.parameters = {
		size: size,
		divisions: divisions,
		color1: color1,
		color2: color2
	};

	size = size || 10;
	divisions = divisions || 10;
	color1 = new Color( color1 !== undefined ? color1 : 0x444444 );
	color2 = new Color( color2 !== undefined ? color2 : 0x888888 );

	var center = divisions / 2;
	var step = size / divisions;
	var halfSize = size / 2;

	var vertices = [], colors = [];

	for ( var i = 0, j = 0, k = - halfSize; i <= divisions; i ++, k += step ) {

		vertices.push( - halfSize, 0, k, halfSize, 0, k );
		vertices.push( k, 0, - halfSize, k, 0, halfSize );

		var color = i === center ? color1 : color2;

		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;

	}

	var geometry = new BufferGeometry();
	geometry.addAttribute( 'position', new Float32BufferAttribute( vertices, 3 ) );
	geometry.addAttribute( 'color', new Float32BufferAttribute( colors, 3 ) );

	var material = new LineBasicMaterial( { vertexColors: VertexColors } );

	LineSegments.call( this, geometry, material );

}

GridHelper.prototype = Object.assign( Object.create( LineSegments.prototype ), {

	constructor: GridHelper,

	copy( source ) {

		LineSegments.prototype.copy.call( this, source );

		Object.assign( this.parameters, source.parameters );

		return this;

	},

	clone() {

		var parameters = this.parameters;

		return new this.constructor( parameters.size, parameters.divisions, parameters.color1, parameters.color2 );

	}

} );

export { GridHelper };
<commit_msg>GridHelper: Fix code style<commit_after>/**
 * @author mrdoob / http://mrdoob.com/
 */

import { LineSegments } from '../objects/LineSegments.js';
import { VertexColors } from '../constants.js';
import { LineBasicMaterial } from '../materials/LineBasicMaterial.js';
import { Float32BufferAttribute } from '../core/BufferAttribute.js';
import { BufferGeometry } from '../core/BufferGeometry.js';
import { Color } from '../math/Color.js';

function GridHelper( size, divisions, color1, color2 ) {

	this.parameters = {
		size: size,
		divisions: divisions,
		color1: color1,
		color2: color2
	};

	size = size || 10;
	divisions = divisions || 10;
	color1 = new Color( color1 !== undefined ? color1 : 0x444444 );
	color2 = new Color( color2 !== undefined ? color2 : 0x888888 );

	var center = divisions / 2;
	var step = size / divisions;
	var halfSize = size / 2;

	var vertices = [], colors = [];

	for ( var i = 0, j = 0, k = - halfSize; i <= divisions; i ++, k += step ) {

		vertices.push( - halfSize, 0, k, halfSize, 0, k );
		vertices.push( k, 0, - halfSize, k, 0, halfSize );

		var color = i === center ? color1 : color2;

		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;
		color.toArray( colors, j ); j += 3;

	}

	var geometry = new BufferGeometry();
	geometry.addAttribute( 'position', new Float32BufferAttribute( vertices, 3 ) );
	geometry.addAttribute( 'color', new Float32BufferAttribute( colors, 3 ) );

	var material = new LineBasicMaterial( { vertexColors: VertexColors } );

	LineSegments.call( this, geometry, material );

}

GridHelper.prototype = Object.assign( Object.create( LineSegments.prototype ), {

	constructor: GridHelper,

	copy: function ( source ) {

		LineSegments.prototype.copy.call( this, source );

		Object.assign( this.parameters, source.parameters );

		return this;

	},

	clone: function () {

		var parameters = this.parameters;

		return new this.constructor( parameters.size, parameters.divisions, parameters.color1, parameters.color2 );

	}

} );

export { GridHelper };
<|endoftext|>


<commit_before>import React from 'react';
import { render } from 'react-dom';
import { createStore, applyMiddleware } from 'redux';
import { Provider } from 'react-redux';
import thunk from 'redux-thunk';
import promiseMiddleware from 'redux-promise-middleware';
import reducers from './reducers';
import App from './containers/App';
import { fetch } from './actions';

const initialState = {
	dataFromAPI: {
		loading: false,
		filter: {},
		response: {}
	}
};

const middleware = [thunk, promiseMiddleware()];

const store = createStore(reducers, initialState, applyMiddleware(...middleware));

store.dispatch(fetch());

render(
	<Provider store={store}>
		<App />
	</Provider>,
	document.getElementById('root')
);
<commit_msg>Add redux dev tools support<commit_after>import React from 'react';
import { render } from 'react-dom';
import { createStore, applyMiddleware, compose } from 'redux';
import { Provider } from 'react-redux';
import thunk from 'redux-thunk';
import promiseMiddleware from 'redux-promise-middleware';
import reducers from './reducers';
import App from './containers/App';
import { fetch } from './actions';

const initialState = {
	dataFromAPI: {
		loading: false,
		filter: {},
		response: {}
	}
};

const middleware = [thunk, promiseMiddleware()];

const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose;
const store = createStore(reducers, initialState, composeEnhancers(applyMiddleware(...middleware)));

store.dispatch(fetch());

render(
	<Provider store={store}>
		<App />
	</Provider>,
	document.getElementById('root')
);
<|endoftext|>