<commit_before>/**
 * @file ScrollableTable component
 * @author liangxiaojun(liangxiaojun@derbysoft.com)
 */

import React, {Component, createRef} from 'react';
import PropTypes from 'prop-types';
import classNames from 'classnames';

import BaseTable from '../_BaseTable';

import Theme from '../Theme';
import TableFragment from '../_statics/TableFragment';
import HorizontalAlign from '../_statics/HorizontalAlign';
import SelectMode from '../_statics/SelectMode';
import SelectAllMode from '../_statics/SelectAllMode';
import SortingType from '../_statics/SortingType';

import Util from '../_vendors/Util';

class ScrollableTable extends Component {

    static Fragment = TableFragment;
    static Align = HorizontalAlign;
    static Fixed = HorizontalAlign;
    static SelectMode = SelectMode;
    static SelectAllMode = SelectAllMode;
    static SortingType = SortingType;

    constructor(props, ...restArgs) {

        super(props, ...restArgs);

        this.headScroller = createRef();
        this.bodyScroller = createRef();
        this.footScroller = createRef();

    }

    componentDidMount() {

        const {
            isHeadFixed, isFootFixed,
            onGetBodyScrollerEl, onGetHeadScrollerEl, onGetFootScrollerEl
        } = this.props;

        this.bodyScroller && onGetBodyScrollerEl && onGetBodyScrollerEl(this.bodyScroller.current);

        isHeadFixed && this.headScroller && onGetHeadScrollerEl
        && onGetHeadScrollerEl(this.headScroller.current);

        isFootFixed && this.footScroller && onGetFootScrollerEl
        && onGetFootScrollerEl(this.footScroller.current);

    }

    render() {

        const {
            className, style, bodyScrollerStyle, maskStyle, tableStyle, footStyle,
            isHeadFixed, isFootFixed, scroll,
            onScroll, onWheel, ...restProps
        } = this.props;

        return (

                {
                    isHeadFixed ?

                                <BaseTable {...restProps}
                                           style={tableStyle}
                                           fragment={TableFragment.HEAD}/>

                        :
                        null
                }

                            <BaseTable {...restProps}
                                       style={tableStyle}/>

                {
                    isFootFixed ?

                                <BaseTable {...restProps}
                                           style={tableStyle}
                                           fragment={TableFragment.FOOT}/>

                        :
                        null
                }

        );

    }
}

ScrollableTable.propTypes = {

    /**
     * The CSS class name of the root element.
     */
    className: PropTypes.string,

    /**
     * Override the styles of the root element.
     */
    style: PropTypes.object,

    bodyScrollerStyle: PropTypes.object,
    maskStyle: PropTypes.object,
    tableStyle: PropTypes.object,
    footStyle: PropTypes.object,

    fixed: PropTypes.oneOfType([PropTypes.bool, PropTypes.oneOf(Util.enumerateValue(HorizontalAlign))]),

    /**
     * The theme of the table select radio or checkbox.
     */
    selectTheme: PropTypes.oneOf(Util.enumerateValue(Theme)),

    /**
     * The select mode of table.
     */
    selectMode: PropTypes.oneOf(Util.enumerateValue(SelectMode)),

    /**
     * The select all mode of table, all or current page.
     */
    selectAllMode: PropTypes.oneOf(Util.enumerateValue(SelectAllMode)),

    /**
     * Children passed into table header.
     */
    columns: PropTypes.arrayOf(PropTypes.shape({

        /**
         * fixed position of column ( true / 'left' / 'right' )
         */
        fixed: PropTypes.oneOfType([PropTypes.bool, PropTypes.oneOf(Util.enumerateValue(HorizontalAlign))]),

        /**
         * width of column
         */
        width: PropTypes.number,

        /**
         * minimum width of column
         */
        minWidth: PropTypes.number,

        /**
         * The class name of header.
         */
        headClassName: PropTypes.string,

        /**
         * Override the styles of header.
         */
        headStyle: PropTypes.object,

        /**
         * The render content in header.
         * (1) string，example： 'id'
         * (2) callback，example：function (colIndex) {return colIndex;}
         */
        headRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table header cell
         */
        headAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table header
         */
        headSpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * The class name of td.
         */
        bodyClassName: PropTypes.string,

        /**
         * Override the styles of td.
         */
        bodyStyle: PropTypes.object,

        /**
         * The render content in table.
         * (1) data key，example： 'id'
         * (2) data key tamplate，example：'${id} - ${name}'
         * (3) callback，example：function (rowData, rowIndex, colIndex) {return rowData.id;}
         */
        bodyRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table body cell
         */
        bodyAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table body
         */
        bodySpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * The class name of footer.
         */
        footClassName: PropTypes.string,

        /**
         * Override the styles of footer.
         */
        footStyle: PropTypes.object,

        /**
         * The render content in footer.
         * (1) string，example： 'id'
         * (2) callback，example：function (colIndex) {return colIndex;}
         */
        footRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table footer cell
         */
        footAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table foot
         */
        footSpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * If true,this column can be sorted.
         */
        sortable: PropTypes.bool,

        /**
         * Sorting property.
         */
        sortingProp: PropTypes.string,

        defaultSortingType: PropTypes.oneOf(Util.enumerateValue(SortingType))

    })).isRequired,

    data: PropTypes.array,
    baseColIndex: PropTypes.number,
    expandRows: PropTypes.array,

    /**
     * sorting
     */
    sorting: PropTypes.shape({
        prop: PropTypes.string,
        type: PropTypes.oneOf(Util.enumerateValue(SortingType))
    }),
    defaultSortingType: PropTypes.oneOf(Util.enumerateValue(SortingType)),
    sortingAscIconCls: PropTypes.string,
    sortingDescIconCls: PropTypes.string,
    sortingFunc: PropTypes.func,

    /**
     * pagination
     */
    isPaginated: PropTypes.bool,
    pagination: PropTypes.shape({
        pageSize: PropTypes.number,
        page: PropTypes.number
    }),
    pageSizes: PropTypes.array,

    /**
     * fixed
     */
    isHeadFixed: PropTypes.bool,
    isFootFixed: PropTypes.bool,

    /**
     * hidden
     */
    isHeadHidden: PropTypes.bool,
    isFootHidden: PropTypes.bool,

    scroll: PropTypes.shape({
        width: PropTypes.number,
        height: PropTypes.number
    }),

    /**
     * callback
     */
    onGetBodyScrollerEl: PropTypes.func,
    onGetHeadScrollerEl: PropTypes.func,
    onGetFootScrollerEl: PropTypes.func,
    hasChildren: PropTypes.func,
    onExpandChange: PropTypes.func,
    onScroll: PropTypes.func,
    onWheel: PropTypes.func,
    onSortChange: PropTypes.func

};

ScrollableTable.defaultProps = {

    selectMode: SelectMode.SINGLE_SELECT,
    selectAllMode: SelectAllMode.CURRENT_PAGE,

    baseColIndex: 0,
    expandRows: [],

    defaultSortingType: SortingType.ASC,
    sortingAscIconCls: 'fas fa-angle-up',
    sortingDescIconCls: 'fas fa-angle-down',

    isPaginated: true,
    pagination: {
        pageSize: 10,
        page: 0
    },
    pageSizes: [5, 10, 15, 20],

    isHeadFixed: false,
    isFootFixed: false,

    isHeadHidden: false,
    isFootHidden: false

};

export default ScrollableTable;
<commit_msg>update ScrollableTable<commit_after>/**
 * @file ScrollableTable component
 * @author liangxiaojun(liangxiaojun@derbysoft.com)
 */

import React, {Component, createRef} from 'react';
import PropTypes from 'prop-types';
import classNames from 'classnames';

import BaseTable from '../_BaseTable';

import Theme from '../Theme';
import TableFragment from '../_statics/TableFragment';
import HorizontalAlign from '../_statics/HorizontalAlign';
import SelectMode from '../_statics/SelectMode';
import SelectAllMode from '../_statics/SelectAllMode';
import SortingType from '../_statics/SortingType';

import Util from '../_vendors/Util';

class ScrollableTable extends Component {

    static Fragment = TableFragment;
    static Align = HorizontalAlign;
    static Fixed = HorizontalAlign;
    static SelectMode = SelectMode;
    static SelectAllMode = SelectAllMode;
    static SortingType = SortingType;

    constructor(props, ...restArgs) {

        super(props, ...restArgs);

        this.headScroller = createRef();
        this.bodyScroller = createRef();
        this.footScroller = createRef();

    }

    componentDidMount() {

        const {
            isHeadFixed, isFootFixed,
            onGetBodyScrollerEl, onGetHeadScrollerEl, onGetFootScrollerEl
        } = this.props;

        this.bodyScroller && onGetBodyScrollerEl && onGetBodyScrollerEl(this.bodyScroller.current);

        isHeadFixed && this.headScroller && onGetHeadScrollerEl
        && onGetHeadScrollerEl(this.headScroller.current);

        isFootFixed && this.footScroller && onGetFootScrollerEl
        && onGetFootScrollerEl(this.footScroller.current);

    }

    render() {

        const {
            className, style, bodyScrollerStyle, maskStyle, tableStyle, footStyle,
            isHeadFixed, isFootFixed, scroll,
            onScroll, onWheel, ...restProps
        } = this.props;

        return (

                {
                    isHeadFixed ?

                                <BaseTable {...restProps}
                                           style={tableStyle}
                                           fragment={TableFragment.HEAD}/>

                        :
                        null
                }

                            <BaseTable {...restProps}
                                       style={tableStyle}/>

                {
                    isFootFixed ?

                                <BaseTable {...restProps}
                                           style={tableStyle}
                                           fragment={TableFragment.FOOT}/>

                        :
                        null
                }

        );

    }
}

