<commit_before>// Backbone.NativeView.js 0.2.2
// ---------------

//     (c) 2014 Adam Krebs, Jimmy Yuen Ho Wong
//     Backbone.NativeView may be freely distributed under the MIT license.
//     For all details and documentation:
//     https://github.com/akre54/Backbone.NativeView

(function (factory) {
  if (typeof define === 'function' && define.amd) { define(['underscore', 'backbone'], factory);
  } else if (typeof exports === 'object') { factory(require('underscore'), require('backbone'));
  } else { factory(_, Backbone); }
}(function (_, Backbone) {
  // Cached regex to match an opening '<' of an HTML tag, possibly left-padded
  // with whitespace.
  var paddedLt = /^\s*</;

  // Caches a local reference to `Element.prototype` for faster access.
  var ElementProto = (typeof Element !== 'undefined' && Element.prototype) || {};

  // Cross-browser event listener shims
  var elementAddEventListener = ElementProto.addEventListener || function(eventName, listener) {
    return this.attachEvent('on' + eventName, listener);
  }
  var elementRemoveEventListener = ElementProto.removeEventListener || function(eventName, listener) {
    return this.detachEvent('on' + eventName, listener);
  }

  // Find the right `Element#matches` for IE>=9 and modern browsers.
  var matchesSelector = ElementProto && ElementProto.matches ||
      ElementProto[_.find(['webkit', 'moz', 'ms', 'o'], function(prefix) {
        return !!ElementProto[prefix + 'MatchesSelector'];
      }) + 'MatchesSelector'] ||
      // Make our own `Element#matches` for IE8
      function(selector) {
        // We'll use querySelectorAll to find all element matching the selector,
        // then check if the given element is included in that list.
        // Executing the query on the parentNode reduces the resulting nodeList,
        // document doesn't have a parentNode, though.
        var nodeList = (this.parentNode || document).querySelectorAll(selector) || [];
        for (var i = 0, l = nodeList.length; i < l; i++) {
          if (nodeList[i] == this) return true;
        }
        return false;
      };

  // Cache Backbone.View for later access in constructor
  var BBView = Backbone.View;

  // To extend an existing view to use native methods, extend the View prototype
  // with the mixin: _.extend(MyView.prototype, Backbone.NativeViewMixin);
  Backbone.NativeViewMixin = {

    _domEvents: null,

    constructor: function() {
      this._domEvents = [];
      return BBView.apply(this, arguments);
    },

    $: function(selector) {
      return this.el.querySelectorAll(selector);
    },

    _removeElement: function() {
      this.undelegateEvents();
      if (this.el.parentNode) this.el.parentNode.removeChild(this.el);
    },

    _setElement: function(element) {
      if (typeof element == 'string') {
        if (paddedLt.test(element)) {
          var el = document.createElement('div');
          el.innerHTML = element;
          this.el = el.firstChild;
        } else {
          this.el = document.querySelector(element);
        }
      } else {
        this.el = element;
      }
    },

    _setAttributes: function(attrs) {
      for (var attr in attrs) {
        attr in this.el ? this.el[attr] = attrs[attr] : this.el.setAttribute(attr, attrs[attr]);
      }
    },

    // Make a event delegation handler for the given `eventName` and `selector`
    // and attach it to `this.el`.
    // If selector is empty, the listener will be bound to `this.el`. If not, a
    // new handler that will recursively traverse up the event target's DOM
    // hierarchy looking for a node that matches the selector. If one is found,
    // the event's `delegateTarget` property is set to it and the return the
    // result of calling bound `listener` with the parameters given to the
    // handler.
    delegate: function(eventName, selector, listener) {
      if (_.isFunction(selector)) {
        listener = selector;
        selector = null;
      }

      var root = this.el, handler;
      if (!selector) handler = listener;
      else handler = function (e) {
        var node = e.target || e.srcElement;
        for (; node && node != root; node = node.parentNode) {
          if (matchesSelector.call(node, selector)) {
            e.delegateTarget = node;
            return listener.apply(this, arguments);
          }
        }
      };

      elementAddEventListener.call(root, eventName, handler, false);
      this._domEvents.push({eventName: eventName, handler: handler, listener: listener, selector: selector});
      return handler;
    },

    // Remove a single delegated event. Either `eventName` or `selector` must
    // be included, `selector` and `listener` are optional.
    undelegate: function(eventName, selector, listener) {
      if (_.isFunction(selector)) {
        listener = selector;
        selector = null;
      }

      var handlers = this._domEvents;

      if (this.el) {
        _(handlers).chain()
          .filter(function(item) {
            return item.eventName === eventName &&
              (listener ? item.listener === listener : true) &&
              (selector ? item.selector === selector : true);
          })
          .forEach(function(item) {
            elementRemoveEventListener.call(this.el, item.eventName, item.handler, false);
            handlers.splice(_.indexOf(handlers, item), 1);
          }, this);
      }
      return this;
    },

    // Remove all events created with `delegate` from `el`
    undelegateEvents: function() {
      if (this.el) {
        _.each(this._domEvents, function(item) {
          elementRemoveEventListener.call(this.el, item.eventName, item.handler, false);
        }, this);
        this._domEvents = [];
      }
      return this;
    }
  };

  Backbone.NativeView = Backbone.View.extend(Backbone.NativeViewMixin);

  return Backbone.NativeView;
}));
<commit_msg>style cleanup. remove some underscore-specific features<commit_after>// Backbone.NativeView.js 0.2.2
// ---------------

//     (c) 2014 Adam Krebs, Jimmy Yuen Ho Wong
//     Backbone.NativeView may be freely distributed under the MIT license.
//     For all details and documentation:
//     https://github.com/akre54/Backbone.NativeView

(function (factory) {
  if (typeof define === 'function' && define.amd) { define(['underscore', 'backbone'], factory);
  } else if (typeof exports === 'object') { factory(require('underscore'), require('backbone'));
  } else { factory(_, Backbone); }
}(function (_, Backbone) {
  // Cached regex to match an opening '<' of an HTML tag, possibly left-padded
  // with whitespace.
  var paddedLt = /^\s*</;

  // Caches a local reference to `Element.prototype` for faster access.
  var ElementProto = (typeof Element !== 'undefined' && Element.prototype) || {};

  // Cross-browser event listener shims
  var elementAddEventListener = ElementProto.addEventListener || function(eventName, listener) {
    return this.attachEvent('on' + eventName, listener);
  }
  var elementRemoveEventListener = ElementProto.removeEventListener || function(eventName, listener) {
    return this.detachEvent('on' + eventName, listener);
  }

  // Find the right `Element#matches` for IE>=9 and modern browsers.
  var matchesSelector = ElementProto && ElementProto.matches ||
      ElementProto[_.find(['webkit', 'moz', 'ms', 'o'], function(prefix) {
        return !!ElementProto[prefix + 'MatchesSelector'];
      }) + 'MatchesSelector'] ||
      // Make our own `Element#matches` for IE8
      function(selector) {
        // We'll use querySelectorAll to find all element matching the selector,
        // then check if the given element is included in that list.
        // Executing the query on the parentNode reduces the resulting nodeList,
        // document doesn't have a parentNode, though.
        var nodeList = (this.parentNode || document).querySelectorAll(selector) || [];
        for (var i = 0, l = nodeList.length; i < l; i++) {
          if (nodeList[i] == this) return true;
        }
        return false;
      };

  // Cache Backbone.View for later access in constructor
  var BBView = Backbone.View;

  // To extend an existing view to use native methods, extend the View prototype
  // with the mixin: _.extend(MyView.prototype, Backbone.NativeViewMixin);
  Backbone.NativeViewMixin = {

    _domEvents: null,

    constructor: function() {
      this._domEvents = [];
      return BBView.apply(this, arguments);
    },

    $: function(selector) {
      return this.el.querySelectorAll(selector);
    },

    _removeElement: function() {
      this.undelegateEvents();
      if (this.el.parentNode) this.el.parentNode.removeChild(this.el);
    },

    _setElement: function(element) {
      if (typeof element == 'string') {
        if (paddedLt.test(element)) {
          var el = document.createElement('div');
          el.innerHTML = element;
          this.el = el.firstChild;
        } else {
          this.el = document.querySelector(element);
        }
      } else {
        this.el = element;
      }
    },

    _setAttributes: function(attrs) {
      for (var attr in attrs) {
        attr in this.el ? this.el[attr] = attrs[attr] : this.el.setAttribute(attr, attrs[attr]);
      }
    },

    // Make a event delegation handler for the given `eventName` and `selector`
    // and attach it to `this.el`.
    // If selector is empty, the listener will be bound to `this.el`. If not, a
    // new handler that will recursively traverse up the event target's DOM
    // hierarchy looking for a node that matches the selector. If one is found,
    // the event's `delegateTarget` property is set to it and the return the
    // result of calling bound `listener` with the parameters given to the
    // handler.
    delegate: function(eventName, selector, listener) {
      if (typeof selector === 'function') {
        listener = selector;
        selector = null;
      }

      var handler = selector ? function (e) {
        var node = e.target || e.srcElement;
        for (; node && node != this.el; node = node.parentNode) {
          if (matchesSelector.call(node, selector)) {
            e.delegateTarget = node;
            return listener.apply(this, arguments);
          }
        }
      } : listener;

      elementAddEventListener.call(this.el, eventName, handler, false);
      this._domEvents.push({eventName: eventName, handler: handler, listener: listener, selector: selector});
      return handler;
    },

    // Remove a single delegated event. Either `eventName` or `selector` must
    // be included, `selector` and `listener` are optional.
    undelegate: function(eventName, selector, listener) {
      if (typeof selector === 'function') {
        listener = selector;
        selector = null;
      }

      if (this.el) {
        var handlers = this._domEvents.slice();
        for (var i = 0, len = handlers.length; i < len; i++) {
          var item = handlers[i];

          var match = item.eventName === eventName &&
              (listener ? item.listener === listener : true) &&
              (selector ? item.selector === selector : true);

          if (!match) continue;

          elementRemoveEventListener.call(this.el, item.eventName, item.handler, false);
          this._domEvents.splice(_.indexOf(handlers, item), 1);
        }
      }
      return this;
    },

    // Remove all events created with `delegate` from `el`
    undelegateEvents: function() {
      if (this.el) {
        for (var i = 0, len = this._domEvents.length; i < len; i++) {
          var item = this._domEvents[i];
          elementRemoveEventListener.call(this.el, item.eventName, item.handler, false);
        };
        this._domEvents = [];
      }
      return this;
    }
  };

  Backbone.NativeView = Backbone.View.extend(Backbone.NativeViewMixin);

  return Backbone.NativeView;
}));
<|endoftext|>


<commit_before>"use strict";
/*global process require exports console */

// Copyright 2011 Chris Williams <chris@iterativedesigns.com>

var Buffer = require('buffer').Buffer;
var SerialPortBinding = require("bindings")("serialport.node");
var util = require('util');
var fs = require('fs');
var stream = require('stream');
var path = require('path');
var async = require('async');
var child_process = require('child_process');

var BAUDRATES = [500000, 230400, 115200, 57600, 38400, 19200, 9600, 4800, 2400, 1800, 1200, 600, 300, 200, 150, 134, 110, 75, 50];
var DATABITS = [8, 7, 6, 5];
var STOPBITS = [1, 2, 1.5];
var PARITY = ['none', 'even', 'mark', 'odd', 'space'];
var FLOWCONTROL = [false, true];

