<commit_before>import React from 'react'
import styled, { keyframes } from 'styled-components'
import PropTypes from 'prop-types'
import {
  Card,
  Flexbox,
  Image,
  Text,
  Title
} from '../../'
import IconColorful from '../../content/IconColorful/IconColorful'

const textColor = '#4a4a4a'

const placeHolderShimmer = keyframes`
  0% { -webkit-transform: translateX(-180%) }
  100% { -webkit-transform: translateX(70%) }
`;

const BackgroundMasker = styled.div`
  background: #fff;
  position: absolute;
`

const AnimatedBackground = styled.div`
  animation-name: ${placeHolderShimmer};
  animation-duration: 1s;
  animation-fill-mode: forwards;
  animation-iteration-count: infinite;
  animation-timing-function: linear;
  background: #f6f7f8;
  background: linear-gradient(to right, transparent 30%, #dddddd 70%, transparent 100%);
  height: 300px;
  position: relative;
`

const PanelLoading = styled(({ className, minHeight, title }) => (
  <Card title={title} minHeight={minHeight}>

      <AnimatedBackground />
      <BackgroundMasker style={{ top: 182, left: 0, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 185, bottom: 0, width: 18 }} />
      <BackgroundMasker style={{ top: 200, left: 185, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 218, left: 0, right: 0, height: 12 }} />
      <BackgroundMasker style={{ top: 230, left: 254, right: 0, height: 14 }} />
      <BackgroundMasker style={{ top: 244, left: 0, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 262, left: 120, right: 0, height: 10 }} />
      <BackgroundMasker style={{ top: 272, left: 0, right: 0, height: 28 }} />

  </Card>
))`
  background: #eeeeee;
  border-color: #e5e6e9 #dfe0e4 #d0d1d5;
  min-height: 300px;
  position: relative;
  overflow: hidden;
`

const DefaultImage = styled(({ className }) => (

    <IconColorful name='community' size={130} />

))`
  display: flex;
  justify-content: center;
  align-items: center;
  height: 185px;
  background-color: #424242;
`

const Panel = ({
  loading,
  image,
  minHeight,
  sectionTitle,
  author,
  title,
  description
}) => loading ? <PanelLoading title={sectionTitle} minHeight={minHeight} /> : (
  <Card title={sectionTitle} minHeight={minHeight}>
    {image
      ? <Image src={image} height={185} />
      : <DefaultImage />
    }

    <Flexbox padding={{ x: 16, y: 14 }}>
      <Title.H4>{title}</Title.H4>
      <Text fontSize={16} lineHeight={1.31} color={textColor} margin={{ y: 8 }}>
        {description}
      </Text>
      <Text fontSize={13} lineHeight={1.85} color={textColor}>
        {author}
      </Text>
    </Flexbox>
  </Card>
)

const { bool, string, number } = PropTypes

Panel.propTypes = {
  loading: bool,
  sectionTitle: string,
  minHeight: number,
  image: string,
  title: string.isRequired,
  description: string.isRequired,
  author: string.isRequired
}

Panel.defaultProps = {
  loading: false,
  minHeight: 320
}

Panel.displayName = 'Panel'

/* @component */
export default Panel
<commit_msg>chore(styleguide): adjust panel component author position<commit_after>import React from 'react'
import styled, { keyframes } from 'styled-components'
import PropTypes from 'prop-types'
import { Card } from '../../'
import Flexbox from '../../layout/Flexbox2/Flexbox2'
import IconColorful from '../../content/IconColorful/IconColorful'
import Image from '../../content/Image/Image'
import Spacing from '../../layout/Spacing/Spacing'
import Text from '../../content/Text/Text'
import Title from '../../content/Title/Title'

const textColor = '#4a4a4a'

const placeHolderShimmer = keyframes`
  0% { -webkit-transform: translateX(-180%) }
  100% { -webkit-transform: translateX(70%) }
`

const BackgroundMasker = styled.div`
  background: #fff;
  position: absolute;
`

const AnimatedBackground = styled.div`
  animation-name: ${placeHolderShimmer};
  animation-duration: 1s;
  animation-fill-mode: forwards;
  animation-iteration-count: infinite;
  animation-timing-function: linear;
  background: #f6f7f8;
  background: linear-gradient(to right, transparent 30%, #dddddd 70%, transparent 100%);
  height: 300px;
  position: relative;
`

const PanelLoading = styled(({ className, minHeight, title }) => (
  <Card title={title} minHeight={minHeight}>

      <AnimatedBackground />
      <BackgroundMasker style={{ top: 182, left: 0, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 185, bottom: 0, width: 18 }} />
      <BackgroundMasker style={{ top: 200, left: 185, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 218, left: 0, right: 0, height: 12 }} />
      <BackgroundMasker style={{ top: 230, left: 254, right: 0, height: 14 }} />
      <BackgroundMasker style={{ top: 244, left: 0, right: 0, height: 18 }} />
      <BackgroundMasker style={{ top: 262, left: 120, right: 0, height: 10 }} />
      <BackgroundMasker style={{ top: 272, left: 0, right: 0, height: 28 }} />

  </Card>
))`
  background: #eeeeee;
  border-color: #e5e6e9 #dfe0e4 #d0d1d5;
  min-height: 300px;
  position: relative;
  overflow: hidden;
`

const DefaultImage = styled(({ className }) => (

    <IconColorful name='community' size={130} />

))`
  display: flex;
  justify-content: center;
  align-items: center;
  height: 185px;
  background-color: #424242;
`

const Panel = ({
  loading,
  image,
  minHeight,
  sectionTitle,
  author,
  title,
  description
}) => loading ? <PanelLoading title={sectionTitle} minHeight={minHeight} /> : (
  <Card title={sectionTitle} minHeight={minHeight}>
    <Flexbox vertical spacing='between'>

        {image
          ? <Image src={image} height={185} />
          : <DefaultImage />
        }

        <Spacing padding={{ x: 16, top: 14 }}>
          <Title.H4>{title}</Title.H4>
          <Spacing margin={{ y: 8 }}>
            <Text fontSize={16} lineHeight={1.31} color={textColor}>
              {description}
            </Text>
          </Spacing>
        </Spacing>

      <Spacing padding={{ x: 16, bottom: 14 }}>
        <Text fontSize={13} lineHeight={1.85} color={textColor}>
          {author}
        </Text>
      </Spacing>
    </Flexbox>
  </Card>
)

const { bool, string, number } = PropTypes

Panel.propTypes = {
  loading: bool,
  sectionTitle: string,
  minHeight: number,
  image: string,
  title: string.isRequired,
  description: string.isRequired,
  author: string.isRequired
}

Panel.defaultProps = {
  loading: false,
  minHeight: 320
}

Panel.displayName = 'Panel'

/* @component */
export default Panel
<|endoftext|>


<commit_before>(function() {
  'use strict';

  angular
    .module('app')
    .controller('SearchCtrl', SearchController);

  SearchController.$inject = ['$scope', 'findApi', 'utils'];

  function SearchController($scope, findApi, utils) {
    var vm = this;
    vm.url = sessionStorage.getItem('url') || null;
    vm.dataAPI = null;
    vm.fields = null;
    vm.testArray = null;
    vm.newItem = {};
    vm.errorData = {};

    vm.itemsPost = [];

    vm.objFormPost = {
      value: ''
    };

    $scope.$watch('vm.url', function() {
      // vm.showResult = false;
      vm.errorData.show = false;
      vm.errorData = {};
    });

    ////////

    vm.getData = function() {

      if(vm.url) {
        sessionStorage.setItem('url', vm.url);

        return findApi.getData(vm.url).then(function(data) {
          if (data.data.length > 0) {
            vm.dataAPI = data.data;
            vm.fields = Object.getOwnPropertyNames(data.data[0]);
          }

          // show section
          vm.showResult = true;

        }, function(error) {
          vm.showResult = false;
          vm.errorData.method = error.config.method;
          vm.errorData.message = error.data.message || error.data;
          vm.errorData.status = error.status;
          vm.errorData.show = true;
        });
      }

    };

    vm.showPostForm = function() {
      if(vm.postForm) {
        vm.postForm = false;
      } else {
        vm.postForm = true;
      }
    };
    vm.hidePostForm = function() {
      if(vm.postForm) {
        vm.postForm = false;
      }
    };

    vm.addItem = function() {
      vm.itemsPost.push({
        key: '',
        value: ''
      });
    };

    vm.postData = function(obj) {
      return findApi.postData(vm.url, obj).then(function(data) {
        if(vm.showResult) {
          return findApi.getData(vm.url).then(function(data) {
            vm.dataAPI = data.data;
            vm.fields = Object.getOwnPropertyNames(data.data[0]);
          });
        }
      });
    };

    vm.deleteData = function(id, param) {
      var finalURL = null;

      vm.url = utils.formatURL(vm.url);
      finalURL = vm.url + id;

      vm.errorData = {};

      if(param === 'input') {
          finalURL = vm.url;
      }

      return findApi.deleteData(finalURL).then(function(data) {
        return findApi.getData(vm.url).then(function(data) {
          vm.dataAPI = data.data;
          vm.fields = Object.getOwnPropertyNames(data.data[0]);

          if(vm.dataAPI.length === 0) {
            vm.showAdd = true;
          }

        });
      });
    };

    vm.updateData = function(data) {
      return findApi.updateData(vm.url + data._id, data).then(function(data) {
        return findApi.getData(vm.url).then(function(data) {
          vm.dataAPI = data.data;
          vm.fields = Object.getOwnPropertyNames(data.data[0]);
        });
      });
    };

  }

}());
<commit_msg>refactor<commit_after>(function() {
  'use strict';

  angular
    .module('app')
    .controller('SearchCtrl', SearchController);

  SearchController.$inject = ['$scope', 'findApi', 'utils'];

  function SearchController($scope, findApi, utils) {
    var vm = this;

    vm.url = sessionStorage.getItem('url') || null;
    vm.dataAPI = null;
    vm.fields = null;
    vm.errorData = {};
    vm.itemsPost = [];

    $scope.$watch('vm.url', function() {
      vm.errorData.show = false;
      vm.errorData = {};
    });

    ////////

    vm.getData = function() {
      if(vm.url) {
        sessionStorage.setItem('url', vm.url);

        return findApi.getData(vm.url).then(function(data) {
          if (data.data.length > 0) {
            vm.dataAPI = data.data;
            vm.fields = data.data[0] ? Object.getOwnPropertyNames(data.data[0]) : null;
          }
          // show section
          vm.showResult = true;
        }, function(error) {
          vm.showResult = false;
          vm.errorData.method = error.config.method;
          vm.errorData.message = error.data.message || error.data;
          vm.errorData.status = error.status;
          vm.errorData.show = true;
        });
      }
    };

    vm.showPostForm = function() {
      if(vm.postForm) {
        vm.postForm = false;
      } else {
        vm.postForm = true;
      }
    };
    vm.hidePostForm = function() {
      if(vm.postForm) {
        vm.postForm = false;
      }
    };

    vm.addItem = function() {
      vm.itemsPost.push({
        key: '',
        value: ''
      });
    };

    vm.removeItem = function() {
      vm.itemsPost.pop();
    };

    vm.postData = function(obj) {
      var newObj = {};

      for(var i=0, size = vm.itemsPost.length; i < size; i++) {
          newObj[vm.itemsPost[i].key] = vm.itemsPost[i].value;
      }

      obj = obj || newObj;

      return findApi.postData(vm.url, obj).then(function(data) {
        if(vm.showResult) {
          return findApi.getData(vm.url).then(function(data) {
            vm.dataAPI = data.data;
            vm.fields = data.data[0] ? Object.getOwnPropertyNames(data.data[0]) : null;
          });
        }
      });

    };

    vm.deleteData = function(id, param) {
      var finalURL = null;

      vm.url = utils.formatURL(vm.url);
      finalURL = vm.url + id;

      vm.errorData = {};

      if(param === 'input') {
          finalURL = vm.url;
      }

      return findApi.deleteData(finalURL).then(function(data) {
        return findApi.getData(vm.url).then(function(data) {
          vm.dataAPI = data.data;
          vm.fields = data.data[0] ? Object.getOwnPropertyNames(data.data[0]) : null;
          vm.showAdd = vm.dataAPI.length ? true : false;
        });
      });
    };

    vm.updateData = function(data) {
      return findApi.updateData(vm.url + data._id, data).then(function(data) {
        return findApi.getData(vm.url).then(function(data) {
          vm.dataAPI = data.data;
          vm.fields = data.data[0] ? Object.getOwnPropertyNames(data.data[0]) : null;
        });
      });
    };

  }

}());
<|endoftext|>