ScrollableTable.propTypes = {

    /**
     * The CSS class name of the root element.
     */
    className: PropTypes.string,

    /**
     * Override the styles of the root element.
     */
    style: PropTypes.object,

    bodyScrollerStyle: PropTypes.object,
    maskStyle: PropTypes.object,
    tableStyle: PropTypes.object,
    footStyle: PropTypes.object,

    fixed: PropTypes.oneOfType([PropTypes.bool, PropTypes.oneOf(Util.enumerateValue(HorizontalAlign))]),

    /**
     * The theme of the table select radio or checkbox.
     */
    selectTheme: PropTypes.oneOf(Util.enumerateValue(Theme)),

    /**
     * The select mode of table.
     */
    selectMode: PropTypes.oneOf(Util.enumerateValue(SelectMode)),

    /**
     * The select all mode of table, all or current page.
     */
    selectAllMode: PropTypes.oneOf(Util.enumerateValue(SelectAllMode)),

    /**
     * Children passed into table header.
     */
    columns: PropTypes.arrayOf(PropTypes.shape({

        /**
         * fixed position of column ( true / 'left' / 'right' )
         */
        fixed: PropTypes.oneOfType([PropTypes.bool, PropTypes.oneOf(Util.enumerateValue(HorizontalAlign))]),

        /**
         * width of column
         */
        width: PropTypes.number,

        /**
         * minimum width of column
         */
        minWidth: PropTypes.number,

        /**
         * The class name of header.
         */
        headClassName: PropTypes.string,

        /**
         * Override the styles of header.
         */
        headStyle: PropTypes.object,

        /**
         * The render content in header.
         * (1) string，example： 'id'
         * (2) callback，example：function (colIndex) {return colIndex;}
         */
        headRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table header cell
         */
        headAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table header
         */
        headSpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * The class name of td.
         */
        bodyClassName: PropTypes.string,

        /**
         * Override the styles of td.
         */
        bodyStyle: PropTypes.object,

        /**
         * The render content in table.
         * (1) data key，example： 'id'
         * (2) data key tamplate，example：'${id} - ${name}'
         * (3) callback，example：function (rowData, rowIndex, colIndex) {return rowData.id;}
         */
        bodyRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table body cell
         */
        bodyAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table body
         */
        bodySpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * The class name of footer.
         */
        footClassName: PropTypes.string,

        /**
         * Override the styles of footer.
         */
        footStyle: PropTypes.object,

        /**
         * The render content in footer.
         * (1) string，example： 'id'
         * (2) callback，example：function (colIndex) {return colIndex;}
         */
        footRenderer: PropTypes.oneOfType([PropTypes.string, PropTypes.func]),

        /**
         * align of table footer cell
         */
        footAlign: PropTypes.oneOf(Util.enumerateValue(HorizontalAlign)),

        /**
         * column span of table foot
         */
        footSpan: PropTypes.oneOfType([PropTypes.number, PropTypes.func]),

        /**
         * If true,this column can be sorted.
         */
        sortable: PropTypes.bool,

        /**
         * Sorting property.
         */
        sortingProp: PropTypes.string,

        defaultSortingType: PropTypes.oneOf(Util.enumerateValue(SortingType))

    })).isRequired,

    data: PropTypes.array,
    baseColIndex: PropTypes.number,
    expandRows: PropTypes.array,

    /**
     * sorting
     */
    sorting: PropTypes.shape({
        prop: PropTypes.string,
        type: PropTypes.oneOf(Util.enumerateValue(SortingType))
    }),
    defaultSortingType: PropTypes.oneOf(Util.enumerateValue(SortingType)),
    sortingAscIconCls: PropTypes.string,
    sortingDescIconCls: PropTypes.string,
    sortingFunc: PropTypes.func,

    /**
     * pagination
     */
    isPaginated: PropTypes.bool,
    pagination: PropTypes.shape({
        pageSize: PropTypes.number,
        page: PropTypes.number
    }),
    pageSizes: PropTypes.array,

    /**
     * fixed
     */
    isHeadFixed: PropTypes.bool,
    isFootFixed: PropTypes.bool,

    /**
     * hidden
     */
    isHeadHidden: PropTypes.bool,
    isFootHidden: PropTypes.bool,

    scroll: PropTypes.shape({
        width: PropTypes.number,
        height: PropTypes.number
    }),

    /**
     * callback
     */
    onGetBodyScrollerEl: PropTypes.func,
    onGetHeadScrollerEl: PropTypes.func,
    onGetFootScrollerEl: PropTypes.func,
    onExpandChange: PropTypes.func,
    onScroll: PropTypes.func,
    onWheel: PropTypes.func,
    onSortChange: PropTypes.func

};

ScrollableTable.defaultProps = {

    selectMode: SelectMode.SINGLE_SELECT,
    selectAllMode: SelectAllMode.CURRENT_PAGE,

    baseColIndex: 0,
    expandRows: [],

    defaultSortingType: SortingType.ASC,
    sortingAscIconCls: 'fas fa-angle-up',
    sortingDescIconCls: 'fas fa-angle-down',

    isPaginated: true,
    pagination: {
        pageSize: 10,
        page: 0
    },
    pageSizes: [5, 10, 15, 20],

    isHeadFixed: false,
    isFootFixed: false,

    isHeadHidden: false,
    isFootHidden: false

};

export default ScrollableTable;
<|endoftext|>


<commit_before>
/**
 * statistics of /proc/stat
 */
var nick = {
  cpu: ['user','nice','system','idle','iowait','irq','softirq','steal','guest','guest_nice']
};

// cpu usage
function stat() {
  this.data = initrow();
  this.curr = initrow();
  this.prev = initrow();
}

// init stat row
function initrow() {
  return {
    cpu: {},
    system: {
      interrupt: 0,
      contextsw: 0
    },
    process: {
      running: 0,
      blocked: 0
    }
  };
}

// init cpu row
function initcpurow() {
  return {
    user: 0,
    nice: 0,
    system: 0,
    iowait: 0,
    idle: 0,
    irq: 0,
    softirq: 0,
    steal: 0,
    guest: 0,
    guest_nice: 0
  };
}

function getcpu(row, name) {
  var cpu = row.cpu[name];
  if (cpu) {
    return cpu;
  } else {
    return row.cpu[name] = initcpurow();
  }
}

// make object values to percent value
stat.prototype.percentize = function(obj) {
  var total = 0, name;
  for (name in obj) {
    total += obj[name];
  }
  obj.idle = 100;
  if (total > 0) {
    for (name in obj) {
      if (name === 'idle') {
        continue;
      }
      var value = obj[name];
      value = value > 0 ? Math.round(value / total * 1000) / 10 : 0;
      obj[name] = value;
      obj.idle -= value;
    }
    obj.idle = Math.round(obj.idle * 10) / 10;
  }
};
stat.prototype.get = function get(nstat, callback) {
  var self = this;
  var curr = this.curr;
  var prev = this.prev;
  var data = this.data;
  nstat.lines(
    '/proc/stat',
    function(line) {
      var columns = line.split(/\s+/);
      var type = columns[0], value;
      if (/^cpu+/.test(type)) {
        // cpu
        var cpuname = type;
        if (cpuname === 'cpu') {
          cpuname = 'total';
        }
        for (var i = 1; i < columns.length; i++) {
          var cname = nick.cpu[i-1];
          value = Number(columns[i]);
          var cpucurr = getcpu(curr, cpuname);
          var cpuprev = getcpu(prev, cpuname);
          var cpudata = getcpu(data, cpuname);

          cpucurr[cname] = value;
          cpudata[cname] = cpuprev[cname] === 0 ? 0 : value - cpuprev[cname];
        }
        self.percentize(data.cpu[cpuname]);
      } else if (type === 'intr') {
        // interrupts
        value = Number(columns[1]);
        curr.system.interrupt = value;
        data.system.interrupt =  (prev.system.interrupt === 0) ? 0 : value - prev.system.interrupt;
      } else if (type === 'ctxt') {
        // context switch
        value = Number(columns[1]);
        curr.system.contextsw = value;
        data.system.contextsw = (prev.system.contextsw === 0) ? 0 : value - prev.system.contextsw;
      } else if (type === 'procs_running') {
        // running processes
        data.process.running = Number(columns[1]);
      } else if (type === 'procs_blocked') {
        // blocked processes
        data.process.blocked = Number(columns[1]);
      }
    },
    function(err) {
      self.prev = self.curr;
      self.curr = initrow();
      if (err) {
        callback(err);
      } else {
        callback(null, self.data);
      }
    }
  );
};

module.exports = new stat;
<commit_msg>Fix cpu stats<commit_after>
/**
 * statistics of /proc/stat
 */
var nick = {
  cpu: ['user','nice','system','idle','iowait','irq','softirq','steal','guest','guest_nice']
};

// cpu usage
function stat() {
  this.data = initrow();
  this.curr = initrow();
  this.prev = initrow();
}

// init stat row
function initrow() {
  return {
    cpu: {},
    system: {
      interrupt: 0,
      contextsw: 0
    },
    process: {
      running: 0,
      blocked: 0
    }
  };
}

// init cpu row
function initcpurow() {
  return {
    user: 0,
    nice: 0,
    system: 0,
    iowait: 0,
    idle: 0,
    irq: 0,
    softirq: 0,
    steal: 0,
    guest: 0,
    guest_nice: 0
  };
}

function getcpu(row, name) {
  var cpu = row.cpu[name];
  if (cpu) {
    return cpu;
  } else {
    return row.cpu[name] = initcpurow();
  }
}

// make object values to percent value
stat.prototype.percentize = function(obj) {
  var total = 0, name;
  for (name in obj) {
    total += obj[name];
  }
  obj.idle = 100;
  if (total > 0) {
    for (name in obj) {
      if (name === 'idle') {
        continue;
      }
      var value = obj[name];
      value = value > 0 ? Math.round(value / total * 100) : 0;
      obj[name] = value;
      obj.idle -= value;
    }
  }
};
stat.prototype.get = function get(nstat, callback) {
  var self = this;
  var curr = this.curr;
  var prev = this.prev;
  var data = this.data;
  nstat.lines(
    '/proc/stat',
    function(line) {
      var columns = line.split(/\s+/);
      var type = columns[0], value;
      if (/^cpu+/.test(type)) {
        // cpu
        var cpuname = type;
        if (cpuname === 'cpu') {
          cpuname = 'total';
        }
        for (var i = 1; i < columns.length; i++) {
          var cname = nick.cpu[i-1];
          value = Number(columns[i]);
          var cpucurr = getcpu(curr, cpuname);
          var cpuprev = getcpu(prev, cpuname);
          var cpudata = getcpu(data, cpuname);

          cpucurr[cname] = value;
          cpudata[cname] = cpuprev[cname] === 0 ? 0 : value - cpuprev[cname];
        }
        self.percentize(data.cpu[cpuname]);
      } else if (type === 'intr') {
        // interrupts
        value = Number(columns[1]);
        curr.system.interrupt = value;
        data.system.interrupt =  (prev.system.interrupt === 0) ? 0 : value - prev.system.interrupt;
      } else if (type === 'ctxt') {
        // context switch
        value = Number(columns[1]);
        curr.system.contextsw = value;
        data.system.contextsw = (prev.system.contextsw === 0) ? 0 : value - prev.system.contextsw;
      } else if (type === 'procs_running') {
        // running processes
        data.process.running = Number(columns[1]);
      } else if (type === 'procs_blocked') {
        // blocked processes
        data.process.blocked = Number(columns[1]);
      }
    },
    function(err) {
      self.prev = self.curr;
      self.curr = initrow();
      if (err) {
        callback(err);
      } else {
        callback(null, self.data);
      }
    }
  );
};

module.exports = new stat;
<|endoftext|>


<commit_before>var sys = require('sys');
exports.events = [function() {
  this.addListener('message.receive', function(from, content, to, type, id) {
    if (/^ping$/.exec(content)) {
      this.push(from, 'pong');
    } else {
       // this.push(from, 'command unknow : ' + content);
     }
  });
  this.addListener('presence.receive', function(from, to, status, priority) {
    return;
    this.push('admin@localhost', 'receive presence from : ' + from
                                 + ' to : ' + to
				 + ' status : ' + status
				 + ' priority : ' + priority);
  });
  this.addListener('message.sent', function(to, msg) {
    sys.puts('[ send ] ' + to + ': ' + msg);
  });
}];<commit_msg>subscribe automatically contact on request (plugins/test.js)<commit_after>var sys = require('sys');
exports.events = [function() {
  this.addListener('message.receive', function(from, content, to, type, id) {
    if (/^ping$/.exec(content)) {
      this.push(from, 'pong');
    } else {
       // this.push(from, 'command unknow : ' + content);
     }
  });
  this.addListener('presence.receive', function(from, to, status, priority) {
    if (type == 'subscribe') {
      this.subscribe(from);
    }
    return;
    this.push('admin@localhost', 'receive presence from : ' + from
                                 + ' to : ' + to
				 + ' status : ' + status
				 + ' priority : ' + priority);
  });
  this.addListener('message.sent', function(to, msg) {
    sys.puts('[ send ] ' + to + ': ' + msg);
  });
}];<|endoftext|>