var parsers = {
  raw: function (emitter, buffer) {
    emitter.emit("data", buffer);
  },
  readline: function (delimiter) {
    if (typeof delimiter === "undefined" || delimiter === null) { delimiter = "\r"; }
    // Delimiter buffer saved in closure
    var data = "";
    return function (emitter, buffer) {
      // Collect data
      data += buffer.toString();
      // Split collected data by delimiter
      var parts = data.split(delimiter)
      data = parts.pop();
      parts.forEach(function (part, i, array) {
        emitter.emit('data', part);
      });
    };
  }
};

// The default options, can be overwritten in the 'SerialPort' constructor
var _options = {
  baudrate: 9600,
  databits: 8,
  stopbits: 1,
  parity: 'none',
  flowcontrol: false,
  buffersize: 255,
  parser: parsers.raw
};
function SerialPort (path, options, openImmediately) {
  options = options || {};
  options.__proto__ = _options;
  openImmediately = (openImmediately === undefined || openImmediately === null) ? true : openImmediately;

  var self = this;

  if (BAUDRATES.indexOf(options.baudrate) == -1) {
    throw new Error('Invalid "baudrate": ' + options.baudrate);
  }
  if (DATABITS.indexOf(options.databits) == -1) {
    throw new Error('Invalid "databits": ' + options.databits);
  }
  if (STOPBITS.indexOf(options.stopbits) == -1) {
    throw new Error('Invalid "stopbits": ' + options.stopbits);
  }
  if (PARITY.indexOf(options.parity) == -1) {
    throw new Error('Invalid "parity": ' + options.parity);
  }
  if (FLOWCONTROL.indexOf(options.flowcontrol) == -1) {
    throw new Error('Invalid "flowcontrol": ' + options.flowcontrol);
  }
  if (!path) {
    throw new Error('Invalid port specified: ' + path);
  }

  stream.Stream.call(this);

  options = options || {};
  options.baudRate = options.baudRate || options.baudrate || 9600;
  options.dataBits = options.dataBits || options.databits || 8;
  options.parity = options.parity || 'none';
  options.stopBits = options.stopBits || options.stopbits || 1;
  options.bufferSize = options.bufferSize || options.buffersize || 100;
  if (!('flowControl' in options)) {
    options.flowControl = false;
  }
  options.dataCallback = function (data) {
    options.parser(self, data);
  };
  options.errorCallback = function (err) {
    self.emit('error', err);
  };
  options.disconnectedCallback = function () {
    if (self.closing) {
      return;
    }
    self.emit('error', new Error("Disconnected"));
    self.close();
  };

  if (process.platform == 'win32') {
    path = '\\\\.\\' + path;
  }

  this.options = options;
  this.path = path;

  if (openImmediately) {
    process.nextTick(function () {
      self.open();
    });
  }
}

util.inherits(SerialPort, stream.Stream);

SerialPort.prototype.open = function (callback) {
  var self = this;
  SerialPortBinding.open(this.path, this.options, function (err, fd) {
    self.fd = fd;
    if (err) {
      return self.emit('error', err);
    }
    if (process.platform !== 'win32') {
      self.readStream = fs.createReadStream(self.path, { bufferSize: self.options.bufferSize, fd: fd });
      self.readStream.on("data", self.options.dataCallback);
      self.readStream.on("error", self.options.errorCallback);
      self.readStream.on("close", function () {
        self.close();
      });
      self.readStream.on("end", function () {
        self.emit('end');
      });
    }

    self.emit('open');
    if (callback) { callback(err); }
  });
};

