<commit_before>angular.module('MassAutoComplete', [])
.directive('massAutocomplete', ["$timeout", "$window", "$document", "$q", function ($timeout, $window, $document, $q) {
  'use strict';

  return {
    restrict: "A",
    scope: { options: '&massAutocomplete' },
    transclude: true,
    template:
      '' +
      '
 0" style="position:absolute;">' +
        '
' +
          '
 0" ' +
            'class="ac-menu-item" ng-class="$index == selected_index ? \'ac-state-focus\': \'\'">' +
            '' +
          '
' +
        '
' +
      '
',
    link: function (scope, element) {
      scope.container = angular.element(element[0].getElementsByClassName('ac-container')[0]);
    },
    controller: ["$scope", function ($scope) {
      var that = this;

      var KEYS = {
        TAB: 9,
        ESC: 27,
        ENTER: 13,
        UP: 38,
        DOWN: 40
      };

      var EVENTS = {
        KEYDOWN: 'keydown',
        RESIZE: 'resize',
        BLUR: 'blur'
      };

      var _user_options = $scope.options() || {};
      var user_options = {
        debounce_position: _user_options.debounce_position || 150,
        debounce_attach: _user_options.debounce_attach || 300,
        debounce_suggest: _user_options.debounce_suggest || 200,
        debounce_blur: _user_options.debounce_blur || 150
      };

      var current_element,
          current_model,
          current_options,
          previous_value,
          value_watch,
          last_selected_value;

      $scope.show_autocomplete = false;

      // Debounce - taken from underscore
      function debounce(func, wait, immediate) {
          var timeout;
          return function() {
              var context = this, args = arguments;
              var later = function() {
                  timeout = null;
                  if (!immediate) func.apply(context, args);
              };
              var callNow = immediate && !timeout;
              clearTimeout(timeout);
              timeout = setTimeout(later, wait);
              if (callNow) func.apply(context, args);
          };
      }

      function _position_autocomplete() {
        var rect = current_element[0].getBoundingClientRect(),
            scrollTop = $document[0].body.scrollTop || $document[0].documentElement.scrollTop || $window.pageYOffset,
            scrollLeft = $document[0].body.scrollLeft || $document[0].documentElement.scrollLeft || $window.pageXOffset,
            container = $scope.container[0];

        container.style.top = rect.top + rect.height + scrollTop + 'px';
        container.style.left = rect.left + scrollLeft + 'px';
        container.style.width = rect.width + 'px';
      }
      var position_autocomplete = debounce(_position_autocomplete, user_options.debounce_position);

      // Attach autocomplete behaviour to an input element.
      function _attach(ngmodel, target_element, options) {
        // Element is already attached.
        if (current_element === target_element) return;
        // Safe: clear previously attached elements.
        if (current_element) that.detach();
        // The element is still the active element.
        if (target_element[0] !== $document[0].activeElement) return;

        options.on_attach && options.on_attach();

        current_element = target_element;
        current_model = ngmodel;
        current_options = options;
        previous_value = ngmodel.$viewValue;

        $scope.results = [];
        $scope.selected_index = -1;
        bind_element();

        value_watch = $scope.$watch(
          function () {
            return ngmodel.$modelValue;
          },
          function (nv, ov) {
            // Prevent suggestion cycle when the value is the last value selected.
            // When selecting from the menu the ng-model is updated and this watch
            // is triggered. This causes another suggestion cycle that will provide as
            // suggestion the value that is currently selected - this is unnecessary.
            if (nv === last_selected_value)
              return;

            if ($scope.results)
              $scope.results.length = 0;

            _position_autocomplete();
            suggest(nv);
          }
        );
      };
      that.attach = debounce(_attach, user_options.debounce_attach);

      function _suggest(term) {
        $scope.selected_index = 0;
        $scope.show_autocomplete = false;
        $scope.waiting_for_suggestion = true;

        if (typeof(term) === 'string' && term.length > 0) {
          $q.when(current_options.suggest(term),
            function suggest_succeeded(suggestions) {
              // Add the original term as the first value to enable the user
              // to return to his original expression after suggestions were made.
              if (suggestions && suggestions.length > 0) {
                $scope.results = [{ value: term, label: ''}].concat(suggestions);
                $scope.show_autocomplete = true;
              } else {
                $scope.results = [];
              }
            },
            function suggest_failed(error) {
              current_options.on_error && current_options.on_error(error);
            }
          ).finally(function suggest_finally() {
            $scope.waiting_for_suggestion = false;
          });
        } else {
          $scope.waiting_for_suggestion = false;
          $scope.$apply();
        }
      };
      var suggest = debounce(_suggest, user_options.debounce_suggest);

      // Trigger end of editing and remove all attachments made by
      // this directive to the input element.
      that.detach = function () {
        if (current_element) {
          update_model_value();
          current_options.on_detach && current_options.on_detach(current_element.val());
        }

        // Clear references and events.
        $scope.show_autocomplete = false;
        current_element.unbind(EVENTS.KEYDOWN);
        current_element.unbind(EVENTS.BLUR);
        angular.element($window).unbind(EVENTS.RESIZE);
        value_watch();
        $scope.selected_index = $scope.results = undefined;
        current_model = current_element = previous_value = undefined;
      };

      // Update angular's model view value.
      // It is important that before triggering hooks the model's view
      // value will be synced with the visible value to the user. This will
      // allow the consumer controller to rely on its local ng-model.
      function update_model_value() {
        var val = current_element.val();
        if (current_model.$modelValue !== val) {
          current_model.$setViewValue(val);
          current_model.$render();
        }
        return val;
      }

      // Set the current selection while navigating through the menu.
      function set_selection(i) {
        // We use jquery val instead of setting the model's view value
        // because we watch the model value and setting it will trigger
        // a new suggestion cycle.
        current_element.val($scope.results[i].value);
        $scope.selected_index = i;
      }

      // Apply and accept the current selection made from the menu.
      // When selecting from the menu directly (using click or touch) the
      // selection is directly applied.
      $scope.apply_selection = function (i) {
        current_element[0].focus();
        if (!$scope.show_autocomplete || i > $scope.results.length || i < 0)
          return;

        set_selection(i);
        last_selected_value = update_model_value();
        $scope.show_autocomplete = false;

        current_options.on_select && current_options.on_select($scope.results[$scope.selected_index]);
      };

      function bind_element() {
        angular.element($window).bind(EVENTS.RESIZE, position_autocomplete);

        current_element.bind(EVENTS.BLUR, function () {
          // Detach the element from the auto complete when input loses focus.
          // Focus is lost when a selection is made from the auto complete menu
          // using the mouse (or touch). In that case we don't want to detach so
          // we wait several ms for the input to regain focus.
          if (!$scope.show_autocomplete)
            $timeout(function() {
              if (!current_element || current_element[0] !== $document[0].activeElement)
                that.detach();
            }, user_options.debounce_blur);
        });

        current_element.bind(EVENTS.KEYDOWN, function (e) {
          // Reserve key combinations with shift for different purposes.
          if (e.shiftKey) return;

          switch (e.keyCode) {
            // Close the menu if it's open. Or, undo changes made to the value
            // if the menu is closed.
            case KEYS.ESC:
              if ($scope.show_autocomplete) {
                $scope.show_autocomplete = false;
                $scope.$apply();
              } else {
                current_element.val(previous_value);
              }
              break;

            // Select an element and close the menu. Or, if a selection is
            // unavailable let the event propagate.
            case KEYS.ENTER:
              // Accept a selection only if results exist, the menu is
              // displayed and the results are valid (no current request
              // for new suggestions is active).
              if ($scope.show_autocomplete &&
                  $scope.selected_index > 0 &&
                  !$scope.waiting_for_suggestion) {
                $scope.apply_selection($scope.selected_index);
                // When selecting an item from the AC list the focus is set on
                // the input element. So the enter will cause a keypress event
                // on the input itself. Since this enter is not intended for the
                // input but for the AC result we prevent propagation to parent
                // elements because this event is not of their concern. We cannot
                // prevent events from firing when the event was registered on
                // the input itself.
                e.stopPropagation();
              }

              $scope.show_autocomplete = false;
              $scope.$apply();
              break;

            // Navigate the menu when it's open. When it's not open fall back
            // to default behavior.
            case KEYS.TAB:
              if (!$scope.show_autocomplete)
                break;

              e.preventDefault();
              /* falls through */

            // Open the menu when results exists but are not displayed. Or,
            // select the next element when the menu is open. When reaching
            // bottom wrap to top.
            case KEYS.DOWN:
              if ($scope.results.length > 0) {
                if ($scope.show_autocomplete) {
                  set_selection($scope.selected_index + 1 > $scope.results.length - 1 ? 0 : $scope.selected_index + 1);
                } else {
                  $scope.show_autocomplete = true;
                  $scope.selected_index = 0;
                }
                $scope.$apply();
              }
              break;

            // Navigate up in the menu. When reaching the top wrap to bottom.
            case KEYS.UP:
              if ($scope.show_autocomplete) {
                e.preventDefault();
                set_selection($scope.selected_index - 1 >= 0 ? $scope.selected_index - 1 : $scope.results.length - 1);
                $scope.$apply();
              }
              break;
          }
        });
      }

      $scope.$on('$destroy', function () {
        that.detach();
        $scope.container.remove();
      });
    }]
  };
}])