<commit_before>
var trigger = ['whats the time', 'the time', 'what is the current time', 'tell me the time', 'what time is it', 'what time it is', 'time', 'current time', 'date', 'whats the date', 'todays date'];
var help    = [{
               usage       : 'time OR whats the time',
               description : 'Will return the current time [@ned time]'
              }];
module.exports.help = help

var currTime = function()
{
    var days = ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"];
    var months = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];

    var date = new Date();
    var hr   = date.getHours();
    var m    = date.getMinutes();
    var day  = days[date.getDay()];
    var dat  = date.getDate();
    var mon  = months[date.getMonth()];
    var ampm = (hr > 11) ? 'PM' : 'AM';
    var curr = "It's " + hr % 12 + ":" + m + " " + ampm + ", " + day + " " + mon + " " + dat;

    var output = ["It's time to get a watch", curr, curr, curr, curr];

    return output[Math.floor(Math.random()*output.length)];
}

module.exports.load = function(bot)
{
    var assembleInput = "("+trigger.join("|")+")";
    var callerRegEx   = new RegExp(Util.NedCaller.source + Util.NedName.source   + " " + assembleInput + "(.*)$", "i");
    var pmCallerRegEx = new RegExp(Util.NedCaller.source + Util.NedPMName.source + ""  + assembleInput + "(.*)$", "i");

    bot.onMessage(callerRegEx, onMessage);
    bot.onPrivateMessage(pmCallerRegEx, onMessage);
};

