/*
       Licensed to the Apache Software Foundation (ASF) under one
       or more contributor license agreements.  See the NOTICE file
       distributed with this work for additional information
       regarding copyright ownership.  The ASF licenses this file
       to you under the Apache License, Version 2.0 (the
       "License"); you may not use this file except in compliance
       with the License.  You may obtain a copy of the License at

         http://www.apache.org/licenses/LICENSE-2.0

       Unless required by applicable law or agreed to in writing,
       software distributed under the License is distributed on an
       "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
       KIND, either express or implied.  See the License for the
       specific language governing permissions and limitations
       under the License.
*/

// define indexOf for IE (code from https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/indexOf)
if (!Array.prototype.indexOf)
{
  Array.prototype.indexOf = function(searchElement /*, fromIndex */)
  {
    "use strict";

    if (this === void 0 || this === null)
      throw new TypeError();

    var t = Object(this);
    var len = t.length >>> 0;
    if (len === 0)
      return -1;

    var n = 0;
    if (arguments.length > 0)
    {
      n = Number(arguments[1]);
      if (n !== n) // shortcut for verifying if it's NaN
        n = 0;
      else if (n !== 0 && n !== (1 / 0) && n !== -(1 / 0))
        n = (n > 0 || -1) * Math.floor(Math.abs(n));
    }

    if (n >= len)
      return -1;

    var k = n >= 0
          ? n
          : Math.max(len - Math.abs(n), 0);

    for (; k < len; k++)
    {
      if (k in t && t[k] === searchElement)
        return k;
    }
    return -1;
  };
}
if($('#commit_graph')){
    // graph size settings
    var x_space = 10;
    var y_space = 20;
    var point_offset = 5;
    var point_size = 10;
    var page_size = 15;

    var data;
    var offset = 1;
    var selected_commit = -1;
    var y_offset = offset * y_space;
    var tree, next_column, max_x_pos, max_row;

    var $graph_holder = $('#graph_holder');
    var $scroll_placeholder = $('#graph_scroll_placeholder');
    var $canvas = $('#commit_graph');
    var $highlighter = $('#commit_highlighter');
    var highlighter = $highlighter[0];
    var canvas = $canvas[0];
    var highlighter_ctx = highlighter.getContext('2d');
    var canvas_ctx = canvas.getContext('2d');

    // graph set up
    var commit_rows = [];
    var taken_coords = {};

    canvas.height = 300;
    highlighter.height = canvas.height;
    highlighter_ctx.fillStyle = "#ccc";

    function setHeight(cnt) {
      /*
       * Set proper canvas height for cnt commits.
       *
       * There is a canvas height limit in all modern browsers (about 8k pixels).
       * So we keep the canvas height small and redraw the canvas on scroll with needed part of commit graph.
       * We need to keep placeholder of the needed height inside $graph_holder to enable default scrollbar.
       */
      graph_height = (cnt + .5) * y_space + 10;
      $scroll_placeholder.height(graph_height);
    }

    $.getJSON(document.location.href+'_data', function(data) {
        data = data;
        tree = data['built_tree'];
        next_column = data['next_column'];
        max_x_pos = x_space*next_column;
        max_row = data['max_row']
        setHeight(max_row);

        // Calculate the (x,y) positions of all the commits
        for(var c in tree){
            var commit = tree[c];
            var x_pos = x_space+(commit.column*x_space);
            var y_pos = y_space+((commit.row)*y_space);
            if (!taken_coords[x_pos]){
                taken_coords[x_pos] = [y_pos]
            }
            else if(taken_coords[x_pos].indexOf(y_pos) == -1){
                taken_coords[x_pos].push(y_pos);
            }
            commit_rows[commit.row] = {
                url: commit.url,
                x_pos: x_pos,
                y_pos: y_pos }
        }
        drawGraph(offset);
        selectCommit(0);
    });

    function selectCommit(index) {
      if (index < 0 || index > max_row) return;
      var commit = commit_rows[index];
      highlighter_ctx.clearRect(0, 0, canvas.width, canvas.height);
      highlighter_ctx.fillRect(
          0, (commit.y_pos - y_offset) - y_space/4,
          750, y_space)
      if (selected_commit != index) {
        $('#commit_view').html('<em>Loading commit details...</em>');
        $.get(commit.url+'basic',function(result){
            $('#commit_view').html(result);
        });
      }
      selected_commit = index;
    }

    $canvas.click(function(evt) {
        var y = Math.floor((evt.pageY-$canvas.offset().top) / y_space);
        selectCommit(offset+y-1);
    });

    function color(index) {
      /* choose color for colorblind users (according to http://jfly.iam.u-tokyo.ac.jp/color/#pallet) */
      switch(index){
        case 0: return "rgb(213,94,0)";
        case 1: return "rgb(0,114,178)";
        case 2: return "rgb(240,228,66)";
        case 3: return "rgb(0,158,115)";
        case 4: return "rgb(230,159,0)";
        default: return "rgb(86,180,223)";
      }
    }

    function drawGraph(offset) {
        // Clear the canvas and set the contetx
        var canvas_ctx = canvas.getContext('2d');
        highlighter_ctx.clearRect(0, 0, canvas.width, canvas.height);
        canvas_ctx.clearRect(0, 0, canvas.width, canvas.height);
        canvas_ctx.fillStyle = "rgb(0,0,0)";
        canvas_ctx.lineWidth = 1;
        canvas_ctx.lineJoin = 'round';
        canvas_ctx.textBaseline = "top";
        canvas_ctx.font = "12px sans-serif";

        for(var c in tree){
            var commit = tree[c];
            var x_pos = x_space+(commit.column*x_space);
            var y_pos = y_space+((commit.row-offset)*y_space);

            for(var i=0,len=commit.parents.length;i<len;i++){
                var parent = tree[commit.parents[i]];
                var parent_x = x_space+parent.column*x_space
                var parent_y = y_space+(parent.row-offset)*y_space;

                canvas_ctx.strokeStyle = color(parent.column % 6);

                // Vertical
                canvas_ctx.beginPath();
                canvas_ctx.moveTo(parent_x+point_offset, y_pos+y_space);
                canvas_ctx.lineTo(parent_x+point_offset, parent_y+point_offset);
                canvas_ctx.stroke();

                // Diagonal
                canvas_ctx.beginPath()
                canvas_ctx.moveTo(x_pos + point_offset, y_pos+point_offset);
                canvas_ctx.lineTo(parent_x+point_offset, y_pos+y_space);
                canvas_ctx.stroke();
            }
        }
        // draw commit points and message text
        canvas_ctx.fillStyle = "rgb(0,0,0)";
        for(var c in tree){
            var commit = tree[c];
            var x_pos = x_space+(commit.column*x_space);
            var y_pos = y_space+((commit.row-offset)*y_space);

            canvas_ctx.strokeStyle = canvas_ctx.fillStyle = color(commit.column % 6);
            canvas_ctx.beginPath();
            canvas_ctx.arc(x_pos + point_offset, y_pos + point_offset, point_offset, 0, 2 * Math.PI, false);
            canvas_ctx.fill();
            canvas_ctx.stroke();
            canvas_ctx.fillStyle = "#000";
            canvas_ctx.fillText(commit.short_id + " " + commit.message, (1+next_column) * x_space, y_pos);
        }
    }

    function setOffset(x) {
      offset = Math.round(x);
      if (offset < 1)
        offset = 1;
      else if (offset > (max_row - page_size))
        offset = max_row - page_size + 2;
      y_offset = offset * y_space;
      drawGraph(offset);
      if (selected_commit >= offset - 1 && selected_commit <= offset + page_size)
        selectCommit(selected_commit);
    }

    $graph_holder.scroll(function() {
      var y = $(this).scrollTop();
      setOffset(y / y_space);
      $canvas.css('top', y);
      $highlighter.css('top', y);
    });
}