<commit_before>var Lang = A.Lang,
	isArray = Lang.isArray,
	isObject = Lang.isObject,
	isString = Lang.isString,
	isUndefined = Lang.isUndefined,

	_serialize = A.IO.prototype._serialize,

	toInt = Lang.toInt,

	clamp = function(value, min, max) {
		return Math.min(Math.max(value, min), max);
	},

	DateMath = A.DataType.DateMath,

	_DASH = '-',
	_DOT = '.',
	_SPACE = ' ',

	SCHEDULER_EVENT = 'scheduler-event',
	SCHEDULER_EVENT_RECORDER = 'scheduler-event-recorder',

	ACTIVE_VIEW = 'activeView',
	ARROW = 'arrow',
	BODY = 'body',
	BODY_CONTENT = 'bodyContent',
	BORDER_RADIUS = 'borderRadius',
	BOUNDING_BOX = 'boundingBox',
	CANCEL = 'cancel',
	CLICK = 'click',
	CONSTRAIN = 'constrain',
	CONTENT = 'content',
	DATE = 'date',
	DATE_FORMAT = 'dateFormat',
	DELETE = 'delete',
	END_DATE = 'endDate',
	EVENT = 'event',
	FOOTER_CONTENT = 'footerContent',
	FORM = 'form',
	HEADER = 'header',
	ISO_TIME = 'isoTime',
	NODE = 'node',
	OFFSET_HEIGHT = 'offsetHeight',
	OFFSET_WIDTH = 'offsetWidth',
	OVERLAY = 'overlay',
	OVERLAY_OFFSET = 'overlayOffset',
	PX = 'px',
	RECORDER = 'recorder',
	RENDERED = 'rendered',
	REGION = 'region',
	RIGHT = 'right',
	SAVE = 'save',
	SCHEDULER = 'scheduler',
	SCHEDULER_CHANGE = 'schedulerChange',
	SHADOW = 'shadow',
	START_DATE = 'startDate',
	STRINGS = 'strings',
	SUBMIT = 'submit',
	TEMPLATE = 'template',
	TITLE = 'title',
	TOOLBAR = 'toolbar',
	TOP = 'top',
	VISIBLE_CHANGE = 'visibleChange',

	getCN = A.getClassName,

	CSS_SCHEDULER_EVENT = getCN(SCHEDULER_EVENT),
	CSS_SCHEDULER_EVENT_TITLE = getCN(SCHEDULER_EVENT, TITLE),

	CSS_SCHEDULER_EVENT_RECORDER = getCN(SCHEDULER_EVENT, RECORDER),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW, TOP),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_SHADOW = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW, SHADOW),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_BODY = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, BODY),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, CONTENT),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_DATE = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, DATE),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_FORM = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, FORM),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_HEADER = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, HEADER),

	TPL_OVERLAY_BODY_CONTENT = new A.Template(
		'

',
		'

',
		'<input type="hidden" name="startDate" value="{startDate}" />',
		'<input type="hidden" name="endDate" value="{endDate}" />',
		'
',
			'<input class="', CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT, '" name="content" value="{content}" />',
		'
',
		'
',
			'{date}',
		'
'
	),

	TPL_OVERLAY_FORM = '<form class="' + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_FORM + '" id="schedulerEventRecorderForm"></form>';

var SchedulerEventRecorder = A.Component.create({
	NAME: SCHEDULER_EVENT_RECORDER,

	ATTRS: {
		allDay: {
			value: false
		},

		content: {
		},

		duration: {
			value: 60
		},

		dateFormat: {
			validator: isString,
			value: '%a, %B %d,'
		},

		event: {
		},

		eventClass: {
			valueFn: function() {
				return A.SchedulerEvent;
			}
		},

		strings: {
			value: {},
			setter: function(val) {
				return A.merge(
					{
						'delete': 'Delete',
						'description-hint': 'e.g., Dinner at Brian\'s',
						cancel: 'Cancel',
						description: 'Description',
						edit: 'Edit',
						save: 'Save',
						when: 'When'
					},
					val || {}
				);
			},
			validator: isObject
		},

		overlay: {
			validator: isObject,
			value: {
				constrain: true,
				visible: false,
				width: 300,
				zIndex: 500
			}
		},

		// See #2530972
		overlayOffset: {
			value: [15, -38],
			validator: isArray
		},

		template: {
			value: TPL_OVERLAY_BODY_CONTENT
		},

		toolbar: {
			setter: function(val) {
				var instance = this;
				var strings = instance.get(STRINGS);

				return A.merge({
					children: [
						{
							handler: A.bind(instance._handleSaveEvent, instance),
							label: strings[SAVE]
						},
						{
							handler: A.bind(instance._handleCancelEvent, instance),
							label: strings[CANCEL]
						},
						{
							handler: A.bind(instance._handleDeleteEvent, instance),
							label: strings[DELETE]
						}
					]
				}, val || {});
			},
			validator: isObject,
			value: {}
		}
	},

	EXTENDS: A.SchedulerEvent,

	prototype: {

		initializer: function() {
			var instance = this;

			instance.get(NODE).addClass(CSS_SCHEDULER_EVENT_RECORDER);

			instance.publish('cancel', {
				defaultFn: instance._defCancelEventFn
			});

			instance.publish('delete', {
				defaultFn: instance._defDeleteEventFn
			});

			instance.publish('edit', {
				defaultFn: instance._defEditEventFn
			});

			instance.publish('save', {
				defaultFn: instance._defSaveEventFn
			});

			instance.after(SCHEDULER_CHANGE, instance._afterSchedulerChange);

			instance[OVERLAY] = new A.Overlay(instance.get(OVERLAY));
			instance[TOOLBAR] = new A.Toolbar(instance.get(TOOLBAR));

			instance[OVERLAY].on(VISIBLE_CHANGE, A.bind(instance._onOverlayVisibleChange, instance));
		},

		getOverlayContentNode: function() {
			var instance = this;
			var overlayBB = instance[OVERLAY].get(BOUNDING_BOX);

			return overlayBB.one(_DOT + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT);
		},

		getUpdatedSchedulerEvent: function(optAttrMap) {
			var instance = this,
				schedulerEvent = instance.get(EVENT),
				options = {
					silent: !schedulerEvent
				},
				formValues = instance.serializeForm();

			if (!schedulerEvent) {
				schedulerEvent = instance.clone();
			}

			schedulerEvent.set(SCHEDULER, instance.get(SCHEDULER), { silent: true });
			schedulerEvent.setAttrs(A.merge(formValues, optAttrMap), options);

			return schedulerEvent;
		},

		_afterSchedulerChange: function(event) {
			var instance = this;
			var scheduler = event.newVal;
			var schedulerBB = scheduler.get(BOUNDING_BOX);

			schedulerBB.delegate(CLICK, A.bind(instance._onClickSchedulerEvent, instance), _DOT + CSS_SCHEDULER_EVENT);
		},

		_defCancelEventFn: function(event) {
			var instance = this;

			instance.get(NODE).remove();

			instance.hideOverlay();
		},

		_defDeleteEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			scheduler.removeEvents(instance.get(EVENT));

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_defEditEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_defSaveEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			scheduler.addEvents(event.newSchedulerEvent);

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_handleCancelEvent: function(event) {
			var instance = this;

			instance.fire('cancel');

			event.preventDefault();
		},

		_handleDeleteEvent: function(event) {
			var instance = this;

			instance.fire('delete', {
				schedulerEvent: instance.get(EVENT)
			});

			event.preventDefault();
		},

		_handleSaveEvent: function(event) {
			var instance = this,
				eventName = instance.get(EVENT) ? 'edit' : 'save';

			instance.fire(eventName, {
				newSchedulerEvent: instance.getUpdatedSchedulerEvent()
			});

			event.preventDefault();
		},

		_onClickSchedulerEvent: function(event) {
			var instance = this;
			var evt = event.currentTarget.getData(SCHEDULER_EVENT);

			if (evt) {
				instance.set(EVENT, evt, { silent: true });
				instance.showOverlay([event.pageX, event.pageY]);

				instance.get(NODE).remove();
			}
		},

		_onOverlayVisibleChange: function(event) {
			var instance = this;

			if (event.newVal) {
				instance.populateForm();

				if (!instance.get(EVENT)) {
					var overlayContentNode = instance.getOverlayContentNode();

					if (overlayContentNode) {
						setTimeout(function() {
							overlayContentNode.selectText();
						}, 0);
					}
				}
			}
			else {
				instance.set(EVENT, null, { silent: true });

				instance.get(NODE).remove();
			}
		},

		_onSubmitForm: function(event) {
			var instance = this;

			instance._handleSaveEvent(event);
		},

		_renderOverlay: function() {
			var instance = this;
			var strings = instance.get(STRINGS);

			instance[OVERLAY].render();
			instance[TOOLBAR].render();

			var overlayBB = instance[OVERLAY].get(BOUNDING_BOX);
			overlayBB.addClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY);

			instance[OVERLAY].set(FOOTER_CONTENT, instance[TOOLBAR].get(BOUNDING_BOX));

			instance.formNode = A.Node.create(TPL_OVERLAY_FORM);

			instance[OVERLAY].set(BODY_CONTENT, instance.formNode);

			instance.formNode.on(SUBMIT, A.bind(instance._onSubmitForm, instance));
		},

		getFormattedDate: function() {
			var instance = this;
			var dateFormat = instance.get(DATE_FORMAT);
			var evt = (instance.get(EVENT) || instance);

			var endDate = evt.get(END_DATE);
			var scheduler = evt.get(SCHEDULER);
			var startDate = evt.get(START_DATE);
			var fmtHourFn = (scheduler.get(ACTIVE_VIEW).get(ISO_TIME) ? DateMath.toIsoTimeString : DateMath.toUsTimeString);

			return [ evt._formatDate(startDate, dateFormat), fmtHourFn(startDate), _DASH, fmtHourFn(endDate) ].join(_SPACE);
		},

		getTemplateData: function() {
			var instance = this,
				strings = instance.get(STRINGS),
				evt = instance.get(EVENT) || instance,
				content = evt.get(CONTENT);

			if (isUndefined(content)) {
				content = strings['description-hint'];
			}

			return {
				content: content,
				date: instance.getFormattedDate(),
				endDate: evt.get(END_DATE).getTime(),
				startDate: evt.get(START_DATE).getTime()
			};
		},

		hideOverlay: function() {
			var instance = this;

			instance[OVERLAY].hide();
		},

		populateForm: function() {
			var instance = this;

			instance.formNode.setContent(
				instance.get(TEMPLATE).parse(instance.getTemplateData())
			);
		},

		serializeForm: function() {
			var instance = this;

			return A.QueryString.parse(_serialize(instance.formNode.getDOM()));
		},

		showOverlay: function(xy) {
			var instance = this,
				originalXY = xy.concat([]),
				overlay = instance[OVERLAY],
				overlayBB = overlay.get(BOUNDING_BOX);

			if (!instance[OVERLAY].get(RENDERED)) {
				instance._renderOverlay();
			}

			overlay.show();

			var arrows = overlayBB.all(_DOT + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW),
				firstArrow = arrows.item(0),
				firstArrowHeight = firstArrow.get(OFFSET_HEIGHT),
				firstArrowWidth = firstArrow.get(OFFSET_WIDTH);

			arrows.removeClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP).show();

			xy[0] -= overlayBB.get(OFFSET_WIDTH)*0.5;
			xy[1] -= overlayBB.get(OFFSET_HEIGHT) + firstArrowHeight*0.5;

			var constrainedXY = overlay.getConstrainedXY(xy);

			if (constrainedXY[1] !== xy[1]) {
				xy[1] = originalXY[1] + firstArrowHeight*0.5;

				arrows.addClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP);
			}

			xy = overlay.getConstrainedXY(xy);

			overlay.set('xy', xy);

			var arrowX = clamp(originalXY[0] - firstArrowWidth*0.5, xy[0], xy[0] + overlayBB.get(OFFSET_WIDTH));

			arrows.setX(arrowX);
		}
	}
});