var onMessage = function(channel, frm, msg, x)
{
    var self             = this;
    var isPrivateMessage = (arguments.length == 3) ? true : false;
    var from             = isPrivateMessage ? '' : frm;
    var tempMessage      = isPrivateMessage ? frm : msg;
    var roomName         = channel.split('@')[0];
    var isSingleWord     = (tempMessage.indexOf(" ") == -1) ? true : false;

    var caller           = /^([\@\!\#\$\~\%\/\\/]*)?/;
    var ned              = (isPrivateMessage && isSingleWord) ?
                           /([Nn][Ee][Dd][Dd]?([Dd]?[Aa][Rr][Dd])?(( *[^A-Za-z0-9]* *))?)?$/ :
                           /([Nn][Ee][Dd][Dd]?([Dd]?[Aa][Rr][Dd])?(( *[^A-Za-z0-9]* *))? ?)?/;

    var assembleInput    = "("+trigger.join("|")+")";
    var regEx            = new RegExp(caller.source + ned.source + assembleInput, "i");
    var message          = tempMessage.replace(regEx, '');
    var isEmpty          = (message.split(' ').join('').length == 0 || message.length == 0) ? true : false;
    var isPrivate        = (isPrivateMessage) ? 1 : 0;
    var message          = Util.clarify(message.split("+").join("%2B"));

    if(isEmpty)
    {
        self.message(channel, currTime());
    }
    else
    {
        var input = Util.padd(message);

        // Actual function begins here

        if(input.length > 0)
        {
            self.message(channel, currTime());

        // actual function ends here

        }
        else
        {
            self.message(channel, currTime());
        }

        GLOBAL.nothingFound = false;
    }

    return true;
};

<commit_msg>Converted time<commit_after>var plugin = {
              name        : 'time',
              trigger     : ['whats the time', 'the time', 'what is the current time', 'tell me the time', 'what time is it', 'what time it is', 'time', 'current time', 'date', 'whats the date', 'todays date'],
              enabled     : 'true',
              fuzzy       : 'true',
              description : 'Tells you the time',
              usage       : 'ned time'
             };

module.exports.plugin = plugin;

module.exports[plugin.name] = function(get)
{
    var days = ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"];
    var months = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];

    var date = new Date();
    var hr   = date.getHours();
    var m    = date.getMinutes();
    var day  = days[date.getDay()];
    var dat  = date.getDate();
    var mon  = months[date.getMonth()];
    var ampm = (hr > 11) ? 'PM' : 'AM';
    var curr = "It's " + hr % 12 + ":" + m + " " + ampm + ", " + day + " " + mon + " " + dat;

    var currTime = ["It's time to get a watch", curr, curr, curr, curr];
    sendMessage(Util.chooseRandom(currTime));

    return true;
}
<|endoftext|>


<commit_before>/*
	var vid = new Whammy.Video();
	vid.add(canvas or data url)
	vid.compile()
*/

var Whammy = (function(){
	// in this case, frames has a very specific meaning, which will be
	// detailed once i finish writing the code

	function toWebM(frames){
		var info = checkFrames(frames);
		var counter = 0;
		var EBML = [
			{
				"id": 0x1a45dfa3, // EBML
				"data": [
					{
						"data": 1,
						"id": 0x4286 // EBMLVersion
					},
					{
						"data": 1,
						"id": 0x42f7 // EBMLReadVersion
					},
					{
						"data": 4,
						"id": 0x42f2 // EBMLMaxIDLength
					},
					{
						"data": 8,
						"id": 0x42f3 // EBMLMaxSizeLength
					},
					{
						"data": "webm",
						"id": 0x4282 // DocType
					},
					{
						"data": 2,
						"id": 0x4287 // DocTypeVersion
					},
					{
						"data": 2,
						"id": 0x4285 // DocTypeReadVersion
					}
				]
			},
			{
				"id": 0x18538067, // Segment
				"data": [
					{
						"id": 0x1549a966, // Info
						"data": [
							{
								"data": 1e6, //do things in millisecs (num of nanosecs for duration scale)
								"id": 0x2ad7b1 // TimecodeScale
							},
							{
								"data": "whammy",
								"id": 0x4d80 // MuxingApp
							},
							{
								"data": "whammy",
								"id": 0x5741 // WritingApp
							},
							{
								"data": doubleToString(info.duration),
								"id": 0x4489 // Duration
							}
						]
					},
					{
						"id": 0x1654ae6b, // Tracks
						"data": [
							{
								"id": 0xae, // TrackEntry
								"data": [
									{
										"data": 1,
										"id": 0xd7 // TrackNumber
									},
									{
										"data": 1,
										"id": 0x63c5 // TrackUID
									},
									{
										"data": 0,
										"id": 0x9c // FlagLacing
									},
									{
										"data": "und",
										"id": 0x22b59c // Language
									},
									{
										"data": "V_VP8",
										"id": 0x86 // CodecID
									},
									{
										"data": "VP8",
										"id": 0x258688 // CodecName
									},
									{
										"data": 1,
										"id": 0x83 // TrackType
									},
									{
										"id": 0xe0,  // Video
										"data": [
											{
												"data": info.width,
												"id": 0xb0 // PixelWidth
											},
											{
												"data": info.height,
												"id": 0xba // PixelHeight
											}
										]
									}
								]
							}
						]
					},
					{
						"id": 0x1f43b675, // Cluster
						"data": [
							{
								"data": 0,
								"id": 0xe7 // Timecode
							}
						].concat(frames.map(function(webp){
							var block = makeSimpleBlock({
								discardable: 0,
								frame: webp.data.slice(4),
								invisible: 0,
								keyframe: 1,
								lacing: 0,
								trackNum: 1,
								timecode: Math.round(counter)
							});
							counter += webp.duration;
							return {
								data: block,
								id: 0xa3
							};
						}))
					}
				]
			}
		];
		var video = generateEBML(EBML);
		return 'data:video/webm;base64,' + btoa(video);
	}

	// sums the lengths of all the frames and gets the duration, woo

	function checkFrames(frames){
		var width = frames[0].width,
			height = frames[0].height,
			duration = frames[0].duration;
		for(var i = 1; i < frames.length; i++){
			if(frames[i].width != width) throw "Frame " + (i + 1) + " has a different width";
			if(frames[i].height != height) throw "Frame " + (i + 1) + " has a different height";
			if(frames[i].duration < 0) throw "Frame " + (i + 1) + " has a weird duration";
			duration += frames[i].duration;
		}
		return {
			duration: duration,
			width: width,
			height: height
		};
	}

	// here is something else taken from weppy more or less unharmed

	//Converting between a string of 0010101001's and binary back and forth is probably inefficient
	//TODO: get rid of this function
	function toBinStr(bits){
		var data = '';
		var pad = (bits.length % 8) ? (new Array(1 + 8 - (bits.length % 8))).join('0') : '';
		bits = pad + bits;
		for(var i = 0; i < bits.length; i+= 8){
			data += String.fromCharCode(parseInt(bits.substr(i,8),2))
		}
		return data;
	}

	function generateEBML(json){
		var ebml = '';
		for(var i = 0; i < json.length; i++){
			var data = json[i].data;
			if(typeof data == 'object') data = generateEBML(data);
			if(typeof data == 'number') data = toBinStr(data.toString(2));

			var len = data.length;
			var zeroes = Math.ceil(Math.ceil(Math.log(len)/Math.log(2))/8);
			var size_str = len.toString(2);
			var padded = (new Array((zeroes * 7 + 7 + 1) - size_str.length)).join('0') + size_str;
			var size = (new Array(zeroes)).join('0') + '1' + padded;

			ebml += toBinStr(json[i].id.toString(2)) + toBinStr(size) + data;

		}
		return ebml;
	}
	//woot, a function that's actually written for this project!
	//this parses some json markup and makes it into that binary magic
	//which can then get shoved into the matroska comtainer (peaceably)

	function makeSimpleBlock(data){
		var flags = 0;
		if (data.keyframe) flags |= 128;
		if (data.invisible) flags |= 8;
		if (data.lacing) flags |= (data.lacing << 1);
		if (data.discardable) flags |= 1;
		if (data.trackNum > 127) {
			throw "TrackNumber > 127 not supported";
		}
		var out = [data.trackNum | 0x80, data.timecode >> 8, data.timecode & 0xff, flags].map(function(e){
			return String.fromCharCode(e)
		}).join('') + data.frame;

		return out;
	}

	// here's something else taken verbatim from weppy, awesome rite?

	function parseWebP(riff){
		var VP8 = riff.RIFF[0].WEBP[0];

		var frame_start = VP8.indexOf('\x9d\x01\x2a'); //A VP8 keyframe starts with the 0x9d012a header
		for(var i = 0, c = []; i < 4; i++) c[i] = VP8.charCodeAt(frame_start + 3 + i);

		var width, horizontal_scale, height, vertical_scale, tmp;

		//the code below is literally copied verbatim from the bitstream spec
		tmp = (c[1] << 8) | c[0];
		width = tmp & 0x3FFF;
		horizontal_scale = tmp >> 14;
		tmp = (c[3] << 8) | c[2];
		height = tmp & 0x3FFF;
		vertical_scale = tmp >> 14;
		return {
			width: width,
			height: height,
			data: VP8,
			riff: riff
		}
	}

	// i think i'm going off on a riff by pretending this is some known
	// idiom which i'm making a casual and brilliant pun about, but since
	// i can't find anything on google which conforms to this idiomatic
	// usage, I'm assuming this is just a consequence of some psychotic
	// break which makes me make up puns. well, enough riff-raff (aha a
	// rescue of sorts), this function was ripped wholesale from weppy

	function parseRIFF(string){
		var offset = 0;
		var chunks = {};

		while (offset < string.length) {
			var id = string.substr(offset, 4);
			var len = parseInt(string.substr(offset + 4, 4).split('').map(function(i){
				var unpadded = i.charCodeAt(0).toString(2);
				return (new Array(8 - unpadded.length + 1)).join('0') + unpadded
			}).join(''),2);
			var data = string.substr(offset + 4 + 4, len);
			offset += 4 + 4 + len;
			chunks[id] = chunks[id] || [];

			if (id == 'RIFF' || id == 'LIST') {
				chunks[id].push(parseRIFF(data));
			} else {
				chunks[id].push(data);
			}
		}
		return chunks;
	}

	// here's a little utility function that acts as a utility for other functions
	// basically, the only purpose is for encoding "Duration", which is encoded as
	// a double (considerably more difficult to encode than an integer)
	function doubleToString(num){
		return [].slice.call(
			new Uint8Array(
				(
					new Float64Array([num]) //create a float64 array
				).buffer) //extract the array buffer
			, 0) // convert the Uint8Array into a regular array
			.map(function(e){ //since it's a regular array, we can now use map
				return String.fromCharCode(e) // encode all the bytes individually
			})
			.reverse() //correct the byte endianness (assume it's little endian for now)
			.join('') // join the bytes in holy matrimony as a string
	}

	function WhammyVideo(speed, quality){ // a more abstract-ish API
		this.frames = [];
		this.duration = 1000 / speed;
		this.quality = quality || 0.8;
	}

	WhammyVideo.prototype.add = function(frame, duration){
		if(typeof duration != 'undefined' && this.duration) throw "you can't pass a duration if the fps is set";
		if('canvas' in frame){ //CanvasRenderingContext2D
			frame = frame.canvas;
		}
		if('toDataURL' in frame){
			frame = frame.toDataURL('image/webp', this.quality)
		}else if(typeof frame != "string"){
			throw "frame must be a a HTMLCanvasElement, a CanvasRenderingContext2D or a DataURI formatted string"
		}
		if (!(/^data:image\/webp;base64,/ig).test(frame)) {
			throw "Input must be formatted properly as a base64 encoded DataURI of type image/webp";
		}
		this.frames.push({
			image: frame,
			duration: duration || this.duration
		})
	}

	WhammyVideo.prototype.compile = function(){
		return toWebM(this.frames.map(function(frame){
			var webp = parseWebP(parseRIFF(atob(frame.image.slice(23))));
			webp.duration = frame.duration;
			return webp;
		}))
	}
	return {
		Video: WhammyVideo,
		fromImageArray: function(images, fps){
			return toWebM(images.map(function(image){
				var webp = parseWebP(parseRIFF(atob(image.slice(23))))
				webp.duration = 1000 / fps;
				return webp;
			}))
		},
		toWebM: toWebM
		// expose methods of madness
	}
})()<commit_msg>switching to blobs, despite slower<commit_after>/*
	var vid = new Whammy.Video();
	vid.add(canvas or data url)
	vid.compile()
*/

var Whammy = (function(){
	// in this case, frames has a very specific meaning, which will be
	// detailed once i finish writing the code

	function toWebM(frames){
		var info = checkFrames(frames);
		var counter = 0;
		var EBML = [
			{
				"id": 0x1a45dfa3, // EBML
				"data": [
					{
						"data": 1,
						"id": 0x4286 // EBMLVersion
					},
					{
						"data": 1,
						"id": 0x42f7 // EBMLReadVersion
					},
					{
						"data": 4,
						"id": 0x42f2 // EBMLMaxIDLength
					},
					{
						"data": 8,
						"id": 0x42f3 // EBMLMaxSizeLength
					},
					{
						"data": "webm",
						"id": 0x4282 // DocType
					},
					{
						"data": 2,
						"id": 0x4287 // DocTypeVersion
					},
					{
						"data": 2,
						"id": 0x4285 // DocTypeReadVersion
					}
				]
			},
			{
				"id": 0x18538067, // Segment
				"data": [
					{
						"id": 0x1549a966, // Info
						"data": [
							{
								"data": 1e6, //do things in millisecs (num of nanosecs for duration scale)
								"id": 0x2ad7b1 // TimecodeScale
							},
							{
								"data": "whammy",
								"id": 0x4d80 // MuxingApp
							},
							{
								"data": "whammy",
								"id": 0x5741 // WritingApp
							},
							{
								"data": doubleToString(info.duration),
								"id": 0x4489 // Duration
							}
						]
					},
					{
						"id": 0x1654ae6b, // Tracks
						"data": [
							{
								"id": 0xae, // TrackEntry
								"data": [
									{
										"data": 1,
										"id": 0xd7 // TrackNumber
									},
									{
										"data": 1,
										"id": 0x63c5 // TrackUID
									},
									{
										"data": 0,
										"id": 0x9c // FlagLacing
									},
									{
										"data": "und",
										"id": 0x22b59c // Language
									},
									{
										"data": "V_VP8",
										"id": 0x86 // CodecID
									},
									{
										"data": "VP8",
										"id": 0x258688 // CodecName
									},
									{
										"data": 1,
										"id": 0x83 // TrackType
									},
									{
										"id": 0xe0,  // Video
										"data": [
											{
												"data": info.width,
												"id": 0xb0 // PixelWidth
											},
											{
												"data": info.height,
												"id": 0xba // PixelHeight
											}
										]
									}
								]
							}
						]
					},
					{
						"id": 0x1f43b675, // Cluster
						"data": [
							{
								"data": 0,
								"id": 0xe7 // Timecode
							}
						].concat(frames.map(function(webp){
							var block = makeSimpleBlock({
								discardable: 0,
								frame: webp.data.slice(4),
								invisible: 0,
								keyframe: 1,
								lacing: 0,
								trackNum: 1,
								timecode: Math.round(counter)
							});
							counter += webp.duration;
							return {
								data: block,
								id: 0xa3
							};
						}))
					}
				]
			}
		];
		return generateEBML(EBML)
	}

	// sums the lengths of all the frames and gets the duration, woo

	function checkFrames(frames){
		var width = frames[0].width,
			height = frames[0].height,
			duration = frames[0].duration;
		for(var i = 1; i < frames.length; i++){
			if(frames[i].width != width) throw "Frame " + (i + 1) + " has a different width";
			if(frames[i].height != height) throw "Frame " + (i + 1) + " has a different height";
			if(frames[i].duration < 0) throw "Frame " + (i + 1) + " has a weird duration";
			duration += frames[i].duration;
		}
		return {
			duration: duration,
			width: width,
			height: height
		};
	}

	// here is something else taken from weppy more or less unharmed

	function bitsToBuffer(bits){
		var data = [];
		var pad = (bits.length % 8) ? (new Array(1 + 8 - (bits.length % 8))).join('0') : '';
		bits = pad + bits;
		for(var i = 0; i < bits.length; i+= 8){
			data.push(parseInt(bits.substr(i,8),2))
		}
		return new Uint8Array(data);
	}

	function numToBuffer(num){
		var parts = [];
		while(num > 0){
			parts.push(num & 0xff)
			num = num >> 8
		}
		return new Uint8Array(parts.reverse());
	}

	function strToBuffer(str){
		// return new Blob([str]);

		var arr = new Uint8Array(str.length);
		for(var i = 0; i < str.length; i++){
			arr[i] = str.charCodeAt(i)
		}
		return arr;
		// this is slower
		// return new Uint8Array(str.split('').map(function(e){
		// 	return e.charCodeAt(0)
		// }))
	}
	function generateEBML(json){
		var ebml = [];
		for(var i = 0; i < json.length; i++){
			var data = json[i].data;
			// console.log(data);
			if(typeof data == 'object') data = generateEBML(data);
			if(typeof data == 'number') data = bitsToBuffer(data.toString(2));
			if(typeof data == 'string') data = strToBuffer(data);
			// console.log(data)

			var len = data.size || data.byteLength;
			var zeroes = Math.ceil(Math.ceil(Math.log(len)/Math.log(2))/8);
			var size_str = len.toString(2);
			var padded = (new Array((zeroes * 7 + 7 + 1) - size_str.length)).join('0') + size_str;
			var size = (new Array(zeroes)).join('0') + '1' + padded;

			//i actually dont quite understand what went on up there, so I'm not really
			//going to fix this, i'm probably just going to write some hacky thing which
			//converts that string into a buffer-esque thing

			ebml.push(numToBuffer(json[i].id));
			ebml.push(bitsToBuffer(size));
			ebml.push(data)

		}
		return new Blob(ebml, {
			type: "video/webm"
		});
	}

	//OKAY, so the following two functions are the string-based old stuff, the reason they're
	//still sort of in here, is that they're actually faster than the new blob stuff because
	//getAsFile isn't widely implemented, or at least, it doesn't work in chrome, which is the
	// only browser which supports get as webp

	//Converting between a string of 0010101001's and binary back and forth is probably inefficient
	//TODO: get rid of this function
	function toBinStr_old(bits){
		var data = '';
		var pad = (bits.length % 8) ? (new Array(1 + 8 - (bits.length % 8))).join('0') : '';
		bits = pad + bits;
		for(var i = 0; i < bits.length; i+= 8){
			data += String.fromCharCode(parseInt(bits.substr(i,8),2))
		}
		return data;
	}

	function generateEBML_old(json){
		var ebml = '';
		for(var i = 0; i < json.length; i++){
			var data = json[i].data;
			if(typeof data == 'object') data = generateEBML_old(data);
			if(typeof data == 'number') data = toBinStr_old(data.toString(2));

			var len = data.length;
			var zeroes = Math.ceil(Math.ceil(Math.log(len)/Math.log(2))/8);
			var size_str = len.toString(2);
			var padded = (new Array((zeroes * 7 + 7 + 1) - size_str.length)).join('0') + size_str;
			var size = (new Array(zeroes)).join('0') + '1' + padded;

			ebml += toBinStr_old(json[i].id.toString(2)) + toBinStr_old(size) + data;

		}
		return ebml;
	}

	//woot, a function that's actually written for this project!
	//this parses some json markup and makes it into that binary magic
	//which can then get shoved into the matroska comtainer (peaceably)

	function makeSimpleBlock(data){
		var flags = 0;
		if (data.keyframe) flags |= 128;
		if (data.invisible) flags |= 8;
		if (data.lacing) flags |= (data.lacing << 1);
		if (data.discardable) flags |= 1;
		if (data.trackNum > 127) {
			throw "TrackNumber > 127 not supported";
		}
		var out = [data.trackNum | 0x80, data.timecode >> 8, data.timecode & 0xff, flags].map(function(e){
			return String.fromCharCode(e)
		}).join('') + data.frame;

		return out;
	}

	// here's something else taken verbatim from weppy, awesome rite?

	function parseWebP(riff){
		var VP8 = riff.RIFF[0].WEBP[0];

		var frame_start = VP8.indexOf('\x9d\x01\x2a'); //A VP8 keyframe starts with the 0x9d012a header
		for(var i = 0, c = []; i < 4; i++) c[i] = VP8.charCodeAt(frame_start + 3 + i);

		var width, horizontal_scale, height, vertical_scale, tmp;

		//the code below is literally copied verbatim from the bitstream spec
		tmp = (c[1] << 8) | c[0];
		width = tmp & 0x3FFF;
		horizontal_scale = tmp >> 14;
		tmp = (c[3] << 8) | c[2];
		height = tmp & 0x3FFF;
		vertical_scale = tmp >> 14;
		return {
			width: width,
			height: height,
			data: VP8,
			riff: riff
		}
	}

	// i think i'm going off on a riff by pretending this is some known
	// idiom which i'm making a casual and brilliant pun about, but since
	// i can't find anything on google which conforms to this idiomatic
	// usage, I'm assuming this is just a consequence of some psychotic
	// break which makes me make up puns. well, enough riff-raff (aha a
	// rescue of sorts), this function was ripped wholesale from weppy

	function parseRIFF(string){
		var offset = 0;
		var chunks = {};

		while (offset < string.length) {
			var id = string.substr(offset, 4);
			var len = parseInt(string.substr(offset + 4, 4).split('').map(function(i){
				var unpadded = i.charCodeAt(0).toString(2);
				return (new Array(8 - unpadded.length + 1)).join('0') + unpadded
			}).join(''),2);
			var data = string.substr(offset + 4 + 4, len);
			offset += 4 + 4 + len;
			chunks[id] = chunks[id] || [];

			if (id == 'RIFF' || id == 'LIST') {
				chunks[id].push(parseRIFF(data));
			} else {
				chunks[id].push(data);
			}
		}
		return chunks;
	}

	// here's a little utility function that acts as a utility for other functions
	// basically, the only purpose is for encoding "Duration", which is encoded as
	// a double (considerably more difficult to encode than an integer)
	function doubleToString(num){
		return [].slice.call(
			new Uint8Array(
				(
					new Float64Array([num]) //create a float64 array
				).buffer) //extract the array buffer
			, 0) // convert the Uint8Array into a regular array
			.map(function(e){ //since it's a regular array, we can now use map
				return String.fromCharCode(e) // encode all the bytes individually
			})
			.reverse() //correct the byte endianness (assume it's little endian for now)
			.join('') // join the bytes in holy matrimony as a string
	}

	function toDataURL(video){
		return 'data:video/webm;base64,' + btoa(video);
	}

	function WhammyOutput(str){
		this.str = str;
		this.size = str.length;
	}
	WhammyOutput.prototype.toBlob = function(){
		return new Blob([this.str], {
			type: "video/webm"
		});
	}
	WhammyOutput.prototype.toObjectURL = function(){
		return (window.URL || window.webkitURL).createObjectURL(this.toBlob())
	}
	WhammyOutput.prototype.toDataURL = function(){
		return toDataURL(this.str)
	}
	WhammyOutput.prototype.toString = function(){
		return this.toObjectURL(); // TODO: fall back to data urls
		// return this.toDataURL()
	}

	function WhammyVideo(speed, quality){ // a more abstract-ish API
		this.frames = [];
		this.duration = 1000 / speed;
		this.quality = quality || 0.8;
	}

	WhammyVideo.prototype.add = function(frame, duration){
		if(typeof duration != 'undefined' && this.duration) throw "you can't pass a duration if the fps is set";
		if('canvas' in frame){ //CanvasRenderingContext2D
			frame = frame.canvas;
		}
		if('toDataURL' in frame){
			frame = frame.toDataURL('image/webp', this.quality)
		}else if(typeof frame != "string"){
			throw "frame must be a a HTMLCanvasElement, a CanvasRenderingContext2D or a DataURI formatted string"
		}
		if (!(/^data:image\/webp;base64,/ig).test(frame)) {
			throw "Input must be formatted properly as a base64 encoded DataURI of type image/webp";
		}
		this.frames.push({
			image: frame,
			duration: duration || this.duration
		})
	}

	WhammyVideo.prototype.compile = function(){
		return new WhammyOutput(toWebM(this.frames.map(function(frame){
			var webp = parseWebP(parseRIFF(atob(frame.image.slice(23))));
			webp.duration = frame.duration;
			return webp;
		})))
	}

	return {
		Video: WhammyVideo,
		fromImageArray: function(images, fps){
			return toDataURL(toWebM(images.map(function(image){
				var webp = parseWebP(parseRIFF(atob(image.slice(23))))
				webp.duration = 1000 / fps;
				return webp;
			})))
		},
		toWebM: toWebM,
		toDataURL: toDataURL
		// expose methods of madness
	}
})()<|endoftext|>


<commit_before>/*
 * printThis v1.5
 * @desc Printing plug-in for jQuery
 * @author Jason Day
 *
 * Resources (based on) :
 *              jPrintArea: http://plugins.jquery.com/project/jPrintArea
 *              jqPrint: https://github.com/permanenttourist/jquery.jqprint
 *              Ben Nadal: http://www.bennadel.com/blog/1591-Ask-Ben-Print-Part-Of-A-Web-Page-With-jQuery.htm
 *
 * Licensed under the MIT licence:
 *              http://www.opensource.org/licenses/mit-license.php
 *
 * (c) Jason Day 2015
 *
 * Usage:
 *
 *  $("#mySelector").printThis({
 *      debug: false,               * show the iframe for debugging
 *      importCSS: true,            * import page CSS
 *      importStyle: false,         * import style tags
 *      printContainer: true,       * grab outer container as well as the contents of the selector
 *      loadCSS: "path/to/my.css",  * path to additional css file - us an array [] for multiple
 *      pageTitle: "",              * add title to print page
 *      removeInline: false,        * remove all inline styles from print elements
 *      printDelay: 333,            * variable print delay
 *      header: null,               * prefix to html
 *      formValues: true            * preserve input/form values
 *  });
 *
 * Notes:
 *  - the loadCSS will load additional css (with or without @media print) into the iframe, adjusting layout
 */
;
(function($) {
    var opt;
    $.fn.printThis = function(options) {
        opt = $.extend({}, $.fn.printThis.defaults, options);
        var $element = this instanceof jQuery ? this : $(this);

        var strFrameName = "printThis-" + (new Date()).getTime();

        if (window.location.hostname !== document.domain && navigator.userAgent.match(/msie/i)) {
            // Ugly IE hacks due to IE not inheriting document.domain from parent
            // checks if document.domain is set by comparing the host name against document.domain
            var iframeSrc = "javascript:document.write(\"\")";
            var printI = document.createElement('iframe');
            printI.name = "printIframe";
            printI.id = strFrameName;
            printI.className = "MSIE";
            document.body.appendChild(printI);
            printI.src = iframeSrc;

        } else {
            // other browsers inherit document.domain, and IE works if document.domain is not explicitly set
            var $frame = $("");
            $frame.appendTo("body");
        }

        var $iframe = $("#" + strFrameName);

        // show frame if in debug mode
        if (!opt.debug) $iframe.css({
            position: "absolute",
            width: "0px",
            height: "0px",
            left: "-600px",
            top: "-600px"
        });

        // $iframe.ready() and $iframe.load were inconsistent between browsers
        setTimeout(function() {

            // Add doctype to fix the style difference between printing and render
            function setDocType($iframe,doctype){
                var win, doc;
                win = $iframe.get(0);
                win = win.contentWindow || win.contentDocument || win;
                doc = win.document || win.contentDocument || win;
                doc.open();
                doc.write(doctype);
                doc.close();
            }
            if(opt.doctypeString){
                setDocType($iframe,opt.doctypeString);
            }

            var $doc = $iframe.contents(),
                $head = $doc.find("head"),
                $body = $doc.find("body");

            // add base tag to ensure elements use the parent domain
            $head.append('<base href="' + document.location.protocol + '//' + document.location.host + '">');

            // import page stylesheets
            if (opt.importCSS) $("link[rel=stylesheet]").each(function() {
                var href = $(this).attr("href");
                if (href) {
                    var media = $(this).attr("media") || "all";
                    $head.append("<link type='text/css' rel='stylesheet' href='" + href + "' media='" + media + "'>")
                }
            });

            // import style tags
            if (opt.importStyle) $("style").each(function() {
                $(this).clone().appendTo($head);
                //$head.append($(this));
            });

            //add title of the page
            if (opt.pageTitle) $head.append("<title>" + opt.pageTitle + "</title>");

            // import additional stylesheet(s)
            if (opt.loadCSS) {
               if( $.isArray(opt.loadCSS)) {
                    jQuery.each(opt.loadCSS, function(index, value) {
                       $head.append("<link type='text/css' rel='stylesheet' href='" + this + "'>");
                    });
                } else {
                    $head.append("<link type='text/css' rel='stylesheet' href='" + opt.loadCSS + "'>");
                }
            }

            // print header
            if (opt.header) $body.append(opt.header);

            // grab $.selector as container
            if (opt.printContainer) $body.append($element.outer());

            // otherwise just print interior elements of container
            else $element.each(function() {
                $body.append($(this).html());
            });

            // capture form/field values
            if (opt.formValues) {
                // loop through inputs
                var $input = $element.find('input');
                if ($input.length) {
                    $input.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $checker = $this.is(':checkbox') || $this.is(':radio'),
                            $iframeInput = $doc.find('input[name="' + $name + '"]'),
                            $value = $this.val();

                        //order matters here
                        if (!$checker) {
                            $iframeInput.val($value);
                        } else if ($this.is(':checked')) {
                            if ($this.is(':checkbox')) {
                                $iframeInput.attr('checked', 'checked');
                            } else if ($this.is(':radio')) {
                                $doc.find('input[name="' + $name + '"][value=' + $value + ']').attr('checked', 'checked');
                            }
                        }

                    });
                }

                //loop through selects
                var $select = $element.find('select');
                if ($select.length) {
                    $select.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $value = $this.val();
                        $doc.find('select[name="' + $name + '"]').val($value);
                    });
                }

                //loop through textareas
                var $textarea = $element.find('textarea');
                if ($textarea.length) {
                    $textarea.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $value = $this.val();
                        $doc.find('textarea[name="' + $name + '"]').val($value);
                    });
                }
            } // end capture form/field values

            // remove inline styles
            if (opt.removeInline) {
                // $.removeAttr available jQuery 1.7+
                if ($.isFunction($.removeAttr)) {
                    $doc.find("body *").removeAttr("style");
                } else {
                    $doc.find("body *").attr("style", "");
                }
            }

            setTimeout(function() {
                if ($iframe.hasClass("MSIE")) {
                    // check if the iframe was created with the ugly hack
                    // and perform another ugly hack out of neccessity
                    window.frames["printIframe"].focus();
                    $head.append("");
                } else {
                    // proper method
                    if (document.queryCommandSupported("print")) {
                        $iframe[0].contentWindow.document.execCommand("print", false, null);
                    } else {
                        $iframe[0].contentWindow.focus();
                        $iframe[0].contentWindow.print();
                    }
                }

                //remove iframe after print
                if (!opt.debug) {
                    setTimeout(function() {
                        $iframe.remove();
                    }, 1000);
                }

            }, opt.printDelay);

        }, 333);

    };

    // defaults
    $.fn.printThis.defaults = {
        debug: false,           // show the iframe for debugging
        importCSS: true,        // import parent page css
        importStyle: false,     // import style tags
        printContainer: true,   // print outer container/$.selector
        loadCSS: "",            // load an additional css file - load multiple stylesheets with an array []
        pageTitle: "",          // add title to print page
        removeInline: false,    // remove all inline styles
        printDelay: 333,        // variable print delay
        header: null,           // prefix to html
        formValues: true,        // preserve input/form values
        doctypeString: '<!DOCTYPE html>' // html doctype
    };

    // $.selector container
    jQuery.fn.outer = function() {
        return $($("

").html(this.clone())).html()
    }
})(jQuery);
<commit_msg>Can now preserve the BASE tag from the original page<commit_after>/*
 * printThis v1.5
 * @desc Printing plug-in for jQuery
 * @author Jason Day
 *
 * Resources (based on) :
 *              jPrintArea: http://plugins.jquery.com/project/jPrintArea
 *              jqPrint: https://github.com/permanenttourist/jquery.jqprint
 *              Ben Nadal: http://www.bennadel.com/blog/1591-Ask-Ben-Print-Part-Of-A-Web-Page-With-jQuery.htm
 *
 * Licensed under the MIT licence:
 *              http://www.opensource.org/licenses/mit-license.php
 *
 * (c) Jason Day 2015
 *
 * Usage:
 *
 *  $("#mySelector").printThis({
 *      debug: false,               * show the iframe for debugging
 *      importCSS: true,            * import page CSS
 *      importStyle: false,         * import style tags
 *      printContainer: true,       * grab outer container as well as the contents of the selector
 *      loadCSS: "path/to/my.css",  * path to additional css file - us an array [] for multiple
 *      pageTitle: "",              * add title to print page
 *      removeInline: false,        * remove all inline styles from print elements
 *      printDelay: 333,            * variable print delay
 *      header: null,               * prefix to html
 *      base: true,                 * preserve the BASE tag
 *      formValues: true            * preserve input/form values
 *  });
 *
 * Notes:
 *  - the loadCSS will load additional css (with or without @media print) into the iframe, adjusting layout
 */