.directive('massAutocompleteItem', function () {
  'use strict';

  return {
    restrict: "A",
    require: ["^massAutocomplete", "ngModel"],
    scope: false,
    link: function (scope, element, attrs, required) {
      // Prevent html5/browser auto completion.
      attrs.$set('autocomplete', 'off');

      element.bind('focus', function () {
        var options = scope[attrs.massAutocompleteItem];
        if (!options) throw "Invalid options";
        required[0].attach(required[1], element, options);
      });
    }
  };
});
<commit_msg>unbind events only if current_element exists. Resolves #3.<commit_after>angular.module('MassAutoComplete', [])
.directive('massAutocomplete', ["$timeout", "$window", "$document", "$q", function ($timeout, $window, $document, $q) {
  'use strict';

  return {
    restrict: "A",
    scope: { options: '&massAutocomplete' },
    transclude: true,
    template:
      '' +
      '
 0" style="position:absolute;">' +
        '
' +
          '
 0" ' +
            'class="ac-menu-item" ng-class="$index == selected_index ? \'ac-state-focus\': \'\'">' +
            '' +
          '
' +
        '
' +
      '
',
    link: function (scope, element) {
      scope.container = angular.element(element[0].getElementsByClassName('ac-container')[0]);
    },
    controller: ["$scope", function ($scope) {
      var that = this;

      var KEYS = {
        TAB: 9,
        ESC: 27,
        ENTER: 13,
        UP: 38,
        DOWN: 40
      };

      var EVENTS = {
        KEYDOWN: 'keydown',
        RESIZE: 'resize',
        BLUR: 'blur'
      };

      var _user_options = $scope.options() || {};
      var user_options = {
        debounce_position: _user_options.debounce_position || 150,
        debounce_attach: _user_options.debounce_attach || 300,
        debounce_suggest: _user_options.debounce_suggest || 200,
        debounce_blur: _user_options.debounce_blur || 150
      };

      var current_element,
          current_model,
          current_options,
          previous_value,
          value_watch,
          last_selected_value;

      $scope.show_autocomplete = false;

      // Debounce - taken from underscore
      function debounce(func, wait, immediate) {
          var timeout;
          return function() {
              var context = this, args = arguments;
              var later = function() {
                  timeout = null;
                  if (!immediate) func.apply(context, args);
              };
              var callNow = immediate && !timeout;
              clearTimeout(timeout);
              timeout = setTimeout(later, wait);
              if (callNow) func.apply(context, args);
          };
      }

      function _position_autocomplete() {
        var rect = current_element[0].getBoundingClientRect(),
            scrollTop = $document[0].body.scrollTop || $document[0].documentElement.scrollTop || $window.pageYOffset,
            scrollLeft = $document[0].body.scrollLeft || $document[0].documentElement.scrollLeft || $window.pageXOffset,
            container = $scope.container[0];

        container.style.top = rect.top + rect.height + scrollTop + 'px';
        container.style.left = rect.left + scrollLeft + 'px';
        container.style.width = rect.width + 'px';
      }
      var position_autocomplete = debounce(_position_autocomplete, user_options.debounce_position);

      // Attach autocomplete behaviour to an input element.
      function _attach(ngmodel, target_element, options) {
        // Element is already attached.
        if (current_element === target_element) return;
        // Safe: clear previously attached elements.
        if (current_element) that.detach();
        // The element is still the active element.
        if (target_element[0] !== $document[0].activeElement) return;

        options.on_attach && options.on_attach();

        current_element = target_element;
        current_model = ngmodel;
        current_options = options;
        previous_value = ngmodel.$viewValue;

        $scope.results = [];
        $scope.selected_index = -1;
        bind_element();

        value_watch = $scope.$watch(
          function () {
            return ngmodel.$modelValue;
          },
          function (nv, ov) {
            // Prevent suggestion cycle when the value is the last value selected.
            // When selecting from the menu the ng-model is updated and this watch
            // is triggered. This causes another suggestion cycle that will provide as
            // suggestion the value that is currently selected - this is unnecessary.
            if (nv === last_selected_value)
              return;

            if ($scope.results)
              $scope.results.length = 0;

            _position_autocomplete();
            suggest(nv);
          }
        );
      };
      that.attach = debounce(_attach, user_options.debounce_attach);

      function _suggest(term) {
        $scope.selected_index = 0;
        $scope.show_autocomplete = false;
        $scope.waiting_for_suggestion = true;

        if (typeof(term) === 'string' && term.length > 0) {
          $q.when(current_options.suggest(term),
            function suggest_succeeded(suggestions) {
              // Add the original term as the first value to enable the user
              // to return to his original expression after suggestions were made.
              if (suggestions && suggestions.length > 0) {
                $scope.results = [{ value: term, label: ''}].concat(suggestions);
                $scope.show_autocomplete = true;
              } else {
                $scope.results = [];
              }
            },
            function suggest_failed(error) {
              current_options.on_error && current_options.on_error(error);
            }
          ).finally(function suggest_finally() {
            $scope.waiting_for_suggestion = false;
          });
        } else {
          $scope.waiting_for_suggestion = false;
          $scope.$apply();
        }
      };
      var suggest = debounce(_suggest, user_options.debounce_suggest);

      // Trigger end of editing and remove all attachments made by
      // this directive to the input element.
      that.detach = function () {
        if (current_element) {
          update_model_value();
          current_options.on_detach && current_options.on_detach(current_element.val());
          current_element.unbind(EVENTS.KEYDOWN);
          current_element.unbind(EVENTS.BLUR);
        }

        // Clear references and events.
        $scope.show_autocomplete = false;
        angular.element($window).unbind(EVENTS.RESIZE);
        value_watch();
        $scope.selected_index = $scope.results = undefined;
        current_model = current_element = previous_value = undefined;
      };

      // Update angular's model view value.
      // It is important that before triggering hooks the model's view
      // value will be synced with the visible value to the user. This will
      // allow the consumer controller to rely on its local ng-model.
      function update_model_value() {
        var val = current_element.val();
        if (current_model.$modelValue !== val) {
          current_model.$setViewValue(val);
          current_model.$render();
        }
        return val;
      }

      // Set the current selection while navigating through the menu.
      function set_selection(i) {
        // We use jquery val instead of setting the model's view value
        // because we watch the model value and setting it will trigger
        // a new suggestion cycle.
        current_element.val($scope.results[i].value);
        $scope.selected_index = i;
      }

      // Apply and accept the current selection made from the menu.
      // When selecting from the menu directly (using click or touch) the
      // selection is directly applied.
      $scope.apply_selection = function (i) {
        current_element[0].focus();
        if (!$scope.show_autocomplete || i > $scope.results.length || i < 0)
          return;

        set_selection(i);
        last_selected_value = update_model_value();
        $scope.show_autocomplete = false;

        current_options.on_select && current_options.on_select($scope.results[$scope.selected_index]);
      };

      function bind_element() {
        angular.element($window).bind(EVENTS.RESIZE, position_autocomplete);

        current_element.bind(EVENTS.BLUR, function () {
          // Detach the element from the auto complete when input loses focus.
          // Focus is lost when a selection is made from the auto complete menu
          // using the mouse (or touch). In that case we don't want to detach so
          // we wait several ms for the input to regain focus.
          if (!$scope.show_autocomplete)
            $timeout(function() {
              if (!current_element || current_element[0] !== $document[0].activeElement)
                that.detach();
            }, user_options.debounce_blur);
        });

        current_element.bind(EVENTS.KEYDOWN, function (e) {
          // Reserve key combinations with shift for different purposes.
          if (e.shiftKey) return;

          switch (e.keyCode) {
            // Close the menu if it's open. Or, undo changes made to the value
            // if the menu is closed.
            case KEYS.ESC:
              if ($scope.show_autocomplete) {
                $scope.show_autocomplete = false;
                $scope.$apply();
              } else {
                current_element.val(previous_value);
              }
              break;

            // Select an element and close the menu. Or, if a selection is
            // unavailable let the event propagate.
            case KEYS.ENTER:
              // Accept a selection only if results exist, the menu is
              // displayed and the results are valid (no current request
              // for new suggestions is active).
              if ($scope.show_autocomplete &&
                  $scope.selected_index > 0 &&
                  !$scope.waiting_for_suggestion) {
                $scope.apply_selection($scope.selected_index);
                // When selecting an item from the AC list the focus is set on
                // the input element. So the enter will cause a keypress event
                // on the input itself. Since this enter is not intended for the
                // input but for the AC result we prevent propagation to parent
                // elements because this event is not of their concern. We cannot
                // prevent events from firing when the event was registered on
                // the input itself.
                e.stopPropagation();
              }

              $scope.show_autocomplete = false;
              $scope.$apply();
              break;

            // Navigate the menu when it's open. When it's not open fall back
            // to default behavior.
            case KEYS.TAB:
              if (!$scope.show_autocomplete)
                break;

              e.preventDefault();
              /* falls through */

            // Open the menu when results exists but are not displayed. Or,
            // select the next element when the menu is open. When reaching
            // bottom wrap to top.
            case KEYS.DOWN:
              if ($scope.results.length > 0) {
                if ($scope.show_autocomplete) {
                  set_selection($scope.selected_index + 1 > $scope.results.length - 1 ? 0 : $scope.selected_index + 1);
                } else {
                  $scope.show_autocomplete = true;
                  $scope.selected_index = 0;
                }
                $scope.$apply();
              }
              break;

            // Navigate up in the menu. When reaching the top wrap to bottom.
            case KEYS.UP:
              if ($scope.show_autocomplete) {
                e.preventDefault();
                set_selection($scope.selected_index - 1 >= 0 ? $scope.selected_index - 1 : $scope.results.length - 1);
                $scope.$apply();
              }
              break;
          }
        });
      }

      $scope.$on('$destroy', function () {
        that.detach();
        $scope.container.remove();
      });
    }]
  };
}])

.directive('massAutocompleteItem', function () {
  'use strict';

  return {
    restrict: "A",
    require: ["^massAutocomplete", "ngModel"],
    scope: false,
    link: function (scope, element, attrs, required) {
      // Prevent html5/browser auto completion.
      attrs.$set('autocomplete', 'off');

      element.bind('focus', function () {
        var options = scope[attrs.massAutocompleteItem];
        if (!options) throw "Invalid options";
        required[0].attach(required[1], element, options);
      });
    }
  };
});
<|endoftext|>


<commit_before>var
$userimage = $('#userimage .inner'),
$coverimage = $('#coverimage .inner'),
$dragger = $('#dragger'),
$draggerBorder = $('#dragger-border'),
$sizer = $('#size-slider'),
$loading = $('#loading');
$uploading = $('#uploading');
var $originSize = $coverimage.width();
var $exportSize = 500;

function resetUserImage(pos) {
  $userimage
    .css('background-size',pos[0]+'px '+pos[1]+'px')
    .css('background-position',pos[2]+'px '+pos[3]+'px');
}

function changeSizerValue(value) {
  $sizer.slider('value', value)
}

$(window).load(function() {
  var
  container_size = $userimage.width(),
  userimage_size = $util.getImgSize($util.getBackgroundImageUrl($userimage));
  pos = resizeDragger(userimage_size,container_size);
  nonImageLoadState();
  resetUserImage(pos)
});

$(document).ready(function() {
  $("body").iealert({
    support: 'ie9',
    title: '您的瀏覽器太舊啦！',
    text: '請更新您的瀏覽器，我們推薦您使用 Google Chrome',
    closeBtn: false,
    upgradeTitle: '下載 Google Chrome',
    upgradeLink: 'http://www.google.com/chrome/'
  });

  // dragger
  $draggerBorder.css('position', 'absolute').css('z-index', '-100').css('width', '100%').css('height', '100%')
  $dragger.draggable({
    drag: function(event) {
      $userimage.css('background-position',$dragger.css('left')+' '+$dragger.css('top'));
      if($userimage.hasClass('dragged') == false) $userimage.addClass('dragged');
      var value = $('input[name=template]:checked').val();
      // if(value == 9 || value == 10) $userimage.attr('class','inner');
    },
    containment: $draggerBorder
  });

  // size slider
  $sizer.slider({
    value: 100,
    max: 200,
    min: 100,
    slide: function(event, ui) {
      var
      truesize = $util.getBackgroundSize($userimage.css('background-size')),
      position = $util.getBackgroundPosition($userimage.css('background-position')),
      center = $util.getBackgroundCenterPoint(truesize,position);
      $('<img/>').attr('src',$util.getBackgroundImageUrl($userimage))
      .load(function() {
        var
        size = [$originSize, $originSize],
        width = size[0]*(ui.value)/100,
        height = size[1]*(ui.value)/100,
        left = center[0] - width*0.5,
        top = center[1] - height*0.5;

        if(top > 0){
          top = 0
        } else if(top + height < $originSize) {
          top = $originSize - height
        }
        if(left > 0){
          left = 0;
        } else if(left + width < $originSize){
          left = $originSize - width
        }

        $dragger
          .css('width',width+'px').css('height',height+'px')
          .css('top',top+'px').css('left',left+'px');
        $userimage
          .css('background-size',width+'px '+height+'px')
          .css('background-position',left+'px '+top+'px');
        originSize = $coverimage.width()
        // console.log(width, height)
        borderWidth  = width <= originSize ? originSize : originSize + ((width - originSize) * 2)
        borderHeight = height <= originSize ? originSize : originSize + ((height - originSize) * 2)
        // console.log(borderWidth, borderHeight)
        borderLeft = (originSize / 2) - borderWidth*0.5,
        borderTop = (originSize / 2) - borderHeight*0.5;
        $draggerBorder
          .css('width',borderWidth+'px').css('height',borderHeight+'px')
          .css('top',borderTop+'px').css('left',borderLeft+'px');
      });
      if(ui.value == 100) {
        $dragger.draggable( 'disable' )
      } else {
        $dragger.draggable( 'enable' )
      }
    }
  });

  // change template
  $('body').delegate('input[name=template]','change',function(){
    var
    width,
    value = $(this).val(),
    url = 'images/object/'+value+'.png';

    $coverimage.css('background-image','url('+url+')');
    if($userimage.hasClass('dragged') == true) $userimage.attr('class', 'inner dragged');
    else $userimage.attr('class', 'inner');
  });

  $("#normalSubmit").click(function() {
    downloadImage();
  });
});