A.SchedulerEventRecorder = SchedulerEventRecorder;<commit_msg>AUI-776 Allow pressing escape or clicking outside the event overlay to cancel creating a new event<commit_after>var Lang = A.Lang,
	isArray = Lang.isArray,
	isObject = Lang.isObject,
	isString = Lang.isString,
	isUndefined = Lang.isUndefined,

	_serialize = A.IO.prototype._serialize,

	toInt = Lang.toInt,

	clamp = function(value, min, max) {
		return Math.min(Math.max(value, min), max);
	},

	DateMath = A.DataType.DateMath,

	_DASH = '-',
	_DOT = '.',
	_SPACE = ' ',

	SCHEDULER_EVENT = 'scheduler-event',
	SCHEDULER_EVENT_RECORDER = 'scheduler-event-recorder',

	ACTIVE_VIEW = 'activeView',
	ARROW = 'arrow',
	BODY = 'body',
	BODY_CONTENT = 'bodyContent',
	BORDER_RADIUS = 'borderRadius',
	BOUNDING_BOX = 'boundingBox',
	CANCEL = 'cancel',
	CLICK = 'click',
	CONSTRAIN = 'constrain',
	CONTENT = 'content',
	DATE = 'date',
	DATE_FORMAT = 'dateFormat',
	DELETE = 'delete',
	END_DATE = 'endDate',
	EVENT = 'event',
	FOOTER_CONTENT = 'footerContent',
	FORM = 'form',
	HEADER = 'header',
	ISO_TIME = 'isoTime',
	KEY_DOWN = 'keydown',
	NODE = 'node',
	OFFSET_HEIGHT = 'offsetHeight',
	OFFSET_WIDTH = 'offsetWidth',
	OVERLAY = 'overlay',
	OVERLAY_OFFSET = 'overlayOffset',
	PX = 'px',
	RECORDER = 'recorder',
	RENDERED = 'rendered',
	REGION = 'region',
	RIGHT = 'right',
	SAVE = 'save',
	SCHEDULER = 'scheduler',
	SCHEDULER_CHANGE = 'schedulerChange',
	SHADOW = 'shadow',
	START_DATE = 'startDate',
	STRINGS = 'strings',
	SUBMIT = 'submit',
	TEMPLATE = 'template',
	TITLE = 'title',
	TOOLBAR = 'toolbar',
	TOP = 'top',
	VISIBLE_CHANGE = 'visibleChange',

	getCN = A.getClassName,

	CSS_SCHEDULER_EVENT = getCN(SCHEDULER_EVENT),
	CSS_SCHEDULER_EVENT_TITLE = getCN(SCHEDULER_EVENT, TITLE),

	CSS_SCHEDULER_EVENT_RECORDER = getCN(SCHEDULER_EVENT, RECORDER),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW, TOP),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_SHADOW = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, ARROW, SHADOW),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_BODY = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, BODY),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, CONTENT),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_DATE = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, DATE),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_FORM = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, FORM),
	CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_HEADER = getCN(SCHEDULER, EVENT, RECORDER, OVERLAY, HEADER),

	TPL_OVERLAY_BODY_CONTENT = new A.Template(
		'

',
		'

',
		'<input type="hidden" name="startDate" value="{startDate}" />',
		'<input type="hidden" name="endDate" value="{endDate}" />',
		'
',
			'<input class="', CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT, '" name="content" value="{content}" />',
		'
',
		'
',
			'{date}',
		'
'
	),

	TPL_OVERLAY_FORM = '<form class="' + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_FORM + '" id="schedulerEventRecorderForm"></form>';