;
(function($) {
    var opt;
    $.fn.printThis = function(options) {
        opt = $.extend({}, $.fn.printThis.defaults, options);
        var $element = this instanceof jQuery ? this : $(this);

        var strFrameName = "printThis-" + (new Date()).getTime();

        if (window.location.hostname !== document.domain && navigator.userAgent.match(/msie/i)) {
            // Ugly IE hacks due to IE not inheriting document.domain from parent
            // checks if document.domain is set by comparing the host name against document.domain
            var iframeSrc = "javascript:document.write(\"\")";
            var printI = document.createElement('iframe');
            printI.name = "printIframe";
            printI.id = strFrameName;
            printI.className = "MSIE";
            document.body.appendChild(printI);
            printI.src = iframeSrc;

        } else {
            // other browsers inherit document.domain, and IE works if document.domain is not explicitly set
            var $frame = $("");
            $frame.appendTo("body");
        }

        var $iframe = $("#" + strFrameName);

        // show frame if in debug mode
        if (!opt.debug) $iframe.css({
            position: "absolute",
            width: "0px",
            height: "0px",
            left: "-600px",
            top: "-600px"
        });

        // $iframe.ready() and $iframe.load were inconsistent between browsers
        setTimeout(function() {

            // Add doctype to fix the style difference between printing and render
            function setDocType($iframe,doctype){
                var win, doc;
                win = $iframe.get(0);
                win = win.contentWindow || win.contentDocument || win;
                doc = win.document || win.contentDocument || win;
                doc.open();
                doc.write(doctype);
                doc.close();
            }
            if(opt.doctypeString){
                setDocType($iframe,opt.doctypeString);
            }

            var $doc = $iframe.contents(),
                $head = $doc.find("head"),
                $body = $doc.find("body");

            // add base tag to ensure elements use the parent domain
			if (opt.base && $('base').length > 0) {
				// take the base tag from the original page
				$head.append('<base href="' + $('base').attr('href') + '">');
			} else {
				$head.append('<base href="' + document.location.protocol + '//' + document.location.host + '">');
			}

            // import page stylesheets
            if (opt.importCSS) $("link[rel=stylesheet]").each(function() {
                var href = $(this).attr("href");
                if (href) {
                    var media = $(this).attr("media") || "all";
                    $head.append("<link type='text/css' rel='stylesheet' href='" + href + "' media='" + media + "'>")
                }
            });

            // import style tags
            if (opt.importStyle) $("style").each(function() {
                $(this).clone().appendTo($head);
                //$head.append($(this));
            });

            //add title of the page
            if (opt.pageTitle) $head.append("<title>" + opt.pageTitle + "</title>");

            // import additional stylesheet(s)
            if (opt.loadCSS) {
               if( $.isArray(opt.loadCSS)) {
                    jQuery.each(opt.loadCSS, function(index, value) {
                       $head.append("<link type='text/css' rel='stylesheet' href='" + this + "'>");
                    });
                } else {
                    $head.append("<link type='text/css' rel='stylesheet' href='" + opt.loadCSS + "'>");
                }
            }

            // print header
            if (opt.header) $body.append(opt.header);

            // grab $.selector as container
            if (opt.printContainer) $body.append($element.outer());

            // otherwise just print interior elements of container
            else $element.each(function() {
                $body.append($(this).html());
            });

            // capture form/field values
            if (opt.formValues) {
                // loop through inputs
                var $input = $element.find('input');
                if ($input.length) {
                    $input.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $checker = $this.is(':checkbox') || $this.is(':radio'),
                            $iframeInput = $doc.find('input[name="' + $name + '"]'),
                            $value = $this.val();

                        //order matters here
                        if (!$checker) {
                            $iframeInput.val($value);
                        } else if ($this.is(':checked')) {
                            if ($this.is(':checkbox')) {
                                $iframeInput.attr('checked', 'checked');
                            } else if ($this.is(':radio')) {
                                $doc.find('input[name="' + $name + '"][value=' + $value + ']').attr('checked', 'checked');
                            }
                        }

                    });
                }

                //loop through selects
                var $select = $element.find('select');
                if ($select.length) {
                    $select.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $value = $this.val();
                        $doc.find('select[name="' + $name + '"]').val($value);
                    });
                }

                //loop through textareas
                var $textarea = $element.find('textarea');
                if ($textarea.length) {
                    $textarea.each(function() {
                        var $this = $(this),
                            $name = $(this).attr('name'),
                            $value = $this.val();
                        $doc.find('textarea[name="' + $name + '"]').val($value);
                    });
                }
            } // end capture form/field values

            // remove inline styles
            if (opt.removeInline) {
                // $.removeAttr available jQuery 1.7+
                if ($.isFunction($.removeAttr)) {
                    $doc.find("body *").removeAttr("style");
                } else {
                    $doc.find("body *").attr("style", "");
                }
            }

            setTimeout(function() {
                if ($iframe.hasClass("MSIE")) {
                    // check if the iframe was created with the ugly hack
                    // and perform another ugly hack out of neccessity
                    window.frames["printIframe"].focus();
                    $head.append("");
                } else {
                    // proper method
                    if (document.queryCommandSupported("print")) {
                        $iframe[0].contentWindow.document.execCommand("print", false, null);
                    } else {
                        $iframe[0].contentWindow.focus();
                        $iframe[0].contentWindow.print();
                    }
                }

                //remove iframe after print
                if (!opt.debug) {
                    setTimeout(function() {
                        $iframe.remove();
                    }, 1000);
                }

            }, opt.printDelay);

        }, 333);

    };

    // defaults
    $.fn.printThis.defaults = {
        debug: false,           // show the iframe for debugging
        importCSS: true,        // import parent page css
        importStyle: false,     // import style tags
        printContainer: true,   // print outer container/$.selector
        loadCSS: "",            // load an additional css file - load multiple stylesheets with an array []
        pageTitle: "",          // add title to print page
        removeInline: false,    // remove all inline styles
        printDelay: 333,        // variable print delay
        header: null,           // prefix to html
        formValues: true,       // preserve input/form values
		base: true,             // preserve the base tag (if available)
        doctypeString: '<!DOCTYPE html>' // html doctype
    };

    // $.selector container
    jQuery.fn.outer = function() {
        return $($("

").html(this.clone())).html()
    }
})(jQuery);<|endoftext|>