window.getBase64 = function() {
  var
  basesize = $userimage.width(),
  size = $util.getBackgroundSize($userimage.css('background-size')),
  position = $util.getBackgroundPosition($userimage.css('background-position')),
  scale = basesize/$exportSize;

  var
  template = $('input[name=template]:checked').val(),
  source = $('#source').val(),
  w = size[0]/scale,
  h = size[1]/scale,
  x = position[0]/scale,
  y = position[1]/scale;

  var cover = new Image();
  cover.src = 'images/object/'+template+'.png';

  var userimage = new Image();
  userimage.src = source;

  var resize_canvas = document.getElementById("result");
  resize_canvas.width = $exportSize;
  resize_canvas.height = $exportSize;
  var ctx = resize_canvas.getContext("2d");
  ctx.rect(0,0,$exportSize,$exportSize);
  ctx.fillStyle="#CCCCCC";
  ctx.fill();
  ctx.drawImage(userimage,x,y,w,h);
  ctx.drawImage(cover,0,0,$exportSize,$exportSize);

  return resize_canvas.toDataURL("image/png");
}

function downloadImage(){
  var base64 = getBase64()
  $("#normalSubmit").src('href',base64);
}

//uploader
$(function(){
  var dropZone = document.getElementById('drop');
  dropZone.addEventListener('dragover', handleDragOver, false);
  dropZone.addEventListener('drop', handleFileSelect, false);

  $('.uploadBtn').click(function(){
    $('#uploadInput').click();
  });
  $('#uploadInput').on('change',function(){
    input = document.getElementById('uploadInput');
    if(input.files[0]) {
      loadImage(input.files);
      changeSizerValue(100)
    }
  });
});

// drag image
function handleFileSelect(evt) {
  evt.stopPropagation();
  evt.preventDefault();
  var files = evt.dataTransfer.files;
  loadImage(files);
}
function handleDragOver(evt) {
  evt.stopPropagation();
  evt.preventDefault();
  evt.dataTransfer.dropEffect = 'copy';
}

// function
window.loadImage = function(files) {
  var file, fr, img;
  if (!files) {
    alert('悲劇！您的瀏覽器不支援檔案上傳！')
  } else {
    $uploading.fadeIn();
    $loading.show();
    file = files[0];
    fr = new FileReader();
    fr.onload = createImage;
    fr.readAsDataURL(file);
  }
  function createImage() {
    img = new Image();
    img.onload = imageLoaded;
    img.src = fr.result;
  }
  function imageLoaded() {
    var canvas = document.getElementById("canvas")
    if( this.width > this.height) {
      sx = (this.width - this.height) / 2
      sy = 0
      imgW = this.height
      imgH = this.height
    } else if( this.width < this.height) {
      sx = 0
      sy = (this.height - this.width) / 2
      imgW = this.width
      imgH = this.width
    } else { // width == height
      sx = 0
      sy = 0
      imgW = this.width
      imgH = this.height
    }
    var ctx = canvas.getContext("2d");
    ctx.drawImage(img, sx, sy, imgW, imgH, 0, 0, $exportSize, $exportSize);
    var base64 = canvas.toDataURL("image/png");

    $('#source').attr('value',base64);
    $userimage.css('background-image','url('+base64+')');

    var thumb = document.getElementById("thumb");
    var thumb_w,thumb_h;
    if(img.width > img.height) {
      thumb_h = 100;
      thumb_w = 100*(img.width/img.height);
    }
    else {
      thumb_w = 100;
      thumb_h = 100*(img.height/img.width);
    }
    thumb.width = thumb_w;
    thumb.height = thumb_h;
    var ctx = thumb.getContext("2d");
    ctx.drawImage(img,0,0,thumb_w,thumb_h);
    var thumbbase64 = thumb.toDataURL("image/png");
    $('#templates label').css('background-image','url('+thumbbase64+')');
    $('#normalSubmit').attr('href',base64);

    $('<img/>').attr('src',base64)
    .load(function() {
      var
      value = $('input[name=template]:checked').val(),
      container_size = $userimage.width(),
      userimage_size = [$originSize, $originSize];
      pos = resizeDragger(userimage_size, container_size,value);
      resetUserImage(pos)

      $loading.hide();
      $uploading.fadeOut();
    });
  }
}
function resizeDragger(size,wrapper,value,upload,init)
{
  value = typeof value !== 'undefined' ? value : 1;
  upload = typeof upload !== 'undefined' ? upload : 0;

  var scale, width, height, top, left;
  if(size[0] > size[1]) {
    scale = (wrapper/size[1]);
    width = size[0]*scale;
    height = wrapper;
    top = 0;
    left = (width - wrapper)*0.5*-1;
  }
  else {
    scale = (wrapper/size[0]);
    width = wrapper;
    height = size[1]*scale;
    top = (height - wrapper)*0.5*-1;
    left = 0;
  }

  // if(value == 6){
  //   left = wrapper*0.2*-1;
  //   if(size[0] > size[1]) left -= (width-wrapper)*0.5;
  // }
  // else if(value == 9){
  //   $sizer.slider('value',65);
  //   if(size[0] > size[1]) {
  //     left = wrapper*0.65*0.13*0.5;
  //     width *=0.65;
  //     height *=0.65;
  //     top = (wrapper - height)*0.48;
  //   }
  //   else {
  //     left = wrapper*0.65*0.13*0.5;
  //     width *=0.65;
  //     height *=0.65;
  //     top = (wrapper - height)*0.48;
  //   }
  // }
  // else if(value == 10){
  //   $sizer.slider('value',92);
  //   if(size[0] > size[1]) {
  //     width = wrapper*0.92;
  //     height = width*(size[1]/size[0]);
  //     top = wrapper*0.045;
  //     left = (wrapper-width)*0.5;
  //   }
  //   else {
      // width = width*0.92;
      // height = height*0.92;
      // top = wrapper*0.045;
      // left = (wrapper-width)*0.5;
  //   }
  // }
  $dragger
    .css('width',width+'px').css('height',height+'px')
    .css('top',top+'px').css('left',left+'px');
  // $userimage
  //   .css('background-size',width+'px '+height+'px')
  //   .css('background-position',left+'px '+top+'px');
  return [width, height, left, top]
}

// 沒有圖片上傳時的預設圖片處理 function，目的是讓預設圖片也可以被下載
function nonImageLoadState() {
  var dftImage = new Image();
  dftImage.src = "/images/sample.jpg";
  function drawDftImage(dftImage) {
    var dftcv = document.getElementById("canvas");
    dftcv.width = $exportSize;
    dftcv.height = $exportSize;
    var dftctx = dftcv.getContext("2d");
    dftctx.drawImage(dftImage, 0, 0, dftImage.width, dftImage.height, 0, 0, $exportSize, $exportSize);
    var dftimgbase64 = dftcv.toDataURL("image/png");
    $('#source').attr('value',dftimgbase64);
    value = $originSize+'px '+$originSize+'px'
    $userimage.css('background-image','url('+dftimgbase64+')').
      css('background-size', value)
  }
  drawDftImage(dftImage);
}

window.onresize = function(e) {
  $originSize = $coverimage.width()
  resizeDragger($originSize, $originSize)
  resetUserImage([$originSize, $originSize, 0, 0])
  $draggerBorder
    .css('width', '100%').css('height', '100%')
    .css('top', 'auto').css('left', 'auto')
  changeSizerValue(100)
  $dragger.draggable( 'disable' )
}

// smooth-scroll-link
$('.smooth-scroll-link').smoothScroll();
<commit_msg>fix bug<commit_after>var
$userimage = $('#userimage .inner'),
$coverimage = $('#coverimage .inner'),
$dragger = $('#dragger'),
$draggerBorder = $('#dragger-border'),
$sizer = $('#size-slider'),
$loading = $('#loading');
$uploading = $('#uploading');
var $originSize = $coverimage.width();
var $exportSize = 500;

function resetUserImage(pos) {
  $userimage
    .css('background-size',pos[0]+'px '+pos[1]+'px')
    .css('background-position',pos[2]+'px '+pos[3]+'px');
}

function changeSizerValue(value) {
  $sizer.slider('value', value)
}

$(window).load(function() {
  var
  container_size = $userimage.width(),
  userimage_size = $util.getImgSize($util.getBackgroundImageUrl($userimage));
  pos = resizeDragger(userimage_size,container_size);
  nonImageLoadState();
  resetUserImage(pos)
});

$(document).ready(function() {
  $("body").iealert({
    support: 'ie9',
    title: '您的瀏覽器太舊啦！',
    text: '請更新您的瀏覽器，我們推薦您使用 Google Chrome',
    closeBtn: false,
    upgradeTitle: '下載 Google Chrome',
    upgradeLink: 'http://www.google.com/chrome/'
  });

  // dragger
  $draggerBorder.css('position', 'absolute').css('z-index', '-100').css('width', '100%').css('height', '100%')
  $dragger.draggable({
    drag: function(event) {
      $userimage.css('background-position',$dragger.css('left')+' '+$dragger.css('top'));
      if($userimage.hasClass('dragged') == false) $userimage.addClass('dragged');
      var value = $('input[name=template]:checked').val();
      // if(value == 9 || value == 10) $userimage.attr('class','inner');
    },
    containment: $draggerBorder
  });

  // size slider
  $sizer.slider({
    value: 100,
    max: 200,
    min: 100,
    slide: function(event, ui) {
      var
      truesize = $util.getBackgroundSize($userimage.css('background-size')),
      position = $util.getBackgroundPosition($userimage.css('background-position')),
      center = $util.getBackgroundCenterPoint(truesize,position);
      $('<img/>').attr('src',$util.getBackgroundImageUrl($userimage))
      .load(function() {
        var
        size = [$originSize, $originSize],
        width = size[0]*(ui.value)/100,
        height = size[1]*(ui.value)/100,
        left = center[0] - width*0.5,
        top = center[1] - height*0.5;

        if(top > 0){
          top = 0
        } else if(top + height < $originSize) {
          top = $originSize - height
        }
        if(left > 0){
          left = 0;
        } else if(left + width < $originSize){
          left = $originSize - width
        }

        $dragger
          .css('width',width+'px').css('height',height+'px')
          .css('top',top+'px').css('left',left+'px');
        $userimage
          .css('background-size',width+'px '+height+'px')
          .css('background-position',left+'px '+top+'px');
        originSize = $coverimage.width()
        // console.log(width, height)
        borderWidth  = width <= originSize ? originSize : originSize + ((width - originSize) * 2)
        borderHeight = height <= originSize ? originSize : originSize + ((height - originSize) * 2)
        // console.log(borderWidth, borderHeight)
        borderLeft = (originSize / 2) - borderWidth*0.5,
        borderTop = (originSize / 2) - borderHeight*0.5;
        $draggerBorder
          .css('width',borderWidth+'px').css('height',borderHeight+'px')
          .css('top',borderTop+'px').css('left',borderLeft+'px');
      });
      if(ui.value == 100) {
        $dragger.draggable( 'disable' )
      } else {
        $dragger.draggable( 'enable' )
      }
    }
  });

  // change template
  $('body').delegate('input[name=template]','change',function(){
    var
    width,
    value = $(this).val(),
    url = 'images/object/'+value+'.png';

    $coverimage.css('background-image','url('+url+')');
    if($userimage.hasClass('dragged') == true) $userimage.attr('class', 'inner dragged');
    else $userimage.attr('class', 'inner');
  });

  $("#normalSubmit").click(function() {
    downloadImage();
  });
});