var SchedulerEventRecorder = A.Component.create({
	NAME: SCHEDULER_EVENT_RECORDER,

	ATTRS: {
		allDay: {
			value: false
		},

		content: {
		},

		duration: {
			value: 60
		},

		dateFormat: {
			validator: isString,
			value: '%a, %B %d,'
		},

		event: {
		},

		eventClass: {
			valueFn: function() {
				return A.SchedulerEvent;
			}
		},

		strings: {
			value: {},
			setter: function(val) {
				return A.merge(
					{
						'delete': 'Delete',
						'description-hint': 'e.g., Dinner at Brian\'s',
						cancel: 'Cancel',
						description: 'Description',
						edit: 'Edit',
						save: 'Save',
						when: 'When'
					},
					val || {}
				);
			},
			validator: isObject
		},

		overlay: {
			validator: isObject,
			value: {
				constrain: true,
				visible: false,
				width: 300,
				zIndex: 500
			}
		},

		// See #2530972
		overlayOffset: {
			value: [15, -38],
			validator: isArray
		},

		template: {
			value: TPL_OVERLAY_BODY_CONTENT
		},

		toolbar: {
			setter: function(val) {
				var instance = this;
				var strings = instance.get(STRINGS);

				return A.merge({
					children: [
						{
							handler: A.bind(instance._handleSaveEvent, instance),
							label: strings[SAVE]
						},
						{
							handler: A.bind(instance._handleCancelEvent, instance),
							label: strings[CANCEL]
						},
						{
							handler: A.bind(instance._handleDeleteEvent, instance),
							label: strings[DELETE]
						}
					]
				}, val || {});
			},
			validator: isObject,
			value: {}
		}
	},

	EXTENDS: A.SchedulerEvent,

	prototype: {

		initializer: function() {
			var instance = this;

			instance.get(NODE).addClass(CSS_SCHEDULER_EVENT_RECORDER);

			instance.publish('cancel', {
				defaultFn: instance._defCancelEventFn
			});

			instance.publish('delete', {
				defaultFn: instance._defDeleteEventFn
			});

			instance.publish('edit', {
				defaultFn: instance._defEditEventFn
			});

			instance.publish('save', {
				defaultFn: instance._defSaveEventFn
			});

			instance.after(SCHEDULER_CHANGE, instance._afterSchedulerChange);

			instance[OVERLAY] = new A.Overlay(instance.get(OVERLAY));
			instance[TOOLBAR] = new A.Toolbar(instance.get(TOOLBAR));

			instance[OVERLAY].on(VISIBLE_CHANGE, A.bind(instance._onOverlayVisibleChange, instance));
		},

		getOverlayContentNode: function() {
			var instance = this;
			var overlayBB = instance[OVERLAY].get(BOUNDING_BOX);

			return overlayBB.one(_DOT + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_CONTENT);
		},

		getUpdatedSchedulerEvent: function(optAttrMap) {
			var instance = this,
				schedulerEvent = instance.get(EVENT),
				options = {
					silent: !schedulerEvent
				},
				formValues = instance.serializeForm();

			if (!schedulerEvent) {
				schedulerEvent = instance.clone();
			}

			schedulerEvent.set(SCHEDULER, instance.get(SCHEDULER), { silent: true });
			schedulerEvent.setAttrs(A.merge(formValues, optAttrMap), options);

			return schedulerEvent;
		},

		_afterSchedulerChange: function(event) {
			var instance = this;
			var scheduler = event.newVal;
			var schedulerBB = scheduler.get(BOUNDING_BOX);

			schedulerBB.delegate(CLICK, A.bind(instance._onClickSchedulerEvent, instance), _DOT + CSS_SCHEDULER_EVENT);
		},

		_defCancelEventFn: function(event) {
			var instance = this;

			instance.get(NODE).remove();

			instance.hideOverlay();
		},

		_defDeleteEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			scheduler.removeEvents(instance.get(EVENT));

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_defEditEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_defSaveEventFn: function(event) {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);

			scheduler.addEvents(event.newSchedulerEvent);

			instance.hideOverlay();

			scheduler.syncEventsUI();
		},

		_handleCancelEvent: function(event) {
			var instance = this;

			instance.fire('cancel');

			event.preventDefault();
		},

		_handleClickOutSide: function(event) {
			var instance = this;

			instance.fire('cancel');
		},

		_handleDeleteEvent: function(event) {
			var instance = this;

			instance.fire('delete', {
				schedulerEvent: instance.get(EVENT)
			});

			event.preventDefault();
		},

		_handleEscapeEvent: function(event) {
			var instance = this;

			if (instance[OVERLAY].get(RENDERED) && (event.keyCode == A.Event.KeyMap.ESC)) {
				instance.fire('cancel');

				event.preventDefault();
			}
		},

		_handleSaveEvent: function(event) {
			var instance = this,
				eventName = instance.get(EVENT) ? 'edit' : 'save';

			instance.fire(eventName, {
				newSchedulerEvent: instance.getUpdatedSchedulerEvent()
			});

			event.preventDefault();
		},

		_onClickSchedulerEvent: function(event) {
			var instance = this;
			var evt = event.currentTarget.getData(SCHEDULER_EVENT);

			if (evt) {
				instance.set(EVENT, evt, { silent: true });
				instance.showOverlay([event.pageX, event.pageY]);

				instance.get(NODE).remove();
			}
		},

		_onOverlayVisibleChange: function(event) {
			var instance = this;

			if (event.newVal) {
				instance.populateForm();

				if (!instance.get(EVENT)) {
					var overlayContentNode = instance.getOverlayContentNode();

					if (overlayContentNode) {
						setTimeout(function() {
							overlayContentNode.selectText();
						}, 0);
					}
				}
			}
			else {
				instance.set(EVENT, null, { silent: true });

				instance.get(NODE).remove();
			}
		},

		_onSubmitForm: function(event) {
			var instance = this;

			instance._handleSaveEvent(event);
		},

		_renderOverlay: function() {
			var instance = this;
			var scheduler = instance.get(SCHEDULER);
			var schedulerBB = scheduler.get(BOUNDING_BOX);
			var strings = instance.get(STRINGS);

			instance[OVERLAY].render(schedulerBB);
			instance[TOOLBAR].render(schedulerBB);

			var overlayBB = instance[OVERLAY].get(BOUNDING_BOX);
			overlayBB.addClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY);

			instance[OVERLAY].set(FOOTER_CONTENT, instance[TOOLBAR].get(BOUNDING_BOX));

			instance.formNode = A.Node.create(TPL_OVERLAY_FORM);

			instance[OVERLAY].set(BODY_CONTENT, instance.formNode);

			instance.formNode.on(SUBMIT, A.bind(instance._onSubmitForm, instance));

			scheduler.get(BOUNDING_BOX).on('clickoutside', A.bind(instance._handleClickOutSide, instance));
		},

		getFormattedDate: function() {
			var instance = this;
			var dateFormat = instance.get(DATE_FORMAT);
			var evt = (instance.get(EVENT) || instance);

			var endDate = evt.get(END_DATE);
			var scheduler = evt.get(SCHEDULER);
			var startDate = evt.get(START_DATE);
			var fmtHourFn = (scheduler.get(ACTIVE_VIEW).get(ISO_TIME) ? DateMath.toIsoTimeString : DateMath.toUsTimeString);

			return [ evt._formatDate(startDate, dateFormat), fmtHourFn(startDate), _DASH, fmtHourFn(endDate) ].join(_SPACE);
		},

		getTemplateData: function() {
			var instance = this,
				strings = instance.get(STRINGS),
				evt = instance.get(EVENT) || instance,
				content = evt.get(CONTENT);

			if (isUndefined(content)) {
				content = strings['description-hint'];
			}

			return {
				content: content,
				date: instance.getFormattedDate(),
				endDate: evt.get(END_DATE).getTime(),
				startDate: evt.get(START_DATE).getTime()
			};
		},

		hideOverlay: function() {
			var instance = this;

			instance[OVERLAY].hide();
		},

		populateForm: function() {
			var instance = this;

			instance.formNode.setContent(
				instance.get(TEMPLATE).parse(instance.getTemplateData())
			);
		},

		serializeForm: function() {
			var instance = this;

			return A.QueryString.parse(_serialize(instance.formNode.getDOM()));
		},

		showOverlay: function(xy) {
			var instance = this,
				originalXY = xy.concat([]),
				overlay = instance[OVERLAY],
				overlayBB = overlay.get(BOUNDING_BOX);

			if (!instance[OVERLAY].get(RENDERED)) {
				instance._renderOverlay();
			}

			overlay.show();

			instance.handleEscapeEvent = A.on(KEY_DOWN, A.bind(instance._handleEscapeEvent, instance));

			var arrows = overlayBB.all(_DOT + CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW),
				firstArrow = arrows.item(0),
				firstArrowHeight = firstArrow.get(OFFSET_HEIGHT),
				firstArrowWidth = firstArrow.get(OFFSET_WIDTH);

			arrows.removeClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP).show();

			xy[0] -= overlayBB.get(OFFSET_WIDTH)*0.5;
			xy[1] -= overlayBB.get(OFFSET_HEIGHT) + firstArrowHeight*0.5;

			var constrainedXY = overlay.getConstrainedXY(xy);

			if (constrainedXY[1] !== xy[1]) {
				xy[1] = originalXY[1] + firstArrowHeight*0.5;

				arrows.addClass(CSS_SCHEDULER_EVENT_RECORDER_OVERLAY_ARROW_TOP);
			}

			xy = overlay.getConstrainedXY(xy);

			overlay.set('xy', xy);

			var arrowX = clamp(originalXY[0] - firstArrowWidth*0.5, xy[0], xy[0] + overlayBB.get(OFFSET_WIDTH));

			arrows.setX(arrowX);
		}
	}
});

A.SchedulerEventRecorder = SchedulerEventRecorder;<|endoftext|>


<commit_before>/**
 * Created by tlzhang on 2015/5/11.
 */