<commit_before>import { arr, obj, string } from "lively.lang";
import { pt, Color, Rectangle } from "lively.graphics";
import { show, Label, morph, Morph, GridLayout } from "./index.js";
import { connect, signal } from "lively.bindings";
import { ShadowObject } from "./rendering/morphic-default.js";

export default class Window extends Morph {

  static get properties() {
    return {
      title:        {after: ["submorphs"]},
      targetMorph:  {after: ["submorphs"]},
      submorphs:    {defaultValue: [], initialize() { return this.controls(); }},
      dropShadow:   {initialize() { return new ShadowObject(true); }},
      fill:         {defaultValue: Color.lightGray},
      borderRadius: {defaultValue: 7},
      borderColor:  {defaultValue: Color.gray},
      borderWidth:  {defaultValue: 1},
      clipMode:     {defaultValue: "hidden"},
      resizable:    {defaultValue: true}
    }
  }

  constructor(props = {}) {
    super(props);
    this.resetPropertyCache();
    this.relayoutWindowControls();
    connect(this, "extent", this, "relayoutWindowControls");
    connect(this.titleLabel(), "value", this, "relayoutWindowControls");
  }

  get isWindow() { return true }

  get targetMorph() { return arr.withoutAll(this.submorphs, this.controls())[0]; }
  set targetMorph(morph) {
    var ctrls = this.controls();
    arr.withoutAll(this.submorphs, ctrls).forEach(ea => ea.remove());
    if (morph) this.addMorph(morph, ctrls[0]);
    this.whenRendered().then(() => this.relayoutWindowControls());
  }

  targetMorphBounds() { return new Rectangle(0, 25, this.width, this.height - 25); }

  resetPropertyCache() {
    // For remembering the position and extents of the window states
    this.propertyCache = {
      nonMinizedBounds: null,
      nonMaximizedBounds: null,
      minimizedBounds: null
    };
  }

  relayoutWindowControls() {
    var innerB = this.innerBounds(),
        title = this.titleLabel(),
        labelBounds = innerB.withHeight(25),
        buttonOffset = arr.last(this.buttons()).bounds().right() + 3,
        minLabelBounds = labelBounds.withLeftCenter(pt(buttonOffset, labelBounds.height/2));

    // resizer
    this.resizer().bottomRight = innerB.bottomRight();

    // targetMorph
    if (this.targetMorph)
      this.targetMorph.setBounds(this.targetMorphBounds());

    // title
    title.textBounds().width < labelBounds.width - 2*buttonOffset ?
      title.center = labelBounds.center() :
      title.leftCenter = minLabelBounds.leftCenter();
  }

  controls() {
    return this.buttons().concat(this.titleLabel()).concat(this.resizable ? this.resizer() : []);
  }