window.getBase64 = function() {
  var
  basesize = $userimage.width(),
  size = $util.getBackgroundSize($userimage.css('background-size')),
  position = $util.getBackgroundPosition($userimage.css('background-position')),
  scale = basesize/$exportSize;

  var
  template = $('input[name=template]:checked').val(),
  source = $('#source').val(),
  w = size[0]/scale,
  h = size[1]/scale,
  x = position[0]/scale,
  y = position[1]/scale;

  var cover = new Image();
  cover.src = 'images/object/'+template+'.png';

  var userimage = new Image();
  userimage.src = source;

  var resize_canvas = document.getElementById("result");
  resize_canvas.width = $exportSize;
  resize_canvas.height = $exportSize;
  var ctx = resize_canvas.getContext("2d");
  ctx.rect(0,0,$exportSize,$exportSize);
  ctx.fillStyle="#CCCCCC";
  ctx.fill();
  ctx.drawImage(userimage,x,y,w,h);
  ctx.drawImage(cover,0,0,$exportSize,$exportSize);

  return resize_canvas.toDataURL("image/png");
}

function downloadImage(){
  var base64 = getBase64()
  $("#normalSubmit").attr('href',base64);
}

//uploader
$(function(){
  var dropZone = document.getElementById('drop');
  dropZone.addEventListener('dragover', handleDragOver, false);
  dropZone.addEventListener('drop', handleFileSelect, false);

  $('.uploadBtn').click(function(){
    $('#uploadInput').click();
  });
  $('#uploadInput').on('change',function(){
    input = document.getElementById('uploadInput');
    if(input.files[0]) {
      loadImage(input.files);
      changeSizerValue(100)
    }
  });
});

// drag image
function handleFileSelect(evt) {
  evt.stopPropagation();
  evt.preventDefault();
  var files = evt.dataTransfer.files;
  loadImage(files);
}
function handleDragOver(evt) {
  evt.stopPropagation();
  evt.preventDefault();
  evt.dataTransfer.dropEffect = 'copy';
}

// function
window.loadImage = function(files) {
  var file, fr, img;
  if (!files) {
    alert('悲劇！您的瀏覽器不支援檔案上傳！')
  } else {
    $uploading.fadeIn();
    $loading.show();
    file = files[0];
    fr = new FileReader();
    fr.onload = createImage;
    fr.readAsDataURL(file);
  }
  function createImage() {
    img = new Image();
    img.onload = imageLoaded;
    img.src = fr.result;
  }
  function imageLoaded() {
    var canvas = document.getElementById("canvas")
    if( this.width > this.height) {
      sx = (this.width - this.height) / 2
      sy = 0
      imgW = this.height
      imgH = this.height
    } else if( this.width < this.height) {
      sx = 0
      sy = (this.height - this.width) / 2
      imgW = this.width
      imgH = this.width
    } else { // width == height
      sx = 0
      sy = 0
      imgW = this.width
      imgH = this.height
    }
    var ctx = canvas.getContext("2d");
    ctx.drawImage(img, sx, sy, imgW, imgH, 0, 0, $exportSize, $exportSize);
    var base64 = canvas.toDataURL("image/png");

    $('#source').attr('value',base64);
    $userimage.css('background-image','url('+base64+')');

    var thumb = document.getElementById("thumb");
    var thumb_w,thumb_h;
    if(img.width > img.height) {
      thumb_h = 100;
      thumb_w = 100*(img.width/img.height);
    }
    else {
      thumb_w = 100;
      thumb_h = 100*(img.height/img.width);
    }
    thumb.width = thumb_w;
    thumb.height = thumb_h;
    var ctx = thumb.getContext("2d");
    ctx.drawImage(img,0,0,thumb_w,thumb_h);
    var thumbbase64 = thumb.toDataURL("image/png");
    $('#templates label').css('background-image','url('+thumbbase64+')');
    $('#normalSubmit').attr('href',base64);

    $('<img/>').attr('src',base64)
    .load(function() {
      var
      value = $('input[name=template]:checked').val(),
      container_size = $userimage.width(),
      userimage_size = [$originSize, $originSize];
      pos = resizeDragger(userimage_size, container_size,value);
      resetUserImage(pos)

      $loading.hide();
      $uploading.fadeOut();
    });
  }
}
function resizeDragger(size,wrapper,value,upload,init)
{
  value = typeof value !== 'undefined' ? value : 1;
  upload = typeof upload !== 'undefined' ? upload : 0;

  var scale, width, height, top, left;
  if(size[0] > size[1]) {
    scale = (wrapper/size[1]);
    width = size[0]*scale;
    height = wrapper;
    top = 0;
    left = (width - wrapper)*0.5*-1;
  }
  else {
    scale = (wrapper/size[0]);
    width = wrapper;
    height = size[1]*scale;
    top = (height - wrapper)*0.5*-1;
    left = 0;
  }

  // if(value == 6){
  //   left = wrapper*0.2*-1;
  //   if(size[0] > size[1]) left -= (width-wrapper)*0.5;
  // }
  // else if(value == 9){
  //   $sizer.slider('value',65);
  //   if(size[0] > size[1]) {
  //     left = wrapper*0.65*0.13*0.5;
  //     width *=0.65;
  //     height *=0.65;
  //     top = (wrapper - height)*0.48;
  //   }
  //   else {
  //     left = wrapper*0.65*0.13*0.5;
  //     width *=0.65;
  //     height *=0.65;
  //     top = (wrapper - height)*0.48;
  //   }
  // }
  // else if(value == 10){
  //   $sizer.slider('value',92);
  //   if(size[0] > size[1]) {
  //     width = wrapper*0.92;
  //     height = width*(size[1]/size[0]);
  //     top = wrapper*0.045;
  //     left = (wrapper-width)*0.5;
  //   }
  //   else {
      // width = width*0.92;
      // height = height*0.92;
      // top = wrapper*0.045;
      // left = (wrapper-width)*0.5;
  //   }
  // }
  $dragger
    .css('width',width+'px').css('height',height+'px')
    .css('top',top+'px').css('left',left+'px');
  // $userimage
  //   .css('background-size',width+'px '+height+'px')
  //   .css('background-position',left+'px '+top+'px');
  return [width, height, left, top]
}

// 沒有圖片上傳時的預設圖片處理 function，目的是讓預設圖片也可以被下載
function nonImageLoadState() {
  var dftImage = new Image();
  dftImage.src = "/images/sample.jpg";
  function drawDftImage(dftImage) {
    var dftcv = document.getElementById("canvas");
    dftcv.width = $exportSize;
    dftcv.height = $exportSize;
    var dftctx = dftcv.getContext("2d");
    dftctx.drawImage(dftImage, 0, 0, dftImage.width, dftImage.height, 0, 0, $exportSize, $exportSize);
    var dftimgbase64 = dftcv.toDataURL("image/png");
    $('#source').attr('value',dftimgbase64);
    value = $originSize+'px '+$originSize+'px'
    $userimage.css('background-image','url('+dftimgbase64+')').
      css('background-size', value)
  }
  drawDftImage(dftImage);
}

window.onresize = function(e) {
  $originSize = $coverimage.width()
  resizeDragger($originSize, $originSize)
  resetUserImage([$originSize, $originSize, 0, 0])
  $draggerBorder
    .css('width', '100%').css('height', '100%')
    .css('top', 'auto').css('left', 'auto')
  changeSizerValue(100)
  $dragger.draggable( 'disable' )
}

// smooth-scroll-link
$('.smooth-scroll-link').smoothScroll();
<|endoftext|>


<commit_before>;(function ($, window, undefined) {
  'use strict';

  var $doc = $(document),
      Modernizr = window.Modernizr;

  $(document).ready(function() {
    $.fn.foundationAlerts           ? $doc.foundationAlerts() : null;
    $.fn.foundationButtons          ? $doc.foundationButtons() : null;
    $.fn.foundationAccordion        ? $doc.foundationAccordion() : null;
    $.fn.foundationNavigation       ? $doc.foundationNavigation() : null;
    $.fn.foundationTopBar           ? $doc.foundationTopBar() : null;
    $.fn.foundationCustomForms      ? $doc.foundationCustomForms() : null;
    $.fn.foundationMediaQueryViewer ? $doc.foundationMediaQueryViewer() : null;
    $.fn.foundationTabs             ? $doc.foundationTabs({callback : $.foundation.customForms.appendCustomMarkup}) : null;
    $.fn.foundationTooltips         ? $doc.foundationTooltips() : null;
    $.fn.foundationMagellan         ? $doc.foundationMagellan() : null;
    $.fn.foundationClearing         ? $doc.foundationClearing() : null;

    $('input, textarea').placeholder();
  });

  // UNCOMMENT THE LINE YOU WANT BELOW IF YOU WANT IE8 SUPPORT AND ARE USING .block-grids
  // $('.block-grid.two-up>li:nth-child(2n+1)').css({clear: 'both'});
  // $('.block-grid.three-up>li:nth-child(3n+1)').css({clear: 'both'});
  // $('.block-grid.four-up>li:nth-child(4n+1)').css({clear: 'both'});
  // $('.block-grid.five-up>li:nth-child(5n+1)').css({clear: 'both'});

  // Hide address bar on mobile devices (except if #hash present, so we don't mess up deep linking).
  if (Modernizr.touch && !window.location.hash) {
    $(window).load(function () {
      setTimeout(function () {
        window.scrollTo(0, 1);
      }, 0);
    });
  }

})(jQuery, this);

$(document).ready(function() {
  $("#install_app").click(function() {
    var request = window.navigator.mozApps.install('http://status.hackerspace.gr/manifest.webapp');
    request.onsuccess = function () {
      // Save the App object that is returned
      var appRecord = this.result;
    };
    request.onerror = function () {
      // Display the error information from the DOMError object
      alert('Install failed, error: ' + this.error.name);
    };
  });
});

//get hackers counter
function get_counter() {
  $.ajax({
    url: 'http://hackerspace.gr/api.php?action=query&prop=revisions&rvprop=content&format=json&titles=Network/Leases',
    dataType: 'jsonp',
    crossDomain: true,
    cache: false
  }).done(function(json) {
    var count = json.query.pages[168].revisions[0]["*"];
    $('#counter').html(count);
    if (count == "0") {
      $('.counter.panel').attr("id","close");
      $('#openornot').html('hackers in space, means that space is now closed!');
    } else {
      $('.counter.panel').attr("id","open");
      $('#openornot').html('hackers in space, means that space is now open!');
    }
  });
};