(function(document,undefined,$){
    var Controller = (function(){
        var controller = function(){};
        controller.fn = controller.prototype;

        controller.fn.proxy = function(func,obj,args,funcBef){
            if(!func) return;
            var self = this;
            return (function(){
                if(typeof funcBef === "function")
                    funcBef.call(obj || self);
                return func.call(obj || self,args);
            });
        };

        controller.fn.load = function(func){
            return $(this.proxy(func));
        };

        controller.fn.include = function(obj){
            return $.extend(this,obj);
        };

        return controller;
    })();

    var Tree = (function(){

        var opts = {
            'folder-cls':'tree-icon folder',
            'file-cls':'tree-icon file',
            'root-id':'/_anchor',
            'elem-id':'/',
            'root-text':'root',
            'node-name':'新节点',
            'folder':'folder',
            'file':'file',
            'isExpandAll':false
        };

        var defaultMenuOptions = {
            menu_box_cls:'',
            menu_body_cls:'',
            menu_ul_cls:'',
            menu_li_cls:'',
            menu_li_a_cls:'',
            menu_arrow_cls:'',
            onContextMenu:function(){
                return true;
            },
            data:[{
                text: '新建',
                children: [{
                    text:'文件夹',

                    click:function(){
                        if(!this._obj) return;
                    }
                },{
                    text:'文件',

                    click:function(){
                        if(!this._obj) return;
                    }
                }]
            },{
                text:'重命名',

                click:function(){
                    if(!this) return;
                }
            },{
                text:'删除',

                click:function(){
                    if(!this) return;
                }
            }]
        };

        function tree(elem,options){
            if(typeof options != 'object')
                return;

            this._options = options;
            this._elem = elem;
            this._isExpandAll = this._options.isExpandAll || opts['isExpandAll'];
            this._controller = new Controller;
            this._initTree.call(this);
        }

        tree.prototype = function(){

            /**
             * create root
             */
            _createRoot = function(){
                var root = document.createElement("div");
                root.className = 'root';
                var i  = document.createElement("i");
                i.className = 'tree-icon tree-ocl';

                var a = document.createElement("a");
                a.className = 'tree-root tree-disabled';
                a.href = 'javascript:;';
                a.id = this._options['id']?this._options['id']:opts['root-id'];

                var a_i = document.createElement("i");
                a_i.className = 'tree-icon folder';
                a.appendChild(a_i);

                var a_span = document.createElement("span");
                a_span.innerHTML = this._options['text']?this._options['text']:opts['root-text'];
                a.appendChild(a_span);

                root.appendChild(i);
                root.appendChild(a);
                return root;
            };

            _createNode = function(option){
                var node = document.createElement("li");

                node.id = option['id']?option['id']:'';

                var node_i = document.createElement("i");
                node_i.className = 'tree-icon tree-ocl';

                var node_a = document.createElement("a");
                node_a.className = 'tree-anchor';
                node_a.href = 'javascript:;';

                var node_a_i = document.createElement("i");
                var clsName = option['status']?option['status']:opts['folder'];
                node_a_i.className = 'tree-icon ' + clsName;

                if(clsName === "file"){
                    if(this._isExpandAll)
                        node.className = 'tree-node tree-open tree-leaf';
                    else
                        node.className = 'tree-node tree-closed tree-leaf';
                }else{
                    if(this._isExpandAll)
                        node.className = 'tree-node tree-open';
                    else
                        node.className = 'tree-node tree-closed';
                }

                var node_a_span = document.createElement("span");
                node_a_span.innerHTML = option['text']?option['text']:opts['node-name'];

                node_a.appendChild(node_a_i);
                node_a.appendChild(node_a_span);

                node.appendChild(node_i);
                node.appendChild(node_a);
                return node;
            };

            _createGroup = function(){
                var group = document.createElement("ul");
                group.className = 'tree-children';
                if(!this._isExpandAll){
                    group.style['display'] = "none";
                }
                return group;
            };

            /**
             * create container
             */
            _createContainer = function(){
                var container = document.createElement("ul");
                container.className = 'tree-container-ul tree-children tree-striped';
                return container;
            };

            _createContainerChildren = function(){
                var containerChildren = document.createElement("li");
                if(this._isExpandAll)
                    containerChildren.className = 'tree-node tree-open tree-last';
                else
                    containerChildren.className = 'tree-node tree-closed tree-last';
                containerChildren.id = opts['elem-id'];
                return containerChildren;
            };

            _createTreeNode = function(children,group,node){
                var allNode;
                var self = this;
                var vGroup;
                var getNode = function(children,group,node){
                    for(var i = 0;i<children.length;i++){
                        if(!_isPropNull(children[i])){
                            continue;
                        }
                        var node_ = _createNode.call(self,children[i],children[i]['text']);
                        if(node){
                            if(!vGroup) vGroup = _createGroup.call(self);
                            vGroup.appendChild(node_);
                            node.appendChild(vGroup);
                            if(i === (children.length - 1)){
                                vGroup = null;
                                group = null;
                            }
                        }

                        if(!node)
                            allNode = node_;

                        if(!group){
                            group = _createGroup.call(self);
                        }

                        if(children[i]['children']){
                            getNode.call(self,children[i]['children'],group,node_);
                        }else{
                            var clsName = node_.className;
                            if(i === (children.length - 1)){
                                if(clsName.indexOf('tree-last') == -1)
                                    clsName  += " tree-last";
                            }

                            node_.className = clsName;
                            group.appendChild(allNode);
                            self.containerChildren.appendChild(group);
                            group = null;
                        }
                    }
                };

                getNode(children,group,node);
            };

            _initTree = function(){
                this._elem = this._elem.length?this._elem[0]:this._elem;
                this._elem = _initTreeProp.call(this,this._elem);
                this.container = _createContainer.call(this);
                this.containerChildren = _createContainerChildren.call(this);
                var root = _createRoot.call(this);
                this.containerChildren.appendChild(root);

                _createTreeNode.call(this,this._options['children']);

                this.container.appendChild(this.containerChildren);
                this._elem.appendChild(this.container);
                _addContextMenu.call(this);

                //set last one tree-last
                var _node = $(this._elem).find('.root').siblings("ul:last");
                if(_node){
                    var _li = _node.children("li:last").get(0);
                    if(_li){
                        if(!$(_li).hasClass('tree-last')){
                            $(_li).addClass('tree-last');
                        }
                    }
                }

                //set no children class tree-closed
                var _node = $(this._elem).find('.root').siblings("ul");
                if(_node && _node.length > 0){
                    _node.each(function(){
                        var _li = $(this).children("li:last").get(0);
                        var _ul = $(_li).children('ul');
                        var isHaveChildren = false;
                        if(_ul && _ul.length > 0){
                            if($(_ul.get(0)).find('li').length > 0){
                                isHaveChildren = true;
                            }
                        }

                        if(_li){
                            if(!isHaveChildren){
                                if($(_li).hasClass('tree-open')){
                                    $(_li).removeClass('tree-open');
                                }

                                if(!$(_li).hasClass('tree-closed')){
                                    $(_li).addClass('tree-closed');
                                }
                            }
                        }
                    });
                }

                _bindIClick.call(this);
            };

            /**
             * bind contextMenu event
             */
            _addContextMenu = function(){

                $(this._elem).bind('contextmenu',function(e){
                    e.stopPropagation();
                    return false;
                });

                $(this._elem).find('.root').siblings("ul").each(function(){
                    var a = $(this).find("a");
                    if(a.find("i").length > 0){
                        var i = a.find("i");
                        if(i.hasClass('folder')){
                            a.contextMenu(defaultMenuOptions);
                        }
                    }
                });
            };

            _bindIClick = function(){
                var self = this;
                $(this._elem).find(".tree-node").each(function(){
                    if($(this).hasClass("tree-leaf")) return true;
                    var i = $(this).children('i.tree-ocl').get(0);
                    if(!i) return true;
                    //var i = $(this).find("i.tree-ocl");
                    console.log(111);
                    $(i).bind('click',self._controller.proxy(_iClick,$(i)));
                });

                $(self._elem).find("div.root i.tree-ocl").bind('click',self._controller.proxy(_rootClick,$(self._elem).find("div.root")));
            };

            _iClick = function(){
                if($(this).siblings("ul.tree-children").is(":hidden")){
                    if($(this).closest("li.tree-node").hasClass('tree-closed')){
                        $(this).closest("li.tree-node").removeClass('tree-closed');
                        $(this).closest("li.tree-node").addClass('tree-open');
                    }
                    $(this).siblings("ul.tree-children").show();
                }else{
                    if($(this).closest("li.tree-node").hasClass('tree-open')){
                        $(this).closest("li.tree-node").removeClass('tree-open');
                        $(this).closest("li.tree-node").addClass('tree-closed');
                    }
                    $(this).siblings("ul.tree-children").hide();
                }
            };

            _rootClick = function(){
                if($(this).closest("li.tree-node").hasClass('tree-open')){
                    if($(this).closest("li.tree-node").hasClass('tree-open')){
                        $(this).closest("li.tree-node").removeClass('tree-open');
                        $(this).closest("li.tree-node").addClass('tree-closed');
                    }
                    $(this).siblings("ul.tree-children").hide();
                }else if($(this).closest("li.tree-node").hasClass('tree-closed')){
                    if($(this).closest("li.tree-node").hasClass('tree-closed')){
                        $(this).closest("li.tree-node").removeClass('tree-closed');
                        $(this).closest("li.tree-node").addClass('tree-open');
                    }
                    $(this).siblings("ul.tree-children").show();
                }

                $(this).siblings("ul.tree-children").each(function(){
                    $(this).find("li").each(function(){
                       if($(this).hasClass("tree-open")){
                           $(this).removeClass("tree-open")
                       }

                       if(!$(this).hasClass("tree-closed")){
                           $(this).addClass("tree-closed")
                       }

                        $(this).find("ul.tree-children").hide();
                    });
                });
            };

            _initTreeProp = function(elem){
                elem.className = 'tree tree-default tree-default-small';
                return elem;
            };

            _isLoadCSSStyle = function(){
                try{
                    var es = document.getElementsByTagName('link');
                    for(var i=0;i<es.length;i++)
                        if(es[i]['href'].indexOf('style.css')!=-1)
                            return true;
                    return false;
                }catch(e){
                    throw new Error("can not load " + 'style.css');
                }
            };

            /**
             * judge object is or not null.
             * @param object
             */
            _isPropNull = function(object){
                if(typeof object === "object" && !(object instanceof Array)){
                    var hasProp = false;
                    for(var prop in object){
                        hasProp = true;
                        break;
                    }

                    if(hasProp){
                        return true;
                    }else{
                        return false;
                    }
                }

                return false;
            };

            return{
                _initTree:this._initTree
            };
        }();

        return tree;

    })(window,document,undefined,jQuery);

    $.fn.tree = function(options){
        if(!options) return;
        return new Tree(this,options);
    }

})(document,undefined,jQuery);

<commit_msg>Update tree.js<commit_after>/**
 * Created by tlzhang on 2015/5/11.
 */