  buttons() {

    let defaultStyle = {
      type: "ellipse",
      extent: pt(14,14),
      onHoverIn() { this.submorphs[0].visible = true; },
      onHoverOut() { this.submorphs[0].visible = false; }
    };

    return arr.compact([

      this.getSubmorphNamed("close") || morph({
        ...defaultStyle,
        name: "close",
        center: pt(15,13),
        borderColor: Color.darkRed,
        fill: Color.rgb(255,96,82),
        onMouseDown: (evt) => { this.close(); },
        submorphs: [
          Label.icon("times", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      }),

      this.getSubmorphNamed("minimize") || morph({
        ...defaultStyle,
        center: pt(35,13),
        name: "minimize",
        borderColor: Color.brown,
        fill: Color.rgb(255,190,6),
        onMouseDown: (evt) => { this.toggleMinimize(); },
        submorphs: [
          Label.icon("minus", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      }),

      this.resizable ? (this.getSubmorphNamed("maximize") || morph({
        ...defaultStyle,
        name: "maximize",
        center: pt(55,13),
        borderColor: Color.darkGreen,
        fill: Color.green,
        onMouseDown: (evt) => { this.toggleMaximize(); },
        submorphs: [
          Label.icon("plus", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      })) : undefined
    ]);
  }

  titleLabel() {
    return this.getSubmorphNamed("titleLabel") || morph({
      padding: Rectangle.inset(0, 2, 0, 0),
      type: "label",
      name: "titleLabel",
      fill: null,
      fontColor: Color.darkGray,
      reactsToPointer: false,
      value: ""
    });
  }

  resizer() {
    const win = this;
    return this.getSubmorphNamed("resizer") || morph({
      name: "resizer",
      nativeCursor: "nwse-resize",
      extent: pt(20,20),
      fill: Color.transparent,
      bottomRight: this.extent,
      onDrag(evt) {
        win.resizeBy(evt.state.dragDelta);
        this.bottomRight = win.extent;
      }
    });
  }

  get title() { return this.titleLabel().textString; }
  set title(title) {
    var textAndAttrs = typeof title === "string" ? [[title, {}]] : title,
        maxLength = 100, length = 0, truncated = [];
    for (let ea of textAndAttrs) {
      let [string, attr] = ea;
      string = string.replace(/\n/g, "");
      var delta = string.length + length - maxLength;
      if (delta > 0) string = string.slice(0, -delta);
      truncated.push([string, attr || {}]);
      if (length >= maxLength) break;
    }
    this.titleLabel().value = truncated;
  }

  toggleMinimize() {
    var cache = this.propertyCache,
        bounds = this.bounds(),
        duration = 200,
        easing = Expo.easeOut;
    if (this.minimized) {
      cache.minimizedBounds = bounds;
      this.animate({bounds: cache.nonMinizedBounds || bounds, duration, easing});
    } else {
      cache.nonMinizedBounds = bounds;
      var minimizedBounds = cache.minimizedBounds || bounds.withExtent(pt(this.width, 25)),
          labelBounds = this.titleLabel().textBounds(),
          buttonOffset = arr.last(this.buttons()).bounds().right() + 3;
      if (labelBounds.width + 2*buttonOffset < minimizedBounds.width)
        minimizedBounds = minimizedBounds.withWidth(labelBounds.width + buttonOffset + 3);
      cache.minimizedBounds = minimizedBounds;
      this.animate({bounds: cache.minimizedBounds, duration, easing});
    }
    this.minimized = !this.minimized;
    this.resizer().visible = !this.minimized;
  }

  toggleMaximize() {
    var cache = this.propertyCache,
        easing = Expo.easeOut,
        duration = 200;
    if (this.maximized) {
      this.animate({bounds: cache.nonMaximizedBounds, duration, easing});
      this.resizer().bottomRight = this.extent;
      this.maximized = false;
    } else {
      cache.nonMaximizedBounds = this.bounds();
      this.animate({bounds: this.world().visibleBounds().insetBy(5), duration, easing});
      this.resizer().visible = true;
      this.maximized = true;
      this.minimized = false;
    }
  }

  close() {
    var world = this.world();
    this.deactivate();
    this.remove();

    var next = world.activeWindow() || arr.last(world.getWindows());
    next && next.activate();

    signal(this, "windowClosed", this);
    if (this.targetMorph && typeof this.targetMorph.onWindowClose === "function")
      this.targetMorph.onWindowClose();
  }

  onMouseDown(evt) {
    this.activate();
  }

  focus() {
    var w = this.world(), t = this.targetMorph;
    if (!w || !t) return;
    if (w.focusedMorph && (w.focusedMorph === t || t.isAncestorOf(w.focusedMorph))) return;
    t.focus();
  }

  isActive() {
    var w = this.world();
    if (!w) return false;
    if (this.titleLabel().fontWeight != "bold") return false;
    return arr.last(w.getWindows()) === this;
  }

  activate() {
    if (this.isActive()) { this.focus(); return this; }

    if (!this.world()) {
      this.openInWorldNearHand()
    } else this.bringToFront();
    var w = this.world() || this.env.world;

    arr.without(w.getWindows(), this).forEach(ea => ea.deactivate());
    this.titleLabel().fontWeight = "bold";
    this.focus();

    signal(this, "windowActivated", this);
    setTimeout(() => {
      this.relayoutWindowControls();
    }, 0)

    return this;
  }

  deactivate() {
    this.titleLabel().fontWeight = "normal";
    this.relayoutWindowControls();
  }
}
<commit_msg>properties: window fix<commit_after>import { arr, obj, string } from "lively.lang";
import { pt, Color, Rectangle } from "lively.graphics";
import { show, Label, morph, Morph, GridLayout } from "./index.js";
import { connect, signal } from "lively.bindings";
import { ShadowObject } from "./rendering/morphic-default.js";

export default class Window extends Morph {

  static get properties() {
    return {
      title:        {after: ["submorphs"]},
      targetMorph:  {after: ["submorphs"]},
      submorphs:    {initialize() { this.submorphs = this.controls(); }},
      dropShadow:   {initialize() { this.dropShadow = new ShadowObject(true); }},
      fill:         {defaultValue: Color.lightGray},
      borderRadius: {defaultValue: 7},
      borderColor:  {defaultValue: Color.gray},
      borderWidth:  {defaultValue: 1},
      clipMode:     {defaultValue: "hidden"},
      resizable:    {defaultValue: true}
    }
  }

  constructor(props = {}) {
    super(props);
    this.resetPropertyCache();
    this.relayoutWindowControls();
    connect(this, "extent", this, "relayoutWindowControls");
    connect(this.titleLabel(), "value", this, "relayoutWindowControls");
  }

  get isWindow() { return true }

  get targetMorph() { return arr.withoutAll(this.submorphs, this.controls())[0]; }
  set targetMorph(morph) {
    var ctrls = this.controls();
    arr.withoutAll(this.submorphs, ctrls).forEach(ea => ea.remove());
    if (morph) this.addMorph(morph, ctrls[0]);
    this.whenRendered().then(() => this.relayoutWindowControls());
  }

  targetMorphBounds() { return new Rectangle(0, 25, this.width, this.height - 25); }

  resetPropertyCache() {
    // For remembering the position and extents of the window states
    this.propertyCache = {
      nonMinizedBounds: null,
      nonMaximizedBounds: null,
      minimizedBounds: null
    };
  }

  relayoutWindowControls() {
    var innerB = this.innerBounds(),
        title = this.titleLabel(),
        labelBounds = innerB.withHeight(25),
        buttonOffset = arr.last(this.buttons()).bounds().right() + 3,
        minLabelBounds = labelBounds.withLeftCenter(pt(buttonOffset, labelBounds.height/2));

    // resizer
    this.resizer().bottomRight = innerB.bottomRight();

    // targetMorph
    if (this.targetMorph)
      this.targetMorph.setBounds(this.targetMorphBounds());

    // title
    title.textBounds().width < labelBounds.width - 2*buttonOffset ?
      title.center = labelBounds.center() :
      title.leftCenter = minLabelBounds.leftCenter();
  }

  controls() {
    return this.buttons().concat(this.titleLabel()).concat(this.resizable ? this.resizer() : []);
  }

  buttons() {

    let defaultStyle = {
      type: "ellipse",
      extent: pt(14,14),
      onHoverIn() { this.submorphs[0].visible = true; },
      onHoverOut() { this.submorphs[0].visible = false; }
    };

    return arr.compact([

      this.getSubmorphNamed("close") || morph({
        ...defaultStyle,
        name: "close",
        center: pt(15,13),
        borderColor: Color.darkRed,
        fill: Color.rgb(255,96,82),
        onMouseDown: (evt) => { this.close(); },
        submorphs: [
          Label.icon("times", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      }),

      this.getSubmorphNamed("minimize") || morph({
        ...defaultStyle,
        center: pt(35,13),
        name: "minimize",
        borderColor: Color.brown,
        fill: Color.rgb(255,190,6),
        onMouseDown: (evt) => { this.toggleMinimize(); },
        submorphs: [
          Label.icon("minus", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      }),

      this.resizable ? (this.getSubmorphNamed("maximize") || morph({
        ...defaultStyle,
        name: "maximize",
        center: pt(55,13),
        borderColor: Color.darkGreen,
        fill: Color.green,
        onMouseDown: (evt) => { this.toggleMaximize(); },
        submorphs: [
          Label.icon("plus", {
            fill: null, visible: false,
            center: defaultStyle.extent.scaleBy(.5), opacity: 0.5
          })]
      })) : undefined
    ]);
  }

  titleLabel() {
    return this.getSubmorphNamed("titleLabel") || morph({
      padding: Rectangle.inset(0, 2, 0, 0),
      type: "label",
      name: "titleLabel",
      fill: null,
      fontColor: Color.darkGray,
      reactsToPointer: false,
      value: ""
    });
  }

  resizer() {
    const win = this;
    return this.getSubmorphNamed("resizer") || morph({
      name: "resizer",
      nativeCursor: "nwse-resize",
      extent: pt(20,20),
      fill: Color.transparent,
      bottomRight: this.extent,
      onDrag(evt) {
        win.resizeBy(evt.state.dragDelta);
        this.bottomRight = win.extent;
      }
    });
  }

  get title() { return this.titleLabel().textString; }
  set title(title) {
    var textAndAttrs = typeof title === "string" ? [[title, {}]] : title,
        maxLength = 100, length = 0, truncated = [];
    for (let ea of textAndAttrs) {
      let [string, attr] = ea;
      string = string.replace(/\n/g, "");
      var delta = string.length + length - maxLength;
      if (delta > 0) string = string.slice(0, -delta);
      truncated.push([string, attr || {}]);
      if (length >= maxLength) break;
    }
    this.titleLabel().value = truncated;
  }

  toggleMinimize() {
    var cache = this.propertyCache,
        bounds = this.bounds(),
        duration = 200,
        easing = Expo.easeOut;
    if (this.minimized) {
      cache.minimizedBounds = bounds;
      this.animate({bounds: cache.nonMinizedBounds || bounds, duration, easing});
    } else {
      cache.nonMinizedBounds = bounds;
      var minimizedBounds = cache.minimizedBounds || bounds.withExtent(pt(this.width, 25)),
          labelBounds = this.titleLabel().textBounds(),
          buttonOffset = arr.last(this.buttons()).bounds().right() + 3;
      if (labelBounds.width + 2*buttonOffset < minimizedBounds.width)
        minimizedBounds = minimizedBounds.withWidth(labelBounds.width + buttonOffset + 3);
      cache.minimizedBounds = minimizedBounds;
      this.animate({bounds: cache.minimizedBounds, duration, easing});
    }
    this.minimized = !this.minimized;
    this.resizer().visible = !this.minimized;
  }

  toggleMaximize() {
    var cache = this.propertyCache,
        easing = Expo.easeOut,
        duration = 200;
    if (this.maximized) {
      this.animate({bounds: cache.nonMaximizedBounds, duration, easing});
      this.resizer().bottomRight = this.extent;
      this.maximized = false;
    } else {
      cache.nonMaximizedBounds = this.bounds();
      this.animate({bounds: this.world().visibleBounds().insetBy(5), duration, easing});
      this.resizer().visible = true;
      this.maximized = true;
      this.minimized = false;
    }
  }

  close() {
    var world = this.world();
    this.deactivate();
    this.remove();

    var next = world.activeWindow() || arr.last(world.getWindows());
    next && next.activate();

    signal(this, "windowClosed", this);
    if (this.targetMorph && typeof this.targetMorph.onWindowClose === "function")
      this.targetMorph.onWindowClose();
  }

  onMouseDown(evt) {
    this.activate();
  }

  focus() {
    var w = this.world(), t = this.targetMorph;
    if (!w || !t) return;
    if (w.focusedMorph && (w.focusedMorph === t || t.isAncestorOf(w.focusedMorph))) return;
    t.focus();
  }

  isActive() {
    var w = this.world();
    if (!w) return false;
    if (this.titleLabel().fontWeight != "bold") return false;
    return arr.last(w.getWindows()) === this;
  }

  activate() {
    if (this.isActive()) { this.focus(); return this; }

    if (!this.world()) {
      this.openInWorldNearHand()
    } else this.bringToFront();
    var w = this.world() || this.env.world;

    arr.without(w.getWindows(), this).forEach(ea => ea.deactivate());
    this.titleLabel().fontWeight = "bold";
    this.focus();

    signal(this, "windowActivated", this);
    setTimeout(() => {
      this.relayoutWindowControls();
    }, 0)

    return this;
  }

  deactivate() {
    this.titleLabel().fontWeight = "normal";
    this.relayoutWindowControls();
  }
}
<|endoftext|>


<commit_before>@import zone.js
function initialize() {
        var location = {lat: 'latitude', lng: 'longitude'};
        var map = new google.maps.Map(document.getElementById('map'), {
          center: fenway,
          zoom: 14
        var geocoder;
  var map;
  function initialize() {
    geocoder = new google.maps.Geocoder();
    var latlng = new google.maps.LatLng(1.352083, 103.819836);
    var mapOptions = {
      zoom: 8,
      center: latlng
    }
    map = new google.maps.Map(document.getElementById("map"), mapOptions);
  }

  function codeAddress() {
    var address = document.getElementById("address").value;
    geocoder.geocode( { 'address': address}, function(results, status) {
      if (status == google.maps.GeocoderStatus.OK) {
        map.setCenter(results[0].geometry.location);
        var marker = new google.maps.Marker({
            map: map,
            position: results[0].geometry.location
        });
      } else {
        alert("Geocode was not successful for the following reason: " + status);
      }
    });
  }

<commit_msg>Cleaning up window.js, converting more things to variables<commit_after>@import zone.js
function initialize() {
        var location = {lat: 'latitude', lng: 'longitude'};
        var map = new google.maps.Map(document.getElementById('map'), {
          center: location,
          zoom: 14
        var geocoder;
  var map;
  function initialize() {
    geocoder = new google.maps.Geocoder();
    var latlng = new google.maps.LatLng('latitude', 'longitude');
    var mapOptions = {
      zoom: 8,
      center: latlng
    }
    map = new google.maps.Map(document.getElementById("map"), mapOptions);
  }

  function codeAddress() {
    var address = document.getElementById("address").value;
    geocoder.geocode( { 'address': address}, function(results, status) {
      if (status == google.maps.GeocoderStatus.OK) {
        map.setCenter(results[0].geometry.location);
        var marker = new google.maps.Marker({
            map: map,
            position: results[0].geometry.location
        });
      } else {
        alert("Geocode was not successful for the following reason: " + status);
      }
    });
  }

<|endoftext|>


<commit_before>import React from 'react';
import PropTypes from 'prop-types';
import { Table } from 'antd';

const DataTable = ({ model, data, children, translate, rowKey, params, total, setParams, ...rest }) => {

  const columns = React.Children.map(children, (child, index) => {

    const { source, ...rest } = child.props;

    return ({
      title: translate(`models.${model}.fields.${source}`),
      dataIndex: source,
      key: index,
      render: (value, record) => React.cloneElement(child, {
        record
      }),
      ...rest,
    })
  });

  const handleChange = (pagination, filters, sorter) => {
    const newParams = {
      _page: pagination.current,
      _limit: pagination.pageSize,
    };
    if (sorter.field && sorter.order !== false) {
      newParams._sort = sorter.field;
      newParams._order = sorter.order === "descend" ? "desc" : "asc";
    } else {
      newParams._sort = null;
      newParams._order = "asc";
    }
    setParams(newParams);
  };

  return (

  );

};

DataTable.defaultProps = {
  data: [],
  rowKey: "id",
  params: {},
  total: 0,
};

DataTable.propTypes = {
  model: PropTypes.string,
  data: PropTypes.array,
  translate: PropTypes.func,
  rowKey: PropTypes.string,
  params: PropTypes.object,
  total: PropTypes.number,
  setParams: PropTypes.func,
};

export default DataTable;<commit_msg>表格支持按钮<commit_after>import React from 'react';
import PropTypes from 'prop-types';
import { Table } from 'antd';

const DataTable = ({ model, data, children, translate, rowKey, params, total, setParams, ...rest }) => {

  const columns = React.Children.map(children, (child, index) => {

    const { source, ...rest } = child.props;

    return ({
      title: source ? translate(`models.${model}.fields.${source}`) : "",
      dataIndex: source,
      key: index,
      render: (value, record) => React.cloneElement(child, {
        record,
        model,
      }),
      ...rest,
    })
  });

  const handleChange = (pagination, filters, sorter) => {
    const newParams = {
      _page: pagination.current,
      _limit: pagination.pageSize,
    };
    if (sorter.field && sorter.order !== false) {
      newParams._sort = sorter.field;
      newParams._order = sorter.order === "descend" ? "desc" : "asc";
    } else {
      newParams._sort = null;
      newParams._order = "asc";
    }
    setParams(newParams);
  };

  return (

  );

};

DataTable.defaultProps = {
  data: [],
  rowKey: "id",
  params: {},
  total: 0,
};

DataTable.propTypes = {
  model: PropTypes.string,
  data: PropTypes.array,
  translate: PropTypes.func,
  rowKey: PropTypes.string,
  params: PropTypes.object,
  total: PropTypes.number,
  setParams: PropTypes.func,
};

export default DataTable;<|endoftext|>


<commit_before>import { Mongo } from 'meteor/mongo';
import { SimpleSchema } from 'meteor/aldeed:simple-schema';

class StudentCollection extends Mongo.Collection{

}
<commit_msg>Done basic Student Schema<commit_after>import { Mongo } from 'meteor/mongo';
import { SimpleSchema } from 'meteor/aldeed:simple-schema';

class StudentCollection extends Mongo.Collection{
  insert(studentData, callBack){
    const studentDocument = studentData;
    let result;
    //validate document
    result = super.insert( studentDocument, callBack);
    return result;
  };

  update(updatedModule, callBack){
    const studentDocument = updatedModule;

    const result = super.update(studentDocument, callback);

    return result;
  };

  remove(selector){
    const result = super.remove(selector);
    return result;
  };
}

Students = new StudentCollection();
StudentSchema = {
  _id: {
    Type: 'String',
  },
  studentEmail: {
    Type: 'String',
  },
  studentPlannerID:{
    Type: '[String]',
  },
  studentExemptionModule: {
    Type: '[String]',
    optional: true,
  },
  studentAcademicCohort: {
    Type: 'String',
    optional: false,
  },
  studentPreviousHighestEducation: {
    Type: 'String',
    optional: true,
  }
}

Students.attachSchema(StudentSchema);
<|endoftext|>


<commit_before>import { Component, provide } from '@angular/core';
import {bootstrap} from '@angular/platform-browser-dynamic';
import {LocationStrategy, HashLocationStrategy, Location} from '@angular/common';
import {
	Routes,
	Route,
	ROUTER_PROVIDERS,
	ROUTER_DIRECTIVES
} from '@angular/router';

// Video Component
@Component({
    selector: 'my-video',
    template: `

I LOVE THIS VIDEO!

        `,

    styles: [`h1{background:#0f0;}`]
})
class Video { }

//Music Component
@Component({
    selector: 'my-music',
    template: `

THAT'S FANTASTIC MUSIC!, RoutParams: {{id}}

        `,
    styles: [`h1{background:#f00;}`]
})
class Music {
	routerOnActivate(curr, prev, currTree, prevTree) {
		this.id =  curr.getParam('id');
	}
 }

@Component({
    selector: 'my-router',
	directives: [ROUTER_DIRECTIVES],
    template : `

            video |
            music

            <router-outlet></router-outlet>

    `

})
@Routes([
    new Route({path: '/video', component: Video, useAsDefault: true }),
    new Route({path:'/music/:id', component:Music })
])
class App{}

bootstrap(App, [
    ROUTER_PROVIDERS,
    provide(LocationStrategy, { useClass: HashLocationStrategy })
]);<commit_msg>update to angular2 rc.1<commit_after>import { Component, provide } from '@angular/core';
import {bootstrap} from '@angular/platform-browser-dynamic';
import {LocationStrategy, HashLocationStrategy, Location} from '@angular/common';
import {
	Routes,
	Route,
	ROUTER_PROVIDERS,
	ROUTER_DIRECTIVES
} from '@angular/router';

// Video Component
@Component({
    selector: 'my-video',
    template: `

I LOVE THIS VIDEO!

        `,

    styles: [`h1{background:#0f0;}`]
})
class Video { }

//Music Component
@Component({
    selector: 'my-music',
    template: `

THAT'S FANTASTIC MUSIC!, RoutParams: {{id}}

        `,
    styles: [`h1{background:#f00;}`]
})
class Music {
	routerOnActivate(curr, prev, currTree, prevTree) {
		this.id =  curr.getParam('id');
	}
 }

@Component({
    selector: 'my-router',
	directives: [ROUTER_DIRECTIVES],
    template : `

            video |
            music

            <router-outlet></router-outlet>

    `

})
@Routes([
    new Route({path: '/video', component: Video }),
    new Route({path:'/music/:id', component:Music })
])
class App{
    constructor(location:Location) {
        location.go('/video');
    }
}

bootstrap(App, [
    ROUTER_PROVIDERS,
    provide(LocationStrategy, { useClass: HashLocationStrategy })
]);<|endoftext|>