function get_activity() {
  $.ajax({
    type: 'GET',
    url: 'http://done.hackerspace.gr/api/v1/feed?limit=5',
    dataType: 'jsonp',
    jsonpCallback: 'func',
    success: function(data) {
      $('#activities').empty();
      $.each(data, function(i,v) {
        $('#activities').append('

' + v.content +
          '

' + v.author + ' @ ' +
          $.timeago(v.timestamp) + '

');
      });
    }
  });
};

function get_news() {
  $('#news_wrapper').FeedEk({
    FeedUrl : 'http://hackerspace.gr/wiki/index.php?title=News&action=feed&feed=rss',
    MaxCount : 5,
    ShowDesc : false,
    ShowPubDate:true,
    TitleLinkTarget:'_blank'
  });
};

//Display All future events in ical file as list.
function displayEvents(events,events_current,limit) {
  //Foreach event
  for ( var i=0; i<Math.min(limit,events.length); i++) {
    //Create a list item
    var li = document.createElement('li');
    li.setAttribute('class', 'event');
    //Add details from cal file.
    li.innerHTML = '

' +
    events[i].SUMMARY + '

' + events[i].day + ' ' + events[i].start_day + '/' +
    events[i].start_month + ' ' +events[i].start_time + ' - ' + events[i].end_time + '

';
    //Add list item to list.
    document.getElementById('calendar').appendChild(li);
  }
  for ( var j=0; j<Math.min(limit,events.length); j++) {
    //Create a list item
    var li = document.createElement('li');
    li.setAttribute('class', 'event');
    //Add details from cal file.
    li.innerHTML = '

now
' +
    events_current[j].SUMMARY + '

' + events_current[j].day + ' ' + events_current[j].start_day + '/' +
    events_current[j].start_month + ' ' +events_current[j].start_time + ' - ' + events_current[j].end_time + '

';
    document.getElementById('calendar_current').appendChild(li);
  }
}

var a, b;

function get_events() {
  var ical_url = 'http://hackerspace.gr/archive/hsgr.ics';
  //Create new ical parser
  new ical_parser(ical_url, function(cal) {
    //When ical parser has loaded file
    //get future events
    a = cal.getFutureEvents();
    b = cal.getCurrentEvents();
    //And display them
    displayEvents(a,b,6);
  });
}

$(document).ready(function() {
  $('#loading').toggle();
  get_counter();
  get_events();
  get_activity();
  get_news();
  var refreshId = setInterval(function() {
    get_counter();
  }, 100000);
});
<commit_msg>Only number from count should be taken into consideration.<commit_after>;(function ($, window, undefined) {
  'use strict';

  var $doc = $(document),
      Modernizr = window.Modernizr;

  $(document).ready(function() {
    $.fn.foundationAlerts           ? $doc.foundationAlerts() : null;
    $.fn.foundationButtons          ? $doc.foundationButtons() : null;
    $.fn.foundationAccordion        ? $doc.foundationAccordion() : null;
    $.fn.foundationNavigation       ? $doc.foundationNavigation() : null;
    $.fn.foundationTopBar           ? $doc.foundationTopBar() : null;
    $.fn.foundationCustomForms      ? $doc.foundationCustomForms() : null;
    $.fn.foundationMediaQueryViewer ? $doc.foundationMediaQueryViewer() : null;
    $.fn.foundationTabs             ? $doc.foundationTabs({callback : $.foundation.customForms.appendCustomMarkup}) : null;
    $.fn.foundationTooltips         ? $doc.foundationTooltips() : null;
    $.fn.foundationMagellan         ? $doc.foundationMagellan() : null;
    $.fn.foundationClearing         ? $doc.foundationClearing() : null;

    $('input, textarea').placeholder();
  });

  // UNCOMMENT THE LINE YOU WANT BELOW IF YOU WANT IE8 SUPPORT AND ARE USING .block-grids
  // $('.block-grid.two-up>li:nth-child(2n+1)').css({clear: 'both'});
  // $('.block-grid.three-up>li:nth-child(3n+1)').css({clear: 'both'});
  // $('.block-grid.four-up>li:nth-child(4n+1)').css({clear: 'both'});
  // $('.block-grid.five-up>li:nth-child(5n+1)').css({clear: 'both'});

  // Hide address bar on mobile devices (except if #hash present, so we don't mess up deep linking).
  if (Modernizr.touch && !window.location.hash) {
    $(window).load(function () {
      setTimeout(function () {
        window.scrollTo(0, 1);
      }, 0);
    });
  }

})(jQuery, this);

$(document).ready(function() {
  $("#install_app").click(function() {
    var request = window.navigator.mozApps.install('http://status.hackerspace.gr/manifest.webapp');
    request.onsuccess = function () {
      // Save the App object that is returned
      var appRecord = this.result;
    };
    request.onerror = function () {
      // Display the error information from the DOMError object
      alert('Install failed, error: ' + this.error.name);
    };
  });
});

//get hackers counter
function get_counter() {
  $.ajax({
    url: 'http://hackerspace.gr/api.php?action=query&prop=revisions&rvprop=content&format=json&titles=Network/Leases',
    dataType: 'jsonp',
    crossDomain: true,
    cache: false
  }).done(function(json) {
    var count = json.query.pages[168].revisions[0]["*"];
    var splitted = count.split(" ");
    if ( isNaN(splitted[0]) ) {
      $('.counter.panel').attr("id","close");
      $('#openornot').html('0 hackers in space, means that space is now closed!');
    } else if (splitted[0] == "0") {
      $('#counter').html(splitted[0]);
      $('.counter.panel').attr("id","close");
      $('#openornot').html('hackers in space, means that space is now closed!');
    } else {
      $('#counter').html(splitted[0]);
      $('.counter.panel').attr("id","open");
      $('#openornot').html('hackers in space, means that space is now open!');
    }
  });
};

function get_activity() {
  $.ajax({
    type: 'GET',
    url: 'http://done.hackerspace.gr/api/v1/feed?limit=5',
    dataType: 'jsonp',
    jsonpCallback: 'func',
    success: function(data) {
      $('#activities').empty();
      $.each(data, function(i,v) {
        $('#activities').append('

' + v.content +
          '

' + v.author + ' @ ' +
          $.timeago(v.timestamp) + '

');
      });
    }
  });
};

function get_news() {
  $('#news_wrapper').FeedEk({
    FeedUrl : 'http://hackerspace.gr/wiki/index.php?title=News&action=feed&feed=rss',
    MaxCount : 5,
    ShowDesc : false,
    ShowPubDate:true,
    TitleLinkTarget:'_blank'
  });
};

//Display All future events in ical file as list.
function displayEvents(events,events_current,limit) {
  //Foreach event
  for ( var i=0; i<Math.min(limit,events.length); i++) {
    //Create a list item
    var li = document.createElement('li');
    li.setAttribute('class', 'event');
    //Add details from cal file.
    li.innerHTML = '

' +
    events[i].SUMMARY + '

' + events[i].day + ' ' + events[i].start_day + '/' +
    events[i].start_month + ' ' +events[i].start_time + ' - ' + events[i].end_time + '

';
    //Add list item to list.
    document.getElementById('calendar').appendChild(li);
  }
  for ( var j=0; j<Math.min(limit,events.length); j++) {
    //Create a list item
    var li = document.createElement('li');
    li.setAttribute('class', 'event');
    //Add details from cal file.
    li.innerHTML = '

now
' +
    events_current[j].SUMMARY + '

' + events_current[j].day + ' ' + events_current[j].start_day + '/' +
    events_current[j].start_month + ' ' +events_current[j].start_time + ' - ' + events_current[j].end_time + '

';
    document.getElementById('calendar_current').appendChild(li);
  }
}

var a, b;

function get_events() {
  var ical_url = 'http://hackerspace.gr/archive/hsgr.ics';
  //Create new ical parser
  new ical_parser(ical_url, function(cal) {
    //When ical parser has loaded file
    //get future events
    a = cal.getFutureEvents();
    b = cal.getCurrentEvents();
    //And display them
    displayEvents(a,b,6);
  });
}

$(document).ready(function() {
  $('#loading').toggle();
  get_counter();
  get_events();
  get_activity();
  get_news();
  var refreshId = setInterval(function() {
    get_counter();
  }, 100000);
});
<|endoftext|>


<commit_before>'use strict';

// TEMPORARY MEASURE
var video_id = 0;
var videos = [];

function WorldDynamicContent() {

    this.floating_pictures = [];
    this.entity_walls      = [];
    this.videos            = [];

    this.css_scene_added = false;

    this.dynamic_content_loaded = false;

    this.prepare_for_save = function() {
        // TODO : Eventually default should be false.
        var save_needed = true;

        // For dynamic worlds.
        if (this.hasOwnProperty('world_name_changed')) {
            if (this.world_name_changed) {
                this.entity.set_property(ENTITY_PROPERTY_NAME, this.world_name);
                save_needed = true;
            }
        }

        for (var r = 0; r < this.root_attachables.length; r++) {
            this.root_attachables[r].update_values_for_entity();
        }
    };

    this.load_dynamic_content = function() {

        // Load all the entity walls. These are the base objects that have sub objects to load.
        var base_wall_entities = this.entity.get_children_of_type(ENTITY_TYPE_WALL);
        for (var w = 0 ; w < base_wall_entities.length; w++) {

            // Check the type of object to load based off the immediate child of this wall entity.
            var child_entity = base_wall_entities[w].get_child();

            if (child_entity.get_type() === ENTITY_TYPE_ENTITY_WALL) {
                this.load_entity_wall(child_entity);
            } else if (child_entity.get_type() === ENTITY_TYPE_VIDEO) {
                this.load_video_wall(child_entity);
            }else {
                // TODO :
                l('TODO : COVER LOADING FUNCTIONALITY OF THIS ENTITY CHILD TYPE!!');
            }
        }

        this.dynamic_content_loaded = true;
    };

    /*___      ___   ___
     |__  |\ |  |  |  |  \ /    |  |  /\  |    |
     |___ | \|  |  |  |   |     |/\| /~~\ |___ |___ */
    this.create_new_entity_wall = function(this_context) {
        var entity_wall = new EntityWall(this_context);
        this_context.entity_walls.push(entity_wall);
    };

    // TODO : Eventually change the naming of entity wall entities lol.
    this.load_entity_wall = function(entity_wall_entity) {
        var entity_wall = new EntityWall(this, entity_wall_entity);
        this.entity_walls.push(entity_wall);
    };

    /*       __   ___  __
     \  / | |  \ |__  /  \    |  |  /\  |    |
      \/  | |__/ |___ \__/    |/\| /~~\ |___ |___ */
    this.add_css_scene = function() {
        this.css_scene = new THREE.Scene();
        this.container = document.getElementById('video_one');
        this.container.appendChild(MANAGER_RENDERER.css_renderer.domElement);

        //this.container2 = document.getElementById('video_two');
        //this.container2.appendChild(MANAGER_RENDERER.css_renderer.domElement);
    };

    this.add_video_to_css_group = function(video) {
        video_id += 1;
        videos.push(video);

        if (video_id === 3) {
            this.video_group = new THREE.Group();
            for (var v = 0; v < videos.length; v++) {
                this.video_group.add(videos[v]);
            }
            this.css_scene.add(this.video_group);
        }

        /*
        if (!is_defined(this.video_group)) {
            this.video_group = new THREE.Group();
            l('ADDING VIDEO');
            this.css_scene.add(video);
            //this.video_group.add(video);
            //this.css_scene.add(this.video_group);
        }
        //this.video_group.add(video);
        */
    };

    this.add_video_container = function() {
        if (video_id === 1) {
            var div = document.getElementById('video_one');
            //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
            //MANAGER_RENDERER.css_renderer.domElement.appendChild(div);

            video_id += 1;
        } else if (video_id === 2) {
            var div = document.getElementById('video_two');
            MANAGER_RENDERER.css_renderer.domElement.appendChild(div);
            //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
        }

        //var div = document.createElement('div');
        //div.classList.add('container');
        //document.body.appendChild(div);
        //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
    };

    this.create_new_video = function(this_context) {
        if (!this.css_scene_added) {
            this.add_css_scene();
        }

        var video_wall = new FloatingVideo(this_context);
        this_context.videos.push(video_wall);
    };

    this.load_video_wall = function(video_entity) {
        if (!this.css_scene_added) {
            this.add_css_scene();
        }

        //this.add_video_container();

        var video_wall = new FloatingVideo(this, video_entity);
        this.videos.push(video_wall);
    };

}<commit_msg>video click events 37<commit_after>'use strict';

// TEMPORARY MEASURE
var video_id = 0;
var videos = [];

function WorldDynamicContent() {

    this.floating_pictures = [];
    this.entity_walls      = [];
    this.videos            = [];

    this.css_scene_added = false;

    this.dynamic_content_loaded = false;

    this.prepare_for_save = function() {
        // TODO : Eventually default should be false.
        var save_needed = true;

        // For dynamic worlds.
        if (this.hasOwnProperty('world_name_changed')) {
            if (this.world_name_changed) {
                this.entity.set_property(ENTITY_PROPERTY_NAME, this.world_name);
                save_needed = true;
            }
        }

        for (var r = 0; r < this.root_attachables.length; r++) {
            this.root_attachables[r].update_values_for_entity();
        }
    };

    this.load_dynamic_content = function() {

        // Load all the entity walls. These are the base objects that have sub objects to load.
        var base_wall_entities = this.entity.get_children_of_type(ENTITY_TYPE_WALL);
        for (var w = 0 ; w < base_wall_entities.length; w++) {

            // Check the type of object to load based off the immediate child of this wall entity.
            var child_entity = base_wall_entities[w].get_child();

            if (child_entity.get_type() === ENTITY_TYPE_ENTITY_WALL) {
                this.load_entity_wall(child_entity);
            } else if (child_entity.get_type() === ENTITY_TYPE_VIDEO) {
                this.load_video_wall(child_entity);
            }else {
                // TODO :
                l('TODO : COVER LOADING FUNCTIONALITY OF THIS ENTITY CHILD TYPE!!');
            }
        }

        this.dynamic_content_loaded = true;
    };

    /*___      ___   ___
     |__  |\ |  |  |  |  \ /    |  |  /\  |    |
     |___ | \|  |  |  |   |     |/\| /~~\ |___ |___ */
    this.create_new_entity_wall = function(this_context) {
        var entity_wall = new EntityWall(this_context);
        this_context.entity_walls.push(entity_wall);
    };

    // TODO : Eventually change the naming of entity wall entities lol.
    this.load_entity_wall = function(entity_wall_entity) {
        var entity_wall = new EntityWall(this, entity_wall_entity);
        this.entity_walls.push(entity_wall);
    };

    /*       __   ___  __
     \  / | |  \ |__  /  \    |  |  /\  |    |
      \/  | |__/ |___ \__/    |/\| /~~\ |___ |___ */
    this.add_css_scene = function() {
        this.css_scene = new THREE.Scene();
        this.container = document.getElementById('video_one');
        this.container.appendChild(MANAGER_RENDERER.css_renderer.domElement);

        this.video_group = new THREE.Group();
        this.css_scene.add(this.video_group);

        //this.container2 = document.getElementById('video_two');
        //this.container2.appendChild(MANAGER_RENDERER.css_renderer.domElement);
    };

    this.add_video_to_css_group = function(video) {
        this.video_group.add(video);

        /*
        // THIS CODE WORKS
        video_id += 1;
        videos.push(video);

        if (video_id === 3) {
            this.video_group = new THREE.Group();
            for (var v = 0; v < videos.length; v++) {
                this.video_group.add(videos[v]);
            }
            this.css_scene.add(this.video_group);
        }
        */

    };

    this.add_video_container = function() {
        if (video_id === 1) {
            var div = document.getElementById('video_one');
            //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
            //MANAGER_RENDERER.css_renderer.domElement.appendChild(div);

            video_id += 1;
        } else if (video_id === 2) {
            var div = document.getElementById('video_two');
            MANAGER_RENDERER.css_renderer.domElement.appendChild(div);
            //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
        }

        //var div = document.createElement('div');
        //div.classList.add('container');
        //document.body.appendChild(div);
        //div.appendChild(MANAGER_RENDERER.css_renderer.domElement);
    };

    this.create_new_video = function(this_context) {
        if (!this.css_scene_added) {
            this.add_css_scene();
        }

        var video_wall = new FloatingVideo(this_context);
        this_context.videos.push(video_wall);
    };

    this.load_video_wall = function(video_entity) {
        if (!this.css_scene_added) {
            this.add_css_scene();
        }

        //this.add_video_container();

        var video_wall = new FloatingVideo(this, video_entity);
        this.videos.push(video_wall);
    };

}<|endoftext|>


<commit_before>'use strict';
const BearerToken = require('hapi-auth-bearer-token');
const Blipp = require('blipp');
const H2o2 = require('h2o2');
const Hapi = require('hapi');
const Inert = require('inert');
const Vision = require('vision');

const HapiSwagger = require('../');
const Pack = require('../package');
const Routes = require('./routes');

/**
 * validation function for bearer strategy
 *
 * @param  {Object} token
 * @param  {Function} callback
 */
const validateBearer = function (token, callback) {

    if (token === '12345') {
        callback(null, true, {
            token: token,
            user: {
                username: 'glennjones',
                name: 'Glenn Jones',
                groups: ['admin', 'user']
            }
        });
    } else {
        // for bad token keep err as null
        callback(null, false, {});
    }
};

let server = new Hapi.Server();
server.connection({
    host: 'localhost',
    port: 3000
});

let swaggerOptions = {
    info: {
        'title': 'Test API Documentation',
        'description': 'This is a sample example of API documentation.',
        'version': Pack.version,
        'termsOfService': 'https://github.com/glennjones/hapi-swagger/',
        'contact': {
            'email': 'glennjonesnet@gmail.com'
        },
        'license': {
            'name': 'MIT',
            'url': 'https://raw.githubusercontent.com/glennjones/hapi-swagger/master/license.txt'
        }
    },
    tags: [{
        'name': 'sum',
        'description': 'working with maths',
        'externalDocs': {
            'description': 'Find out more',
            'url': 'http://example.org'
        }
    }, {
        'name': 'store',
        'description': 'storing data',
        'externalDocs': {
            'description': 'Find out more',
            'url': 'http://example.org'
        }
    }]
};

server.register([
    Inert,
    Vision,
    Blipp,
    H2o2,
    BearerToken,
    {
        register: HapiSwagger,
        options: swaggerOptions
    }], (err) => {

        server.auth.strategy('bearer', 'bearer-access-token', {
            'accessTokenName': 'access_token',
            'validateFunc': validateBearer
        });
        server.route(Routes);

        server.start((err) => {
            if (err) {
                console.log(err);
            } else {
                console.log('Server running at:', server.info.uri);
            }
        });
    });

<commit_msg>Updated testserver<commit_after>'use strict';
const BearerToken = require('hapi-auth-bearer-token');
const Blipp = require('blipp');
const H2o2 = require('h2o2');
const Hapi = require('hapi');
const Inert = require('inert');
const Vision = require('vision');

const HapiSwagger = require('../');
const Pack = require('../package');
const Routes = require('./routes');

/**
 * validation function for bearer strategy
 *
 * @param  {Object} token
 * @param  {Function} callback
 */
const validateBearer = function (token, callback) {

    if (token === '12345') {
        callback(null, true, {
            token: token,
            user: {
                username: 'glennjones',
                name: 'Glenn Jones',
                groups: ['admin', 'user']
            }
        });
    } else {
        // for bad token keep err as null
        callback(null, false, {});
    }
};

let server = new Hapi.Server();
server.connection({
    host: 'localhost',
    port: 3000
});

let swaggerOptions = {
    basePath: '/v1/',
    pathPrefixSize: 2,
    info: {
        'title': 'Test API Documentation',
        'description': 'This is a sample example of API documentation.',
        'version': Pack.version,
        'termsOfService': 'https://github.com/glennjones/hapi-swagger/',
        'contact': {
            'email': 'glennjonesnet@gmail.com'
        },
        'license': {
            'name': 'MIT',
            'url': 'https://raw.githubusercontent.com/glennjones/hapi-swagger/master/license.txt'
        }
    },
    tags: [{
        'name': 'sum',
        'description': 'working with maths',
        'externalDocs': {
            'description': 'Find out more',
            'url': 'http://example.org'
        }
    }, {
        'name': 'store',
        'description': 'storing data',
        'externalDocs': {
            'description': 'Find out more',
            'url': 'http://example.org'
        }
    }]
};

server.register([
    Inert,
    Vision,
    Blipp,
    H2o2,
    BearerToken,
    {
        register: HapiSwagger,
        options: swaggerOptions
    }], (err) => {

        server.auth.strategy('bearer', 'bearer-access-token', {
            'accessTokenName': 'access_token',
            'validateFunc': validateBearer
        });
        server.route(Routes);

        server.start((err) => {
            if (err) {
                console.log(err);
            } else {
                console.log('Server running at:', server.info.uri);
            }
        });
    });

<|endoftext|>


<commit_before>// Copyright: All contributers to the Umple Project
// This file is made available subject to the open source license found at:
// http://umple.org/license
//
// Models classes in the graphical view of UmpleOnline

UmpleClassFactory = new Object();
UmpleClassFactory.defaultSize = new UmplePosition(0,0,109,41);
UmpleClassFactory.verticalError = new UmplePosition(0,-1,0,0);

UmpleClassFactory.create = function(data)
{
  var umpleClass = new UmpleClass();
  umpleClass.id = data.id;
  umpleClass.name = data.name;
  umpleClass.position.x = data.position.x;
  umpleClass.position.y = data.position.y;
  umpleClass.position.width = data.position.width;
  umpleClass.position.height = data.position.height;
  umpleClass.extendsClass = data.extendsClass;

  for (var i = 0; i < data.attributes.length; i++)
  {
    umpleClass.attributes.push(UmpleAttributeFactory.create(data.attributes[i]));
  }
  return umpleClass;
}

UmpleClassFactory.perimeterPosition = function(umpleClass, currentPosition, offset)
{
  if (typeof(offset) == "undefined")
  {
    offset = new UmplePosition(0,0,0,0);
  }

  var x = currentPosition.x;
  var y = currentPosition.y;

  var delta = 0;
  var minX = offset.x + umpleClass.position.x + delta;
  var maxX = minX + umpleClass.position.width;

  var minY = offset.y + umpleClass.position.y + delta;
  var maxY = minY + umpleClass.position.height;

  var realX = x < minX  ? minX  : x > maxX  ? maxX : x;
  var realY = y < minY ? minY : y > maxY ? maxY : y;

  var minXDelta = x - minX;
  var maxXDelta = maxX - x;
  var minYDelta = y - minY;
  var maxYDelta = maxY - y;

  var deltaX = Math.min(minXDelta,maxXDelta);
  var deltaY = Math.min(minYDelta,maxYDelta);

  if (deltaX < deltaY)
  {
    realX = minXDelta < maxXDelta ? minX : maxX;
  }
  else if (deltaY < deltaX)
  {
    realY = minYDelta < maxYDelta ? minY : maxY;
  }

  return new UmplePosition(Math.round(realX),Math.round(realY),0,0);
}

function UmpleClass()
{
  this.id;
  this.name;
  this.position = new UmplePosition(0,0,109,41);
  this.attributes = [];
  this.extendsClass;

  this.addAttribute = function(typeAndName)
  {
    var attribute = new UmpleAttribute("","");
    attribute.set(typeAndName);
    this.attributes.push(attribute);
    return this.attributes.length - 1;
  }

  this.removeAttribute = function(index)
  {
    var attribute = this.attributes[index];
    attribute.deleteType = attribute.type;
    attribute.deleteName = attribute.name;
  }

  this.resetAttribute = function(index)
  {
    if (this.attributes[index].deleteName != null)
    {
      this.attributes.splice(index,1);
    }
    else
    {
      this.attributes[index] = this.attributes[index].copy();
    }
  }

  this.setExtendsClass = function(umpleClassId)
  {
  	this.extendsClass = umpleClassId;
  }

  this.removeExtendsClass = function()
  {
  	this.extendsClass = null;
  }

  // Used by triOverlap to enable associations to line up properly
  this.borderLines = function()
  {
  	var classObj = jQuery("#" + this.id);
  	var width = classObj.width();
  	var height = classObj.height();

  	var topLeft = this.position;
  	var topRight = this.position.add(new UmplePosition(width,0,0,0));
  	var bottomLeft = this.position.add(new UmplePosition(0,height,0,0));
  	var bottomRight = this.position.add(new UmplePosition(width,height,0,0));

  	borders = [];
  	borders.push(new UmpleLine(topLeft, topRight));
  	borders.push(new UmpleLine(topLeft, bottomLeft));
  	borders.push(new UmpleLine(bottomLeft, bottomRight));
  	borders.push(new UmpleLine(topRight, bottomRight));

  	return borders;
  }

  this.drawable = function()
  {
    var classDiv = this.drawClass();
	var generalizationDiv = this.drawGeneralization();
	var divs = [classDiv,generalizationDiv];
    return divs;
  }

  this.drawClass = function()
  {
  	var classSel = "#" + this.id;
  	var existingClassDiv = jQuery(classSel).get();

  	if (existingClassDiv == undefined || existingClassDiv == null || existingClassDiv == "")
  	{
  	  classDiv = jQuery("

");
  	  classDiv.addClass("umpleClass");
  	}
  	else
  	{
  	  classDiv = jQuery(existingClassDiv);
  	  removalSel = format("div#{0} .classTable," +
  	   					  "div#{0} .umpleAttribute," +
  	   					  "div#{0} .umpleAttributeNew," +
  	   					  "div#{0} .anchor, " +
  	   					  "div#{0} .hover", this.id);
  	  jQuery(removalSel).remove();
  	}

  	classDiv.attr("id", this.id);

  	var offset = -3.5;
    var bottomOffset = -3;

    var attributesInnerHtml = '';
    var classInnerHtml = '';

    if (this.attributes.length > 0)
    {
      // For each attribute, output the html
      for (var i=0; i<this.attributes.length; i++)
      {
        var attr = this.attributes[i];
        if (Page.isPhotoReady())
        {
          attributesInnerHtml += format('
{0} : {1}
',attr.name,attr.type);
        }
        else
        {
          attributesInnerHtml += format('
{0} : {1}
',attr.name,attr.type,this.id,i,"'");
        }
      }
    } // End of loop adding attributes

    attributesInnerHtml += format('
{1}
',this.id,Page.isPhotoReady() ? ' ' : '-- Add More --');
    if (!Page.isPhotoReady())
    {
// The following commented out to remove unneeded hovers that are not selectable anyway
// Similar code removed from UmpleClass.drawClass
/*
      classInnerHtml +=
      this.anchorDivHtml("anchor",0) +
      this.anchorDivHtml("anchor",1) +
      this.anchorDivHtml("anchor",2) +
      this.anchorDivHtml("anchor",3) +
      this.anchorDivHtml("anchor",4) +
      this.anchorDivHtml("anchor",5) +
      this.anchorDivHtml("anchor",6) +
      this.anchorDivHtml("anchor",7) +

      this.anchorDivHtml("hover",0) +
      this.anchorDivHtml("hover",1) +
      this.anchorDivHtml("hover",2) +
      this.anchorDivHtml("hover",3) +
      this.anchorDivHtml("hover",4) +
      this.anchorDivHtml("hover",5) +
      this.anchorDivHtml("hover",6) +
      this.anchorDivHtml("hover",7);
*/
    }

    classInnerHtml +=
      format(
      '
', this.id) +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.height) +
      '
' +
      '      ';

    if (Page.isPhotoReady())
    {
      classInnerHtml += format('{1}',this.id,this.name);
    }
    else
    {
      classInnerHtml += format('{1}',this.id,this.name);
    }

    classInnerHtml +=
      '    	' +
      '
' +
      format(
      '
' +
      '    {0}' +
      '    	' +
      '
',attributesInnerHtml) +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.width) +
      '
';

    var existing = classDiv.html();
    classDiv.html(classInnerHtml + existing);

	return classDiv;
  }

  this.drawableClassOutline = function()
  {
    var classSel = "#tempClass";
    var classDiv = jQuery(classSel).get();

    if (classDiv == undefined || classDiv == null || classDiv == "")
    {
      classDiv = jQuery("

");
      classDiv.addClass("umpleClass");
      classDiv.attr("id", this.id);
    }
    else
    {
      classDiv = jQuery(classSel);
    }

    var classInnerHtml =
      '
' +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.height) +
      '
' +
      '      ' +
      format(
      '      {1}',this.id,this.name) +
      '    	' +
      '
' +
      '
' +
      '    ' +
      '    	' +
      '
' +
      '
' +
      format(
      '     ' +
      '    	' +
      '
',this.id,this.position.width) +
      '
';

    classDiv.html(classInnerHtml);
    return classDiv;
  }

  this.drawGeneralization = function()
  {
  	var parent = UmpleSystem.find(this.extendsClass);
    if (parent == null)
    {
      return null;
    }

  	var umpleGeneralization = new UmpleGeneralization();
  	umpleGeneralization.childId = this.id;
  	umpleGeneralization.parentId = parent.id;
  	umpleGeneralization.childPosition = this.position;
  	umpleGeneralization.parentPosition = parent.position;

  	generalizationDiv = umpleGeneralization.drawable();

    return generalizationDiv;
  }

  this.anchorDivHtml = function(type,index)
  {
    return format('

',this.id,type,index,type,type,"move");
  }

}<commit_msg>Updating Umpleonline for colour<commit_after>// Copyright: All contributers to the Umple Project
// This file is made available subject to the open source license found at:
// http://umple.org/license
//
// Models classes in the graphical view of UmpleOnline

UmpleClassFactory = new Object();
UmpleClassFactory.defaultSize = new UmplePosition(0,0,109,41);
UmpleClassFactory.verticalError = new UmplePosition(0,-1,0,0);

UmpleClassFactory.create = function(data)
{
  var umpleClass = new UmpleClass();
  umpleClass.id = data.id;
  umpleClass.name = data.name;
  umpleClass.displayColor = data.displayColor;
  umpleClass.position.x = data.position.x;
  umpleClass.position.y = data.position.y;
  umpleClass.position.width = data.position.width;
  umpleClass.position.height = data.position.height;
  umpleClass.extendsClass = data.extendsClass;

  for (var i = 0; i < data.attributes.length; i++)
  {
    umpleClass.attributes.push(UmpleAttributeFactory.create(data.attributes[i]));
  }
  return umpleClass;
}

UmpleClassFactory.perimeterPosition = function(umpleClass, currentPosition, offset)
{
  if (typeof(offset) == "undefined")
  {
    offset = new UmplePosition(0,0,0,0);
  }

  var x = currentPosition.x;
  var y = currentPosition.y;

  var delta = 0;
  var minX = offset.x + umpleClass.position.x + delta;
  var maxX = minX + umpleClass.position.width;

  var minY = offset.y + umpleClass.position.y + delta;
  var maxY = minY + umpleClass.position.height;

  var realX = x < minX  ? minX  : x > maxX  ? maxX : x;
  var realY = y < minY ? minY : y > maxY ? maxY : y;

  var minXDelta = x - minX;
  var maxXDelta = maxX - x;
  var minYDelta = y - minY;
  var maxYDelta = maxY - y;

  var deltaX = Math.min(minXDelta,maxXDelta);
  var deltaY = Math.min(minYDelta,maxYDelta);

  if (deltaX < deltaY)
  {
    realX = minXDelta < maxXDelta ? minX : maxX;
  }
  else if (deltaY < deltaX)
  {
    realY = minYDelta < maxYDelta ? minY : maxY;
  }

  return new UmplePosition(Math.round(realX),Math.round(realY),0,0);
}

function UmpleClass()
{
  this.id;
  this.name;
  this.displayColor = "";
  this.position = new UmplePosition(0,0,109,41);
  this.attributes = [];
  this.extendsClass;

  this.addAttribute = function(typeAndName)
  {
    var attribute = new UmpleAttribute("","");
    attribute.set(typeAndName);
    this.attributes.push(attribute);
    return this.attributes.length - 1;
  }

  this.removeAttribute = function(index)
  {
    var attribute = this.attributes[index];
    attribute.deleteType = attribute.type;
    attribute.deleteName = attribute.name;
  }

  this.resetAttribute = function(index)
  {
    if (this.attributes[index].deleteName != null)
    {
      this.attributes.splice(index,1);
    }
    else
    {
      this.attributes[index] = this.attributes[index].copy();
    }
  }

  this.setExtendsClass = function(umpleClassId)
  {
  	this.extendsClass = umpleClassId;
  }

  this.removeExtendsClass = function()
  {
  	this.extendsClass = null;
  }

  // Used by triOverlap to enable associations to line up properly
  this.borderLines = function()
  {
  	var classObj = jQuery("#" + this.id);
  	var width = classObj.width();
  	var height = classObj.height();

  	var topLeft = this.position;
  	var topRight = this.position.add(new UmplePosition(width,0,0,0));
  	var bottomLeft = this.position.add(new UmplePosition(0,height,0,0));
  	var bottomRight = this.position.add(new UmplePosition(width,height,0,0));

  	borders = [];
  	borders.push(new UmpleLine(topLeft, topRight));
  	borders.push(new UmpleLine(topLeft, bottomLeft));
  	borders.push(new UmpleLine(bottomLeft, bottomRight));
  	borders.push(new UmpleLine(topRight, bottomRight));

  	return borders;
  }

  this.drawable = function()
  {
    var classDiv = this.drawClass();
	var generalizationDiv = this.drawGeneralization();
	var divs = [classDiv,generalizationDiv];
    return divs;
  }

  this.drawClass = function()
  {
  	var classSel = "#" + this.id;
  	var existingClassDiv = jQuery(classSel).get();

  	if (existingClassDiv == undefined || existingClassDiv == null || existingClassDiv == "")
  	{
  	  classDiv = jQuery("

");
  	  classDiv.addClass("umpleClass");
  	}
  	else
  	{
  	  classDiv = jQuery(existingClassDiv);
  	  removalSel = format("div#{0} .classTable," +
  	   					  "div#{0} .umpleAttribute," +
  	   					  "div#{0} .umpleAttributeNew," +
  	   					  "div#{0} .anchor, " +
  	   					  "div#{0} .hover", this.id);
  	  jQuery(removalSel).remove();
  	}

  	classDiv.attr("id", this.id);

  	var offset = -3.5;
    var bottomOffset = -3;

    var attributesInnerHtml = '';
    var classInnerHtml = '';

    if (this.attributes.length > 0)
    {
      // For each attribute, output the html
      for (var i=0; i<this.attributes.length; i++)
      {
        var attr = this.attributes[i];
        if (Page.isPhotoReady())
        {
          attributesInnerHtml += format('
{0} : {1}
',attr.name,attr.type);
        }
        else
        {
          attributesInnerHtml += format('
{0} : {1}
',attr.name,attr.type,this.id,i,"'");
        }
      }
    } // End of loop adding attributes

    attributesInnerHtml += format('
{1}
',this.id,Page.isPhotoReady() ? ' ' : '-- Add More --');
    if (!Page.isPhotoReady())
    {
// The following commented out to remove unneeded hovers that are not selectable anyway
// Similar code removed from UmpleClass.drawClass
/*
      classInnerHtml +=
      this.anchorDivHtml("anchor",0) +
      this.anchorDivHtml("anchor",1) +
      this.anchorDivHtml("anchor",2) +
      this.anchorDivHtml("anchor",3) +
      this.anchorDivHtml("anchor",4) +
      this.anchorDivHtml("anchor",5) +
      this.anchorDivHtml("anchor",6) +
      this.anchorDivHtml("anchor",7) +

      this.anchorDivHtml("hover",0) +
      this.anchorDivHtml("hover",1) +
      this.anchorDivHtml("hover",2) +
      this.anchorDivHtml("hover",3) +
      this.anchorDivHtml("hover",4) +
      this.anchorDivHtml("hover",5) +
      this.anchorDivHtml("hover",6) +
      this.anchorDivHtml("hover",7);
*/
    }

    classInnerHtml +=
      format(
      '
', this.id) +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.height) +
      '
' +
      '      ';

    if (Page.isPhotoReady())
    {
      classInnerHtml += format('{1}',this.id,this.name);
    }
    else
    {
      classInnerHtml += format('{1}',this.id,this.name);
    }

    classInnerHtml +=
      '    	' +
      '
' +
      format(
      '
' +
      '    {0}' +
      '    	' +
      '
',attributesInnerHtml) +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.width) +
      '
';

    var existing = classDiv.html();
    classDiv.html(classInnerHtml + existing);

	return classDiv;
  }

  this.drawableClassOutline = function()
  {
    var classSel = "#tempClass";
    var classDiv = jQuery(classSel).get();

    if (classDiv == undefined || classDiv == null || classDiv == "")
    {
      classDiv = jQuery("

");
      classDiv.addClass("umpleClass");
      classDiv.attr("id", this.id);
    }
    else
    {
      classDiv = jQuery(classSel);
    }

    var classInnerHtml =
      '
' +
      format(
      '
' +
      '     ' +
      '    	' +
      '
',this.id,this.position.height) +
      '
' +
      '      ' +
      format(
      '      {1}',this.id,this.name) +
      '    	' +
      '
' +
      '
' +
      '    ' +
      '    	' +
      '
' +
      '
' +
      format(
      '     ' +
      '    	' +
      '
',this.id,this.position.width) +
      '
';

    classDiv.html(classInnerHtml);
    return classDiv;
  }

  this.drawGeneralization = function()
  {
  	var parent = UmpleSystem.find(this.extendsClass);
    if (parent == null)
    {
      return null;
    }

  	var umpleGeneralization = new UmpleGeneralization();
  	umpleGeneralization.childId = this.id;
  	umpleGeneralization.parentId = parent.id;
  	umpleGeneralization.childPosition = this.position;
  	umpleGeneralization.parentPosition = parent.position;

  	generalizationDiv = umpleGeneralization.drawable();

    return generalizationDiv;
  }

  this.anchorDivHtml = function(type,index)
  {
    return format('

',this.id,type,index,type,type,"move");
  }

}<|endoftext|>


<commit_before>// Underscore-contrib (underscore.function.combinators.js 0.0.1)
// (c) 2013 Michael Fogus, DocumentCloud and Investigative Reporters & Editors
// Underscore-contrib may be freely distributed under the MIT license.

(function(root) {

  // Baseline setup
  // --------------

  // Establish the root object, `window` in the browser, or `global` on the server.
  var _ = root._ || require('underscore');

  // Helpers
  // -------

  var existy = function(x) { return x != null; };
  var truthy = function(x) { return (x !== false) && existy(x); };
  var __reverse = [].reverse;
  var __slice = [].slice;

  // Mixing in the combinator functions
  // ----------------------------------

  _.mixin({
    // Takes a value and returns a function that always returns
    // said value.
    always: function(value) {
      return function() { return value; };
    },

    // Takes some value as its first argument and runs it through a
    // pipeline of functions given as the rest arguments.
    pipeline: function(/*, funs */){
      var funs = arguments;

      return function(seed) {
        return _.reduce(funs,
                        function(l,r) { return r(l); },
                        seed);
      };
    },

    // Composes a bunch of predicates into a single predicate that
    // checks all elements of an array for conformance to all of the
    // original predicates.
    conjoin: function(/* preds */) {
      var preds = arguments;

      return function(array) {
        return _.every(array, function(e) {
          return _.every(preds, function(p) {
            return p(e);
          });
        });
      };
    },

    // Composes a bunch of predicates into a single predicate that
    // checks all elements of an array for conformance to any of the
    // original predicates.
    disjoin: function(/* preds */) {
      var preds = arguments;

      return function(array) {
        return _.some(array, function(e) {
          return _.some(preds, function(p) {
            return p(e);
          });
        });
      };
    },

    // Takes a predicate-like and returns a comparator (-1,0,1).
    comparator: function(fun) {
      return function(x, y) {
        if (truthy(fun(x, y)))
          return -1;
        else if (truthy(fun(y, x)))
          return 1;
        else
          return 0;
      };
    },

    // Returns a function that reverses the sense of a given predicate-like.
    complement: function(pred) {
      return function() {
        return !pred.apply(null, arguments);
      };
    },

    // Takes a function expecting varargs and
    // returns a function that takes an array and
    // uses its elements as the args to  the original
    // function
    splat: function(fun) {
      return function(array) {
        return fun.apply(null, array);
      };
    },

    // Takes a function expecting an array and returns
    // a function that takes varargs and wraps all
    // in an array that is passed to the original function.
    unsplat: function(fun) {
      var funLength = fun.length;

      if (funLength < 1) {
        return fun;
      }
      else if (funLength === 1)  {
        return function () {
          return fun.call(this, __slice.call(arguments, 0));
        };
      }
      else {
        return function () {
          var numberOfArgs = arguments.length,
              namedArgs = __slice.call(arguments, 0, funLength - 1),
              numberOfMissingNamedArgs = Math.max(funLength - numberOfArgs - 1, 0),
              argPadding = new Array(numberOfMissingNamedArgs),
              variadicArgs = __slice.call(arguments, fun.length - 1);

          return fun.apply(this, namedArgs.concat(argPadding).concat([variadicArgs]));
        };
      }
    },

    // Same as unsplat, but the rest of the arguments are collected in the
    // first parameter, e.g. unsplatl( function (args, callback) { ... ]})
    unsplatl: function(fun) {
      var funLength = fun.length;

      if (funLength < 1) {
        return fun;
      }
      else if (funLength === 1)  {
        return function () {
          return fun.call(this, __slice.call(arguments, 0))
        }
      }
      else {
        return function () {
          var numberOfArgs = arguments.length,
              namedArgs = __slice.call(arguments, Math.max(numberOfArgs - funLength + 1, 0)),
              variadicArgs = __slice.call(arguments, 0, Math.max(numberOfArgs - funLength + 1, 0));

          return fun.apply(this, [variadicArgs].concat(namedArgs));
        }
      }
    },

    // Returns a function that returns an array of the calls to each
    // given function for some arguments.
    juxt: function(/* funs */) {
      var funs = arguments;

      return function(/* args */) {
        var args = arguments;
        return _.map(funs, function(f) {
          return f.apply(null, args);
        });
      };
    },

    // Returns a function that protects a given function from receiving
    // non-existy values.  Each subsequent value provided to `fnull` acts
    // as the default to the original function should a call receive non-existy
    // values in the defaulted arg slots.
    fnull: function(fun /*, defaults */) {
      var defaults = _.rest(arguments);

      return function(/*args*/) {
        var args = _.toArray(arguments);
        var sz = _.size(defaults);

        for(var i = 0; i < sz; i++) {
          if (!existy(args[i]))
            args[i] = defaults[i];
        }

        return fun.apply(null, args);
      };
    },

    // Flips the first two args of a function
    flip2: function(fun) {
      return function(/* args */) {
        var tmp = arguments[0];
        arguments[0] = arguments[1];
        arguments[1] = tmp;

        return fun.apply(null, arguments);
      };
    },

    // Flips an arbitrary number of args of a function
    flip: function(fun) {
      return function(/* args */) {
        var reversed = __reverse.call(arguments);

        return fun.apply(null, reversed);
      };
    },

    k: _.always,
    t: _.pipeline
  });

  _.unsplatr = _.unsplat;

})(this);
<commit_msg>Added array support to _.pipeline, closes #29<commit_after>// Underscore-contrib (underscore.function.combinators.js 0.0.1)
// (c) 2013 Michael Fogus, DocumentCloud and Investigative Reporters & Editors
// Underscore-contrib may be freely distributed under the MIT license.

(function(root) {

  // Baseline setup
  // --------------

  // Establish the root object, `window` in the browser, or `global` on the server.
  var _ = root._ || require('underscore');

  // Helpers
  // -------

  var existy = function(x) { return x != null; };
  var truthy = function(x) { return (x !== false) && existy(x); };
  var __reverse = [].reverse;
  var __slice = [].slice;

  // Mixing in the combinator functions
  // ----------------------------------

  _.mixin({
    // Takes a value and returns a function that always returns
    // said value.
    always: function(value) {
      return function() { return value; };
    },

    // Takes some number of functions, either as an array or variadically
    // and returns a function that takes some value as its first argument
    // and runs it through a pipeline of the original functions given.
    pipeline: function(/*, funs */){
      var funs = (_.isArray(arguments[0])) ? arguments[0] : arguments;

      return function(seed) {
        return _.reduce(funs,
                        function(l,r) { return r(l); },
                        seed);
      };
    },

    // Composes a bunch of predicates into a single predicate that
    // checks all elements of an array for conformance to all of the
    // original predicates.
    conjoin: function(/* preds */) {
      var preds = arguments;

      return function(array) {
        return _.every(array, function(e) {
          return _.every(preds, function(p) {
            return p(e);
          });
        });
      };
    },

    // Composes a bunch of predicates into a single predicate that
    // checks all elements of an array for conformance to any of the
    // original predicates.
    disjoin: function(/* preds */) {
      var preds = arguments;

      return function(array) {
        return _.some(array, function(e) {
          return _.some(preds, function(p) {
            return p(e);
          });
        });
      };
    },

    // Takes a predicate-like and returns a comparator (-1,0,1).
    comparator: function(fun) {
      return function(x, y) {
        if (truthy(fun(x, y)))
          return -1;
        else if (truthy(fun(y, x)))
          return 1;
        else
          return 0;
      };
    },

    // Returns a function that reverses the sense of a given predicate-like.
    complement: function(pred) {
      return function() {
        return !pred.apply(null, arguments);
      };
    },

    // Takes a function expecting varargs and
    // returns a function that takes an array and
    // uses its elements as the args to  the original
    // function
    splat: function(fun) {
      return function(array) {
        return fun.apply(null, array);
      };
    },

    // Takes a function expecting an array and returns
    // a function that takes varargs and wraps all
    // in an array that is passed to the original function.
    unsplat: function(fun) {
      var funLength = fun.length;

      if (funLength < 1) {
        return fun;
      }
      else if (funLength === 1)  {
        return function () {
          return fun.call(this, __slice.call(arguments, 0));
        };
      }
      else {
        return function () {
          var numberOfArgs = arguments.length,
              namedArgs = __slice.call(arguments, 0, funLength - 1),
              numberOfMissingNamedArgs = Math.max(funLength - numberOfArgs - 1, 0),
              argPadding = new Array(numberOfMissingNamedArgs),
              variadicArgs = __slice.call(arguments, fun.length - 1);

          return fun.apply(this, namedArgs.concat(argPadding).concat([variadicArgs]));
        };
      }
    },

    // Same as unsplat, but the rest of the arguments are collected in the
    // first parameter, e.g. unsplatl( function (args, callback) { ... ]})
    unsplatl: function(fun) {
      var funLength = fun.length;

      if (funLength < 1) {
        return fun;
      }
      else if (funLength === 1)  {
        return function () {
          return fun.call(this, __slice.call(arguments, 0))
        };
      }
      else {
        return function () {
          var numberOfArgs = arguments.length,
              namedArgs = __slice.call(arguments, Math.max(numberOfArgs - funLength + 1, 0)),
              variadicArgs = __slice.call(arguments, 0, Math.max(numberOfArgs - funLength + 1, 0));

          return fun.apply(this, [variadicArgs].concat(namedArgs));
        };
      }
    },

    // Returns a function that returns an array of the calls to each
    // given function for some arguments.
    juxt: function(/* funs */) {
      var funs = arguments;

      return function(/* args */) {
        var args = arguments;
        return _.map(funs, function(f) {
          return f.apply(null, args);
        });
      };
    },

    // Returns a function that protects a given function from receiving
    // non-existy values.  Each subsequent value provided to `fnull` acts
    // as the default to the original function should a call receive non-existy
    // values in the defaulted arg slots.
    fnull: function(fun /*, defaults */) {
      var defaults = _.rest(arguments);

      return function(/*args*/) {
        var args = _.toArray(arguments);
        var sz = _.size(defaults);

        for(var i = 0; i < sz; i++) {
          if (!existy(args[i]))
            args[i] = defaults[i];
        }

        return fun.apply(null, args);
      };
    },

    // Flips the first two args of a function
    flip2: function(fun) {
      return function(/* args */) {
        var tmp = arguments[0];
        arguments[0] = arguments[1];
        arguments[1] = tmp;

        return fun.apply(null, arguments);
      };
    },

    // Flips an arbitrary number of args of a function
    flip: function(fun) {
      return function(/* args */) {
        var reversed = __reverse.call(arguments);

        return fun.apply(null, reversed);
      };
    },

    k: _.always,
    t: _.pipeline
  });

  _.unsplatr = _.unsplat;

})(this);
<|endoftext|>