(function(document,undefined,$){
    var Controller = (function(){
        var controller = function(){};
        controller.fn = controller.prototype;

        controller.fn.proxy = function(func,obj,args,funcBef){
            if(!func) return;
            var self = this;
            return (function(){
                if(typeof funcBef === "function")
                    funcBef.call(obj || self);
                return func.call(obj || self,args);
            });
        };

        controller.fn.load = function(func){
            return $(this.proxy(func));
        };

        controller.fn.include = function(obj){
            return $.extend(this,obj);
        };

        return controller;
    })();

    var Tree = (function(){

        var opts = {
            'folder-cls':'tree-icon folder',
            'file-cls':'tree-icon file',
            'root-id':'/_anchor',
            'elem-id':'/',
            'root-text':'root',
            'node-name':'新节点',
            'folder':'folder',
            'file':'file',
            'isExpandAll':false
        };

        var defaultMenuOptions = {
            menu_box_cls:'',
            menu_body_cls:'',
            menu_ul_cls:'',
            menu_li_cls:'',
            menu_li_a_cls:'',
            menu_arrow_cls:'',
            onContextMenu:function(){
                return true;
            },
            data:[{
                text: '新建',
                children: [{
                    text:'文件夹',

                    click:function(){
                        if(!this._obj) return;
                    }
                },{
                    text:'文件',

                    click:function(){
                        if(!this._obj) return;
                    }
                }]
            },{
                text:'重命名',

                click:function(){
                    if(!this) return;
                }
            },{
                text:'删除',

                click:function(){
                    if(!this) return;
                }
            }]
        };

        function tree(elem,options){
            if(typeof options != 'object')
                return;

            this._options = options;
            this._elem = elem;
            this._isExpandAll = this._options.isExpandAll || opts['isExpandAll'];
            this._controller = new Controller;
            this._initTree.call(this);
        }

        tree.prototype = function(){

            /**
             * create root
             */
            _createRoot = function(){
                var root = document.createElement("div");
                root.className = 'root';
                var i  = document.createElement("i");
                i.className = 'tree-icon tree-ocl';

                var a = document.createElement("a");
                a.className = 'tree-root tree-disabled';
                a.href = 'javascript:;';
                a.id = this._options['id']?this._options['id']:opts['root-id'];

                var a_i = document.createElement("i");
                a_i.className = 'tree-icon folder';
                a.appendChild(a_i);

                var a_span = document.createElement("span");
                a_span.innerHTML = this._options['text']?this._options['text']:opts['root-text'];
                a.appendChild(a_span);

                root.appendChild(i);
                root.appendChild(a);
                return root;
            };

            _createNode = function(option){
                var node = document.createElement("li");

                node.id = option['id']?option['id']:'';

                var node_i = document.createElement("i");
                node_i.className = 'tree-icon tree-ocl';

                var node_a = document.createElement("a");
                node_a.className = 'tree-anchor';
                node_a.href = 'javascript:;';

                var node_a_i = document.createElement("i");
                var clsName = option['status']?option['status']:opts['folder'];
                node_a_i.className = 'tree-icon ' + clsName;

                if(clsName === "file"){
                    if(this._isExpandAll)
                        node.className = 'tree-node tree-open tree-leaf';
                    else
                        node.className = 'tree-node tree-closed tree-leaf';
                }else{
                    if(this._isExpandAll)
                        node.className = 'tree-node tree-open';
                    else
                        node.className = 'tree-node tree-closed';
                }

                var node_a_span = document.createElement("span");
                node_a_span.innerHTML = option['text']?option['text']:opts['node-name'];

                node_a.appendChild(node_a_i);
                node_a.appendChild(node_a_span);

                node.appendChild(node_i);
                node.appendChild(node_a);
                return node;
            };

            _createGroup = function(){
                var group = document.createElement("ul");
                group.className = 'tree-children';
                if(!this._isExpandAll){
                    group.style['display'] = "none";
                }
                return group;
            };

            /**
             * create container
             */
            _createContainer = function(){
                var container = document.createElement("ul");
                container.className = 'tree-container-ul tree-children tree-striped';
                return container;
            };

            _createContainerChildren = function(){
                var containerChildren = document.createElement("li");
                if(this._isExpandAll)
                    containerChildren.className = 'tree-node tree-open tree-last';
                else
                    containerChildren.className = 'tree-node tree-closed tree-last';
                containerChildren.id = opts['elem-id'];
                return containerChildren;
            };

            _createTreeNode = function(children,group,node){
                var allNode;
                var self = this;
                var vGroup;
                var getNode = function(children,group,node){
                    for(var i = 0;i<children.length;i++){
                        if(!_isPropNull(children[i])){
                            continue;
                        }
                        var node_ = _createNode.call(self,children[i],children[i]['text']);
                        if(node){
                            if(!vGroup) vGroup = _createGroup.call(self);
                            vGroup.appendChild(node_);
                            node.appendChild(vGroup);
                            if(i === (children.length - 1)){
                                vGroup = null;
                                group = null;
                            }
                        }

                        if(!node)
                            allNode = node_;

                        if(!group){
                            group = _createGroup.call(self);
                        }

                        if(children[i]['children']){
                            getNode.call(self,children[i]['children'],group,node_);
                        }else{
                            var clsName = node_.className;
                            if(i === (children.length - 1)){
                                if(clsName.indexOf('tree-last') == -1)
                                    clsName  += " tree-last";
                            }

                            node_.className = clsName;
                            group.appendChild(allNode);
                            self.containerChildren.appendChild(group);
                            group = null;
                        }
                    }
                };

                getNode(children,group,node);
            };

            _initTree = function(){
                this._elem = this._elem.length?this._elem[0]:this._elem;
                this._elem = _initTreeProp.call(this,this._elem);
                this.container = _createContainer.call(this);
                this.containerChildren = _createContainerChildren.call(this);
                var root = _createRoot.call(this);
                this.containerChildren.appendChild(root);

                _createTreeNode.call(this,this._options['children']);

                this.container.appendChild(this.containerChildren);
                this._elem.appendChild(this.container);
                _addContextMenu.call(this);

                //set last one tree-last
                var _node = $(this._elem).find('.root').siblings("ul:last");
                if(_node){
                    var _li = _node.children("li:last").get(0);
                    if(_li){
                        if(!$(_li).hasClass('tree-last')){
                            $(_li).addClass('tree-last');
                        }
                    }
                }

                //set no children class tree-closed
                var _node = $(this._elem).find('.root').siblings("ul");
                if(_node && _node.length > 0){
                    _node.each(function(){
                        var _li = $(this).children("li:last").get(0);
                        var _ul = $(_li).children('ul');
                        var isHaveChildren = false;
                        if(_ul && _ul.length > 0){
                            if($(_ul.get(0)).find('li').length > 0){
                                isHaveChildren = true;
                            }
                        }

                        if(_li){
                            if(!isHaveChildren){
                                if($(_li).hasClass('tree-open')){
                                    $(_li).removeClass('tree-open');
                                }

                                if(!$(_li).hasClass('tree-closed')){
                                    $(_li).addClass('tree-closed');
                                }
                            }
                        }
                    });
                }

                _bindIClick.call(this);
            };

            /**
             * bind contextMenu event
             */
            _addContextMenu = function(){

                $(this._elem).bind('contextmenu',function(e){
                    e.stopPropagation();
                    return false;
                });

                $(this._elem).find('.root').siblings("ul").each(function(){
                    var a = $(this).find("a.tree-anchor");
                    if(!a || a.length == 0) return true;//continue;
                    a.each(function(){
                        if($(this).find("i").length > 0){
                            var i = $(this).find("i.tree-icon");
                            if(i.hasClass('folder')){
                                $(this).contextMenu(defaultMenuOptions);
                            }
                        }
                    });

                });
            };

            _bindIClick = function(){
                var self = this;
                $(this._elem).find(".tree-node").each(function(){
                    if($(this).hasClass("tree-leaf")) return true;
                    var i = $(this).children('i.tree-ocl').get(0);
                    if(!i) return true;
                    //var i = $(this).find("i.tree-ocl");
                    console.log(111);
                    $(i).bind('click',self._controller.proxy(_iClick,$(i)));
                });

                $(self._elem).find("div.root i.tree-ocl").bind('click',self._controller.proxy(_rootClick,$(self._elem).find("div.root")));
            };

            _iClick = function(){
                if($(this).siblings("ul.tree-children").is(":hidden")){
                    if($(this).closest("li.tree-node").hasClass('tree-closed')){
                        $(this).closest("li.tree-node").removeClass('tree-closed');
                        $(this).closest("li.tree-node").addClass('tree-open');
                    }
                    $(this).siblings("ul.tree-children").show();
                }else{
                    if($(this).closest("li.tree-node").hasClass('tree-open')){
                        $(this).closest("li.tree-node").removeClass('tree-open');
                        $(this).closest("li.tree-node").addClass('tree-closed');
                    }
                    $(this).siblings("ul.tree-children").hide();
                }
            };

            _rootClick = function(){
                if($(this).closest("li.tree-node").hasClass('tree-open')){
                    if($(this).closest("li.tree-node").hasClass('tree-open')){
                        $(this).closest("li.tree-node").removeClass('tree-open');
                        $(this).closest("li.tree-node").addClass('tree-closed');
                    }
                    $(this).siblings("ul.tree-children").hide();
                }else if($(this).closest("li.tree-node").hasClass('tree-closed')){
                    /*if(!$(this).hasClass("tree-loading")){//loading
                        $(this).addClass("tree-loading");
                    }*/
                    if($(this).closest("li.tree-node").hasClass('tree-closed')){
                        $(this).closest("li.tree-node").removeClass('tree-closed');
                        $(this).closest("li.tree-node").addClass('tree-open');
                    }

                    /*if($(this).hasClass("tree-loading")){//loading
                        $(this).removeClass("tree-loading");
                    }*/
                    $(this).siblings("ul.tree-children").show();
                }

                $(this).siblings("ul.tree-children").each(function(){
                    $(this).find("li").each(function(){
                       if($(this).hasClass("tree-open")){
                           $(this).removeClass("tree-open")
                       }

                       if(!$(this).hasClass("tree-closed")){
                           $(this).addClass("tree-closed")
                       }

                        $(this).find("ul.tree-children").hide();
                    });
                });
            };

            _initTreeProp = function(elem){
                elem.className = 'tree tree-default tree-default-small';
                return elem;
            };

            _isLoadCSSStyle = function(){
                try{
                    var es = document.getElementsByTagName('link');
                    for(var i=0;i<es.length;i++)
                        if(es[i]['href'].indexOf('style.css')!=-1)
                            return true;
                    return false;
                }catch(e){
                    throw new Error("can not load " + 'style.css');
                }
            };

            /**
             * judge object is or not null.
             * @param object
             */
            _isPropNull = function(object){
                if(typeof object === "object" && !(object instanceof Array)){
                    var hasProp = false;
                    for(var prop in object){
                        hasProp = true;
                        break;
                    }

                    if(hasProp){
                        return true;
                    }else{
                        return false;
                    }
                }

                return false;
            };

            return{
                _initTree:this._initTree
            };
        }();

        return tree;

    })(window,document,undefined,jQuery);

    $.fn.tree = function(options){
        if(!options) return;
        return new Tree(this,options);
    }

})(document,undefined,jQuery);

<|endoftext|>


<commit_before>'use strict';

const Brakes = require('../lib/Brakes');
const http = require('http');
const timer = 100;
let successRate = 2;
let iterations = 0;

function unreliableServiceCall() {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      iterations++;
      if (iterations === 10) {
        successRate = 0.6;
      }
      else if (iterations === 100) {
        successRate = 0.1;
      }
      else if (iterations === 200) {
        successRate = 1;
      }

      if (Math.random() <= successRate) {
        resolve();
      }
      else {
        reject();
      }
    }, timer);
  });
}

const brake = new Brakes(unreliableServiceCall, {
  statInterval: 5,
  threshold: 0.5,
  circuitDuration: 15000,
  timeout: 250
});

const globalStats = Brakes.getGlobalStats();
console.log(globalStats.getHystrixStream())

setInterval(() => {
  console.log(globalStats.getHystrixStream()._readableState.buffer.length)

}, 1000)

/*
Create SSE Hysterix compliant Server
*/
http.createServer((req, res) => {
  res.setHeader('Content-Type', 'text/event-stream;charset=UTF-8');
  res.setHeader('Cache-Control', 'no-cache, no-store, max-age=0, must-revalidate');
  res.setHeader('Pragma', 'no-cache');
  globalStats.getHystrixStream().pipe(res);
}).listen(8081, () => {
  console.log('---------------------');
  console.log('Hysterix Server now live at localhost:8081/hystrix.stream');
  console.log('---------------------');
});

/*
Create SSE Hysterix compliant Server
*/
http.createServer((req, res) => {
  res.setHeader('Content-Type', 'text/event-stream;charset=UTF-8');
  res.setHeader('Cache-Control', 'no-cache, no-store, max-age=0, must-revalidate');
  res.setHeader('Pragma', 'no-cache');
  globalStats.getHystrixStream().pipe(res);
}).listen(8082, () => {
  console.log('---------------------');
  console.log('Hysterix Server now live at localhost:8082/hystrix.stream');
  console.log('---------------------');
});

setInterval(() => {
  brake.exec()
    .then(() => {})
    .catch(() => {});
}, 100);
<commit_msg>reverted hystrix example changes<commit_after>'use strict';

const Brakes = require('../lib/Brakes');
const http = require('http');
const timer = 100;
let successRate = 2;
let iterations = 0;

