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

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Property',
  ids: [ 'name' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'value',  0 ]
  ],
  actions: [
    {
      name: 'deleteRow',
      label: 'X',
      code: function deleteRow() {
        debugger;

      }
    }
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Clock',
  extends: 'com.google.foam.demos.clock.Clock',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    [ 'mass',  0 ],
    [ 'radius', 45 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Text',
  extends: 'foam.graphics.Label',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'width',  100 ],
    [ 'height', 50 ],
    [ 'text', 'Text' ],
    [ 'color', '#000000' ],
    [ 'font', '50px Arial' ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Circle',
  extends: 'foam.graphics.Circle',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'radius', 25 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Box',
  extends: 'foam.graphics.Box',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'width',  50 ],
    [ 'height', 50 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'LivePaint',
  extends: 'foam.u2.Element',

  implements: [ 'foam.memento.MementoMgr' ],

  requires: [
    'com.google.livepaint.Property',
    'foam.dao.EasyDAO',
    'foam.graphics.Box',
    'foam.graphics.CView',
    'foam.graphics.Circle',
    'foam.physics.Physical',
    'foam.physics.PhysicsEngine',
    'foam.u2.PopupView',
    'foam.u2.TableView'
  ],

  exports: [ 'as data' ],

  constants: {
    SELECTED_COLOR:   '#dddddd',
    UNSELECTED_COLOR: '#ffffff'
  },

  axioms: [
    foam.u2.CSS.create({
      code: function() {/*
      ^ { display: flex; }
      ^ > * { padding: 16px; }
      .foam-u2-TableView-selected { background: lightgray; }
      ^ canvas { border: 1px solid black; }
      ^ .foam-u2-ActionView { margin: 10px; }
      ^properties .foam-u2-ActionView { background: white; padding: 0; margin: 2px; border: none; }
      */}
    })
  ],

  properties: [
    {
      name: 'physics',
      factory: function() {
        return this.PhysicsEngine.create();
      }
    },
    'feedback_',
    'currentTool',
    {
      class: 'foam.dao.DAOProperty',
      name: 'tools',
      view: {
        class: 'foam.u2.TableView',
        columns: [ foam.core.Model.NAME ]
      },
      factory: function() {
        var dao = foam.dao.EasyDAO.create({
          of: 'foam.core.Model',
          daoType: 'MDAO'
        });
        dao.put(com.google.foam.demos.robot.Robot.model_);
        dao.put(com.google.livepaint.Clock.model_);
        dao.put(com.google.livepaint.Circle.model_);
        dao.put(com.google.livepaint.Box.model_);
        dao.put(com.google.livepaint.Text.model_);
        return dao;
      }
    },
    {
      name: 'selected',
      view: { class: 'foam.u2.DetailView' },
      postSet: function(o, n) {
        if ( o ) { o.shadowBlur = 0; }
        if ( n ) { n.shadowBlur = 10; n.shadowColor = '#ff0000'; }
      }
    },
    {
      name: 'properties',
      view: {
        class: 'foam.u2.TableView',
        columns: [
          com.google.livepaint.Property.NAME,
          com.google.livepaint.Property.DELETE_ROW
        ]
      },
      factory: function() {
        var dao = foam.dao.EasyDAO.create({
          of: 'com.google.livepaint.Property',
          guid: true,
          seqProperty: this.Property.NAME,
//          daoType: 'MDAO'
          daoType: 'ARRAY'
        });
        dao.put(this.Property.create({name: 'physics', value: this.physics}));
        return dao;
      }
    },
    {
      name: 'canvas',
      factory: function() {
        return this.Box.create({autoRepaint: true, width: 600, height: 500, color: '#f3f3f3'});
      }
    },
  ],

  methods: [

    function initE() {
      this.properties.on.put.sub(this.onPropertyPut);

      this.memento$.sub(function() {
        var m = this.memento;
        if ( this.feedback_ ) return;
        this.canvas.children = [];
        if ( m ) {
          for ( var i = 0 ; i < m.length ; i++ ) {
            var c = m[i];
            this.addCircle(c.x, c.y, c.radius);
          }
        }
        this.selected = null;
      }.bind(this));

      this.
          cssClass(this.myCls()).
          start(this.TOOLS, {selection$: this.currentTool$}).end().
          start('center').
            start(this.BACK,  {label: 'Undo'}).end().
            start(this.FORTH, {label: 'Redo'}).end().
            tag('br').
            start(this.canvas).
              on('click',       this.onClick).
              on('contextmenu', this.onRightClick).
            end().
          end().
          start('div').
            cssClass(this.myCls('properties')).
            add(this.PROPERTIES).
          end().
          add(this.SELECTED);

      this.physics.start();
    },

    function addProperty(value, opt_name) {
      console.log('addProperty: ', value.cls_.id);
      this.properties.put(this.Property.create({
        name: opt_name,
        value: value
      }));
    },

    /*
    function addCircle(x, y, opt_r) {
      var c = this.Circle.create({
        x: x,
        y: y,
        radius: opt_r || 25,
        color: this.UNSELECTED_COLOR,
        border: '#000'});

      this.canvas.addChildren(c);

      return c;
    },
    */

    function updateMemento() {
      this.feedback_ = true;
      this.memento = this.canvas.children.map(function(c) {
        return {x: c.x, y: c.y, radius: c.radius};
      });
      this.feedback_ = false;
    }
  ],

  actions: [
    {
      name: 'deleteProperty',
      label: 'X',
      code: function() {
        debugger;
      }
    }
  ],

  listeners: [
    function onPropertyPut(_, _, _, p) {
      var o = p.value;
      if ( this.CView.isInstance(o) ) {
        this.canvas.add(o);

        if ( this.Physical.isInstance(o) ) {
          this.physics.add(o);
        }
      }
    },

    function onClick(evt) {
      var x = evt.offsetX, y = evt.offsetY;
      var c = this.canvas.findFirstChildAt(x, y);

      if ( c ) {
        this.selected = c;
      } else {
        var tool = this.currentTool;
        if ( ! tool ) return;
        var cls = this.lookup(tool.id);
        var o = cls.create({x: x, y: y});
        this.addProperty(o);
        this.selected = o;
        this.updateMemento();
      }
    },

    function onRightClick(evt) {
      evt.preventDefault();

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

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Property',
  ids: [ 'name' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'value',  0 ]
  ],
  actions: [
    {
      name: 'deleteRow',
      label: 'X',
      code: function deleteRow() {
        debugger;
      }
    }
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Clock',
  extends: 'com.google.foam.demos.clock.Clock',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    [ 'mass',  0 ],
    [ 'radius', 45 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Text',
  extends: 'foam.graphics.Label',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'width',  100 ],
    [ 'height', 50 ],
    [ 'text', 'Text' ],
    [ 'color', '#000000' ],
    [ 'font', '50px Arial' ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Circle',
  extends: 'foam.graphics.Circle',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'radius', 25 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'Box',
  extends: 'foam.graphics.Box',
  implements: [ 'foam.physics.Physical' ],
  properties: [
    {
      class: 'String',
      name: 'name'
    },
    [ 'mass',  0 ],
    [ 'width',  50 ],
    [ 'height', 50 ]
  ]
});

foam.CLASS({
  package: 'com.google.livepaint',
  name: 'LivePaint',
  extends: 'foam.u2.Element',

  implements: [ 'foam.memento.MementoMgr' ],

  requires: [
    'com.google.livepaint.Property',
    'foam.dao.EasyDAO',
    'foam.graphics.Box',
    'foam.graphics.CView',
    'foam.graphics.Circle',
    'foam.physics.Physical',
    'foam.physics.PhysicsEngine',
    'foam.u2.PopupView',
    'foam.u2.TableView'
  ],

  exports: [ 'as data' ],

  constants: {
    SELECTED_COLOR:   '#dddddd',
    UNSELECTED_COLOR: '#ffffff'
  },

  axioms: [
    foam.u2.CSS.create({
      code: function() {/*
      ^ { display: flex; }
      ^ > * { padding: 16px; }
      .foam-u2-TableView-selected { background: lightgray; }
      ^ canvas { border: 1px solid black; }
      ^ .foam-u2-ActionView { margin: 10px; }
      ^properties .foam-u2-ActionView { background: white; padding: 0; margin: 2px; border: none; }
      */}
    })
  ],

  properties: [
    {
      name: 'physics',
      factory: function() {
        return this.PhysicsEngine.create();
      }
    },
    'feedback_',
    'currentTool',
    {
      class: 'foam.dao.DAOProperty',
      name: 'tools',
      view: {
        class: 'foam.u2.TableView',
        columns: [ foam.core.Model.NAME ]
      },
      factory: function() {
        var dao = foam.dao.EasyDAO.create({
          of: 'foam.core.Model',
          daoType: 'MDAO'
        });
        dao.put(com.google.foam.demos.robot.Robot.model_);
        dao.put(com.google.livepaint.Clock.model_);
        dao.put(com.google.livepaint.Circle.model_);
        dao.put(com.google.livepaint.Box.model_);
        dao.put(com.google.livepaint.Text.model_);
        return dao;
      }
    },
    {
      name: 'selected',
      view: { class: 'foam.u2.DetailView' },
      postSet: function(o, n) {
        if ( o ) { o.shadowBlur = 0; }
        if ( n ) { n.shadowBlur = 10; n.shadowColor = '#ff0000'; }
      }
    },
    {
      name: 'properties',
      view: {
        class: 'foam.u2.TableView',
        columns: [
          com.google.livepaint.Property.NAME,
          com.google.livepaint.Property.DELETE_ROW
        ]
      },
      factory: function() {
        var dao = foam.dao.EasyDAO.create({
          of: 'com.google.livepaint.Property',
          guid: true,
          seqProperty: this.Property.NAME,
//          daoType: 'MDAO'
          daoType: 'ARRAY'
        });
        dao.put(this.Property.create({name: 'physics', value: this.physics}));
        return dao;
      }
    },
    {
      name: 'canvas',
      factory: function() {
        return this.Box.create({autoRepaint: true, width: 600, height: 500, color: '#f3f3f3'});
      }
    },
  ],

  methods: [

    function initE() {
      this.properties.on.put.sub(this.onPropertyPut);

      this.memento$.sub(function() {
        var m = this.memento;
        if ( this.feedback_ ) return;
        this.canvas.children = [];
        if ( m ) {
          for ( var i = 0 ; i < m.length ; i++ ) {
            var c = m[i];
            this.addCircle(c.x, c.y, c.radius);
          }
        }
        this.selected = null;
      }.bind(this));

      this.
          cssClass(this.myCls()).
          start(this.TOOLS, {selection$: this.currentTool$}).end().
          start('center').
            start(this.BACK,  {label: 'Undo'}).end().
            start(this.FORTH, {label: 'Redo'}).end().
            tag('br').
            start(this.canvas).
              on('click',       this.onClick).
              on('contextmenu', this.onRightClick).
            end().
          end().
          start('div').
            cssClass(this.myCls('properties')).
            add(this.PROPERTIES).
          end().
          add(this.SELECTED);

      this.physics.start();
    },

    function addProperty(value, opt_name, opt_i) {
      var self = this;
      if ( ! opt_name ) {
        var i = opt_i || 1;
        var prefix = value.cls_.name.toLowerCase();
        this.properties.find(prefix + i).then(function (o) {
          if ( ! o ) {
            self.addProperty(value, prefix + i);
          } else {
            self.addProperty(value, null, i+1);
          }
        }).catch(function(x) {
          self.addProperty(value, prefix+i);
        });
      } else {
        this.properties.put(this.Property.create({
          name: opt_name,
          value: value
        }));
      }
    },

    /*
    function addCircle(x, y, opt_r) {
      var c = this.Circle.create({
        x: x,
        y: y,
        radius: opt_r || 25,
        color: this.UNSELECTED_COLOR,
        border: '#000'});

      this.canvas.addChildren(c);

      return c;
    },
    */

    function updateMemento() {
      this.feedback_ = true;
      this.memento = this.canvas.children.map(function(c) {
        return {x: c.x, y: c.y, radius: c.radius};
      });
      this.feedback_ = false;
    }
  ],

  actions: [
    {
      name: 'deleteProperty',
      label: 'X',
      code: function() {
        debugger;
      }
    }
  ],

  listeners: [
    function onPropertyPut(_, _, _, p) {
      var o = p.value;
      if ( this.CView.isInstance(o) ) {
        this.canvas.add(o);

        if ( this.Physical.isInstance(o) ) {
          this.physics.add(o);
        }
      }
    },

    function onClick(evt) {
      var x = evt.offsetX, y = evt.offsetY;
      var c = this.canvas.findFirstChildAt(x, y);

      if ( c ) {
        this.selected = c;
      } else {
        var tool = this.currentTool;
        if ( ! tool ) return;
        var cls = this.lookup(tool.id);
        var o = cls.create({x: x, y: y});
        this.addProperty(o);
        this.selected = o;
        this.updateMemento();
      }
    },

    function onRightClick(evt) {
      evt.preventDefault();

      if ( ! this.selected ) return;
    }
  ]
});
<|endoftext|>


<commit_before>var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
context.width = canvas.width;
context.height = canvas.height;
context.globalCompositeOperation = "destination-over";

var currentState = null;

var pauseKey = "p";
var canPauseOrResume = true;
var gamePaused = false;

function init() {
  setInterval(tick, 16.666666666);
}

function tick() {
  if (gamePaused) {
    currentState.draw();

    if (isDown(pauseKey))
      pauseOrResumeGame();

    // TODO Draw Pause/Play huge icon on top
  } else {
    if (isDown(pauseKey))
      pauseOrResumeGame();

    currentState.update();
    currentState.draw();
  }
}

function pauseOrResumeGame() {
  if (canPauseOrResume) {
    gamePaused = !gamePaused;

    setTimeout(function() {
      canPauseOrResume = true;
    }, 1000);

    canPauseOrResume = false;
  }
}

function switchState(newState) {
  newState.setup();
  return currentState = newState;
}

function drawCircle(x, y, radius) {
  context.beginPath();
  context.arc(x, y, radius, 0, Math.PI * 2, false);
  context.stroke();
}

function drawRectangle(x, y, width, height, color) {
  if (color) {
    context.fillStyle = color;
    context.fillRect(x, y, width, height);
    context.fillStyle = "#FFFFFF";
  } else {
    context.fillRect(x, y, width, height);
  }
}

function clearCanvas() {
  context.clearRect(0, 0, context.width, context.height);
}

/*************************************** SPRITE */
Sprite = (function() {
  function constructor(image, x, y) {
    this.image = new Image();
    this.image.src = image;
    this.x = x;
    this.y = y;
  }

  constructor.prototype = {
    draw: function() {
      context.drawImage(this.image, this.x, this.y);
    }
  }

  return constructor;
})();

SpriteList = (function() {
  function constructor() {
    this.sprites = [];
  }

  constructor.prototype = {
    draw: function() {
      for (var i = 0; i < this.sprites.length; i++) {
        this.sprites[i].draw();
      }
    },

    push: function(newSprite) {
      this.sprites.push(newSprite);
    }
  }

  return constructor;
})();

/*function loadImage(imageName) {
  var image = new Image();
  image.src = imageName;
}*/

/*************************************** INPUT */
window.addEventListener("keydown", handleKeyDown);
window.addEventListener("keyup", handleKeyUp);

var keyCodeToString = [];
keyCodeToString[8] = "backspace";
keyCodeToString[9] = "tab";
keyCodeToString[13] = "enter";
keyCodeToString[16] = "shift";
keyCodeToString[17] = "ctrl";
keyCodeToString[18] = "alt";
keyCodeToString[19] = "pause";
keyCodeToString[20] = "capslock";
keyCodeToString[27] = "esc";
keyCodeToString[32] = "space";
keyCodeToString[33] = "pageup";
keyCodeToString[34] = "pagedown";
keyCodeToString[35] = "end";
keyCodeToString[36] = "home";
keyCodeToString[37] = "left";
keyCodeToString[38] = "up";
keyCodeToString[39] = "right";
keyCodeToString[40] = "down";
keyCodeToString[45] = "insert";
keyCodeToString[46] = "delete";

keyCodeToString[91] = "leftwindowkey";
keyCodeToString[92] = "rightwindowkey";
keyCodeToString[93] = "selectkey";
keyCodeToString[106] = "multiply";
keyCodeToString[107] = "add";
keyCodeToString[109] = "subtract";
keyCodeToString[110] = "decimalpoint";
keyCodeToString[111] = "divide";

keyCodeToString[144] = "numlock";
keyCodeToString[145] = "scrollock";
keyCodeToString[186] = "semicolon";
keyCodeToString[187] = "equalsign";
keyCodeToString[188] = "comma";
keyCodeToString[189] = "dash";
keyCodeToString[190] = "period";
keyCodeToString[191] = "forwardslash";
keyCodeToString[192] = "graveaccent";
keyCodeToString[219] = "openbracket";
keyCodeToString[220] = "backslash";
keyCodeToString[221] = "closebracket";
keyCodeToString[222] = "singlequote";

var numpadKeys = ["numpad1", "numpad2", "numpad3", "numpad4", "numpad5",
                  "numpad6", "numpad7", "numpad8", "numpad9"];

var numbers = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"];
var letters = ["a", "b", "c", "d", "e", "f", "g", "h", "i", "j",
               "k", "l", "m", "n", "o", "p", "q", "r", "s", "t",
               "u", "v", "w", "x", "y", "z"];

for (var i = 0; numbers[i]; i++) { keyCodeToString[48 + i] = numbers[i]; }
for (var i = 0; letters[i]; i++) { keyCodeToString[65 + i] = letters[i]; }
for (var i = 0; numpadKeys[i]; i++) { keyCodeToString[96 + i] = numpadKeys[i]; }

var pressedKeys = [];
var preventedKeys = [];

function preventKeys(keys) {
  preventedKeys = keys;
}

function handleKeyDown(e) {
  var event = (e) ? e : window.event;
  var name = keyCodeToString[event.keyCode];
  pressedKeys[name] = true;

  if (preventedKeys[name])
    e.preventDefault();
}

function handleKeyUp(e) {
  var event = (e) ? e : window.event;
  var name = keyCodeToString[event.keyCode];
  pressedKeys[name] = false;

  if (preventedKeys[name])
    e.preventDefault();
}

function isDown(name) {
  if (pressedKeys[name])
    return true;
}
<commit_msg>replaced sprites' images with canvas and added asynchronous image loading<commit_after>var canvas = document.getElementById("canvas");
var context = canvas.getContext("2d");
context.width = canvas.width;
context.height = canvas.height;
context.globalCompositeOperation = "destination-over";

var currentState = null;

var pauseKey = "p";
var canPauseOrResume = true;
var gamePaused = false;

function init() {
  setInterval(tick, 16.666666666);
}

function tick() {
  if (gamePaused) {
    currentState.draw();

    if (isDown(pauseKey))
      pauseOrResumeGame();

    // TODO Draw Pause/Play huge icon on top
  } else {
    if (isDown(pauseKey))
      pauseOrResumeGame();

    currentState.update();
    currentState.draw();
  }
}

function pauseOrResumeGame() {
  if (canPauseOrResume) {
    gamePaused = !gamePaused;

    setTimeout(function() {
      canPauseOrResume = true;
    }, 1000);

    canPauseOrResume = false;
  }
}

function switchState(newState) {
  newState.setup();
  return currentState = newState;
}

function drawCircle(x, y, radius) {
  context.beginPath();
  context.arc(x, y, radius, 0, Math.PI * 2, false);
  context.stroke();
}

function drawRectangle(x, y, width, height, color) {
  if (color) {
    context.fillStyle = color;
    context.fillRect(x, y, width, height);
    context.fillStyle = "#FFFFFF";
  } else {
    context.fillRect(x, y, width, height);
  }
}

function clearCanvas() {
  context.clearRect(0, 0, context.width, context.height);
}

/*************************************** SPRITE */
Sprite = (function() {
  function constructor(image, x, y) {
    this.image = new Image();
    this.image.src = image;
    this.x = x;
    this.y = y;
    /* cache image modifications to an internal canvas for performance and flexibility */
    this.internal = document.createElement("canvas");
    this.image.owner = this;
    /* asynchronous image loading and caching */
    this.image.onload = function() {
      this.owner.internal.width = this.width.toString();
      this.owner.internal.height = this.height.toString();
      this.owner.internalctx = this.owner.internal.getContext("2d");
      this.owner.internalctx.drawImage(this, 0, 0);
      /* dump image reference, we no longer need it */
      delete this.owner.image;
    }
  }

  constructor.prototype = {
    draw: function() {
      context.drawImage(this.internal, this.x, this.y);
    }
  }

  return constructor;
})();

SpriteList = (function() {
  function constructor() {
    this.sprites = [];
  }

  constructor.prototype = {
    draw: function() {
      for (var i = 0; i < this.sprites.length; i++) {
        this.sprites[i].draw();
      }
    },

    push: function(newSprite) {
      this.sprites.push(newSprite);
    }
  }

  return constructor;
})();

/*function loadImage(imageName) {
  var image = new Image();
  image.src = imageName;
}*/

/*************************************** INPUT */
window.addEventListener("keydown", handleKeyDown);
window.addEventListener("keyup", handleKeyUp);

var keyCodeToString = [];
keyCodeToString[8] = "backspace";
keyCodeToString[9] = "tab";
keyCodeToString[13] = "enter";
keyCodeToString[16] = "shift";
keyCodeToString[17] = "ctrl";
keyCodeToString[18] = "alt";
keyCodeToString[19] = "pause";
keyCodeToString[20] = "capslock";
keyCodeToString[27] = "esc";
keyCodeToString[32] = "space";
keyCodeToString[33] = "pageup";
keyCodeToString[34] = "pagedown";
keyCodeToString[35] = "end";
keyCodeToString[36] = "home";
keyCodeToString[37] = "left";
keyCodeToString[38] = "up";
keyCodeToString[39] = "right";
keyCodeToString[40] = "down";
keyCodeToString[45] = "insert";
keyCodeToString[46] = "delete";

keyCodeToString[91] = "leftwindowkey";
keyCodeToString[92] = "rightwindowkey";
keyCodeToString[93] = "selectkey";
keyCodeToString[106] = "multiply";
keyCodeToString[107] = "add";
keyCodeToString[109] = "subtract";
keyCodeToString[110] = "decimalpoint";
keyCodeToString[111] = "divide";

keyCodeToString[144] = "numlock";
keyCodeToString[145] = "scrollock";
keyCodeToString[186] = "semicolon";
keyCodeToString[187] = "equalsign";
keyCodeToString[188] = "comma";
keyCodeToString[189] = "dash";
keyCodeToString[190] = "period";
keyCodeToString[191] = "forwardslash";
keyCodeToString[192] = "graveaccent";
keyCodeToString[219] = "openbracket";
keyCodeToString[220] = "backslash";
keyCodeToString[221] = "closebracket";
keyCodeToString[222] = "singlequote";

var numpadKeys = ["numpad1", "numpad2", "numpad3", "numpad4", "numpad5",
                  "numpad6", "numpad7", "numpad8", "numpad9"];

var numbers = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"];
var letters = ["a", "b", "c", "d", "e", "f", "g", "h", "i", "j",
               "k", "l", "m", "n", "o", "p", "q", "r", "s", "t",
               "u", "v", "w", "x", "y", "z"];

for (var i = 0; numbers[i]; i++) { keyCodeToString[48 + i] = numbers[i]; }
for (var i = 0; letters[i]; i++) { keyCodeToString[65 + i] = letters[i]; }
for (var i = 0; numpadKeys[i]; i++) { keyCodeToString[96 + i] = numpadKeys[i]; }

var pressedKeys = [];
var preventedKeys = [];

function preventKeys(keys) {
  preventedKeys = keys;
}

function handleKeyDown(e) {
  var event = (e) ? e : window.event;
  var name = keyCodeToString[event.keyCode];
  pressedKeys[name] = true;

  if (preventedKeys[name])
    e.preventDefault();
}

function handleKeyUp(e) {
  var event = (e) ? e : window.event;
  var name = keyCodeToString[event.keyCode];
  pressedKeys[name] = false;

  if (preventedKeys[name])
    e.preventDefault();
}

function isDown(name) {
  if (pressedKeys[name])
    return true;
}
<|endoftext|>


<commit_before>'use strict';

angular.module('registryApp')
    .service('Sidebar', ['$rootScope', function ($rootScope) {

        var self = {};

        self.open = true;
        self.active = 'apps';

        /**
         * Toggle sidebar visibility
         */
        self.toggleOpen = function () {
            self.open = !self.open;
            $rootScope.$broadcast('sidebar:toggle', self.open);
        };

        /**
         * Set the active page
         * @param active
         */
        self.setActive = function (active) {
            self.active = active;
        };

        /**
         * Get the active page
         * @returns {string}
         */
        self.getActive = function () {
            return self.active;
        };

        return self;

    }])
    .directive('sidebar', ['$templateCache', 'User', 'Sidebar', function ($templateCache, User, Sidebar) {
        return {
            restrict: 'E',
            replace: true,
            template: $templateCache.get('views/partials/sidebar.html'),
            scope: {},
            link: function (scope) {

                scope.view = {};
                scope.view.loading = true;
                scope.view.active = Sidebar.getActive();
                scope.view.open = Sidebar.open;

                scope.view.navigation = [
                    {name: 'apps', link: 'apps', desc: 'Applications', icon: 'puzzle-piece'},
                    {name: 'workflows', link: 'pipelines', desc: 'Workflows', icon: 'cogs'},
                    {name: 'builds', link: 'builds', desc: 'Builds', icon: 'cube'},
                    {name: 'repos', link: 'repos', desc: 'Repositories', icon: 'code-fork'},
                    {name: 'dyole', link: 'pipeline/0/new', desc: 'Workflow Editor', icon: 'terminal'},
                    {name: 'cliche', link: 'cliche', desc: 'Tool Editorr', icon: 'terminal'}
                ];

                scope.SidebarService = Sidebar;

                User.getUser().then(function(result) {
                    scope.view.user = result.user;
                    scope.view.loading = false;

                    if (!_.isEmpty(result.user)) {
                        scope.view.navigation.push({name: 'settings',link: 'settings',  desc: 'Settings', icon: 'gear'});
                    }

                });

                scope.$watch('SidebarService.active', function (n, o) {
                    if (n !== o) {
                        scope.view.active = n;
                    }
                });

                /**
                 * Toggle sidebar visibility
                 */
                scope.toggleSidebar = function () {
                    scope.view.open = !scope.view.open;
                    Sidebar.toggleOpen();
                };

            }
        };
    }]);<commit_msg>renamed apps<commit_after>'use strict';

angular.module('registryApp')
    .service('Sidebar', ['$rootScope', function ($rootScope) {

        var self = {};

        self.open = true;
        self.active = 'apps';

        /**
         * Toggle sidebar visibility
         */
        self.toggleOpen = function () {
            self.open = !self.open;
            $rootScope.$broadcast('sidebar:toggle', self.open);
        };

        /**
         * Set the active page
         * @param active
         */
        self.setActive = function (active) {
            self.active = active;
        };

        /**
         * Get the active page
         * @returns {string}
         */
        self.getActive = function () {
            return self.active;
        };

        return self;

    }])
    .directive('sidebar', ['$templateCache', 'User', 'Sidebar', function ($templateCache, User, Sidebar) {
        return {
            restrict: 'E',
            replace: true,
            template: $templateCache.get('views/partials/sidebar.html'),
            scope: {},
            link: function (scope) {

                scope.view = {};
                scope.view.loading = true;
                scope.view.active = Sidebar.getActive();
                scope.view.open = Sidebar.open;

                scope.view.navigation = [
                    {name: 'tools', link: 'apps', desc: 'Applications', icon: 'puzzle-piece'},
                    {name: 'workflows', link: 'pipelines', desc: 'Workflows', icon: 'cogs'},
                    {name: 'builds', link: 'builds', desc: 'Builds', icon: 'cube'},
                    {name: 'repos', link: 'repos', desc: 'Repositories', icon: 'code-fork'},
                    {name: 'dyole', link: 'pipeline/0/new', desc: 'Workflow Editor', icon: 'terminal'},
                    {name: 'cliche', link: 'cliche', desc: 'Tool Editorr', icon: 'terminal'}
                ];

                scope.SidebarService = Sidebar;

                User.getUser().then(function(result) {
                    scope.view.user = result.user;
                    scope.view.loading = false;

                    if (!_.isEmpty(result.user)) {
                        scope.view.navigation.push({name: 'settings',link: 'settings',  desc: 'Settings', icon: 'gear'});
                    }

                });

                scope.$watch('SidebarService.active', function (n, o) {
                    if (n !== o) {
                        scope.view.active = n;
                    }
                });

                /**
                 * Toggle sidebar visibility
                 */
                scope.toggleSidebar = function () {
                    scope.view.open = !scope.view.open;
                    Sidebar.toggleOpen();
                };

            }
        };
    }]);<|endoftext|>


<commit_before>define([
    'underscore',
    'knockout',
    'knockout-mapping',
    'leaflet',
    'uuid',
    'geojson-extent',
    'views/components/iiif-viewer',
    'leaflet-draw'
], function(_, ko, koMapping, L, uuid, geojsonExtent, IIIFViewerViewmodel) {
    var viewModel = function(params) {
        var self = this;

        var drawControl;
        var drawFeatures = ko.observableArray();
        var editItems = new L.FeatureGroup();
        var tools;

        this.drawFeatures = drawFeatures;
        this.widgets = params.widgets || [];
        this.newNodeId = null;
        this.featureLookup = {};
        this.selectedFeatureIds = ko.observableArray();
        this.lineColor = ko.observable("#3388ff");
        this.fillColor = ko.observable("#3388ff");
        this.lineWidth = ko.observable(3);
        this.pointRadius = ko.observable(10);
        this.lineOpacity = ko.observable(1);
        this.fillOpacity = ko.observable(0.2);
        this.showStylingTools = ko.observable(false);

        this.hideEditorTab = params.hideEditorTab || ko.observable(false);

        this.cancelDrawing = function() {
            _.each(tools, function(tool) {
                tool.disable();
            });
        };

        this.setDrawTool = function(tool) {
            self.cancelDrawing();
            if (tool && tools) tools[tool].enable();
        };

        self.widgets.forEach(function(widget) {
            var id = ko.unwrap(widget.node_id);
            self.featureLookup[id] = {
                features: ko.computed(function() {
                    var value = koMapping.toJS(self.tile.data[id]);
                    if (value) return value.features;
                    else return [];
                }),
                selectedTool: ko.observable()
            };
            self.featureLookup[id].selectedTool.subscribe(function(tool) {
                if (drawControl) {
                    if (tool) {
                        _.each(self.featureLookup, function(value, key) {
                            if (key !== id) {
                                value.selectedTool(null);
                            }
                        });
                        self.newNodeId = id;
                    }
                    self.setDrawTool(tool);
                    disableEditing();
                }
            });
        });

        this.selectedTool = ko.pureComputed(function() {
            var tool;
            _.find(self.featureLookup, function(value) {
                var selectedTool = value.selectedTool();
                if (selectedTool) tool = selectedTool;
            });
            return tool;
        });

        this.editing = ko.pureComputed(function() {
            return !!(self.selectedFeatureIds().length > 0 || self.selectedTool());
        });

        this.updateTiles = function() {
            _.each(self.featureLookup, function(value) {
                value.selectedTool(null);
            });
            self.widgets.forEach(function(widget) {
                var id = ko.unwrap(widget.node_id);
                var features = [];
                drawFeatures().forEach(function(feature){
                    if (feature.properties.nodeId === id) {
                        features.push(feature);
                    }
                });
                if (ko.isObservable(self.tile.data[id])) {
                    self.tile.data[id]({
                        type: 'FeatureCollection',
                        features: features
                    });
                }
                else {
                    self.tile.data[id].features(features);
                }
            });
        };

        var updateDrawFeatures = function() {
            drawFeatures([]);
            self.widgets.forEach(function(widget) {
                var id = ko.unwrap(widget.node_id);
                var featureCollection = koMapping.toJS(self.tile.data[id]);
                if (featureCollection && featureCollection.features) {
                    featureCollection.features.forEach(function(feature) {
                        if (feature.properties.manifest && !params.manifest)
                            params.manifest = feature.properties.manifest;
                        if (feature.properties.canvas && !params.canvas)
                            params.canvas = feature.properties.canvas;
                        feature.properties.nodeId = id;
                    });
                    drawFeatures(drawFeatures().concat(featureCollection.features));
                }
            });
        };
        updateDrawFeatures();

        IIIFViewerViewmodel.apply(this, [params]);

        var setTab = this.canvas.subscribe(function(val){
            if (val) {
                self.expandGallery(false);
                self.activeTab(ko.unwrap(self.activeTab) || 'editor');
                setTab.dispose();
            }
        });

        this.expandGallery.subscribe(function(val){
            if (val) {
                self.hideSidePanel();
            }
        });

        this.getAnnotationCount = function(canvas) {
            return drawFeatures().filter(function(feature) {
                return feature.properties.canvas === canvas;
            }).length;
        };

        var disableEditing = function() {
            if (editingFeature) editingFeature.editing.disable();
            editingFeature = undefined;
            self.selectedFeatureIds([]);
        };
        var enableEditing = function(feature) {
            disableEditing();
            editingFeature = feature;
            editingFeature.options.editing || (editingFeature.options.editing = {});
            editingFeature.editing.enable();
            self.styleProperties(feature.feature.properties);
            self.selectedFeatureIds([feature.feature.id]);
        };

        this.styleProperties = ko.computed({
            read: function() {
                return {
                    color: self.lineColor(),
                    fillColor: self.fillColor(),
                    weight: self.lineWidth(),
                    radius: self.pointRadius(),
                    opacity: self.lineOpacity(),
                    fillOpacity: self.fillOpacity()
                };
            },
            write: function(style) {
                self.lineColor(style.color);
                self.fillColor(style.fillColor);
                self.lineWidth(style.weight);
                self.pointRadius(style.radius);
                self.lineOpacity(style.opacity);
                self.fillOpacity(style.fillOpacity);
            }
        });

        var featureClick;
        var drawLayer = ko.computed(function() {
            var selectedFeatureIds = self.selectedFeatureIds();
            var styleProperties = self.styleProperties();
            return L.geoJson({
                type: 'FeatureCollection',
                features: drawFeatures()
            }, {
                pointToLayer: function(feature, latlng) {
                    var style;
                    if (selectedFeatureIds.includes(feature.id)) style = styleProperties;
                    else style = {
                        color: feature.properties.color,
                        fillColor: feature.properties.fillColor,
                        weight: feature.properties.weight,
                        radius: feature.properties.radius,
                        opacity: feature.properties.opacity,
                        fillOpacity: feature.properties.fillOpacity
                    };
                    return L.circleMarker(latlng, style);
                },
                style: function(feature) {
                    var style;
                    if (selectedFeatureIds.includes(feature.id)) style = styleProperties;
                    else style = {
                        color: feature.properties.color,
                        fillColor: feature.properties.fillColor,
                        weight: feature.properties.weight,
                        radius: feature.properties.radius,
                        opacity: feature.properties.opacity,
                        fillOpacity: feature.properties.fillOpacity
                    };
                    return style;
                },
                filter: function(feature) {
                    return feature.properties.canvas === self.canvas();
                },
                onEachFeature: function(feature, layer) {
                    layer.on('click', function(e) {
                        enableEditing(e.target);
                        featureClick = true;
                    });
                }
            });
        });

        drawLayer.subscribe(function(newDrawLayer) {
            var map = self.map();
            var selectedFeatureIds = self.selectedFeatureIds();
            if (map) {
                editItems.clearLayers();
                editItems.addLayer(newDrawLayer);
                newDrawLayer.getLayers().forEach(function(layer) {
                    if (selectedFeatureIds.includes(layer.feature.id)) {
                        layer.options.editing || (layer.options.editing = {});
                        layer.editing.enable();
                    }
                });
            }
        });

        if (this.card) {
            this.card.triggerUpdate = updateDrawFeatures; // can be called by the provisional tile view model to update the drawing
        }

        this.disableDrawing = ko.computed(function() {
            return !self.canvas();
        });

        this.showFeature = function(feature) {
            self.canvas(feature.properties.canvas);
            if (self.manifest() !== feature.properties.manifest) {
                self.manifest(feature.properties.manifest);
                self.getManifestData();
            }
            setTimeout(function() {
                if (feature.geometry.type === 'Point') {
                    var coords = feature.geometry.coordinates;
                    self.map().panTo([coords[1], coords[0]]);
                } else {
                    var extent = geojsonExtent(feature);
                    self.map().fitBounds([
                        [extent[1], extent[0]],
                        [extent[3], extent[2]]
                    ]);
                }
            }, 200);
        };

        var editingFeature;
        this.editFeature = function(feature) {
            var layers = editItems.getLayers()[0].getLayers();
            if (self.manifest() !== feature.properties.manifest) {
                self.manifest(feature.properties.manifest);
                self.getManifestData();
            }
            self.canvas(feature.properties.canvas);
            layers.forEach(function(layer) {
                if (layer.feature.id === feature.id) enableEditing(layer);
            });
        };

        this.deleteFeature = function(feature) {
            drawFeatures().forEach(function(drawFeature) {
                if (drawFeature.id === feature.id) drawFeatures.remove(drawFeature);
            });
            self.updateTiles();
        };

        this.canvas.subscribe(disableEditing);

        this.map.subscribe(function(map) {
            if (map && !drawControl) {
                map.addLayer(editItems);
                editItems.addLayer(drawLayer());

                drawControl = new L.Control.Draw({
                    edit: {
                        featureGroup: editItems
                    }
                });
                map.addControl(drawControl);

                tools = {
                    'draw_point': new L.Draw.CircleMarker(map, drawControl.options.circlemarker),
                    'draw_line_string': new L.Draw.Polyline(map, drawControl.options.polyline),
                    'draw_polygon': new L.Draw.Polygon(map, drawControl.options.polygon)
                };
                self.styleProperties.subscribe(function(styleProperties) {
                    _.each(tools, function(tool) {
                        if (tool.type === "circlemarker") tool.setOptions(styleProperties);
                        else tool.setOptions({ shapeOptions: styleProperties });
                    });
                    self.selectedFeatureIds().forEach(function(id) {
                        drawFeatures().forEach(function(drawFeature) {
                            if (drawFeature.id === id) {
                                drawFeature.properties = Object.assign(
                                    drawFeature.properties,
                                    styleProperties
                                );
                            }
                        });
                        self.updateTiles();
                    });
                });

                map.on('draw:created', function(e) {
                    var feature = e.layer.toGeoJSON();
                    feature.id = uuid.generate();
                    feature.properties = Object.assign({
                        nodeId: self.newNodeId,
                        canvas: self.canvas(),
                        manifest: self.manifest()
                    }, self.styleProperties());
                    drawFeatures.push(feature);
                    self.updateTiles();
                    self.editFeature(feature);
                });

                map.on('draw:editvertex draw:editmove', function() {
                    var layers = editItems.getLayers()[0].getLayers();
                    drawFeatures().forEach(function(drawFeature) {
                        layers.forEach(function(layer) {
                            if (drawFeature.id === layer.feature.id)
                                drawFeature.geometry = layer.toGeoJSON().geometry;
                        });
                    });
                    self.updateTiles();
                });

                map.on('click', function() {
                    if (!featureClick) disableEditing();
                    featureClick = false;
                });

                if (self.form) self.form.on('tile-reset', function() {
                    disableEditing();
                    updateDrawFeatures();
                    _.each(self.featureLookup, function(value) {
                        if (value.selectedTool()) value.selectedTool('');
                    });
                });
            }
        });
    };
    return viewModel;
});
<commit_msg>core changes to support afs 458 #7651<commit_after>define([
    'underscore',
    'knockout',
    'knockout-mapping',
    'leaflet',
    'uuid',
    'geojson-extent',
    'views/components/iiif-viewer',
    'leaflet-draw'
], function(_, ko, koMapping, L, uuid, geojsonExtent, IIIFViewerViewmodel) {
    var viewModel = function(params) {
        var self = this;

        var drawControl;
        var drawFeatures = ko.observableArray();
        var editItems = new L.FeatureGroup();
        var tools;

        this.drawFeatures = drawFeatures;
        this.widgets = params.widgets || [];
        this.newNodeId = null;
        this.featureLookup = {};
        this.selectedFeatureIds = ko.observableArray();
        this.lineColor = ko.observable("#3388ff");
        this.fillColor = ko.observable("#3388ff");
        this.lineWidth = ko.observable(3);
        this.pointRadius = ko.observable(10);
        this.lineOpacity = ko.observable(1);
        this.fillOpacity = ko.observable(0.2);
        this.showStylingTools = ko.observable(false);

        this.hideEditorTab = params.hideEditorTab || ko.observable(false);

        this.cancelDrawing = function() {
            _.each(tools, function(tool) {
                tool.disable();
            });
        };

        this.setDrawTool = function(tool) {
            self.cancelDrawing();
            if (tool && tools) tools[tool].enable();
        };

        self.widgets.forEach(function(widget) {
            var id = ko.unwrap(widget.node_id);
            self.featureLookup[id] = {
                features: ko.computed(function() {
                    var value = koMapping.toJS(self.tile.data[id]);
                    if (value) return value.features;
                    else return [];
                }),
                selectedTool: ko.observable()
            };
            self.featureLookup[id].selectedTool.subscribe(function(tool) {
                if (drawControl) {
                    if (tool) {
                        _.each(self.featureLookup, function(value, key) {
                            if (key !== id) {
                                value.selectedTool(null);
                            }
                        });
                        self.newNodeId = id;
                    }
                    self.setDrawTool(tool);
                    disableEditing();
                }
            });
        });

        this.selectedTool = ko.pureComputed(function() {
            var tool;
            _.find(self.featureLookup, function(value) {
                var selectedTool = value.selectedTool();
                if (selectedTool) tool = selectedTool;
            });
            return tool;
        });

        this.editing = ko.pureComputed(function() {
            return !!(self.selectedFeatureIds().length > 0 || self.selectedTool());
        });

        this.updateTiles = function() {
            _.each(self.featureLookup, function(value) {
                value.selectedTool(null);
            });
            self.widgets.forEach(function(widget) {
                var id = ko.unwrap(widget.node_id);
                var features = [];
                drawFeatures().forEach(function(feature){
                    if (feature.properties.nodeId === id) {
                        features.push(feature);
                    }
                });
                if (ko.isObservable(self.tile.data[id])) {
                    self.tile.data[id]({
                        type: 'FeatureCollection',
                        features: features
                    });
                }
                else {
                    self.tile.data[id].features(features);
                }
            });
        };

        var updateDrawFeatures = function() {
            drawFeatures([]);
            self.widgets.forEach(function(widget) {
                var id = ko.unwrap(widget.node_id);
                var featureCollection = koMapping.toJS(self.tile.data[id]);
                if (featureCollection && featureCollection.features) {
                    featureCollection.features.forEach(function(feature) {
                        if (feature.properties.manifest && !params.manifest)
                            params.manifest = feature.properties.manifest;
                        if (feature.properties.canvas && !params.canvas)
                            params.canvas = feature.properties.canvas;
                        feature.properties.nodeId = id;
                    });
                    drawFeatures(drawFeatures().concat(featureCollection.features));
                }
            });
        };
        updateDrawFeatures();

        IIIFViewerViewmodel.apply(this, [params]);

        var setTab = this.canvas.subscribe(function(val){
            if (val) {
                self.expandGallery(false);
                self.activeTab(ko.unwrap(self.activeTab) || 'editor');
                setTab.dispose();
            }
        });

        this.expandGallery.subscribe(function(val){
            if (val) {
                self.hideSidePanel();
            }
        });

        this.getAnnotationCount = function(canvas) {
            return drawFeatures().filter(function(feature) {
                return feature.properties.canvas === canvas;
            }).length;
        };

        var disableEditing = function() {
            if (editingFeature && editingFeature.editing) editingFeature.editing.disable();
            editingFeature = undefined;
            self.selectedFeatureIds([]);
        };
        var enableEditing = function(feature) {
            disableEditing();
            editingFeature = feature;
            editingFeature.options.editing || (editingFeature.options.editing = {});
            editingFeature.editing.enable();
            self.styleProperties(feature.feature.properties);
            self.selectedFeatureIds([feature.feature.id]);
        };

        this.styleProperties = ko.computed({
            read: function() {
                return {
                    color: self.lineColor(),
                    fillColor: self.fillColor(),
                    weight: self.lineWidth(),
                    radius: self.pointRadius(),
                    opacity: self.lineOpacity(),
                    fillOpacity: self.fillOpacity()
                };
            },
            write: function(style) {
                self.lineColor(style.color);
                self.fillColor(style.fillColor);
                self.lineWidth(style.weight);
                self.pointRadius(style.radius);
                self.lineOpacity(style.opacity);
                self.fillOpacity(style.fillOpacity);
            }
        });

        var featureClick;
        this.featureClick = featureClick;
        var drawLayer = ko.computed(function() {
            var selectedFeatureIds = self.selectedFeatureIds();
            var styleProperties = self.styleProperties();
            return L.geoJson({
                type: 'FeatureCollection',
                features: drawFeatures()
            }, {
                pointToLayer: function(feature, latlng) {
                    var style;
                    if (selectedFeatureIds.includes(feature.id)) style = styleProperties;
                    else style = {
                        color: feature.properties.color,
                        fillColor: feature.properties.fillColor,
                        weight: feature.properties.weight,
                        radius: feature.properties.radius,
                        opacity: feature.properties.opacity,
                        fillOpacity: feature.properties.fillOpacity
                    };
                    return L.circleMarker(latlng, style);
                },
                style: function(feature) {
                    var style;
                    if (selectedFeatureIds.includes(feature.id)) style = styleProperties;
                    else style = {
                        color: feature.properties.color,
                        fillColor: feature.properties.fillColor,
                        weight: feature.properties.weight,
                        radius: feature.properties.radius,
                        opacity: feature.properties.opacity,
                        fillOpacity: feature.properties.fillOpacity
                    };
                    return style;
                },
                filter: function(feature) {
                    return feature.properties.canvas === self.canvas();
                },
                onEachFeature: function(feature, layer) {
                    layer.on('click', function(e) {
                        enableEditing(e.target);
                        featureClick = true;
                    });
                }
            });
        });
        this.drawLayer = drawLayer;

        drawLayer.subscribe(function(newDrawLayer) {
            var map = self.map();
            var selectedFeatureIds = self.selectedFeatureIds();
            if (map) {
                editItems.clearLayers();
                editItems.addLayer(newDrawLayer);
                newDrawLayer.getLayers().forEach(function(layer) {
                    if (selectedFeatureIds.includes(layer.feature.id)) {
                        layer.options.editing || (layer.options.editing = {});
                        layer.editing.enable();
                    }
                });
            }
        });

        if (this.card) {
            this.card.triggerUpdate = updateDrawFeatures; // can be called by the provisional tile view model to update the drawing
        }

        this.disableDrawing = ko.computed(function() {
            return !self.canvas();
        });

        this.showFeature = function(feature) {
            self.canvas(feature.properties.canvas);
            if (self.manifest() !== feature.properties.manifest) {
                self.manifest(feature.properties.manifest);
                self.getManifestData();
            }
            setTimeout(function() {
                if (feature.geometry.type === 'Point') {
                    var coords = feature.geometry.coordinates;
                    self.map().panTo([coords[1], coords[0]]);
                } else {
                    var extent = geojsonExtent(feature);
                    self.map().fitBounds([
                        [extent[1], extent[0]],
                        [extent[3], extent[2]]
                    ]);
                }
            }, 200);
        };

        var editingFeature;
        this.editFeature = function(feature) {
            var layers = editItems.getLayers()[0].getLayers();
            if (self.manifest() !== feature.properties.manifest) {
                self.manifest(feature.properties.manifest);
                self.getManifestData();
            }
            self.canvas(feature.properties.canvas);
            layers.forEach(function(layer) {
                if (layer.feature.id === feature.id) enableEditing(layer);
            });
        };

        this.deleteFeature = function(feature) {
            drawFeatures().forEach(function(drawFeature) {
                if (drawFeature.id === feature.id) drawFeatures.remove(drawFeature);
            });
            self.updateTiles();
        };

        this.canvas.subscribe(disableEditing);

        this.map.subscribe(function(map) {
            if (map && !drawControl) {
                map.addLayer(editItems);
                editItems.addLayer(drawLayer());

                drawControl = new L.Control.Draw({
                    edit: {
                        featureGroup: editItems
                    }
                });
                map.addControl(drawControl);

                tools = {
                    'draw_point': new L.Draw.CircleMarker(map, drawControl.options.circlemarker),
                    'draw_line_string': new L.Draw.Polyline(map, drawControl.options.polyline),
                    'draw_polygon': new L.Draw.Polygon(map, drawControl.options.polygon)
                };
                self.styleProperties.subscribe(function(styleProperties) {
                    _.each(tools, function(tool) {
                        if (tool.type === "circlemarker") tool.setOptions(styleProperties);
                        else tool.setOptions({ shapeOptions: styleProperties });
                    });
                    self.selectedFeatureIds().forEach(function(id) {
                        drawFeatures().forEach(function(drawFeature) {
                            if (drawFeature.id === id) {
                                drawFeature.properties = Object.assign(
                                    drawFeature.properties,
                                    styleProperties
                                );
                            }
                        });
                        self.updateTiles();
                    });
                });

                map.on('draw:created', function(e) {
                    var feature = e.layer.toGeoJSON();
                    feature.id = uuid.generate();
                    feature.properties = Object.assign({
                        nodeId: self.newNodeId,
                        canvas: self.canvas(),
                        manifest: self.manifest()
                    }, self.styleProperties());
                    drawFeatures.push(feature);
                    self.updateTiles();
                    self.editFeature(feature);
                });

                map.on('draw:editvertex draw:editmove', function() {
                    var layers = editItems.getLayers()[0].getLayers();
                    drawFeatures().forEach(function(drawFeature) {
                        layers.forEach(function(layer) {
                            if (drawFeature.id === layer.feature.id)
                                drawFeature.geometry = layer.toGeoJSON().geometry;
                        });
                    });
                    self.updateTiles();
                });

                map.on('click', function() {
                    if (!featureClick) disableEditing();
                    featureClick = false;
                });

                if (self.form) self.form.on('tile-reset', function() {
                    disableEditing();
                    updateDrawFeatures();
                    _.each(self.featureLookup, function(value) {
                        if (value.selectedTool()) value.selectedTool('');
                    });
                });
            }
        });
    };
    return viewModel;
});
<|endoftext|>


<commit_before>import t from 'tcomb'
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/observable/combineLatest';
import 'rxjs/add/operator/filter';
import 'rxjs/add/operator/switchMap';
import 'rxjs/add/observable/of';

function observeCache(cache, a) {
  return cache.getSubject(a).filter(e => e.hasOwnProperty('loading'))
}

export function observe(fetch, a) {
  if (process.env.NODE_ENV !== 'production') {
    t.assert(t.Function.is(fetch), () => 'Invalid argument fetch supplied to observe (expected a function)')
  }

  if (fetch.type === 'product') {
    // fix https://github.com/ReactiveX/rxjs/issues/1686
    return Observable.combineLatest(...fetch.fetches.map((fetch, i) => observe(fetch, a[i])), (...values) => values)
  }
  if (fetch.type === 'composition') {
    const { master, slave, ptoa } = fetch
    return observe(master, a).switchMap(x => {
      if (x.hasOwnProperty('data')) {
        const a1  = ptoa(x.data, a)
        if (x.loading) {
          return {
            loading: true,
            data: slave.cache.getSubject(a1).value
          }
        }
        return observeCache(slave.cache, a1)
      }
      return Observable.of({ loading: true })
    })
  }
  return observeCache(fetch.cache, a)
}
<commit_msg>Observable.of<commit_after>import t from 'tcomb'
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/observable/combineLatest';
import 'rxjs/add/operator/filter';
import 'rxjs/add/operator/switchMap';
import 'rxjs/add/observable/of';

function observeCache(cache, a) {
  return cache.getSubject(a).filter(e => e.hasOwnProperty('loading'))
}

export function observe(fetch, a) {
  if (process.env.NODE_ENV !== 'production') {
    t.assert(t.Function.is(fetch), () => 'Invalid argument fetch supplied to observe (expected a function)')
  }

  if (fetch.type === 'product') {
    // fix https://github.com/ReactiveX/rxjs/issues/1686
    return Observable.combineLatest(...fetch.fetches.map((fetch, i) => observe(fetch, a[i])), (...values) => values)
  }
  if (fetch.type === 'composition') {
    const { master, slave, ptoa } = fetch
    return observe(master, a).switchMap(x => {
      if (x.hasOwnProperty('data')) {
        const a1  = ptoa(x.data, a)
        if (x.loading) {
          return Observable.of({
            loading: true,
            data: slave.cache.getSubject(a1).value.data
          })
        }
        return observeCache(slave.cache, a1)
      }
      return Observable.of({ loading: true })
    })
  }
  return observeCache(fetch.cache, a)
}
<|endoftext|>


<commit_before>export default ngModule => {

    const slugify = require('slugify');

    ngModule.service('MediumsService', MediumsService);

    function MediumsService($firebaseArray, $firebaseObject, FIREBASE_URL) {
        "use strict";

        const ref = new Firebase(`${FIREBASE_URL}/mediums`);

        return {

            listForSource(source) {
                let source_slug = slugify(source).toLowerCase();
                let mediumsRef = ref.child(source_slug);
                return $firebaseArray(mediumsRef);
            },

            addToSource(source, name) {

                let name_slug = slugify(name).toLowerCase();

                let mediums = this.listForSource(source);
                mediums.$add(name_slug);

            }
        };
    }
}<commit_msg>Fixed how mediums are stored in FB<commit_after>export default ngModule => {

    const slugify = require('slugify');

    ngModule.service('MediumsService', MediumsService);

    function MediumsService($firebaseArray, $firebaseObject, FIREBASE_URL) {
        "use strict";

        const ref = new Firebase(`${FIREBASE_URL}/mediums`);

        return {

            listForSource(source) {
                let source_slug = slugify(source).toLowerCase();
                let mediumsRef = ref.child(source_slug);
                return $firebaseArray(mediumsRef);
            },

            addToSource(source, name) {

                let source_slug = slugify(source).toLowerCase();
                let name_slug = slugify(name).toLowerCase();

                let item = $firebaseObject(
                    ref.child(source_slug)
                        .child(name_slug)
                );

                item.$value = true;
                return item.$save();

            }
        };
    }
}<|endoftext|>


<commit_before>import React from 'react'
import PropTypes from 'prop-types'
import { translate } from 'react-i18next'
import { Nav, NavItem } from 'react-bootstrap'
import Icon from 'components/Common/Icon'

class SearchToolbar extends React.Component {
  constructor() {
    super()

    this.searchTypes = ['', 'portal', 'public', 'user']

    this.getActiveType = this.getActiveType.bind(this)
  }

  getActiveType() {
    const defaultType = this.searchTypes[0]
    const { type } = this.props
    return this.searchTypes.includes(type) ? type : defaultType
  }

  render() {
    const { t } = this.props
    return (

{this.props.keyword}

            {(this.props.searching && <Icon name="spinner" spin />) || t('search.toolbar.results', { value: this.props.total })}

            <NavItem eventKey={this.searchTypes[0]} href="#">
              <Icon name="th" />
              {t('page_types.all')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[1]} href="#">
              <Icon name="circle" regular />
              {t('page_types.portal')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[2]} href="#">
              <Icon name="file" regular />
              {t('page_types.public')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[3]} href="#">
              <Icon name="user" regular />
              {t('page_types.user')}
            </NavItem>

    )
  }
}

SearchToolbar.propTypes = {
  keyword: PropTypes.string,
  type: PropTypes.string,
  total: PropTypes.number,
  changeType: PropTypes.func,
  searching: PropTypes.boolean,
  t: PropTypes.func.isRequired,
}
SearchToolbar.defaultProps = {
  keyword: '',
  type: '',
  searching: false,
  total: 0,
}

export default translate()(SearchToolbar)
<commit_msg>Fix: props for arg list<commit_after>import React from 'react'
import PropTypes from 'prop-types'
import { translate } from 'react-i18next'
import { Nav, NavItem } from 'react-bootstrap'
import Icon from 'components/Common/Icon'

class SearchToolbar extends React.Component {
  constructor(props) {
    super(props)

    this.searchTypes = ['', 'portal', 'public', 'user']

    this.getActiveType = this.getActiveType.bind(this)
  }

  getActiveType() {
    const defaultType = this.searchTypes[0]
    const { type } = this.props
    return this.searchTypes.includes(type) ? type : defaultType
  }

  render() {
    const { t } = this.props
    return (

{this.props.keyword}

            {(this.props.searching && <Icon name="spinner" spin />) || t('search.toolbar.results', { value: this.props.total })}

            <NavItem eventKey={this.searchTypes[0]} href="#">
              <Icon name="th" />
              {t('page_types.all')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[1]} href="#">
              <Icon name="circle" regular />
              {t('page_types.portal')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[2]} href="#">
              <Icon name="file" regular />
              {t('page_types.public')}
            </NavItem>
            <NavItem eventKey={this.searchTypes[3]} href="#">
              <Icon name="user" regular />
              {t('page_types.user')}
            </NavItem>

    )
  }
}

SearchToolbar.propTypes = {
  keyword: PropTypes.string,
  type: PropTypes.string,
  total: PropTypes.number,
  changeType: PropTypes.func,
  searching: PropTypes.boolean,
  t: PropTypes.func.isRequired,
}
SearchToolbar.defaultProps = {
  keyword: '',
  type: '',
  searching: false,
  total: 0,
}

export default translate()(SearchToolbar)
<|endoftext|>


<commit_before>
export function parseRangeFilters(stringValue = '') {
  if (!stringValue) {
    return [];
  }
  return stringValue.split('~').map(s => {
    const m = s.match(/range-(-?[0-9.]+)_(-?[0-9.]+)/);
    if (!m) {
      return { start: 0, end: 1000 };
    }
    return { start: m[1] * 1000, end: m[2] * 1000 };
  });
}

export function stringifyRangeFilters(arrayValue = []) {
  return arrayValue.map(({ start, end }) => {
    const startStr = (start / 1000).toFixed(4);
    const endStr = (end / 1000).toFixed(4);
    return `range-${startStr}_${endStr}`;
  }).join('~');
}
<commit_msg>Remove the word 'range' from the range filter list items because we are not going to add other types of filters to that list. Callstack focus filters will be a separate filter list.<commit_after>
export function parseRangeFilters(stringValue = '') {
  if (!stringValue) {
    return [];
  }
  return stringValue.split('~').map(s => {
    const m = s.match(/(-?[0-9.]+)_(-?[0-9.]+)/);
    if (!m) {
      return { start: 0, end: 1000 };
    }
    return { start: m[1] * 1000, end: m[2] * 1000 };
  });
}

export function stringifyRangeFilters(arrayValue = []) {
  return arrayValue.map(({ start, end }) => {
    const startStr = (start / 1000).toFixed(4);
    const endStr = (end / 1000).toFixed(4);
    return `${startStr}_${endStr}`;
  }).join('~');
}
<|endoftext|>


<commit_before>var PhotoTilt = function(options) {

	'use strict';

	var imgUrl = options.url,
		lowResUrl = options.lowResUrl,
		container = options.container || document.body,
		latestTilt = 0,
		viewport,
		imgData,
		img,
		imgLoader,
		delta,
		centerOffset,
		tiltBarWidth,
		tiltCenterOffset,
		tiltBarIndicatorWidth,
		tiltBarIndicator,
		config;

	config = {
		maxTilt: options.maxTilt || 20,
		twoPhase: options.lowResUrl || false,
		reverseTilt: options.reverseTilt || false
	};

	window.requestAnimationFrame =  window.requestAnimationFrame ||
									window.mozRequestAnimationFrame ||
									window.webkitRequestAnimationFrame ||
									window.msRequestAnimationFrame;

	var init = function() {

		var url = config.twoPhase ? lowResUrl : imgUrl;

		generateViewPort();

		preloadImg(url, function() {

			img = imgLoader.cloneNode(false);
			imgLoader = null;

			if (config.twoPhase) {

				preloadImg(imgUrl, function() {
					img.src = imgLoader.src;
					imgLoader = null;
				});

			}

			generateImgData();
			render();
			addEventListeners();

		});

	};

	var updatePosition = function() {

		var tilt = latestTilt,
			pxToMove;

		if (tilt > 0) {
			tilt = Math.min(tilt, config.maxTilt);
		} else {
			tilt = Math.max(tilt, config.maxTilt * -1);
		}

		if (!config.reverseTilt) {
			tilt = tilt * -1;
		}

		pxToMove = (tilt * centerOffset) / config.maxTilt;

		updateImgPosition(imgData,  (centerOffset + pxToMove) * -1);

		updateTiltBar(tilt);

		window.requestAnimationFrame(updatePosition);

	};

	var updateTiltBar = function(tilt) {

		var pxToMove = (tilt * ((tiltBarWidth - tiltBarIndicatorWidth) / 2)) / config.maxTilt;
		setTranslateX(tiltBarIndicator, (tiltCenterOffset + pxToMove) );

	};

	var updateImgPosition = function(imgData, pxToMove) {
		setTranslateX(img, pxToMove);
	};

	var addEventListeners = function() {

		if (window.DeviceOrientationEvent) {

			var averageGamma = [];

			window.addEventListener('deviceorientation', function(eventData) {

				if (averageGamma.length > 8) {
					averageGamma.shift();
				}

				averageGamma.push(eventData.gamma);

				latestTilt = averageGamma.reduce(function(a, b) { return a+b; }) / averageGamma.length;

			}, false);

			window.requestAnimationFrame(updatePosition);

		}

	};

	var setTranslateX = function(node, amount) {
		node.style.webkitTransform =
		node.style.MozTransform =
		node.style.msTransform =
		node.style.transform = "translateX(" + Math.round(amount) + "px)";
	};

	var render = function() {

		var mask,
			tiltBar,
			resizedImgWidth,
			tiltBarPadding = 20;

		mask = document.createElement('div');
		mask.classList.add('mask');

		img.height = viewport.height;
		resizedImgWidth = (imgData.aspectRatio * img.height);

		delta = resizedImgWidth - viewport.width;
		centerOffset = delta / 2;

		tiltBar = document.createElement('div');
		tiltBar.classList.add('tilt-bar');
		tiltBarWidth = viewport.width - tiltBarPadding;

		tiltBarIndicator = document.createElement('div');
		tiltBarIndicator.classList.add('tilt-indicator');

		tiltBarIndicatorWidth = (viewport.width * tiltBarWidth) / resizedImgWidth;
		tiltBarIndicator.style.width = tiltBarIndicatorWidth + 'px';

		tiltCenterOffset = ((tiltBarWidth / 2) - (tiltBarIndicatorWidth / 2));
		updatePosition(0);

		mask.appendChild(img);
		tiltBar.appendChild(tiltBarIndicator);
		mask.appendChild(tiltBar);
		container.appendChild(mask);

	};

	var generateViewPort = function() {

		var containerStyle = window.getComputedStyle(container, null);

		viewport = {
			width: parseInt(containerStyle.width, 10),
			height: parseInt(containerStyle.height, 10)
		};

	};

	var generateImgData = function() {

		imgData = {
			width: img.width,
			height: img.height,
			aspectRatio: img.width / img.height,
			src: img.src
		};

	};

	var preloadImg = function(url, done) {

		imgLoader = new Image();
		imgLoader.addEventListener('load', done, false);
		imgLoader.src = url;
	};

	init();

	return {
		getContainer: function(){
			return container;
		}
	}

};<commit_msg>-Fixing Chrome iOS issue<commit_after>var PhotoTilt = function(options) {

	'use strict';

	var imgUrl = options.url,
		lowResUrl = options.lowResUrl,
		container = options.container || document.body,
		latestTilt = 0,
		viewport,
		imgData,
		img,
		imgLoader,
		delta,
		centerOffset,
		tiltBarWidth,
		tiltCenterOffset,
		tiltBarIndicatorWidth,
		tiltBarIndicator,
		config;

	config = {
		maxTilt: options.maxTilt || 20,
		twoPhase: options.lowResUrl || false,
		reverseTilt: options.reverseTilt || false
	};

	window.requestAnimationFrame =  window.requestAnimationFrame ||
									window.mozRequestAnimationFrame ||
									window.webkitRequestAnimationFrame ||
									window.msRequestAnimationFrame;

	var init = function() {

		var url = config.twoPhase ? lowResUrl : imgUrl;

		generateViewPort();

		preloadImg(url, function() {

			img = imgLoader.cloneNode(false);
			generateImgData();
			imgLoader = null;

			if (config.twoPhase) {

				preloadImg(imgUrl, function() {
					img.src = imgLoader.src;
					imgLoader = null;
				});

			}

			render();
			addEventListeners();

		});

	};

	var updatePosition = function() {

		var tilt = latestTilt,
			pxToMove;

		if (tilt > 0) {
			tilt = Math.min(tilt, config.maxTilt);
		} else {
			tilt = Math.max(tilt, config.maxTilt * -1);
		}

		if (!config.reverseTilt) {
			tilt = tilt * -1;
		}

		pxToMove = (tilt * centerOffset) / config.maxTilt;

		updateImgPosition(imgData,  (centerOffset + pxToMove) * -1);

		updateTiltBar(tilt);

		window.requestAnimationFrame(updatePosition);

	};

	var updateTiltBar = function(tilt) {

		var pxToMove = (tilt * ((tiltBarWidth - tiltBarIndicatorWidth) / 2)) / config.maxTilt;
		setTranslateX(tiltBarIndicator, (tiltCenterOffset + pxToMove) );

	};

	var updateImgPosition = function(imgData, pxToMove) {
		setTranslateX(img, pxToMove);
	};

	var addEventListeners = function() {

		if (window.DeviceOrientationEvent) {

			var averageGamma = [];

			window.addEventListener('deviceorientation', function(eventData) {

				if (averageGamma.length > 8) {
					averageGamma.shift();
				}

				averageGamma.push(eventData.gamma);

				latestTilt = averageGamma.reduce(function(a, b) { return a+b; }) / averageGamma.length;

			}, false);

			window.requestAnimationFrame(updatePosition);

		}

	};

	var setTranslateX = function(node, amount) {
		node.style.webkitTransform =
		node.style.MozTransform =
		node.style.msTransform =
		node.style.transform = "translateX(" + Math.round(amount) + "px)";
	};

	var render = function() {

		var mask,
			tiltBar,
			resizedImgWidth,
			tiltBarPadding = 20;

		mask = document.createElement('div');
		mask.classList.add('mask');

		img.height = viewport.height;
		resizedImgWidth = (imgData.aspectRatio * img.height);

		delta = resizedImgWidth - viewport.width;
		centerOffset = delta / 2;

		tiltBar = document.createElement('div');
		tiltBar.classList.add('tilt-bar');
		tiltBarWidth = viewport.width - tiltBarPadding;

		tiltBarIndicator = document.createElement('div');
		tiltBarIndicator.classList.add('tilt-indicator');

		tiltBarIndicatorWidth = (viewport.width * tiltBarWidth) / resizedImgWidth;
		tiltBarIndicator.style.width = tiltBarIndicatorWidth + 'px';

		tiltCenterOffset = ((tiltBarWidth / 2) - (tiltBarIndicatorWidth / 2));
		updatePosition(0);

		mask.appendChild(img);
		tiltBar.appendChild(tiltBarIndicator);
		mask.appendChild(tiltBar);
		container.appendChild(mask);

	};

	var generateViewPort = function() {

		var containerStyle = window.getComputedStyle(container, null);

		viewport = {
			width: parseInt(containerStyle.width, 10),
			height: parseInt(containerStyle.height, 10)
		};

	};

	var generateImgData = function() {

		imgData = {
			width: imgLoader.width,
			height: imgLoader.height,
			aspectRatio: imgLoader.width / imgLoader.height,
			src: imgLoader.src
		};

	};

	var preloadImg = function(url, done) {

		imgLoader = new Image();
		imgLoader.addEventListener('load', done, false);
		imgLoader.src = url;
	};

	init();

	return {
		getContainer: function(){
			return container;
		}
	}

};<|endoftext|>


<commit_before>'use strict';
const request = require('request');
const core = require('./../core/core.js');
const db = require('./../aslan-messenger/aslan-db.js');

/*
* Fonction appelé par les routes lors de la reception d'un message
*/
function receivedMessage(message, user) {
    console.log("Aslan received a message");
    var m = {
        channel: "Aslan",
        senderID: user._id,
        timestamp: new Date(),
        text: message,
        first_name: user.firstname,
        last_name: user.name
    };

    core.receivedMessage(m);
}

/*
* Fonction appelé par le core pour envoyer un message sur la channel Aslan Messenger
*/
function sendMessage(message) {
	switch(message.type) {
        case "text":
            sendTextMessage(message);
        break;
        case "quickreply":
            sendQuickReplyMessage(message);
        break;
    }
}

/*
* Fonction appelé par le core pour envoyer des messages sur la channel Aslan Messenger
*/
function sendMessages(messages) {
    for(var i=0;i<messages.length;i++) {
        sendMessage(messages[i]);
    }
}

/*
* Fonction qui sauvegarde un message en DB
*/
function save(m) {
    var user_id = m.user_id;
    var message = m.message;
    if(user_id != undefined && message != undefined) {
        db.createMessage(user_id, message, true, function(data){
            console.log(data)
            if(data.length == 0) {
                console.log("Error create message");
            } else {
                console.log(JSON.stringify(data[0]));
            }
        });
    }
}

/*
* Fonction qui envoie un message de type text
*/
function sendTextMessage(message) {
    if(message.senderID != undefined && message.text != undefined) {
        message.message = {text : message.text, type: "text"};
        save(messageData);
    }
}

/*
* Fonction qui envoie un message de type quickreply
*/
function sendQuickReplyMessage(message) {
    if(message.senderID != undefined && message.text != undefined) {
        message.message = {text : message.text, type: "text"};
        save(messageData);
    }
}

/*
* Fonction qui envoie un message audio/file/image/video
*/
function sendFileMessage(message) {

}

exports.receivedMessage = receivedMessage;
exports.sendMessage = sendMessage;
exports.sendMessages = sendMessages;<commit_msg>Ajout de debug<commit_after>'use strict';
const request = require('request');
const core = require('./../core/core.js');
const db = require('./../aslan-messenger/aslan-db.js');

/*
* Fonction appelé par les routes lors de la reception d'un message
*/
function receivedMessage(message, user) {
    console.log("Aslan received a message");
    var m = {
        channel: "Aslan",
        senderID: user._id,
        timestamp: new Date(),
        text: message,
        first_name: user.firstname,
        last_name: user.name
    };
    console.log(JSON.stringify(m));
    core.receivedMessage(m);
}

/*
* Fonction appelé par le core pour envoyer un message sur la channel Aslan Messenger
*/
function sendMessage(message) {
	switch(message.type) {
        case "text":
            sendTextMessage(message);
        break;
        case "quickreply":
            sendQuickReplyMessage(message);
        break;
    }
}

/*
* Fonction appelé par le core pour envoyer des messages sur la channel Aslan Messenger
*/
function sendMessages(messages) {
    for(var i=0;i<messages.length;i++) {
        sendMessage(messages[i]);
    }
}

/*
* Fonction qui sauvegarde un message en DB
*/
function save(m) {
    var user_id = m.user_id;
    var message = m.message;
    if(user_id != undefined && message != undefined) {
        db.createMessage(user_id, message, true, function(data){
            console.log(data)
            if(data.length == 0) {
                console.log("Error create message");
            } else {
                console.log(JSON.stringify(data[0]));
            }
        });
    }
}

/*
* Fonction qui envoie un message de type text
*/
function sendTextMessage(message) {
    if(message.senderID != undefined && message.text != undefined) {
        message.message = {text : message.text, type: "text"};
        save(messageData);
    }
}

/*
* Fonction qui envoie un message de type quickreply
*/
function sendQuickReplyMessage(message) {
    if(message.senderID != undefined && message.text != undefined) {
        message.message = {text : message.text, type: "text"};
        save(messageData);
    }
}

/*
* Fonction qui envoie un message audio/file/image/video
*/
function sendFileMessage(message) {

}

exports.receivedMessage = receivedMessage;
exports.sendMessage = sendMessage;
exports.sendMessages = sendMessages;<|endoftext|>


<commit_before>import smartStatusController from 'tower/smart-status/smart-status.controller.js';
export default [  function() {
    return {
        scope: {
            jobs: '='
        },
        restrict: 'E',
        link: function (scope, element){

            scope.formatter = function(sparklines, options, point){
                var status = options.userOptions.tooltipValueLookups.status[point.offset];
                //capitalize first letter
                status = status.charAt(0).toUpperCase() + status.slice(1);
                return "
Job ID: " +
                  options.userOptions.tooltipValueLookups.jobs[point.offset] +
                  "
Status: ●"+status+"
" ;
            };

            element.sparkline(scope.sparkArray, {
                type: 'tristate',
                width: '4em',
                height: '2em',
                barWidth: 7,
                barSpacing: 2,
                zeroBarColor: 'grey',
                posBarColor: '#00aa00',
                negBarColor: '#aa0000',
                tooltipFormatter: scope.formatter,
                tooltipFormat: '{{value:jobs}}',
                tooltipValueLookups: {
                    jobs: scope.jobIds,
                    status: scope.smartStatus
                }
            });

            $('aw-smart-status:eq('+scope.$index+')').bind('sparklineClick', function(ev) {
                var sparkline = ev.sparklines[0],
                    job = sparkline.getCurrentRegionFields(),
                    id;
                id = sparkline.options.userOptions.tooltipValueLookups.jobs[job.offset];
                location.href = '/#/jobs/' + id;
            });

        },
        controller: smartStatusController
    };
}];
<commit_msg>fixed click event element selector for smart status<commit_after>import smartStatusController from 'tower/smart-status/smart-status.controller.js';
export default [  function() {
    return {
        scope: {
            jobs: '='
        },
        restrict: 'E',
        link: function (scope, element){

            scope.formatter = function(sparklines, options, point){
                var status = options.userOptions.tooltipValueLookups.status[point.offset];
                //capitalize first letter
                status = status.charAt(0).toUpperCase() + status.slice(1);
                return "
Job ID: " +
                  options.userOptions.tooltipValueLookups.jobs[point.offset] +
                  "
Status: ●"+status+"
" ;
            };

            element.sparkline(scope.sparkArray, {
                type: 'tristate',
                width: '4em',
                height: '2em',
                barWidth: 7,
                barSpacing: 2,
                zeroBarColor: 'grey',
                posBarColor: '#00aa00',
                negBarColor: '#aa0000',
                tooltipFormatter: scope.formatter,
                tooltipFormat: '{{value:jobs}}',
                tooltipValueLookups: {
                    jobs: scope.jobIds,
                    status: scope.smartStatus
                }
            });

            element.bind('sparklineClick', function(ev) {
                var sparkline = ev.sparklines[0],
                    job = sparkline.getCurrentRegionFields(),
                    id;
                id = sparkline.options.userOptions.tooltipValueLookups.jobs[job.offset];
                location.href = '/#/jobs/' + id;
            });

        },
        controller: smartStatusController
    };
}];
<|endoftext|>