SerialPort.prototype.write = function (buffer, callback) {
  var self = this;
  if (!this.fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  if (!Buffer.isBuffer(buffer)) {
    buffer = new Buffer(buffer);
  }
  SerialPortBinding.write(this.fd, buffer, function (err, results) {
    if (err) {
      self.emit('error', err);
    }
    if (callback) {
      callback(err, results);
    }
  });
};

SerialPort.prototype.close = function (callback) {
  var self = this;

  var fd = this.fd;
  this.fd = 0;

  if (self.closing) {
    return;
  }
  if (!fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  self.closing = true;
  try {
    if (self.readStream) {
      self.readStream.destroy();
    }

    SerialPortBinding.close(fd, function (err) {
      if (err) {
        self.emit('error', err);
      }
      if (callback) {
        callback(err);
      }
      self.emit('close');
      self.closing = false;
    });
  } catch (ex) {
    self.closing = false;
    throw ex;
  }
};

function listUnix (callback) {
  fs.readdir("/dev/serial/by-id", function (err, files) {
    if (err) {
      // if this directory is not found this could just be because it's not plugged in
      if (err.errno === 34) {
        return callback(null, []);
      }
      return console.log(err);
    }
    var dirName = "/dev/serial/by-id";
    async.map(files, function (file, callback) {
      var fileName = path.join(dirName, file);
      fs.readlink(fileName, function (err, link) {
        if (err) {
          return callback(err);
        }
        link = path.resolve(dirName, link);
        callback(null, {
          comName: link,
          manufacturer: undefined,
          pnpId: file
        });
      });
    // Suspect code per ticket: #104 removed for deeper inspection.
    // fs.readdir("/dev/serial/by-path", function(err_path, paths) {
    //   if (err_path) {
    //     if (err.errno === 34) return callback(null, []);
    //     return console.log(err);
    //   }

    //   var dirName, items;
    //   //check if multiple devices of the same id are connected
    //   if (files.length !== paths.length) {
    //     dirName = "/dev/serial/by-path";
    //     items = paths;
    //   } else {
    //     dirName = "/dev/serial/by-id";
    //     items = files;
    //   }

    //   async.map(items, function (file, callback) {
    //     var fileName = path.join(dirName, file);
    //     fs.readlink(fileName, function (err, link) {
    //       if (err) {
    //         return callback(err);
    //       }
    //       link = path.resolve(dirName, link);
    //       callback(null, {
    //         comName: link,
    //         manufacturer: undefined,
    //         pnpId: file
    //       });
    //     });
    //   }, callback);
    }, callback);
  });
}

exports.list = function (callback) {
  if (process.platform === 'win32') {
    SerialPortBinding.list(callback);
  } else if (process.platform === 'darwin') {
    SerialPortBinding.list(callback);
  } else {
    listUnix(callback);
  }
};

SerialPort.prototype.flush = function (callback) {
  var self = this;
  var fd = this.fd;

  if (!fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  SerialPortBinding.flush(fd, function (err, result) {
    if (err) {
      self.emit('error', err);
    }
    if (callback) {
      callback(err, result);
    }
  });
};

module.exports.SerialPort = SerialPort;
module.exports.parsers = parsers;
<commit_msg>clean better on close<commit_after>"use strict";
/*global process require exports console */

// Copyright 2011 Chris Williams <chris@iterativedesigns.com>

var Buffer = require('buffer').Buffer;
var SerialPortBinding = require("bindings")("serialport.node");
var util = require('util');
var fs = require('fs');
var stream = require('stream');
var path = require('path');
var async = require('async');
var child_process = require('child_process');

var BAUDRATES = [500000, 230400, 115200, 57600, 38400, 19200, 9600, 4800, 2400, 1800, 1200, 600, 300, 200, 150, 134, 110, 75, 50];
var DATABITS = [8, 7, 6, 5];
var STOPBITS = [1, 2, 1.5];
var PARITY = ['none', 'even', 'mark', 'odd', 'space'];
var FLOWCONTROL = [false, true];

var parsers = {
  raw: function (emitter, buffer) {
    emitter.emit("data", buffer);
  },
  readline: function (delimiter) {
    if (typeof delimiter === "undefined" || delimiter === null) { delimiter = "\r"; }
    // Delimiter buffer saved in closure
    var data = "";
    return function (emitter, buffer) {
      // Collect data
      data += buffer.toString();
      // Split collected data by delimiter
      var parts = data.split(delimiter)
      data = parts.pop();
      parts.forEach(function (part, i, array) {
        emitter.emit('data', part);
      });
    };
  }
};

// The default options, can be overwritten in the 'SerialPort' constructor
var _options = {
  baudrate: 9600,
  databits: 8,
  stopbits: 1,
  parity: 'none',
  flowcontrol: false,
  buffersize: 255,
  parser: parsers.raw
};
function SerialPort (path, options, openImmediately) {
  options = options || {};
  options.__proto__ = _options;
  openImmediately = (openImmediately === undefined || openImmediately === null) ? true : openImmediately;

  var self = this;

  if (BAUDRATES.indexOf(options.baudrate) == -1) {
    throw new Error('Invalid "baudrate": ' + options.baudrate);
  }
  if (DATABITS.indexOf(options.databits) == -1) {
    throw new Error('Invalid "databits": ' + options.databits);
  }
  if (STOPBITS.indexOf(options.stopbits) == -1) {
    throw new Error('Invalid "stopbits": ' + options.stopbits);
  }
  if (PARITY.indexOf(options.parity) == -1) {
    throw new Error('Invalid "parity": ' + options.parity);
  }
  if (FLOWCONTROL.indexOf(options.flowcontrol) == -1) {
    throw new Error('Invalid "flowcontrol": ' + options.flowcontrol);
  }
  if (!path) {
    throw new Error('Invalid port specified: ' + path);
  }

  stream.Stream.call(this);

  options = options || {};
  options.baudRate = options.baudRate || options.baudrate || 9600;
  options.dataBits = options.dataBits || options.databits || 8;
  options.parity = options.parity || 'none';
  options.stopBits = options.stopBits || options.stopbits || 1;
  options.bufferSize = options.bufferSize || options.buffersize || 100;
  if (!('flowControl' in options)) {
    options.flowControl = false;
  }
  options.dataCallback = function (data) {
    options.parser(self, data);
  };
  options.errorCallback = function (err) {
    self.emit('error', err);
  };
  options.disconnectedCallback = function () {
    if (self.closing) {
      return;
    }
    self.emit('error', new Error("Disconnected"));
    self.close();
  };

  if (process.platform == 'win32') {
    path = '\\\\.\\' + path;
  }

  this.options = options;
  this.path = path;

  if (openImmediately) {
    process.nextTick(function () {
      self.open();
    });
  }
}

util.inherits(SerialPort, stream.Stream);

SerialPort.prototype.open = function (callback) {
  var self = this;
  SerialPortBinding.open(this.path, this.options, function (err, fd) {
    self.fd = fd;
    if (err) {
      return self.emit('error', err);
    }
    if (process.platform !== 'win32') {
      self.readStream = fs.createReadStream(self.path, { bufferSize: self.options.bufferSize, fd: fd });
      self.readStream.on("data", self.options.dataCallback);
      self.readStream.on("error", self.options.errorCallback);
      self.readStream.on("close", function () {
        self.close();
      });
      self.readStream.on("end", function () {
        self.emit('end');
      });
    }

    self.emit('open');
    if (callback) { callback(err); }
  });
};

SerialPort.prototype.write = function (buffer, callback) {
  var self = this;
  if (!this.fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  if (!Buffer.isBuffer(buffer)) {
    buffer = new Buffer(buffer);
  }
  SerialPortBinding.write(this.fd, buffer, function (err, results) {
    if (err) {
      self.emit('error', err);
    }
    if (callback) {
      callback(err, results);
    }
  });
};

SerialPort.prototype.close = function (callback) {
  var self = this;

  var fd = this.fd;
  this.fd = 0;

  if (self.closing) {
    return;
  }
  if (!fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  self.closing = true;
  try {
    if (self.readStream) {
      self.readStream.destroy();
    }

    SerialPortBinding.close(fd, function (err) {
      if (err) {
        self.emit('error', err);
      }
      if (callback) {
        callback(err);
      }
      self.emit('close');
      self.removeAllListeners();
      self.closing = false;
    });
  } catch (ex) {
    self.closing = false;
    throw ex;
  }
};

function listUnix (callback) {
  fs.readdir("/dev/serial/by-id", function (err, files) {
    if (err) {
      // if this directory is not found this could just be because it's not plugged in
      if (err.errno === 34) {
        return callback(null, []);
      }
      return console.log(err);
    }
    var dirName = "/dev/serial/by-id";
    async.map(files, function (file, callback) {
      var fileName = path.join(dirName, file);
      fs.readlink(fileName, function (err, link) {
        if (err) {
          return callback(err);
        }
        link = path.resolve(dirName, link);
        callback(null, {
          comName: link,
          manufacturer: undefined,
          pnpId: file
        });
      });
    // Suspect code per ticket: #104 removed for deeper inspection.
    // fs.readdir("/dev/serial/by-path", function(err_path, paths) {
    //   if (err_path) {
    //     if (err.errno === 34) return callback(null, []);
    //     return console.log(err);
    //   }

    //   var dirName, items;
    //   //check if multiple devices of the same id are connected
    //   if (files.length !== paths.length) {
    //     dirName = "/dev/serial/by-path";
    //     items = paths;
    //   } else {
    //     dirName = "/dev/serial/by-id";
    //     items = files;
    //   }

    //   async.map(items, function (file, callback) {
    //     var fileName = path.join(dirName, file);
    //     fs.readlink(fileName, function (err, link) {
    //       if (err) {
    //         return callback(err);
    //       }
    //       link = path.resolve(dirName, link);
    //       callback(null, {
    //         comName: link,
    //         manufacturer: undefined,
    //         pnpId: file
    //       });
    //     });
    //   }, callback);
    }, callback);
  });
}

exports.list = function (callback) {
  if (process.platform === 'win32') {
    SerialPortBinding.list(callback);
  } else if (process.platform === 'darwin') {
    SerialPortBinding.list(callback);
  } else {
    listUnix(callback);
  }
};

SerialPort.prototype.flush = function (callback) {
  var self = this;
  var fd = this.fd;

  if (!fd) {
    if (callback) {
      return callback(new Error("Serialport not open."));
    } else {
      return;
    }
  }

  SerialPortBinding.flush(fd, function (err, result) {
    if (err) {
      self.emit('error', err);
    }
    if (callback) {
      callback(err, result);
    }
  });
};

module.exports.SerialPort = SerialPort;
module.exports.parsers = parsers;
<|endoftext|>


<commit_before>import webpack from 'webpack';
import WebpackDevServer from 'webpack-dev-server';
import config from './webpack.config.babel';
import open from 'open';

const webpackServer = new WebpackDevServer(webpack(config), config.devServer);

webpackServer.listen(config.port, 'localhost', (err) => {
  if (err) {
    console.log(err);
  }

  console.log(`Listening at localhost: ${config.devServer.port}`);
  console.log('Opening your system browser...');
  open(`http://localhost:${config.devServer.port}/webpack-dev-server/`);
});
<commit_msg>Allow console.log statement in server<commit_after>/* eslint no-console: 0 */

import webpack from 'webpack';
import WebpackDevServer from 'webpack-dev-server';
import config from './webpack.config.babel';
import open from 'open';

const webpackServer = new WebpackDevServer(webpack(config), config.devServer);

webpackServer.listen(config.port, 'localhost', (err) => {
  if (err) {
    console.log(err);
  }

  console.log(`Listening at localhost: ${config.devServer.port}`);
  console.log('Opening your system browser...');
  open(`http://localhost:${config.devServer.port}/webpack-dev-server/`);
});
<|endoftext|>


<commit_before>import _ from 'lodash'
import PropTypes from 'prop-types'
import React, { Component } from 'react'
import { Checkbox } from 'semantic-ui-react'

import { docTypes } from 'docs/src/utils'
import ComponentTable from '../ComponentTable'
import ComponentPropsComponents from './ComponentPropsComponents'
import ComponentPropsDescription from './ComponentPropsDescription'

const propsContainerStyle = { overflowX: 'auto' }

export default class ComponentProps extends Component {
  static propTypes = {
    componentsInfo: PropTypes.objectOf(docTypes.componentInfoShape).isRequired,
    displayName: PropTypes.string.isRequired,
  }

  state = {
    activeDisplayName: null,
  }

  componentWillReceiveProps(nextProps) {
    const currentName = this.props.displayName
    const nextName = nextProps.displayName

    if (currentName.displayName !== nextName) {
      this.setState({ activeDisplayName: null })
    }
  }

  handleComponentClick = (e, { name }) => {
    this.setState({ activeDisplayName: name })
  }

  handleToggle = () => {
    const { displayName } = this.props
    const { activeDisplayName } = this.state

    this.setState({ activeDisplayName: activeDisplayName ? false : displayName })
  }

  render() {
    const { displayName, componentsInfo } = this.props
    const { activeDisplayName } = this.state

    const displayNames = _.keys(componentsInfo)
    const { docblock, props } = componentsInfo[activeDisplayName] || {}
    const description = _.get(docblock, 'description', [])

    return (

        <Checkbox slider checked={!!activeDisplayName} label='Props' onClick={this.handleToggle} />
        <ComponentPropsComponents
          activeDisplayName={activeDisplayName}
          displayNames={displayNames}
          onItemClick={this.handleComponentClick}
          parentDisplayName={displayName}
        />

        {activeDisplayName && (

            <ComponentPropsDescription description={_.join(description, ' ')} />
            <ComponentTable displayName={activeDisplayName} props={props} />

        )}

    )
  }
}
<commit_msg>docs(Props): fix "Props" checkbox (#3332)<commit_after>import _ from 'lodash'
import PropTypes from 'prop-types'
import React, { Component } from 'react'
import { Checkbox } from 'semantic-ui-react'

import { docTypes } from 'docs/src/utils'
import ComponentTable from '../ComponentTable'
import ComponentPropsComponents from './ComponentPropsComponents'
import ComponentPropsDescription from './ComponentPropsDescription'

const propsContainerStyle = { overflowX: 'auto' }

export default class ComponentProps extends Component {
  static propTypes = {
    componentsInfo: PropTypes.objectOf(docTypes.componentInfoShape).isRequired,
    displayName: PropTypes.string.isRequired,
  }

  state = {
    activeDisplayName: null,
  }

  componentWillReceiveProps(nextProps) {
    const currentName = this.props.displayName
    const nextName = nextProps.displayName

    if (currentName.displayName !== nextName) {
      this.setState({ activeDisplayName: null })
    }
  }

  handleComponentClick = (e, { name }) => {
    this.setState({ activeDisplayName: name })
  }

  handleToggle = () => {
    const { displayName } = this.props
    const { activeDisplayName } = this.state

    this.setState({ activeDisplayName: activeDisplayName ? false : displayName })
  }

  render() {
    const { displayName, componentsInfo } = this.props
    const { activeDisplayName } = this.state

    const displayNames = _.keys(componentsInfo)
    const { docblock, props } = componentsInfo[activeDisplayName] || {}
    const description = _.get(docblock, 'description', [])

    return (

        <Checkbox slider checked={!!activeDisplayName} label='Props' onChange={this.handleToggle} />
        <ComponentPropsComponents
          activeDisplayName={activeDisplayName}
          displayNames={displayNames}
          onItemClick={this.handleComponentClick}
          parentDisplayName={displayName}
        />

        {activeDisplayName && (

            <ComponentPropsDescription description={_.join(description, ' ')} />
            <ComponentTable displayName={activeDisplayName} props={props} />

        )}

    )
  }
}
<|endoftext|>


<commit_before>var p2 = require('p2');
var _ = require('lodash');
var config = require('./config');

function Sim(gameState) {

    this.gameState = gameState;

    this.scoreHandler = _.noop;
    this.destroyBlockHandler = _.noop;
    this.bounceHandler = _.noop;
    this.blockPlacedHandler = _.noop;

    this.reset();

    // simulation

    this.fixedTimeStep = 1/60;
    this.maxSubSteps = 10;
    this.lastTime = process.hrtime();

}

Sim.prototype.initSensorBlocks = function SimInitSensorBlocks() {
    this.sensorBlocks = _.cloneDeep(this.gameState.grid);
    for (var y = 0; y < this.sensorBlocks.length; ++y) {
        for (var x = 0; x < this.sensorBlocks[y].length; ++x) {
            this.addSensorBlock(x, y);
        }
    }
};

Sim.prototype.update = function SimUpdate() {

    var deltaTime = process.hrtime(this.lastTime);

    this.lastTime = process.hrtime();

    this.world.step( this.fixedTimeStep, deltaTime[1]/1e9, this.maxSubSteps );

    this.pendingRemoval.forEach(this.world.removeBody.bind(this.world));
    this.pendingRemoval = [];

    this.gameState.disc.pos.x = this.discBody.position[0];
    this.gameState.disc.pos.y = this.discBody.position[1];
    this.gameState.disc.angle = this.discBody.interpolatedAngle;
    this.gameState.disc.vel.x = this.discBody.velocity[0];
    this.gameState.disc.vel.y = this.discBody.velocity[1];

    // sync the game grid with only the bodies that are in the world, to prevent ghost blocks in the grid
    for (var y = 0; y < config.GRID.HEIGHT; ++y) {
        for (var x = 0; x < config.GRID.WIDTH; ++x) {
            var grid_block = this.gameState.grid[y][x];

            if (grid_block > 0) {

                // make sure this block that is set in the grid is actually in the world, if not set to 0
                var block = _.find(this.world.bodies, { customType: 'block', customGridPosition: { x: x, y: y } });

                if (!block) {
                    console.log("ERROR: gameState grid out of sync with sim world, block in grid but not in world: ", x, y);
                    this.gameState.grid[y][x] = 0;
                }
            }
        }
    }
};

Sim.prototype.reset = function SimReset() {
    // set up p2-based physics simulation

    this.pendingRemoval = [];

    this.world = new p2.World({
        islandSplit: false,
    });
    this.world.applyGravity = false;
    this.world.applySpringForces = false;
    this.world.applyDamping = false;
    this.world.on('beginContact', this.handleCollision.bind(this));
    this.world.on('endContact', this.handleEndCollision.bind(this));

    // create materials with no friction and perfect bounce

    this.discMaterial = new p2.Material();
    this.bounceMaterial = new p2.Material();

    var bounceContactMaterial = new p2.ContactMaterial(this.bounceMaterial, this.discMaterial, {
        friction : 0.0,
        restitution: 1.0,
    });
    bounceContactMaterial.stiffness = 1e12;
    // bounceContactMaterial.relaxation = 1;
    this.world.addContactMaterial(bounceContactMaterial);

    // add blocks that detect what block the disc is touching

    this.initSensorBlocks();

    // Add a disc

    var discShape = new p2.Circle({ radius: config.DISC.DIAMETER/2 });
    discShape.material = this.discMaterial;
    this.discBody = new p2.Body({
        mass:1,
        position:[0, 0],
        angularVelocity: 0,
        angularDamping: 0,
        damping: 0,
        fixedRotation: true,
        velocity: [0, 0],
        allowSleep: false,
    });
    // start moving in random direction
    setTimeout( function() {
        p2.vec2.set( this.discBody.velocity, config.DISC.INITIAL_SPEED, 0 );
        p2.vec2.rotate( this.discBody.velocity, this.discBody.velocity, Math.random() * Math.PI * 2 );
    }.bind(this), config.DISC.MOVE_DELAY);
    this.discBody.customType = 'disc';
    this.discBody.addShape(discShape);
    this.world.addBody(this.discBody);

    // add some walls

    var topWall    = this.makeWall( [0, config.GRID.HEIGHT/2 + config.GRID.WALL_DEPTH/2],  [config.GRID.WIDTH*2, config.GRID.WALL_DEPTH] );
    var bottomWall = this.makeWall( [0, -config.GRID.HEIGHT/2 - config.GRID.WALL_DEPTH/2], [config.GRID.WIDTH*2, config.GRID.WALL_DEPTH] );
    var rightWall  = this.makeWall( [config.GRID.WIDTH/2 + config.GRID.WALL_DEPTH/2, 0],   [config.GRID.WALL_DEPTH, config.GRID.HEIGHT*2] );
    var leftWall   = this.makeWall( [-config.GRID.WIDTH/2 - config.GRID.WALL_DEPTH/2, 0],  [config.GRID.WALL_DEPTH, config.GRID.HEIGHT*2] );

    this.world.addBody( topWall    );
    this.world.addBody( bottomWall );
    this.world.addBody( rightWall  );
    this.world.addBody( leftWall   );

    // add goals

    var topGoalShape = new p2.Line({ length: config.GOAL.WIDTH });
    var bottomGoalShape = new p2.Line({ length: config.GOAL.WIDTH });
    topGoalShape.sensor = true;
    bottomGoalShape.sensor = true;
    var topGoalBody = new p2.Body({ position: [0, -config.GRID.HEIGHT/2] });
    var botGoalBody = new p2.Body({ position: [0, config.GRID.HEIGHT/2] });
    topGoalBody.addShape(topGoalShape);
    botGoalBody.addShape(bottomGoalShape);
    topGoalBody.damping = 0;
    botGoalBody.damping = 0;
    topGoalBody.customGoal = 'a';
    botGoalBody.customGoal = 'b';

    this.world.addBody(topGoalBody);
    this.world.addBody(botGoalBody);

    this.world.enableBodyCollision();
};

Sim.prototype.createBlock = function SimCreateBlock(x, y, player) {
    var blockShape = new p2.Box({ width: 1.00, height: 1.00 });
    blockShape.material = this.bounceMaterial;

    var px = -1 * config.GRID.WIDTH/2 + 1/2 + x;
    var py = -1 * config.GRID.HEIGHT/2 + 1/2 + y;

    var blockBody = new p2.Body({ position: [px, py] });
    blockBody.addShape(blockShape);
    blockBody.customPlayer = player;
    blockBody.customType = 'block';
    blockBody.customGridPosition = { x: x, y: y };

    return blockBody;
};

Sim.prototype.createSensorBlock = function SimCreateSensorBlock(x, y) {
    var sensorBlockShape = new p2.Box({ width: 1.00, height: 1.00 });
    sensorBlockShape.sensor = true;

    var px = -1 * config.GRID.WIDTH/2 + 1/2 + x;
    var py = -1 * config.GRID.HEIGHT/2 + 1/2 + y;

    var sensorBlockBody = new p2.Body({ position: [px, py] });
    sensorBlockBody.addShape(sensorBlockShape);
    sensorBlockBody.customType = 'sensor-block';
    sensorBlockBody.customGridPosition = { x: x, y: y };
    sensorBlockBody.intersectingDisc = false;

    return sensorBlockBody;
};

/**
 * Find block in world. Returns block if found, if not found returns false.
 * @return {*}
 */
Sim.prototype.findBlock = function SimBlockExists(x, y) {

    // fast loop
    var bodyNames = Object.getOwnPropertyNames(this.world.bodies);
    for (var i = 0, l = bodyNames.length; i < l; ++i) {
        var body = this.world.bodies[bodyNames[i]];

        if (body && body.customGridPosition) {
            if (body.customType === 'block' && body.customGridPosition.x === x && body.customGridPosition.y === y) {
                return body;
            }
        }
    }

    return false;
};

/**
 * Add block to the world.  If block already in world, return false, else returns body created.
 * @return {*}
 */
Sim.prototype.addBlock = function SimAddBlock(x, y, player) {

    // add block to sim

    var theBlock = this.findBlock(x, y);
    if (theBlock) {
        console.log("ERROR: Trying to add block already in world: ", x, y, theBlock.customGridPosition);

        return false;
    }

    if (this.sensorBlocks[y][x].intersectingDisc) {
        console.log('disc is there!');
        return false;
    }

    var blockBody = this.createBlock(x, y, player, true);

    this.world.addBody(blockBody);

    // update gameState grid as well

    this.gameState.grid[y][x] = player === 'a' ? 1 : 2;

    this.blockPlacedHandler();

    return blockBody;
};

/**
 * Add a block to the world that senses when the disc is intersecting it but
 * doesn't collide with the disc.
 */
Sim.prototype.addSensorBlock = function SimAddSensorBlock(x, y) {
    var sensor = this.createSensorBlock(x, y);
    this.world.addBody(sensor);
    this.sensorBlocks[y][x] = sensor;
    return sensor;
};

Sim.prototype.removeBlock = function SimRemoveBlock(x, y) {

    // find the block at x,y
    var block = this.findBlock(x,y);

    // remove it from the world if it exists
    if (block) {
        this.pendingRemoval.push(block);

        // report back the destruction
        this.destroyBlockHandler({ x: x, y: y }, block.customPlayer);
    }

    // update gameState grid as well
    this.gameState.grid[y][x] = 0;

    return block;
};

Sim.prototype.onBlockPlaced = function SimOnBlockPlaced(callback) {
    this.blockPlacedHandler = callback;
};
Sim.prototype.onScore = function SimOnScore(callback) {
    this.scoreHandler = callback;
};

Sim.prototype.onDestroyBlock = function simOnDestroyBlock(callback) {
    this.destroyBlockHandler = callback;
};

Sim.prototype.handleEndCollision = function SimHandleEndCollision(evt) {
    var obj1 = evt.bodyA;
    var obj2 = evt.bodyB;
    var disc;
    var vel;
    var speed;

    if (obj1.customType === 'sensor-block' && obj2.customType === 'disc') {
        obj1.intersectingDisc = false;
        return;
    }
    else if (obj2.customType === 'sensor-block' && obj1.customType === 'disc') {
        obj2.intersectingDisc = false;
        return;
    }

    if (obj1.customType === 'disc') { disc = obj1; }
    if (obj2.customType === 'disc') { disc = obj2; }
    if (disc) {
        vel = p2.vec2.clone( disc.velocity );
        p2.vec2.normalize( vel, vel );
        p2.vec2.scale( vel, vel, config.DISC.BOUNCE_SPEEDUP );
        p2.vec2.add( disc.velocity, disc.velocity, vel );
        speed = p2.vec2.length(disc.velocity);
        if (speed > config.DISC.MAX_SPEED) {
            p2.vec2.normalize( disc.velocity, disc.velocity );
            p2.vec2.scale( disc.velocity, disc.velocity, config.DISC.MAX_SPEED );
        }
    }
    this.bounceHandler();
};

Sim.prototype.onBounce = function SimOnBounce(callback) {
    this.bounceHandler = callback;
};

Sim.prototype.handleCollision = function SimHandleCollision(evt) {
    var obj1 = evt.bodyA;
    var obj2 = evt.bodyB;

    // if the disc hit a block, remove the block from the world
    if (obj1.customType === 'disc' && obj2.customType === 'block') {
        this.destroyBlockHandler({ x: obj2.customGridPosition.x, y: obj2.customGridPosition.y }, obj2.customPlayer);
        this.pendingRemoval.push(obj2);
        this.gameState.grid[obj2.customGridPosition.y][obj2.customGridPosition.x] = 0;
    }
    else if (obj2.customType === 'disc' && obj1.customType === 'block') {
        this.destroyBlockHandler({ x: obj1.customGridPosition.x, y: obj1.customGridPosition.y }, obj1.customPlayer);
        this.pendingRemoval.push(obj1);
        this.gameState.grid[obj1.customGridPosition.y][obj1.customGridPosition.x] = 0;
    }

    // if the disc is intersecting a sensor block, mark it as intersecting
    else if (obj1.customType === 'sensor-block' && obj2.customType === 'disc') {
        obj1.intersectingDisc = true;
    }
    else if (obj2.customType === 'sensor-block' && obj1.customType === 'disc') {
        obj2.intersectingDisc = true;
    }

    // if the disc hit a goal, SCORE!
    else if ([obj1.customGoal, obj2.customGoal].indexOf('a') >= 0) {
        this.scoreHandler('a');
    }
    else if ([obj1.customGoal, obj2.customGoal].indexOf('b') >= 0) {
        this.scoreHandler('b');
    }
};

Sim.prototype.makeWall = function SimMakeWall(position, size) {

    var wallShape = new p2.Box({ width: size[0], height: size[1] });
    wallShape.material = this.bounceMaterial;

    var wallBody = new p2.Body({ position: position });
    wallBody.addShape(wallShape);

    return wallBody;
};

module.exports = Sim;
<commit_msg>use findBlock in grid check<commit_after>var p2 = require('p2');
var _ = require('lodash');
var config = require('./config');

function Sim(gameState) {

    this.gameState = gameState;

    this.scoreHandler = _.noop;
    this.destroyBlockHandler = _.noop;
    this.bounceHandler = _.noop;
    this.blockPlacedHandler = _.noop;

    this.reset();

    // simulation

    this.fixedTimeStep = 1/60;
    this.maxSubSteps = 10;
    this.lastTime = process.hrtime();

}

Sim.prototype.initSensorBlocks = function SimInitSensorBlocks() {
    this.sensorBlocks = _.cloneDeep(this.gameState.grid);
    for (var y = 0; y < this.sensorBlocks.length; ++y) {
        for (var x = 0; x < this.sensorBlocks[y].length; ++x) {
            this.addSensorBlock(x, y);
        }
    }
};

Sim.prototype.update = function SimUpdate() {

    var deltaTime = process.hrtime(this.lastTime);

    this.lastTime = process.hrtime();

    this.world.step( this.fixedTimeStep, deltaTime[1]/1e9, this.maxSubSteps );

    this.pendingRemoval.forEach(this.world.removeBody.bind(this.world));
    this.pendingRemoval = [];

    this.gameState.disc.pos.x = this.discBody.position[0];
    this.gameState.disc.pos.y = this.discBody.position[1];
    this.gameState.disc.angle = this.discBody.interpolatedAngle;
    this.gameState.disc.vel.x = this.discBody.velocity[0];
    this.gameState.disc.vel.y = this.discBody.velocity[1];

    // sync the game grid with only the bodies that are in the world, to prevent ghost blocks in the grid
    for (var y = 0; y < config.GRID.HEIGHT; ++y) {
        for (var x = 0; x < config.GRID.WIDTH; ++x) {
            var grid_block = this.gameState.grid[y][x];

            if (grid_block > 0) {

                // make sure this block that is set in the grid is actually in the world, if not set to 0
                var block = this.findBlock(x, y);

                if (!block) {
                    console.log("ERROR: gameState grid out of sync with sim world, block in grid but not in world: ", x, y);
                    this.gameState.grid[y][x] = 0;
                }
            }
        }
    }
};

Sim.prototype.reset = function SimReset() {
    // set up p2-based physics simulation

    this.pendingRemoval = [];

    this.world = new p2.World({
        islandSplit: false,
    });
    this.world.applyGravity = false;
    this.world.applySpringForces = false;
    this.world.applyDamping = false;
    this.world.on('beginContact', this.handleCollision.bind(this));
    this.world.on('endContact', this.handleEndCollision.bind(this));

    // create materials with no friction and perfect bounce

    this.discMaterial = new p2.Material();
    this.bounceMaterial = new p2.Material();

    var bounceContactMaterial = new p2.ContactMaterial(this.bounceMaterial, this.discMaterial, {
        friction : 0.0,
        restitution: 1.0,
    });
    bounceContactMaterial.stiffness = 1e12;
    // bounceContactMaterial.relaxation = 1;
    this.world.addContactMaterial(bounceContactMaterial);

    // add blocks that detect what block the disc is touching

    this.initSensorBlocks();

    // Add a disc

    var discShape = new p2.Circle({ radius: config.DISC.DIAMETER/2 });
    discShape.material = this.discMaterial;
    this.discBody = new p2.Body({
        mass:1,
        position:[0, 0],
        angularVelocity: 0,
        angularDamping: 0,
        damping: 0,
        fixedRotation: true,
        velocity: [0, 0],
        allowSleep: false,
    });
    // start moving in random direction
    setTimeout( function() {
        p2.vec2.set( this.discBody.velocity, config.DISC.INITIAL_SPEED, 0 );
        p2.vec2.rotate( this.discBody.velocity, this.discBody.velocity, Math.random() * Math.PI * 2 );
    }.bind(this), config.DISC.MOVE_DELAY);
    this.discBody.customType = 'disc';
    this.discBody.addShape(discShape);
    this.world.addBody(this.discBody);

    // add some walls

    var topWall    = this.makeWall( [0, config.GRID.HEIGHT/2 + config.GRID.WALL_DEPTH/2],  [config.GRID.WIDTH*2, config.GRID.WALL_DEPTH] );
    var bottomWall = this.makeWall( [0, -config.GRID.HEIGHT/2 - config.GRID.WALL_DEPTH/2], [config.GRID.WIDTH*2, config.GRID.WALL_DEPTH] );
    var rightWall  = this.makeWall( [config.GRID.WIDTH/2 + config.GRID.WALL_DEPTH/2, 0],   [config.GRID.WALL_DEPTH, config.GRID.HEIGHT*2] );
    var leftWall   = this.makeWall( [-config.GRID.WIDTH/2 - config.GRID.WALL_DEPTH/2, 0],  [config.GRID.WALL_DEPTH, config.GRID.HEIGHT*2] );

    this.world.addBody( topWall    );
    this.world.addBody( bottomWall );
    this.world.addBody( rightWall  );
    this.world.addBody( leftWall   );

    // add goals

    var topGoalShape = new p2.Line({ length: config.GOAL.WIDTH });
    var bottomGoalShape = new p2.Line({ length: config.GOAL.WIDTH });
    topGoalShape.sensor = true;
    bottomGoalShape.sensor = true;
    var topGoalBody = new p2.Body({ position: [0, -config.GRID.HEIGHT/2] });
    var botGoalBody = new p2.Body({ position: [0, config.GRID.HEIGHT/2] });
    topGoalBody.addShape(topGoalShape);
    botGoalBody.addShape(bottomGoalShape);
    topGoalBody.damping = 0;
    botGoalBody.damping = 0;
    topGoalBody.customGoal = 'a';
    botGoalBody.customGoal = 'b';

    this.world.addBody(topGoalBody);
    this.world.addBody(botGoalBody);

    this.world.enableBodyCollision();
};

Sim.prototype.createBlock = function SimCreateBlock(x, y, player) {
    var blockShape = new p2.Box({ width: 1.00, height: 1.00 });
    blockShape.material = this.bounceMaterial;

    var px = -1 * config.GRID.WIDTH/2 + 1/2 + x;
    var py = -1 * config.GRID.HEIGHT/2 + 1/2 + y;

    var blockBody = new p2.Body({ position: [px, py] });
    blockBody.addShape(blockShape);
    blockBody.customPlayer = player;
    blockBody.customType = 'block';
    blockBody.customGridPosition = { x: x, y: y };

    return blockBody;
};

Sim.prototype.createSensorBlock = function SimCreateSensorBlock(x, y) {
    var sensorBlockShape = new p2.Box({ width: 1.00, height: 1.00 });
    sensorBlockShape.sensor = true;

    var px = -1 * config.GRID.WIDTH/2 + 1/2 + x;
    var py = -1 * config.GRID.HEIGHT/2 + 1/2 + y;

    var sensorBlockBody = new p2.Body({ position: [px, py] });
    sensorBlockBody.addShape(sensorBlockShape);
    sensorBlockBody.customType = 'sensor-block';
    sensorBlockBody.customGridPosition = { x: x, y: y };
    sensorBlockBody.intersectingDisc = false;

    return sensorBlockBody;
};

/**
 * Find block in world. Returns block if found, if not found returns false.
 * @return {*}
 */
Sim.prototype.findBlock = function SimBlockExists(x, y) {

    // fast loop
    var bodyNames = Object.getOwnPropertyNames(this.world.bodies);
    for (var i = 0, l = bodyNames.length; i < l; ++i) {
        var body = this.world.bodies[bodyNames[i]];

        if (body && body.customGridPosition) {
            if (body.customType === 'block' && body.customGridPosition.x === x && body.customGridPosition.y === y) {
                return body;
            }
        }
    }

    return false;
};

/**
 * Add block to the world.  If block already in world, return false, else returns body created.
 * @return {*}
 */
Sim.prototype.addBlock = function SimAddBlock(x, y, player) {

    // add block to sim

    var theBlock = this.findBlock(x, y);
    if (theBlock) {
        console.log("ERROR: Trying to add block already in world: ", x, y, theBlock.customGridPosition);

        return false;
    }

    if (this.sensorBlocks[y][x].intersectingDisc) {
        console.log('disc is there!');
        return false;
    }

    var blockBody = this.createBlock(x, y, player, true);

    this.world.addBody(blockBody);

    // update gameState grid as well

    this.gameState.grid[y][x] = player === 'a' ? 1 : 2;

    this.blockPlacedHandler();

    return blockBody;
};

/**
 * Add a block to the world that senses when the disc is intersecting it but
 * doesn't collide with the disc.
 */
Sim.prototype.addSensorBlock = function SimAddSensorBlock(x, y) {
    var sensor = this.createSensorBlock(x, y);
    this.world.addBody(sensor);
    this.sensorBlocks[y][x] = sensor;
    return sensor;
};

Sim.prototype.removeBlock = function SimRemoveBlock(x, y) {

    // find the block at x,y
    var block = this.findBlock(x,y);

    // remove it from the world if it exists
    if (block) {
        this.pendingRemoval.push(block);

        // report back the destruction
        this.destroyBlockHandler({ x: x, y: y }, block.customPlayer);
    }

    // update gameState grid as well
    this.gameState.grid[y][x] = 0;

    return block;
};

Sim.prototype.onBlockPlaced = function SimOnBlockPlaced(callback) {
    this.blockPlacedHandler = callback;
};
Sim.prototype.onScore = function SimOnScore(callback) {
    this.scoreHandler = callback;
};

Sim.prototype.onDestroyBlock = function simOnDestroyBlock(callback) {
    this.destroyBlockHandler = callback;
};

Sim.prototype.handleEndCollision = function SimHandleEndCollision(evt) {
    var obj1 = evt.bodyA;
    var obj2 = evt.bodyB;
    var disc;
    var vel;
    var speed;

    if (obj1.customType === 'sensor-block' && obj2.customType === 'disc') {
        obj1.intersectingDisc = false;
        return;
    }
    else if (obj2.customType === 'sensor-block' && obj1.customType === 'disc') {
        obj2.intersectingDisc = false;
        return;
    }

    if (obj1.customType === 'disc') { disc = obj1; }
    if (obj2.customType === 'disc') { disc = obj2; }
    if (disc) {
        vel = p2.vec2.clone( disc.velocity );
        p2.vec2.normalize( vel, vel );
        p2.vec2.scale( vel, vel, config.DISC.BOUNCE_SPEEDUP );
        p2.vec2.add( disc.velocity, disc.velocity, vel );
        speed = p2.vec2.length(disc.velocity);
        if (speed > config.DISC.MAX_SPEED) {
            p2.vec2.normalize( disc.velocity, disc.velocity );
            p2.vec2.scale( disc.velocity, disc.velocity, config.DISC.MAX_SPEED );
        }
    }
    this.bounceHandler();
};

Sim.prototype.onBounce = function SimOnBounce(callback) {
    this.bounceHandler = callback;
};

Sim.prototype.handleCollision = function SimHandleCollision(evt) {
    var obj1 = evt.bodyA;
    var obj2 = evt.bodyB;

    // if the disc hit a block, remove the block from the world
    if (obj1.customType === 'disc' && obj2.customType === 'block') {
        this.destroyBlockHandler({ x: obj2.customGridPosition.x, y: obj2.customGridPosition.y }, obj2.customPlayer);
        this.pendingRemoval.push(obj2);
        this.gameState.grid[obj2.customGridPosition.y][obj2.customGridPosition.x] = 0;
    }
    else if (obj2.customType === 'disc' && obj1.customType === 'block') {
        this.destroyBlockHandler({ x: obj1.customGridPosition.x, y: obj1.customGridPosition.y }, obj1.customPlayer);
        this.pendingRemoval.push(obj1);
        this.gameState.grid[obj1.customGridPosition.y][obj1.customGridPosition.x] = 0;
    }

    // if the disc is intersecting a sensor block, mark it as intersecting
    else if (obj1.customType === 'sensor-block' && obj2.customType === 'disc') {
        obj1.intersectingDisc = true;
    }
    else if (obj2.customType === 'sensor-block' && obj1.customType === 'disc') {
        obj2.intersectingDisc = true;
    }

    // if the disc hit a goal, SCORE!
    else if ([obj1.customGoal, obj2.customGoal].indexOf('a') >= 0) {
        this.scoreHandler('a');
    }
    else if ([obj1.customGoal, obj2.customGoal].indexOf('b') >= 0) {
        this.scoreHandler('b');
    }
};

Sim.prototype.makeWall = function SimMakeWall(position, size) {

    var wallShape = new p2.Box({ width: size[0], height: size[1] });
    wallShape.material = this.bounceMaterial;

    var wallBody = new p2.Body({ position: position });
    wallBody.addShape(wallShape);

    return wallBody;
};

module.exports = Sim;
<|endoftext|>


<commit_before>var AtomScadPreview, AtomScadPreviewView, CompositeDisposable;

var path = require( 'path');

window.jsDependencies =  [ 'three.min.js', 'orbitcontrols.js', 'projector.js', 'canvasrenderer.js', 'jquery-2.1.3.min.js', 'csg.js', 'threecsg.js', 'openjscad.js', 'formats.js', 'main.js'];

jsDependencies = jsDependencies.map( function( scriptName ) {
  return path.join( atom.packages.getLoadedPackage( 'atom-scad-preview' ).path, 'standalone', scriptName );
});

AtomScadPreviewView = require('./atom-scad-preview-view');

CompositeDisposable = require('atom').CompositeDisposable;

var url = require( 'url' );

module.exports = AtomScadPreview = {
  atomScadPreviewView: null,
  modalPanel: null,
  subscriptions: null,
  activate: function(state) {
    /*
    this.atomScadPreviewView = new AtomScadPreviewView(state.atomScadPreviewViewState);

    this.modalPanel = atom.workspace.addRightPanel({
      item: this.atomScadPreviewView.getElement(),
      visible: false
    });
*/
    this.subscriptions = new CompositeDisposable;
    this.subscriptions.add(atom.commands.add('atom-workspace', {
      'atom-scad-preview:toggle': (function(_this) {
        return function() {
          return _this.toggle();
        };
      })(this)
    }));

    return atom.workspace.addOpener(function(uriToOpen) {
      var error, host, pathname, protocol, ref;

      try {
        ref = url.parse(uriToOpen), protocol = ref.protocol, host = ref.host, pathname = ref.pathname;
      } catch (_error) {
        error = _error;
        return;
      };

      if (protocol !== 'scad-preview:') {
        return;
      }
      try {
        if (pathname) {
          pathname = decodeURI(pathname);
        }
      } catch (_error) {
        error = _error;
        return;
      }

      return new AtomScadPreviewView(pathname);
      /*
      if (host === 'editor') {

        return createMarkdownPreviewView({
          editorId: pathname.substring(1)
        });
      } else {
        return createMarkdownPreviewView({
          filePath: pathname
        });
      }
      */
    });
  },
  deactivate: function() {
    this.modalPanel.destroy();
    this.subscriptions.dispose();
    return this.atomScadPreviewView.destroy();
  },
  serialize: function() {
    return {
      atomScadPreviewViewState: this.atomScadPreviewView.serialize()
    };
  },
  toggle: function() {
    console.log('AtomScadPreview was toggled!');
      var editor = atom.workspace.getActiveTextEditor(),
          activeFile = editor.getPath(),
          uri = 'scad-preview://' + activeFile;

      atom.workspace.open( uri, { split: 'right' } ).then(function( container ) {
      });
  }
};
<commit_msg>rewriting dependencies with package path<commit_after>var AtomScadPreview, AtomScadPreviewView, CompositeDisposable;

var path = require( 'path');

window.jsDependencies =  [ 'three.min.js', 'orbitcontrols.js', 'projector.js', 'canvasrenderer.js', 'jquery-2.1.3.min.js', 'csg.js', 'threecsg.js', 'openjscad.js', 'formats.js', 'main.js'];

jsDependencies = jsDependencies.map( function( scriptName ) {
  return 'file://' + path.join( atom.packages.getLoadedPackage( 'atom-scad-preview' ).path, 'standalone', scriptName );
});

AtomScadPreviewView = require('./atom-scad-preview-view');

CompositeDisposable = require('atom').CompositeDisposable;

var url = require( 'url' );

module.exports = AtomScadPreview = {
  atomScadPreviewView: null,
  modalPanel: null,
  subscriptions: null,
  activate: function(state) {
    /*
    this.atomScadPreviewView = new AtomScadPreviewView(state.atomScadPreviewViewState);

    this.modalPanel = atom.workspace.addRightPanel({
      item: this.atomScadPreviewView.getElement(),
      visible: false
    });
*/
    this.subscriptions = new CompositeDisposable;
    this.subscriptions.add(atom.commands.add('atom-workspace', {
      'atom-scad-preview:toggle': (function(_this) {
        return function() {
          return _this.toggle();
        };
      })(this)
    }));

    return atom.workspace.addOpener(function(uriToOpen) {
      var error, host, pathname, protocol, ref;

      try {
        ref = url.parse(uriToOpen), protocol = ref.protocol, host = ref.host, pathname = ref.pathname;
      } catch (_error) {
        error = _error;
        return;
      };

      if (protocol !== 'scad-preview:') {
        return;
      }
      try {
        if (pathname) {
          pathname = decodeURI(pathname);
        }
      } catch (_error) {
        error = _error;
        return;
      }

      return new AtomScadPreviewView(pathname);
      /*
      if (host === 'editor') {

        return createMarkdownPreviewView({
          editorId: pathname.substring(1)
        });
      } else {
        return createMarkdownPreviewView({
          filePath: pathname
        });
      }
      */
    });
  },
  deactivate: function() {
    this.modalPanel.destroy();
    this.subscriptions.dispose();
    return this.atomScadPreviewView.destroy();
  },
  serialize: function() {
    return {
      atomScadPreviewViewState: this.atomScadPreviewView.serialize()
    };
  },
  toggle: function() {
    console.log('AtomScadPreview was toggled!');
      var editor = atom.workspace.getActiveTextEditor(),
          activeFile = editor.getPath(),
          uri = 'scad-preview://' + activeFile;

      atom.workspace.open( uri, { split: 'right' } ).then(function( container ) {
      });
  }
};
<|endoftext|>


<commit_before>// Nitrogen Compatibility Layer

function querySourceRaw(Id) {
    var val, el = document.getElementById(Id);
    if (!el) return "";
    switch (el.tagName) {
        case 'FIELDSET': val = document.querySelector('#' + Id + ' :checked');
                         val = val ? val.value : ""; break;
        case 'INPUT':
            switch (el.getAttribute("type")) {
                case 'radio': case 'checkbox': val = el.checked ? el.value : ""; break;
                case  'date': val = new Date(Date.parse(el.value)) || ""; break;
                case  'calendar': val = pickers[el.id]._d || ""; break;  //only 4 nitro #calendar{}
                default:     var edit = el.contentEditable;
                    if (edit && edit === 'true') val = el.innerHTML;
                    else val = el.value; }
            break;
        default: var edit = el.contentEditable;
            if (edit && edit === 'true') val = el.innerHTML;
            else val = el.value; }
    return val; }

function querySource(Id) {
    var qs = querySourceRaw(Id);
    if(qs instanceof Date) { return tuple(number(qs.getFullYear()),number(qs.getMonth()+1),number(qs.getDate())); }
    else { return utf8_toByteArray(qs); } }

<commit_msg>fix errors when ids contain special characters<commit_after>// Nitrogen Compatibility Layer

function querySourceRaw(Id) {
    var val, el = document.getElementById(Id);
    if (!el) return "";
    switch (el.tagName) {
        case 'FIELDSET': val = document.querySelector('[id="' + Id + '"] :checked');
                         val = val ? val.value : ""; break;
        case 'INPUT':
            switch (el.getAttribute("type")) {
                case 'radio': case 'checkbox': val = el.checked ? el.value : ""; break;
                case  'date': val = new Date(Date.parse(el.value)) || ""; break;
                case  'calendar': val = pickers[el.id]._d || ""; break;  //only 4 nitro #calendar{}
                default:     var edit = el.contentEditable;
                    if (edit && edit === 'true') val = el.innerHTML;
                    else val = el.value; }
            break;
        default: var edit = el.contentEditable;
            if (edit && edit === 'true') val = el.innerHTML;
            else val = el.value; }
    return val; }

function querySource(Id) {
    var qs = querySourceRaw(Id);
    if(qs instanceof Date) { return tuple(number(qs.getFullYear()),number(qs.getMonth()+1),number(qs.getDate())); }
    else { return utf8_toByteArray(qs); } }
<|endoftext|>


<commit_before>(function(C2C, $) {

  // Mountain wilderness contest stuff
  function mw_associate() {
    var indicator = $('#indicator');

    indicator.show();
    $.post('/documents/addAssociation/main_id/' + $('#id').val() +
           '/document_module/articles/document_id/' + C2C.mw_contest_article_id
    ).always(function() {
      indicator.hide();
    }).fail(function(data) {
      mw_contest_associate.attr('checked', false);
      C2C.showFailure();
    });
  }

  function mw_de_associate() {
    var indicator = $('#indicator');

    indicator.show();
    $.post('/documents/removeAssociation/main_oc_id/' + $('#id').val() +
           '/linked_id/' + C2C.mw_contest_article_id + '/type/oc/strict/1'
    ).always(function() {
      indicator.hide();
    }).done(function(data) {
      $(mw_contest_associate).attr('checked', false);
    }).fail(function() {
      $(mw_contest_associate).attr('checked', true);
      C2C.showFailure();
    });
  }

  function switch_mw_contest_visibility() {
    var mw_contest = $('#mw_contest');
    var mw_contest_associate = $('#mw_contest_associate');

    if (mw_contest.length) {
      if ($('#outing_with_public_transportation').is(':checked')) {
        mw_contest.show();
      } else {
        // hide mw div, uncheck contest checkbox
        mw_contest.hide();

        if (!$('#pseudo_id').length && $(mw_contest_associate).is(':checked')) {
          // de-associated
          mw_de_associate();
        }
      }
    }
  }

  function switch_mw_contest_association() {

    mw_contest_associate = $('#mw_contest_associate');

    if (!$('#pseudo_id').length) {
      if (mw_contest_associate.is(':checked')) {
        // associate
        mw_associate();
      } else {
        // de-associated
        mw_de_associate();
      }
    }
  }

  // be sure to hide fields on startup if needed
  switch_mw_contest_visibility();

  // register events
  $('#outing_with_public_transportation').on('change', switch_mw_contest_visibility);
  $('#mw_contest_associate').on('change', switch_mw_contest_association);

})(window.C2C = window.C2C || {}, jQuery);
<commit_msg>mw code debug<commit_after>(function(C2C, $) {

  // Mountain wilderness contest stuff
  var mw_contest_associate = $('#mw_contest_associate');

  function mw_associate() {
    var indicator = $('#indicator');

    indicator.show();
    $.post('/documents/addAssociation/main_id/' + $('#id').val() +
           '/document_module/articles/document_id/' + C2C.mw_contest_article_id
    ).always(function() {
      indicator.hide();
    }).fail(function(data) {
      mw_contest_associate.prop('checked', false);
      C2C.showFailure();
    });
  }

  function mw_de_associate() {
    var indicator = $('#indicator');

    indicator.show();
    $.post('/documents/removeAssociation/main_oc_id/' + $('#id').val() +
           '/linked_id/' + C2C.mw_contest_article_id + '/type/oc/strict/1'
    ).always(function() {
      indicator.hide();
    }).done(function(data) {
      mw_contest_associate.prop('checked', false);
    }).fail(function() {
      mw_contest_associate.prop('checked', true);
      C2C.showFailure();
    });
  }

  function switch_mw_contest_visibility() {
    var mw_contest = $('#mw_contest');

    if (mw_contest.length) {
      if ($('#outing_with_public_transportation').is(':checked')) {
        mw_contest.show();
      } else {
        // hide mw div, uncheck contest checkbox
        mw_contest.hide();

        if (!$('#pseudo_id').length && mw_contest_associate.is(':checked')) {
          // de-associated
          mw_de_associate();
        }
      }
    }
  }

  function switch_mw_contest_association() {
    if (!$('#pseudo_id').length) {
      if (mw_contest_associate.is(':checked')) {
        // associate
        mw_associate();
      } else {
        // de-associated
        mw_de_associate();
      }
    }
  }

  // be sure to hide fields on startup if needed
  switch_mw_contest_visibility();

  // register events
  $('#outing_with_public_transportation').on('change', switch_mw_contest_visibility);
  mw_contest_associate.on('change', switch_mw_contest_association);

})(window.C2C = window.C2C || {}, jQuery);
<|endoftext|>


<commit_before>/*
 * Initialize a quotes database
 *
 * Inserts the quotes from
 *   _The Pragmatic Programmer_
 * into a local or mLab MongoDB database
 *
 * Problem:  How to end execution without Ctrl-c?
 *
 * Author: Peter Martinson
 * Date:   March 10, 2017
*/
var mongoose = require('mongoose');
var assert   = require('assert');  // node's native unit tester
var dotenv   = require('dotenv');
var config   = require('./config');

// var url      = process.env.MONGOLAB_URI;  // mLab database
// var url      = "mongodb://localhost:27017/pragmatic"; // local database
var url      = "mongodb://" + config.username + ":" + config.password + "@ds123400.mlab.com:23400/quotes";

mongoose.Promise = Promise;
mongoose.connect(url);

var quoteSchema = mongoose.Schema({
  quote_id:       Number,
  source:         String,
  source_href:    String,
  quote:          String,
  quote_href:     String,
  subquote:       String,
  subquote_href:  String
});

var Quote = mongoose.model('Quote', quoteSchema);

// empty the database!
Quote.remove({}, function(err) {
  assert.equal(null, err, "There's something wrong... " + err);
  console.log("database emptied.");
});

// list the quotes
var allQuotes = [
  {
    quote    : "Care About Your Craft",
    subquote : "Why spend your life developing software unless you care about doing it well?"
  },
  {
    quote    : "Think! About Your Work",
    subquote : "Turn off the autopilot and take control. Constantly critique and appraise your work."
  },
  {
    quote    : "Provide Options, Don't Make Lame Excuses",
    subquote : "Instead of excuses, provide options. Don't say it can't be done; explain what can be done."
  },
  {
    quote    : "Don't Live with Broken Windows",
    subquote : "Fix bad designs, wrong decisions, and poor code when you see them."
  },
  {
    quote    : "Be a Catalyst for Change",
    subquote : "You can't force change on people. Instead, show them how the future might be and help them participate in creating it."
  },
  {
    quote    : "Remember the Big Picture",
    subquote : "Don't get so engrossed in the details that you forget to check what's happening around you."
  },
  {
    quote    : "Make Quality a Requirements Issue",
    subquote : "Involve your users in determining the project's real quality requirements."
  },
  {
    quote    : "Invest Regularly in Your Knowledge Portfolio",
    subquote : "Make learning a habit."
  },
  {
    quote    : "Critically Analyze What You Read and Hear",
    subquote : "Don't be swayed by vendors, media hype, or dogma. Analyze information in terms of you and your project."
  },
  {
    quote    : "It's Both What You Say and the Way You Say It",
    subquote : "There's no point in having great ideas if you don't communicate them effectively."
  },
  {
    quote    : "DRY – Don't Repeat Yourself",
    subquote : "Every piece of knowledge must have a single, unambiguous, authoritative representation within a system."
  },
  {
    quote    : "Make It Easy to Reuse",
    subquote : "If it's easy to reuse, people will. Create an environment that supports reuse."
  },
  {
    quote    : "Eliminate Effects Between Unrelated Things",
    subquote : "Design components that are self-contained. independent, and have a single, well-defined purpose."
  },
  {
    quote    : "There Are No Final Decisions",
    subquote : "No decision is cast in stone. Instead, consider each as being written in the sand at the beach, and plan for change."
  },
  {
    quote    : "Use Tracer Bullets to Find the Target",
    subquote : "Tracer bullets let you home in on your target by trying things and seeing how close they land."
  },
  {
    quote    : "Prototype to Learn",
    subquote : "Prototyping is a learning experience. Its value lies not in the code you produce, but in the lessons you learn."
  },
  {
    quote    : "Program Close to the Problem Domain",
    subquote : "Design and code in your user's language."
  },
  {
    quote    : "Estimate to Avoid Surprises",
    subquote : "Estimate before you start. You'll spot potential problems up front."
  },
  {
    quote    : "Iterate the Schedule with the Code",
    subquote : "Use experience you gain as you implement to refine the project time scales."
  },
  {
    quote    : "Keep Knowledge in Plain Text",
    subquote : "Plain text won't become obsolete. It helps leverage your work and simplifies debugging and testing."
  },
  {
    quote    : "Use the Power of Command Shells",
    subquote : "Use the shell when graphical user interfaces don't cut it."
  },
  {
    quote    : "Use a Single Editor Well",
    subquote : "The editor should be an extension of your hand; make sure your editor is configurable, extensible, and programmable."
  },
  {
    quote    : "Always Use Source Code Control",
    subquote : "Source code control is a time machine for your work – you can go back."
  },
  {
    quote    : "Fix the Problem, Not the Blame",
    subquote : "It doesn't really matter whether the bug is your fault or someone else's – it is still your problem, and it still needs to be fixed."
  },
  {
    quote    : "Don't Panic When Debugging",
    subquote : "Take a deep breath and THINK! about what could be causing the bug."
  },
  {
    quote    : "'select' Isn't Broken.",
    subquote : "It is rare to find a bug in the OS or the compiler, or even a third-party product or library. The bug is most likely in the application."
  },
  {
    quote    : "Don't Assume It – Prove It",
    subquote : "Prove your assumptions in the actual environment – with real data and boundary conditions."
  },
  {
    quote    : "Learn a Text Manipulation Language.",
    subquote : "You spend a large part of each day working with text. Why not have the computer do some of it for you?"
  },
  {
    quote    : "Write Code That Writes Code",
    subquote : "Code generators increase your productivity and help avoid duplication."
  },
  {
    quote    : "You Can't Write Perfect Software",
    subquote : "Software can't be perfect. Protect your code and users from the inevitable errors."
  },
  {
    quote    : "Design with Contracts",
    subquote : "Use contracts to document and verify that code does no more and no less than it claims to do."
  },
  {
    quote    : "Crash Early",
    subquote : "A dead program normally does a lot less damage than a crippled one."
  },
  {
    quote    : "Use Assertions to Prevent the Impossible",
    subquote : "Assertions validate your assumptions. Use them to protect your code from an uncertain world."
  },
  {
    quote    : "Use Exceptions for Exceptional Problems",
    subquote : "Exceptions can suffer from all the readability and maintainability problems of classic spaghetti code. Reserve exceptions for exceptional things."
  },
  {
    quote    : "Finish What You Start",
    subquote : "Where possible, the routine or object that allocates a resource should be responsible for deallocating it."
  },
  {
    quote    : "Minimize Coupling Between Modules",
    subquote : "Avoid coupling by writing 'shy' code and applying the Law of Demeter."
  },
  {
    quote    : "Configure, Don't Integrate",
    subquote : "Implement technology choices for an application as configuration options, not through integration or engineering."
  },
  {
    quote    : "Put Abstractions in Code, Details in Metadata",
    subquote : "Program for the general case, and put the specifics outside the compiled code base."
  },
  {
    quote    : "Analyze Workflow to Improve Concurrency",
    subquote : "Exploit concurrency in your user's workflow."
  },
  {
    quote    : "Design Using Services",
    subquote : "Design in terms of services – independent, concurrent objects behind well-defined, consistent interfaces."
  },
  {
    quote    : "Always Design for Concurrency",
    subquote : "Allow for concurrency, and you'll design cleaner interfaces with fewer assumptions."
  },
  {
    quote    : "Separate Views from Models",
    subquote : "Gain flexibility at low cost by designing your application in terms of models and views."
  },
  {
    quote    : "Use Blackboards to Coordinate Workflow",
    subquote : "Use blackboards to coordinate disparate facts and agents, while maintaining independence and isolation among participants."
  },
  {
    quote    : "Don't Program by Coincidence",
    subquote : "Rely only on reliable things. Beware of accidental complexity, and don't confuse a happy coincidence with a purposeful plan."
  },
  {
    quote    : "Estimate the Order of Your Algorithms",
    subquote : "Get a feel for how long things are likely to take before you write code."
  },
  {
    quote    : "Test Your Estimates",
    subquote : "Mathematical analysis of algorithms doesn't tell you everything. Try timing your code in its target environment."
  },
  {
    quote    : "Refactor Early, Refactor Often",
    subquote : "Just as you might weed and rearrange a garden, rewrite, rework, and re-architect code when it needs it. Fix the root of the problem."
  },
  {
    quote    : "Design to Test",
    subquote : "Start thinking about testing before you write a line of code."
  },
  {
    quote    : "Test Your Software, or Your Users Will",
    subquote : "Test ruthlessly. Don't make your users find bugs for you."
  },
  {
    quote    : "Don't Use Wizard Code You Don't Understand",
    subquote : "Wizards can generate reams of code. Make sure you understand all of it before you incorporate it into your project."
  },
  {
    quote    : "Don't Gather Requirements – Dig for Them",
    subquote : "Requirements rarely lie on the surface. They're buried deep beneath layers of assumptions, misconceptions, and politics."
  },
  {
    quote    : "Work With a User to Think Like a User",
    subquote : "It's the best way to gain insight into how the system will really be used."
  },
  {
    quote    : "Abstractions Live Longer than Details",
    subquote : "Invest in the abstraction, not the implementation. Abstractions can survive the barrage of changes from different implementations and new technologies."
  },
  {
    quote    : "Use a Project Glossary",
    subquote : "Create and maintain a single source of all the specific terms and vocabulary for a project."
  },
  {
    quote    : "Don't Think Outside the Box – Find the Box",
    subquote : "When faced with an impossible problem, identify the real constraints. Ask yourself                                                                       : 'Does it have to be done this way? Does it have to be done at all?'"
  },
  {
    quote    : "Start When You're Ready.",
    subquote : "You've been building experience all your life. Don't ignore niggling doubts."
  },
  {
    quote    : "Some Things Are Better Done than Described",
    subquote : "Don't fall into the specification spiral – at some point you need to start coding."
  },
  {
    quote    : "Don't Be a Slave to Formal Methods.",
    subquote : "Don't blindly adopt any technique without putting it into the context of your development practices and capabilities."
  },
  {
    quote    : "Costly Tools Don't Produce Better Designs",
    subquote : "Beware of vendor hype, industry dogma, and the aura of the price tag. Judge tools on their merits."
  },
  {
    quote    : "Organize Teams Around Functionality",
    subquote : "Don't separate designers from coders, testers from data modelers. Build teams the way you build code."
  },
  {
    quote    : "Don't Use Manual Procedures",
    subquote : "A shell script or batch file will execute the same instructions, in the same order, time after time."
  },
  {
    quote    : "Test Early. Test Often. Test Automatically",
    subquote : "Tests that run with every build are much more effective than test plans that sit on a shelf."
  },
  {
    quote    : "Coding Ain't Done 'Til All the Tests Run",
    subquote : "'Nuff said."
  },
  {
    quote    : "Use Saboteurs to Test Your Testing",
    subquote : "Introduce bugs on purpose in a separate copy of the source to verify that testing will catch them."
  },
  {
    quote    : "Test State Coverage, Not Code Coverage",
    subquote : "Identify and test significant program states. Just testing lines of code isn't enough."
  },
  {
    quote    : "Find Bugs Once",
    subquote : "Once a human tester finds a bug, it should be the last time a human tester finds that bug. Automatic tests should check for it from then on."
  },
  {
    quote    : "English is Just a Programming Language",
    subquote : "Write documents as you would write code: honor the DRY principle, use metadata, MVC, automatic generation, and so on."
  },
  {
    quote    : "Build Documentation In, Don't Bolt It On",
    subquote : "Documentation created separately from code is less likely to be correct and up to date."
  },
  {
    quote    : "Gently Exceed Your Users' Expectations",
    subquote : "Come to understand your users' expectations, then deliver just that little bit more."
  },
  {
    quote    : "Sign Your Work",
    subquote : "Craftsmen of an earlier age were proud to sign their work. You should be, too."
  }
];

// Insert the quotes into a complete Model
var allDocuments = [];
allQuotes.forEach(function(element, index) {
  allDocuments[index] = {
    quote_id: index + 1,
    source: "The Pragmatic Programmer",
    source_href:    "",
    quote: element.quote,
    quote_href:     "",
    subquote: element.subquote,
    subquote_href:  ""
  };
});

// Load all documents into the database
Quote.create(allDocuments, function (err, results) {
  console.log(results);
});

<commit_msg>Add link to DB initialization procedure<commit_after>/*
 * Initialize a quotes database
 *
 * Inserts the quotes from
 *   _The Pragmatic Programmer_
 * into a local or mLab MongoDB database
 *
 * Problem:  How to end execution without Ctrl-c?
 *
 * Author: Peter Martinson
 * Date:   March 10, 2017
*/
const mongoose = require('mongoose');
const assert   = require('assert');  // node's native unit tester
const dotenv   = require('dotenv');
const config   = require('./config');
const quoteSchema = require('../models/quoteSchema.js');

// var url      = process.env.MONGOLAB_URI;  // mLab database
// var url      = "mongodb://localhost:27017/pragmatic"; // local database
var url      = "mongodb://" + config.username + ":" + config.password + "@ds123400.mlab.com:23400/quotes";

mongoose.Promise = Promise;
mongoose.connect(url);

var Quote = mongoose.model('Quote', quoteSchema);

// empty the database!
Quote.remove({}, function(err) {
  assert.equal(null, err, "There's something wrong... " + err);
  console.log("database emptied.");
});

// list the quotes
var allQuotes = [
  {
    quote    : "Care About Your Craft",
    subquote : "Why spend your life developing software unless you care about doing it well?"
  },
  {
    quote    : "Think! About Your Work",
    subquote : "Turn off the autopilot and take control. Constantly critique and appraise your work."
  },
  {
    quote    : "Provide Options, Don't Make Lame Excuses",
    subquote : "Instead of excuses, provide options. Don't say it can't be done; explain what can be done."
  },
  {
    quote    : "Don't Live with Broken Windows",
    subquote : "Fix bad designs, wrong decisions, and poor code when you see them."
  },
  {
    quote    : "Be a Catalyst for Change",
    subquote : "You can't force change on people. Instead, show them how the future might be and help them participate in creating it."
  },
  {
    quote    : "Remember the Big Picture",
    subquote : "Don't get so engrossed in the details that you forget to check what's happening around you."
  },
  {
    quote    : "Make Quality a Requirements Issue",
    subquote : "Involve your users in determining the project's real quality requirements."
  },
  {
    quote    : "Invest Regularly in Your Knowledge Portfolio",
    subquote : "Make learning a habit."
  },
  {
    quote    : "Critically Analyze What You Read and Hear",
    subquote : "Don't be swayed by vendors, media hype, or dogma. Analyze information in terms of you and your project."
  },
  {
    quote    : "It's Both What You Say and the Way You Say It",
    subquote : "There's no point in having great ideas if you don't communicate them effectively."
  },
  {
    quote    : "DRY – Don't Repeat Yourself",
    subquote : "Every piece of knowledge must have a single, unambiguous, authoritative representation within a system."
  },
  {
    quote    : "Make It Easy to Reuse",
    subquote : "If it's easy to reuse, people will. Create an environment that supports reuse."
  },
  {
    quote    : "Eliminate Effects Between Unrelated Things",
    subquote : "Design components that are self-contained. independent, and have a single, well-defined purpose."
  },
  {
    quote    : "There Are No Final Decisions",
    subquote : "No decision is cast in stone. Instead, consider each as being written in the sand at the beach, and plan for change."
  },
  {
    quote    : "Use Tracer Bullets to Find the Target",
    subquote : "Tracer bullets let you home in on your target by trying things and seeing how close they land."
  },
  {
    quote    : "Prototype to Learn",
    subquote : "Prototyping is a learning experience. Its value lies not in the code you produce, but in the lessons you learn."
  },
  {
    quote    : "Program Close to the Problem Domain",
    subquote : "Design and code in your user's language."
  },
  {
    quote    : "Estimate to Avoid Surprises",
    subquote : "Estimate before you start. You'll spot potential problems up front."
  },
  {
    quote    : "Iterate the Schedule with the Code",
    subquote : "Use experience you gain as you implement to refine the project time scales."
  },
  {
    quote    : "Keep Knowledge in Plain Text",
    subquote : "Plain text won't become obsolete. It helps leverage your work and simplifies debugging and testing."
  },
  {
    quote    : "Use the Power of Command Shells",
    subquote : "Use the shell when graphical user interfaces don't cut it."
  },
  {
    quote    : "Use a Single Editor Well",
    subquote : "The editor should be an extension of your hand; make sure your editor is configurable, extensible, and programmable."
  },
  {
    quote    : "Always Use Source Code Control",
    subquote : "Source code control is a time machine for your work – you can go back."
  },
  {
    quote    : "Fix the Problem, Not the Blame",
    subquote : "It doesn't really matter whether the bug is your fault or someone else's – it is still your problem, and it still needs to be fixed."
  },
  {
    quote    : "Don't Panic When Debugging",
    subquote : "Take a deep breath and THINK! about what could be causing the bug."
  },
  {
    quote    : "'select' Isn't Broken.",
    subquote : "It is rare to find a bug in the OS or the compiler, or even a third-party product or library. The bug is most likely in the application."
  },
  {
    quote    : "Don't Assume It – Prove It",
    subquote : "Prove your assumptions in the actual environment – with real data and boundary conditions."
  },
  {
    quote    : "Learn a Text Manipulation Language.",
    subquote : "You spend a large part of each day working with text. Why not have the computer do some of it for you?"
  },
  {
    quote    : "Write Code That Writes Code",
    subquote : "Code generators increase your productivity and help avoid duplication."
  },
  {
    quote    : "You Can't Write Perfect Software",
    subquote : "Software can't be perfect. Protect your code and users from the inevitable errors."
  },
  {
    quote    : "Design with Contracts",
    subquote : "Use contracts to document and verify that code does no more and no less than it claims to do."
  },
  {
    quote    : "Crash Early",
    subquote : "A dead program normally does a lot less damage than a crippled one."
  },
  {
    quote    : "Use Assertions to Prevent the Impossible",
    subquote : "Assertions validate your assumptions. Use them to protect your code from an uncertain world."
  },
  {
    quote    : "Use Exceptions for Exceptional Problems",
    subquote : "Exceptions can suffer from all the readability and maintainability problems of classic spaghetti code. Reserve exceptions for exceptional things."
  },
  {
    quote    : "Finish What You Start",
    subquote : "Where possible, the routine or object that allocates a resource should be responsible for deallocating it."
  },
  {
    quote    : "Minimize Coupling Between Modules",
    subquote : "Avoid coupling by writing 'shy' code and applying the Law of Demeter."
  },
  {
    quote    : "Configure, Don't Integrate",
    subquote : "Implement technology choices for an application as configuration options, not through integration or engineering."
  },
  {
    quote    : "Put Abstractions in Code, Details in Metadata",
    subquote : "Program for the general case, and put the specifics outside the compiled code base."
  },
  {
    quote    : "Analyze Workflow to Improve Concurrency",
    subquote : "Exploit concurrency in your user's workflow."
  },
  {
    quote    : "Design Using Services",
    subquote : "Design in terms of services – independent, concurrent objects behind well-defined, consistent interfaces."
  },
  {
    quote    : "Always Design for Concurrency",
    subquote : "Allow for concurrency, and you'll design cleaner interfaces with fewer assumptions."
  },
  {
    quote    : "Separate Views from Models",
    subquote : "Gain flexibility at low cost by designing your application in terms of models and views."
  },
  {
    quote    : "Use Blackboards to Coordinate Workflow",
    subquote : "Use blackboards to coordinate disparate facts and agents, while maintaining independence and isolation among participants."
  },
  {
    quote    : "Don't Program by Coincidence",
    subquote : "Rely only on reliable things. Beware of accidental complexity, and don't confuse a happy coincidence with a purposeful plan."
  },
  {
    quote    : "Estimate the Order of Your Algorithms",
    subquote : "Get a feel for how long things are likely to take before you write code."
  },
  {
    quote    : "Test Your Estimates",
    subquote : "Mathematical analysis of algorithms doesn't tell you everything. Try timing your code in its target environment."
  },
  {
    quote    : "Refactor Early, Refactor Often",
    subquote : "Just as you might weed and rearrange a garden, rewrite, rework, and re-architect code when it needs it. Fix the root of the problem."
  },
  {
    quote    : "Design to Test",
    subquote : "Start thinking about testing before you write a line of code."
  },
  {
    quote    : "Test Your Software, or Your Users Will",
    subquote : "Test ruthlessly. Don't make your users find bugs for you."
  },
  {
    quote    : "Don't Use Wizard Code You Don't Understand",
    subquote : "Wizards can generate reams of code. Make sure you understand all of it before you incorporate it into your project."
  },
  {
    quote    : "Don't Gather Requirements – Dig for Them",
    subquote : "Requirements rarely lie on the surface. They're buried deep beneath layers of assumptions, misconceptions, and politics."
  },
  {
    quote    : "Work With a User to Think Like a User",
    subquote : "It's the best way to gain insight into how the system will really be used."
  },
  {
    quote    : "Abstractions Live Longer than Details",
    subquote : "Invest in the abstraction, not the implementation. Abstractions can survive the barrage of changes from different implementations and new technologies."
  },
  {
    quote    : "Use a Project Glossary",
    subquote : "Create and maintain a single source of all the specific terms and vocabulary for a project."
  },
  {
    quote    : "Don't Think Outside the Box – Find the Box",
    subquote : "When faced with an impossible problem, identify the real constraints. Ask yourself                                                                       : 'Does it have to be done this way? Does it have to be done at all?'"
  },
  {
    quote    : "Start When You're Ready.",
    subquote : "You've been building experience all your life. Don't ignore niggling doubts."
  },
  {
    quote    : "Some Things Are Better Done than Described",
    subquote : "Don't fall into the specification spiral – at some point you need to start coding."
  },
  {
    quote    : "Don't Be a Slave to Formal Methods.",
    subquote : "Don't blindly adopt any technique without putting it into the context of your development practices and capabilities."
  },
  {
    quote    : "Costly Tools Don't Produce Better Designs",
    subquote : "Beware of vendor hype, industry dogma, and the aura of the price tag. Judge tools on their merits."
  },
  {
    quote    : "Organize Teams Around Functionality",
    subquote : "Don't separate designers from coders, testers from data modelers. Build teams the way you build code."
  },
  {
    quote    : "Don't Use Manual Procedures",
    subquote : "A shell script or batch file will execute the same instructions, in the same order, time after time."
  },
  {
    quote    : "Test Early. Test Often. Test Automatically",
    subquote : "Tests that run with every build are much more effective than test plans that sit on a shelf."
  },
  {
    quote    : "Coding Ain't Done 'Til All the Tests Run",
    subquote : "'Nuff said."
  },
  {
    quote    : "Use Saboteurs to Test Your Testing",
    subquote : "Introduce bugs on purpose in a separate copy of the source to verify that testing will catch them."
  },
  {
    quote    : "Test State Coverage, Not Code Coverage",
    subquote : "Identify and test significant program states. Just testing lines of code isn't enough."
  },
  {
    quote    : "Find Bugs Once",
    subquote : "Once a human tester finds a bug, it should be the last time a human tester finds that bug. Automatic tests should check for it from then on."
  },
  {
    quote    : "English is Just a Programming Language",
    subquote : "Write documents as you would write code: honor the DRY principle, use metadata, MVC, automatic generation, and so on."
  },
  {
    quote    : "Build Documentation In, Don't Bolt It On",
    subquote : "Documentation created separately from code is less likely to be correct and up to date."
  },
  {
    quote    : "Gently Exceed Your Users' Expectations",
    subquote : "Come to understand your users' expectations, then deliver just that little bit more."
  },
  {
    quote    : "Sign Your Work",
    subquote : "Craftsmen of an earlier age were proud to sign their work. You should be, too."
  }
];

// Insert the quotes into a complete Model
var allDocuments = [];
allQuotes.forEach(function(element, index) {
  allDocuments[index] = {
    quote_id      : index + 1,
    source        : "The Pragmatic Programmer",
    source_href   : "https://pragprog.com/the-pragmatic-programmer/extracts/tips",
    quote         : element.quote,
    quote_href    : "",
    subquote      : element.subquote,
    subquote_href : ""
  };
});

// Load all documents into the database
Quote.create(allDocuments, function (err, results) {
  console.log(results);
});

<|endoftext|>