function unreliableServiceCall() {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      iterations++;
      if (iterations === 10) {
        successRate = 0.6;
      }
      else if (iterations === 100) {
        successRate = 0.1;
      }
      else if (iterations === 200) {
        successRate = 1;
      }

      if (Math.random() <= successRate) {
        resolve();
      }
      else {
        reject();
      }
    }, timer);
  });
}

const brake = new Brakes(unreliableServiceCall, {
  statInterval: 5,
  threshold: 0.5,
  circuitDuration: 15000,
  timeout: 250
});

const globalStats = Brakes.getGlobalStats();

/*
Create SSE Hysterix compliant Server
*/
http.createServer((req, res) => {
  res.setHeader('Content-Type', 'text/event-stream;charset=UTF-8');
  res.setHeader('Cache-Control', 'no-cache, no-store, max-age=0, must-revalidate');
  res.setHeader('Pragma', 'no-cache');
  globalStats.getHystrixStream().pipe(res);
}).listen(8081, () => {
  console.log('---------------------');
  console.log('Hysterix Server now live at localhost:8081/hystrix.stream');
  console.log('---------------------');
});

/*
Create SSE Hysterix compliant Server
*/
http.createServer((req, res) => {
  res.setHeader('Content-Type', 'text/event-stream;charset=UTF-8');
  res.setHeader('Cache-Control', 'no-cache, no-store, max-age=0, must-revalidate');
  res.setHeader('Pragma', 'no-cache');
  globalStats.getHystrixStream().pipe(res);
}).listen(8082, () => {
  console.log('---------------------');
  console.log('Hysterix Server now live at localhost:8082/hystrix.stream');
  console.log('---------------------');
});

setInterval(() => {
  brake.exec()
    .then(() => {})
    .catch(() => {});
}, 100);
<|endoftext|>


<commit_before>import Ember from 'ember';
import { assert } from 'vertical-collection/-debug/helpers';

const { Array: EmberArray } = Ember;

export default function objectAt(arr, index) {
  assert('arr must be an instance of an Ember Array or Javascript Array', EmberArray.detect(arr) || Array.isArray(arr));

  return arr.objectAt ? arr.objectAt(index) : arr[index];
}
<commit_msg>bugfix(assert): Makes objectAt less restrictive (#117)<commit_after>import { assert } from 'vertical-collection/-debug/helpers';

export default function objectAt(arr, index) {
  assert('arr must be an instance of a Javascript Array or implement `objectAt`', Array.isArray(arr) || typeof arr.objectAt === 'function');

  return arr.objectAt ? arr.objectAt(index) : arr[index];
}
<|endoftext|>


<commit_before>var path = require('path')
var config = require('../config')
var utils = require('./utils')
var projectRoot = path.resolve(__dirname, '../')

module.exports = {
  entry: {
    app: './src/index.js'
  },
  output: {
    path: config.build.assetsRoot,
    publicPath: config.build.assetsPublicPath,
    filename: '[name].js'
  },
  resolve: {
    extensions: ['', '.js', '.vue'],
    fallback: [path.join(__dirname, '../node_modules')],
    alias: {
      'vue': 'vue/dist/vue.common.js',
      'src': path.resolve(__dirname, '../src'),
      'mixins': path.resolve(__dirname, '../src/mixins'),
      'BaseCharts': path.resolve(__dirname, '../src/BaseCharts')
    }
  },
  resolveLoader: {
    fallback: [path.join(__dirname, '../node_modules')]
  },
  module: {
    preLoaders: [
      {
        test: /\.vue$/,
        loader: 'eslint',
        include: projectRoot,
        exclude: /node_modules/
      },
      {
        test: /\.js$/,
        loader: 'eslint',
        include: projectRoot,
        exclude: /node_modules/
      }
    ],
    loaders: [
      {
        test: /\.vue$/,
        loader: 'vue'
      },
      {
        test: /\.js$/,
        loader: 'babel',
        include: projectRoot,
        exclude: /node_modules/
      },
      {
        test: /\.json$/,
        loader: 'json'
      },
      {
        test: /\.html$/,
        loader: 'vue-html'
      },
      {
        test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
        loader: 'url',
        query: {
          limit: 10000,
          name: utils.assetsPath('img/[name].[hash:7].[ext]')
        }
      },
      {
        test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
        loader: 'url',
        query: {
          limit: 10000,
          name: utils.assetsPath('fonts/[name].[hash:7].[ext]')
        }
      }
    ]
  },
  eslint: {
    formatter: require('eslint-friendly-formatter')
  },
  vue: {
    loaders: utils.cssLoaders()
  }
}
<commit_msg>🔥 Remove vue standalone alias from webpack<commit_after>var path = require('path')
var config = require('../config')
var utils = require('./utils')
var projectRoot = path.resolve(__dirname, '../')

module.exports = {
  entry: {
    app: './src/index.js'
  },
  output: {
    path: config.build.assetsRoot,
    publicPath: config.build.assetsPublicPath,
    filename: '[name].js'
  },
  resolve: {
    extensions: ['', '.js', '.vue'],
    fallback: [path.join(__dirname, '../node_modules')],
    alias: {
      'src': path.resolve(__dirname, '../src'),
      'mixins': path.resolve(__dirname, '../src/mixins'),
      'BaseCharts': path.resolve(__dirname, '../src/BaseCharts')
    }
  },
  resolveLoader: {
    fallback: [path.join(__dirname, '../node_modules')]
  },
  module: {
    preLoaders: [
      {
        test: /\.vue$/,
        loader: 'eslint',
        include: projectRoot,
        exclude: /node_modules/
      },
      {
        test: /\.js$/,
        loader: 'eslint',
        include: projectRoot,
        exclude: /node_modules/
      }
    ],
    loaders: [
      {
        test: /\.vue$/,
        loader: 'vue'
      },
      {
        test: /\.js$/,
        loader: 'babel',
        include: projectRoot,
        exclude: /node_modules/
      },
      {
        test: /\.json$/,
        loader: 'json'
      },
      {
        test: /\.html$/,
        loader: 'vue-html'
      },
      {
        test: /\.(png|jpe?g|gif|svg)(\?.*)?$/,
        loader: 'url',
        query: {
          limit: 10000,
          name: utils.assetsPath('img/[name].[hash:7].[ext]')
        }
      },
      {
        test: /\.(woff2?|eot|ttf|otf)(\?.*)?$/,
        loader: 'url',
        query: {
          limit: 10000,
          name: utils.assetsPath('fonts/[name].[hash:7].[ext]')
        }
      }
    ]
  },
  eslint: {
    formatter: require('eslint-friendly-formatter')
  },
  vue: {
    loaders: utils.cssLoaders()
  }
}
<|endoftext|>


<commit_before>/* jshint node: true */

module.exports = function(grunt) {
  "use strict";

  // Project configuration.
  grunt.initConfig({

    // Metadata.
    pkg: grunt.file.readJSON('package.json'),
    banner: '/*!\n' +
              '* Bootstrap v<%= pkg.version %> by @fat and @mdo\n' +
              '* Copyright <%= grunt.template.today("yyyy") %> <%= pkg.author %>\n' +
              '* Licensed under <%= _.pluck(pkg.licenses, "url").join(", ") %>\n' +
              '*\n' +
              '* Designed and built with all the love in the world by @mdo and @fat.\n' +
              '*/\n',
    jqueryCheck: 'if (!jQuery) { throw new Error(\"Bootstrap requires jQuery\") }\n\n',

    // Task configuration.
    clean: {
      dist: ['dist']
    },

    jshint: {
      options: {
        jshintrc: 'js/.jshintrc'
      },
      gruntfile: {
        src: 'Gruntfile.js'
      },
      src: {
        src: ['js/*.js']
      },
      test: {
        src: ['js/tests/unit/*.js']
      }
    },

    concat: {
      options: {
        banner: '<%= banner %><%= jqueryCheck %>',
        stripBanners: false
      },
      bootstrap: {
        src: [
          'js/transition.js',
          'js/alert.js',
          'js/button.js',
          'js/carousel.js',
          'js/collapse.js',
          'js/dropdown.js',
          'js/modal.js',
          'js/tooltip.js',
          'js/popover.js',
          'js/scrollspy.js',
          'js/tab.js',
          'js/affix.js'
        ],
        dest: 'dist/js/<%= pkg.name %>.js'
      }
    },

    uglify: {
      options: {
        banner: '<%= banner %>',
        report: 'min'
      },
      bootstrap: {
        src: ['<%= concat.bootstrap.dest %>'],
        dest: 'dist/js/<%= pkg.name %>.min.js'
      }
    },

    recess: {
      options: {
        compile: true,
        banner: '<%= banner %>'
      },
      bootstrap: {
        src: ['less/bootstrap.less'],
        dest: 'dist/css/<%= pkg.name %>.css'
      },
      min: {
        options: {
          compress: true
        },
        src: ['less/bootstrap.less'],
        dest: 'dist/css/<%= pkg.name %>.min.css'
      },
      theme: {
        src: ['less/theme.less'],
        dest: 'dist/css/<%= pkg.name %>-theme.css'
      },
      theme_min: {
        options: {
          compress: true
        },
        src: ['less/theme.less'],
        dest: 'dist/css/<%= pkg.name %>-theme.min.css'
      }
    },

    copy: {
      fonts: {
        expand: true,
        src: ["fonts/*"],
        dest: 'dist/'
      }
    },

    qunit: {
      options: {
        inject: 'js/tests/unit/phantom.js'
      },
      files: ['js/tests/*.html']
    },

    connect: {
      server: {
        options: {
          port: 3000,
          base: '.'
        }
      }
    },

    jekyll: {
      docs: {}
    },

    validation: {
      options: {
        reset: true
      },
      files: {
        src: ["_gh_pages/**/*.html"]
      }
    },

    watch: {
      src: {
        files: '<%= jshint.src.src %>',
        tasks: ['jshint:src', 'qunit']
      },
      test: {
        files: '<%= jshint.test.src %>',
        tasks: ['jshint:test', 'qunit']
      },
      recess: {
        files: 'less/*.less',
        tasks: ['recess']
      }
    }
  });

  // These plugins provide necessary tasks.
  grunt.loadNpmTasks('grunt-contrib-clean');
  grunt.loadNpmTasks('grunt-contrib-concat');
  grunt.loadNpmTasks('grunt-contrib-connect');
  grunt.loadNpmTasks('grunt-contrib-copy');
  grunt.loadNpmTasks('grunt-contrib-jshint');
  grunt.loadNpmTasks('grunt-contrib-qunit');
  grunt.loadNpmTasks('grunt-contrib-uglify');
  grunt.loadNpmTasks('grunt-contrib-watch');
  grunt.loadNpmTasks('grunt-html-validation');
  grunt.loadNpmTasks('grunt-jekyll');
  grunt.loadNpmTasks('grunt-recess');
  grunt.loadNpmTasks('browserstack-runner');

  // Docs HTML validation task
  grunt.registerTask('validate-html', ['jekyll', 'validation']);

  // Test task.
  var testSubtasks = ['dist-css', 'jshint', 'qunit', 'validate-html'];
  // Only run BrowserStack tests under Travis
  if (process.env.TRAVIS) {
    // Only run BrowserStack tests if this is a mainline commit in twbs/bootstrap, or you have your own BrowserStack key
    if ((process.env.TRAVIS_REPO_SLUG === 'twbs/bootstrap' && process.env.TRAVIS_PULL_REQUEST === 'false') || process.env.TWBS_HAVE_OWN_BROWSERSTACK_KEY) {
      testSubtasks.push('browserstack_runner');
    }
  }
  grunt.registerTask('test', testSubtasks);

  // JS distribution task.
  grunt.registerTask('dist-js', ['concat', 'uglify']);

  // CSS distribution task.
  grunt.registerTask('dist-css', ['recess']);

  // Fonts distribution task.
  grunt.registerTask('dist-fonts', ['copy']);

  // Full distribution task.
  grunt.registerTask('dist', ['clean', 'dist-css', 'dist-fonts', 'dist-js']);

  // Default task.
  grunt.registerTask('default', ['test', 'dist', 'build-customizer']);

  // task for building customizer
  grunt.registerTask('build-customizer', 'Add scripts/less files to customizer.', function () {
    var fs = require('fs')

    function getFiles(type) {
      var files = {}
      fs.readdirSync(type)
        .filter(function (path) {
          return type == 'fonts' ? true : new RegExp('\\.' + type + '$').test(path)
        })
        .forEach(function (path) {
          return files[path] = fs.readFileSync(type + '/' + path, 'utf8')
        })
      return 'var __' + type + ' = ' + JSON.stringify(files) + '\n'
    }

    var customize = fs.readFileSync('customize.html', 'utf-8')
    var files = getFiles('js') + getFiles('less') + getFiles('fonts')
    fs.writeFileSync('docs-assets/js/raw-files.js', files)
  });
};
<commit_msg>Update Gruntfile.js removing pointless reading of customize.html.<commit_after>/* jshint node: true */

module.exports = function(grunt) {
  "use strict";

  // Project configuration.
  grunt.initConfig({

    // Metadata.
    pkg: grunt.file.readJSON('package.json'),
    banner: '/*!\n' +
              '* Bootstrap v<%= pkg.version %> by @fat and @mdo\n' +
              '* Copyright <%= grunt.template.today("yyyy") %> <%= pkg.author %>\n' +
              '* Licensed under <%= _.pluck(pkg.licenses, "url").join(", ") %>\n' +
              '*\n' +
              '* Designed and built with all the love in the world by @mdo and @fat.\n' +
              '*/\n',
    jqueryCheck: 'if (!jQuery) { throw new Error(\"Bootstrap requires jQuery\") }\n\n',

    // Task configuration.
    clean: {
      dist: ['dist']
    },

    jshint: {
      options: {
        jshintrc: 'js/.jshintrc'
      },
      gruntfile: {
        src: 'Gruntfile.js'
      },
      src: {
        src: ['js/*.js']
      },
      test: {
        src: ['js/tests/unit/*.js']
      }
    },

    concat: {
      options: {
        banner: '<%= banner %><%= jqueryCheck %>',
        stripBanners: false
      },
      bootstrap: {
        src: [
          'js/transition.js',
          'js/alert.js',
          'js/button.js',
          'js/carousel.js',
          'js/collapse.js',
          'js/dropdown.js',
          'js/modal.js',
          'js/tooltip.js',
          'js/popover.js',
          'js/scrollspy.js',
          'js/tab.js',
          'js/affix.js'
        ],
        dest: 'dist/js/<%= pkg.name %>.js'
      }
    },

    uglify: {
      options: {
        banner: '<%= banner %>',
        report: 'min'
      },
      bootstrap: {
        src: ['<%= concat.bootstrap.dest %>'],
        dest: 'dist/js/<%= pkg.name %>.min.js'
      }
    },

    recess: {
      options: {
        compile: true,
        banner: '<%= banner %>'
      },
      bootstrap: {
        src: ['less/bootstrap.less'],
        dest: 'dist/css/<%= pkg.name %>.css'
      },
      min: {
        options: {
          compress: true
        },
        src: ['less/bootstrap.less'],
        dest: 'dist/css/<%= pkg.name %>.min.css'
      },
      theme: {
        src: ['less/theme.less'],
        dest: 'dist/css/<%= pkg.name %>-theme.css'
      },
      theme_min: {
        options: {
          compress: true
        },
        src: ['less/theme.less'],
        dest: 'dist/css/<%= pkg.name %>-theme.min.css'
      }
    },

    copy: {
      fonts: {
        expand: true,
        src: ["fonts/*"],
        dest: 'dist/'
      }
    },

    qunit: {
      options: {
        inject: 'js/tests/unit/phantom.js'
      },
      files: ['js/tests/*.html']
    },

    connect: {
      server: {
        options: {
          port: 3000,
          base: '.'
        }
      }
    },

    jekyll: {
      docs: {}
    },

    validation: {
      options: {
        reset: true
      },
      files: {
        src: ["_gh_pages/**/*.html"]
      }
    },

    watch: {
      src: {
        files: '<%= jshint.src.src %>',
        tasks: ['jshint:src', 'qunit']
      },
      test: {
        files: '<%= jshint.test.src %>',
        tasks: ['jshint:test', 'qunit']
      },
      recess: {
        files: 'less/*.less',
        tasks: ['recess']
      }
    }
  });

  // These plugins provide necessary tasks.
  grunt.loadNpmTasks('grunt-contrib-clean');
  grunt.loadNpmTasks('grunt-contrib-concat');
  grunt.loadNpmTasks('grunt-contrib-connect');
  grunt.loadNpmTasks('grunt-contrib-copy');
  grunt.loadNpmTasks('grunt-contrib-jshint');
  grunt.loadNpmTasks('grunt-contrib-qunit');
  grunt.loadNpmTasks('grunt-contrib-uglify');
  grunt.loadNpmTasks('grunt-contrib-watch');
  grunt.loadNpmTasks('grunt-html-validation');
  grunt.loadNpmTasks('grunt-jekyll');
  grunt.loadNpmTasks('grunt-recess');
  grunt.loadNpmTasks('browserstack-runner');

  // Docs HTML validation task
  grunt.registerTask('validate-html', ['jekyll', 'validation']);

  // Test task.
  var testSubtasks = ['dist-css', 'jshint', 'qunit', 'validate-html'];
  // Only run BrowserStack tests under Travis
  if (process.env.TRAVIS) {
    // Only run BrowserStack tests if this is a mainline commit in twbs/bootstrap, or you have your own BrowserStack key
    if ((process.env.TRAVIS_REPO_SLUG === 'twbs/bootstrap' && process.env.TRAVIS_PULL_REQUEST === 'false') || process.env.TWBS_HAVE_OWN_BROWSERSTACK_KEY) {
      testSubtasks.push('browserstack_runner');
    }
  }
  grunt.registerTask('test', testSubtasks);

  // JS distribution task.
  grunt.registerTask('dist-js', ['concat', 'uglify']);

  // CSS distribution task.
  grunt.registerTask('dist-css', ['recess']);

  // Fonts distribution task.
  grunt.registerTask('dist-fonts', ['copy']);

  // Full distribution task.
  grunt.registerTask('dist', ['clean', 'dist-css', 'dist-fonts', 'dist-js']);

  // Default task.
  grunt.registerTask('default', ['test', 'dist', 'build-customizer']);

  // task for building customizer
  grunt.registerTask('build-customizer', 'Add scripts/less files to customizer.', function () {
    var fs = require('fs')

    function getFiles(type) {
      var files = {}
      fs.readdirSync(type)
        .filter(function (path) {
          return type == 'fonts' ? true : new RegExp('\\.' + type + '$').test(path)
        })
        .forEach(function (path) {
          return files[path] = fs.readFileSync(type + '/' + path, 'utf8')
        })
      return 'var __' + type + ' = ' + JSON.stringify(files) + '\n'
    }

    var files = getFiles('js') + getFiles('less') + getFiles('fonts')
    fs.writeFileSync('docs-assets/js/raw-files.js', files)
  });
};
<|endoftext|>


<commit_before>module.exports = function(grunt) {
    // load plugins
    [
        'grunt-cafe-mocha',
        'grunt-contrib-jshint',
        'grunt-exec',
    ].forEach(function(task) {
        grunt.loadNpmTasks(task);
    });
    // configure plugins
    grunt.initConfig({
        cafemocha: {
            all: { src: 'qa/tests-*.js', options: { ui: 'tdd' }, }
        },
        jshint: {
            app: ['pkc.js', 'public/js/**/*.js',
                'lib/**/*.js'
            ],
            qa: ['Gruntfile.js', 'public/qa/**/*.js', 'qa/**/*.js'],
        },
        exec: {
            linkchecker: { cmd: 'linkchecker http://localhost:3000' }
        },
    });
    // register tasks
    grunt.registerTask('default', ['cafemocha:all', 'jshint', 'exec']);
};
<commit_msg>fixed formatting<commit_after>module.exports = function(grunt) {
    // load plugins
    [
        'grunt-cafe-mocha',
        'grunt-contrib-jshint',
        'grunt-exec',
    ].forEach(function(task) {
        grunt.loadNpmTasks(task);
    });
    // configure plugins
    grunt.initConfig({
        cafemocha: {
            all: {
                src: 'qa/tests-*.js',
                options: {
                    ui: 'tdd'
                },
            },
        },
        jshint: {
            app: ['pkc.js', 'public/js/**/*.js',
                'lib/**/*.js'
            ],
            qa: ['Gruntfile.js', 'public/qa/**/*.js', 'qa/**/*.js'],
        },
        exec: {
            linkchecker: { cmd: 'linkchecker http://localhost:3000' }
        },
    });
    // register tasks
    grunt.registerTask('default', ['cafemocha:all', 'jshint', 'exec']);
};
<|endoftext|>