<commit_before>/**
 * Sleep charter, main program
 * Roy Curtis, MIT license, 2017
 */

/*
 * Global state
 */

/**
 * Regex pattern for Google Sheets default date/time format (DD/MM/YYYY HH:mm:ss).
 *
 * Capture groups:
 * 1: DD (day)
 * 2: MM (month)
 * 3: YYYY (year)
 * 4: HH (24 hour)
 * 5: mm (minute)
 * 6: ss (second)
 * @type {RegExp}
 */
var GOOGLE_DATETIME_REGEX =
    /(\d{2}).(\d{2}).(\d{4}) (\d{2}):(\d{2}):(\d{2})/;

var DOM = {
    /** @type HTMLElement */
    sleepChart: null,
    dayBars:    {},
    sleepBars:  []
};

var STATE = {
    entries:    [],
    /** @type HTMLElement */
    selected:   null,
    rescaleIdx: 0,
    rescaling:  false
};

/*
 * Program logic
 */

function main()
{
    DOM.sleepChart = document.querySelector("#sleepChart");

    DOM.sleepChart.onmouseover = function (evt)
    {
        /** @type HTMLElement */
        var selected = evt.target;

        // Do nothing if already hovering over same bar
        if (STATE.selected === selected)
            return;

        // Remove selection class from previously selected bar
        if (STATE.selected !== null)
        {
            STATE.selected.classList.remove("selected");

            if (STATE.selected.pairedBar)
                STATE.selected.pairedBar.classList.remove("selected");

            STATE.selected = null;
        }

        // If started hovering over a(nother) bar
        if ( selected.classList.contains("bar") )
        {
            STATE.selected = selected;
            selected.classList.add("selected");

            if (STATE.selected.pairedBar)
                STATE.selected.pairedBar.classList.add("selected");

            console.log(selected.from, selected.to);
        }
    };

    fetch('sleepData.csv')
        .then(processResponse)
        .then(processData)
        .then(generateDOM)
        .then(finalize)
        .catch(processError);
}

function processResponse(response)
{
    if (!response.ok)
        throw new Error("Response is not OK", response);
    else
        return response.text();
}

function processData(data)
{
    STATE.entries = parseCSV(data);

    // Ensure entries are sorted by earliest from-time to latest from-time
    STATE.entries.sort( function(a, b)
    {
        var from = a[0].getTime(),
            to   = b[0].getTime();

        if      (from > to) return 1;
        else if (from < to) return -1;
        else                return 0;
    });
}

function generateDOM()
{
    for (var i = 0, len = STATE.entries.length; i < len; i++)
    {
        var sleep        = STATE.entries[i],
            from         = sleep[0],
            to           = sleep[1],
            fromDOM      = getDOMForDay(from),
            toDOM        = getDOMForDay(to);

        // Split sleeps that span across days
        if ( from.getDate() !== to.getDate() )
        {
            var bar1  = document.createElement("div"),
                bar2  = document.createElement("div");

            bar1.className = bar2.className = "bar broken";
            bar1.from      = bar2.from      = from;
            bar1.to        = bar2.to        = to;
            bar1.isTopBar  = true;
            bar1.pairedBar = bar2;
            bar2.pairedBar = bar1;

            fromDOM.appendChild(bar1);
            toDOM.appendChild(bar2);
            DOM.sleepBars.push(bar1, bar2);
        }
        else
        {
            // Split day bar into minute segments
            var bar    = document.createElement("div");
            bar.className = "bar";
            bar.from      = from;
            bar.to        = to;

            fromDOM.appendChild(bar);
            DOM.sleepBars.push(bar);
        }
    }
}

function finalize()
{
    console.log(STATE, DOM);
    rescaleSleeps();

    document.body.onresize = function()
    {
        STATE.rescaleIdx = 0;

        if (!STATE.rescaling)
            rescaleSleeps();
    }
}

function processError(error)
{
    console.error(error);
}

/*
 * DOM handling
 */

/**
 * @param {Date} date
 * @returns {HTMLElement}
 */
function getDOMForDay(date)
{
    var year  = date.getFullYear(),
        month = date.getMonth(),
        day   = date.getDate();

    if ( !DOM.dayBars[year] )
    {
        var yearDiv = DOM.dayBars[year] = document.createElement("div");
        yearDiv.className    = "year";
        yearDiv.dataset.year = year;
        yearDiv.innerHTML    = "" + year + "";

        DOM.sleepChart.appendChild(yearDiv);
    }

    if ( !DOM.dayBars[year][month] )
    {
        var monthDiv  = DOM.dayBars[year][month] = document.createElement("div"),
            monthText = date.toLocaleString("en-us", {month: 'long'});
        monthDiv.className     = "month";
        monthDiv.dataset.month = month;
        monthDiv.innerHTML     = "" + monthText + "";

        DOM.dayBars[year].appendChild(monthDiv);
    }

    if ( !DOM.dayBars[year][month][day] )
    {
        var dayBar = DOM.dayBars[year][month][day] = document.createElement("div");
        dayBar.className   = "day";
        dayBar.dataset.day = day;
        dayBar.innerHTML   = "" + day + "";

        DOM.dayBars[year][month].appendChild(dayBar);
    }

    return DOM.dayBars[year][month][day];
}

/**
 * Note: Uses of "| 0" forces calculation into integer (rounded down)
 */
function rescaleSleeps()
{
    if (STATE.rescaleIdx >= DOM.sleepBars.length)
    {
        console.log("Rescale done!");
        STATE.rescaling = false;
        return;
    }
    else
    {
        STATE.rescaling = true;
        requestAnimationFrame(rescaleSleeps);
    }

    if (STATE.rescaleIdx === 0)
        console.log("Beginning rescale...");

    var bar          = DOM.sleepBars[STATE.rescaleIdx],
        from         = bar.from,
        to           = bar.to,
        height       = 0,
        minuteHeight = bar.parentNode.clientHeight / 1440;

    if ( from.getDate() !== to.getDate() )
    {
        if (bar.isTopBar === true)
        {
            height = 1440 - getMinutesOfDay(from);
            bar.style.top    = "0px";
            bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
        }
        else
        {
            height = getMinutesOfDay(to);
            bar.style.bottom = "0px";
            bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
        }
    }
    else
    {
        height = getMinutesOfDay(to) - getMinutesOfDay(from);
        bar.style.bottom = ( (getMinutesOfDay(from) * minuteHeight) | 0 ) + "px";
        bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
    }

    STATE.rescaleIdx++;
}

/*
 * Data parsing
 */

/** @param {string} csv */
function parseCSV(csv)
{
    var lines  = csv.split('\n');

    // Remove CSV header
    lines.shift();
    return lines.map(parseCSVLine);
}

/** @param {string} line */
function parseCSVLine(line)
{
    var ends  = line.split(','),
        begin = parseDate(ends[0]),
        end   = parseDate(ends[1]);

    // Validate date pair
    if (end.getTime() - begin.getTime() <= 0)
        throw new Error("End time is before begin time: " + line);

    return [begin, end];
}

/**
 * Parse Google Sheets default date format (DD/MM/YYYY HH:mm:ss) into Date object
 *
 * @param {string} date
 * @return {Date}
 */
function parseDate(date)
{
    var matches = date.match(GOOGLE_DATETIME_REGEX);

    if (!matches)
        throw new Error("Date/time failed to parse: " + date);
    else if (matches.index !== 0 || matches.length !== 7)
        throw new Error("Date/time parsed incorrectly: " + date);

    return new Date(
        matches[3], matches[2] - 1, matches[1],
        matches[4], matches[5], matches[6]
    );
}

/*
 * Utility
 */

/**
 * @param {Date} date
 */
function getMinutesOfDay(date)
{
    return (date.getHours() * 60) + date.getMinutes();
}

/*
 * Program entry
 */

main();<commit_msg>Implement horizontal scroll wheel<commit_after>/**
 * Sleep charter, main program
 * Roy Curtis, MIT license, 2017
 */

/*
 * Global state
 */

/**
 * Regex pattern for Google Sheets default date/time format (DD/MM/YYYY HH:mm:ss).
 *
 * Capture groups:
 * 1: DD (day)
 * 2: MM (month)
 * 3: YYYY (year)
 * 4: HH (24 hour)
 * 5: mm (minute)
 * 6: ss (second)
 * @type {RegExp}
 */
var GOOGLE_DATETIME_REGEX =
    /(\d{2}).(\d{2}).(\d{4}) (\d{2}):(\d{2}):(\d{2})/;

var DOM = {
    /** @type HTMLElement */
    sleepChart: null,
    dayBars:    {},
    sleepBars:  []
};

var STATE = {
    entries:    [],
    /** @type HTMLElement */
    selected:   null,
    rescaleIdx: 0,
    rescaling:  false
};

/*
 * Program logic
 */

function main()
{
    DOM.sleepChart = document.querySelector("#sleepChart");

    DOM.sleepChart.onmouseover = function (evt)
    {
        /** @type HTMLElement */
        var selected = evt.target;

        // Do nothing if already hovering over same bar
        if (STATE.selected === selected)
            return;

        // Remove selection class from previously selected bar
        if (STATE.selected !== null)
        {
            STATE.selected.classList.remove("selected");

            if (STATE.selected.pairedBar)
                STATE.selected.pairedBar.classList.remove("selected");

            STATE.selected = null;
        }

        // If started hovering over a(nother) bar
        if ( selected.classList.contains("bar") )
        {
            STATE.selected = selected;
            selected.classList.add("selected");

            if (STATE.selected.pairedBar)
                STATE.selected.pairedBar.classList.add("selected");

            console.log(selected.from, selected.to);
        }
    };

    document.onwheel = function(e)
    {
        if (e.ctrlKey || e.shiftKey)
            return;

        window.scrollBy(e.deltaY, 0);
        e.preventDefault();
    };

    fetch('sleepData.csv')
        .then(processResponse)
        .then(processData)
        .then(generateDOM)
        .then(finalize)
        .catch(processError);
}

function processResponse(response)
{
    if (!response.ok)
        throw new Error("Response is not OK", response);
    else
        return response.text();
}

function processData(data)
{
    STATE.entries = parseCSV(data);

    // Ensure entries are sorted by earliest from-time to latest from-time
    STATE.entries.sort( function(a, b)
    {
        var from = a[0].getTime(),
            to   = b[0].getTime();

        if      (from > to) return 1;
        else if (from < to) return -1;
        else                return 0;
    });
}

function generateDOM()
{
    for (var i = 0, len = STATE.entries.length; i < len; i++)
    {
        var sleep        = STATE.entries[i],
            from         = sleep[0],
            to           = sleep[1],
            fromDOM      = getDOMForDay(from),
            toDOM        = getDOMForDay(to);

        // Split sleeps that span across days
        if ( from.getDate() !== to.getDate() )
        {
            var bar1  = document.createElement("div"),
                bar2  = document.createElement("div");

            bar1.className = bar2.className = "bar broken";
            bar1.from      = bar2.from      = from;
            bar1.to        = bar2.to        = to;
            bar1.isTopBar  = true;
            bar1.pairedBar = bar2;
            bar2.pairedBar = bar1;

            fromDOM.appendChild(bar1);
            toDOM.appendChild(bar2);
            DOM.sleepBars.push(bar1, bar2);
        }
        else
        {
            // Split day bar into minute segments
            var bar    = document.createElement("div");
            bar.className = "bar";
            bar.from      = from;
            bar.to        = to;

            fromDOM.appendChild(bar);
            DOM.sleepBars.push(bar);
        }
    }
}

function finalize()
{
    console.log(STATE, DOM);
    rescaleSleeps();

    document.body.onresize = function()
    {
        STATE.rescaleIdx = 0;

        if (!STATE.rescaling)
            rescaleSleeps();
    }
}

function processError(error)
{
    console.error(error);
}

/*
 * DOM handling
 */

/**
 * @param {Date} date
 * @returns {HTMLElement}
 */
function getDOMForDay(date)
{
    var year  = date.getFullYear(),
        month = date.getMonth(),
        day   = date.getDate();

    if ( !DOM.dayBars[year] )
    {
        var yearDiv = DOM.dayBars[year] = document.createElement("div");
        yearDiv.className    = "year";
        yearDiv.dataset.year = year;
        yearDiv.innerHTML    = "" + year + "";

        DOM.sleepChart.appendChild(yearDiv);
    }

    if ( !DOM.dayBars[year][month] )
    {
        var monthDiv  = DOM.dayBars[year][month] = document.createElement("div"),
            monthText = date.toLocaleString("en-us", {month: 'long'});
        monthDiv.className     = "month";
        monthDiv.dataset.month = month;
        monthDiv.innerHTML     = "" + monthText + "";

        DOM.dayBars[year].appendChild(monthDiv);
    }

    if ( !DOM.dayBars[year][month][day] )
    {
        var dayBar = DOM.dayBars[year][month][day] = document.createElement("div");
        dayBar.className   = "day";
        dayBar.dataset.day = day;
        dayBar.innerHTML   = "" + day + "";

        DOM.dayBars[year][month].appendChild(dayBar);
    }

    return DOM.dayBars[year][month][day];
}

/**
 * Note: Uses of "| 0" forces calculation into integer (rounded down)
 */
function rescaleSleeps()
{
    if (STATE.rescaleIdx >= DOM.sleepBars.length)
    {
        console.log("Rescale done!");
        STATE.rescaling = false;
        return;
    }
    else
    {
        STATE.rescaling = true;
        requestAnimationFrame(rescaleSleeps);
    }

    if (STATE.rescaleIdx === 0)
        console.log("Beginning rescale...");

    var bar          = DOM.sleepBars[STATE.rescaleIdx],
        from         = bar.from,
        to           = bar.to,
        height       = 0,
        minuteHeight = bar.parentNode.clientHeight / 1440;

    if ( from.getDate() !== to.getDate() )
    {
        if (bar.isTopBar === true)
        {
            height = 1440 - getMinutesOfDay(from);
            bar.style.top    = "0px";
            bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
        }
        else
        {
            height = getMinutesOfDay(to);
            bar.style.bottom = "0px";
            bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
        }
    }
    else
    {
        height = getMinutesOfDay(to) - getMinutesOfDay(from);
        bar.style.bottom = ( (getMinutesOfDay(from) * minuteHeight) | 0 ) + "px";
        bar.style.height = ( (height * minuteHeight) | 0 ) + "px";
    }

    STATE.rescaleIdx++;
}

/*
 * Data parsing
 */

/** @param {string} csv */
function parseCSV(csv)
{
    var lines  = csv.split('\n');

    // Remove CSV header
    lines.shift();
    return lines.map(parseCSVLine);
}

/** @param {string} line */
function parseCSVLine(line)
{
    var ends  = line.split(','),
        begin = parseDate(ends[0]),
        end   = parseDate(ends[1]);

    // Validate date pair
    if (end.getTime() - begin.getTime() <= 0)
        throw new Error("End time is before begin time: " + line);

    return [begin, end];
}

/**
 * Parse Google Sheets default date format (DD/MM/YYYY HH:mm:ss) into Date object
 *
 * @param {string} date
 * @return {Date}
 */
function parseDate(date)
{
    var matches = date.match(GOOGLE_DATETIME_REGEX);

    if (!matches)
        throw new Error("Date/time failed to parse: " + date);
    else if (matches.index !== 0 || matches.length !== 7)
        throw new Error("Date/time parsed incorrectly: " + date);

    return new Date(
        matches[3], matches[2] - 1, matches[1],
        matches[4], matches[5], matches[6]
    );
}

/*
 * Utility
 */

/**
 * @param {Date} date
 */
function getMinutesOfDay(date)
{
    return (date.getHours() * 60) + date.getMinutes();
}

/*
 * Program entry
 */

main();<|endoftext|>


<commit_before>BUILD_STATE_CLASSES = {
  'Passed': 'build-passed',
  'Building': 'build-building',
  'Failed': 'build-failed'
  }

function buildGroup(group) {
  $( "#pipeline-groups" ).append( pipeline_group_template( { name: group.name } ))

  $.each( group.pipelines, function(i , pipeline) {
    if ( pipeline.instances[0] ) {
      stage_states = _.pluck(pipeline.instances[0].stages, 'status')
      stage_state_classes = stage_states.map(function(a) {return BUILD_STATE_CLASSES[a]});
    }
    pipeline_details = {
      name: pipeline.name,
      link: server + '/go/tab/pipeline/history/' + pipeline.name,
      multistage: stage_state_classes.length > 1,
      paused: pipeline.pause_info.is_paused,
      stage_status_classes: stage_state_classes,
      badge_class: BUILD_STATE_CLASSES[pipeline.instances[0].latest_stage_state] || 'build-none'
    }
    if ( !pipeline.pause_info.is_paused || !config.hide_paused_pipelines ) {
      $( "#pipeline-group-" + group.name ).append( pipeline_badge_template( pipeline_details ))
    }
  });
}

function queryParse(querystring) {
  var result = {};
  (querystring || '').replace(
      new RegExp("([^?=&]+)(=([^&]*))?", "g"),
      function($0, $1, $2, $3) {
          result[$1] = $3 !== undefined ? decodeURIComponent($3) : $3;
      }
  );
  return result;
}

function showError( html ) {
  $( '#error-text' ).append( html + '
');
  $( '#error-panel' ).show();
}

query = queryParse( window.location.search );

server = query.server ? _.trim(query.server, '/' ) : _.trim(config.server, '/' );
url = server + "/go/dashboard.json"

if ( query.pipeline_groups ) {
  pipeline_groups =  _.trim(query.pipeline_groups, '/' )
} else {
  pipeline_groups = config.pipeline_groups ? config.pipeline_groups : null
}

groups = pipeline_groups !== null ? pipeline_groups.split(',') : null

pipeline_group_template = Handlebars.compile( $("#pipeline-group-template").html() );
pipeline_badge_template = Handlebars.compile( $("#pipeline-badge-template").html() );

$.ajax({
  dataType: "json",
  url: url,
  timeout: 10000
}).done(function( data ) {
  if ( groups !== undefined && groups !== null ) {
    $.each( groups, function(i , group) {
      group_object = _.find(data, { 'name': group } )
      if ( typeof group_object !== 'undefined' ) {
        buildGroup( group_object );
      } else {
        showError( "Pipeline group '" + group + "' was not found in the data returned from " + url );
      }
    });
  } else {
    $.each( data, function(i , val) {
      buildGroup(val);
    });
  };
}).fail(function( jqxhr, textStatus, error ) {
  error_html = "Unable to fetch data from " + url
  if ( error ) {
    error_html = error_html + "
Error: " + error
  }
  showError( error_html );
});
<commit_msg>gocd 15.3 compatibility<commit_after>BUILD_STATE_CLASSES = {
  'Passed': 'build-passed',
  'Building': 'build-building',
  'Failed': 'build-failed'
  }

function buildGroup(group) {
  $( "#pipeline-groups" ).append( pipeline_group_template( { name: group.name } ))

  $.each( group._embedded.pipelines, function(i , pipeline) {
    if ( pipeline._embedded.instances[0] ) {
      stage_states = _.pluck(pipeline._embedded.instances[0]._embedded.stages, 'status')
      stage_state_classes = stage_states.map(function(a) {return BUILD_STATE_CLASSES[a]});
    }
    pipeline_details = {
      name: pipeline.name,
      link: server + '/go/tab/pipeline/history/' + pipeline.name,
      multistage: stage_state_classes.length > 1,
      paused: pipeline.pause_info.paused,
      stage_status_classes: stage_state_classes,
      badge_class: BUILD_STATE_CLASSES[pipeline._embedded.instances[0]._embedded.stages[0].status] || 'build-none'
    }
    if ( !pipeline.pause_info.is_paused || !config.hide_paused_pipelines ) {
      $( "#pipeline-group-" + group.name ).append( pipeline_badge_template( pipeline_details ))
    }
  });
}

function queryParse(querystring) {
  var result = {};
  (querystring || '').replace(
      new RegExp("([^?=&]+)(=([^&]*))?", "g"),
      function($0, $1, $2, $3) {
          result[$1] = $3 !== undefined ? decodeURIComponent($3) : $3;
      }
  );
  return result;
}

function showError( html ) {
  $( '#error-text' ).append( html + '
');
  $( '#error-panel' ).show();
}

query = queryParse( window.location.search );

server = query.server ? _.trim(query.server, '/' ) : _.trim(config.server, '/' );
url = server + "/go/api/dashboard"

if ( query.pipeline_groups ) {
  pipeline_groups =  _.trim(query.pipeline_groups, '/' )
} else {
  pipeline_groups = config.pipeline_groups ? config.pipeline_groups : null
}

groups = pipeline_groups !== null ? pipeline_groups.split(',') : null

pipeline_group_template = Handlebars.compile( $("#pipeline-group-template").html() );
pipeline_badge_template = Handlebars.compile( $("#pipeline-badge-template").html() );

$.ajax({
  dataType: "json",
  url: url,
  timeout: 10000,
  headers: {
    Accept : "application/vnd.go.cd.v1+json"
  }
}).done(function( data ) {
  if ( groups !== undefined && groups !== null ) {
    $.each( groups, function(i , group) {
      group_object = _.find(data._embedded.pipeline_groups, { 'name': group } )
      if ( typeof group_object !== 'undefined' ) {
        buildGroup( group_object );
      } else {
        showError( "Pipeline group '" + group + "' was not found in the data returned from " + url );
      }
    });
  } else {
    $.each( data._embedded.pipeline_groups, function(i , val) {
      buildGroup(val);
    });
  };
}).fail(function( jqxhr, textStatus, error ) {
  error_html = "Unable to fetch data from " + url
  if ( error ) {
    error_html = error_html + "
Error: " + error
  }
  showError( error_html );
});
<|endoftext|>


<commit_before>var game = new Phaser.Game(400,450, Phaser.AUTO, 'gameDiv')
var timer = 60
var cursors
var right = true
var counter=0
var swipeLeft=false,swipeRight=false, isGameRunning=true
var timerText=null
var swipeCoordX, swipeCoordY, swipeCoordX2, swipeCoordY2, swipeMinDistance = 100
var isJumped = false, touchingGround = true
var flipper=true
var lastRect

//collisions for P2 Physics
var monkeyCollisionGroup
var ropeCollisionGroup
var groundCollisionGroup

var mainState = {
    preload: function() {
         this.game.load.image('tree', 'assets/tree.png')
         this.game.stage.backgroundColor = "#ffffff"
         this.game.load.spritesheet('monkey','assets/jumpy.png',82,108)
         this.game.load.image('sky','assets/sky.png')
         this.game.load.image('platform','assets/platform.png')
         this.game.load.image('sky','assets/sky.png')
         this.game.load.spritesheet('chain', 'assets/chain.png', 16, 26)
         this.game.load.spritesheet('chain', 'assets/btn.png', 193, 71)
         this.game.load.spritesheet('chain', 'assets/chain.png', 16, 26);
    },

    create: function() {
        //makes phaser state go Full Screen
        fullScreenMode()

        //initialization of global variables
        isGameRunning = true
        right = true
        timer = 60
        isJumped = false
        touchingGround = true

        //start the system
        this.game.physics.startSystem(Phaser.Physics.P2JS)

        this.game.physics.p2.setImpactEvents(true)
        this.game.physics.p2.restitution = 0.8
        this.game.physics.p2.gravity.y = 12000

        //collisions for P2 Physics
        monkeyCollisionGroup = game.physics.p2.createCollisionGroup()
        ropeCollisionGroup = game.physics.p2.createCollisionGroup()
        groundCollisionGroup = game.physics.p2.createCollisionGroup()

        //add preloaded sprites to the game
        this.sky = this.game.add.sprite(0,0,"sky")
        this.tree = this.game.add.sprite(0,0,"tree")
        this.ground = this.game.add.sprite(0,1200,'platform')
        this.monkey = this.game.add.sprite(400,1000,'monkey')

        //apply physics on the objects
        this.game.physics.p2.enable(this.monkey)
        this.game.physics.p2.enable(this.ground)
        this.monkey.body.fixedRotation = true
        this.monkey.body.setRectangle(40, 40)

        //timer ticks interval 1s per tick
        interval=setInterval(function(){timer -= 1},1000)

        //create animations
        this.monkey.animations.add('game',[3, 0, 1, 2], 5, true)

        //start animation
        this.monkey.animations.play('game')

         //scales and anchors
        this.monkey.anchor.setTo(.5, .5)
        this.monkey.scale.setTo(.8, .8)
        this.sky.scale.setTo(2, 2)
        this.ground.scale.setTo(4, 1.8)
        this.ground.body.setRectangle(2000,100)

        this.monkey.body.gravity.y = 1300
        this.ground.body.gravity.y = 0
        this.ground.body.immovable = true
        this.ground.body.static = true

        //update world bounds with the new constraints
        //this.game.physics.p2.updateBoundsCollisionGroup()
        //this.monkey.body.setCollisionGroup(monkeyCollisionGroup)
        //this.ground.body.setCollisionGroup(groundCollisionGroup)
        //this.monkey.body.collides([groundCollisionGroup,ropeCollisionGroup])

        // stop falling from the world's bound
        this.monkey.body.collideWorldBounds = true
        this.ground.body.collideWorldBounds = true

        //camera bounds and activate follow
        this.game.world.setBounds(0, 0, 900, 1200)
        game.camera.follow(this.monkey)

        //keyboard inputs
        cursors = this.game.input.keyboard.createCursorKeys()

        //swipe co-ordinates
        this.game.input.onDown.add(function(pointer) {
            swipeCoordX = pointer.clientX
            swipeCoordY = pointer.clientY
        }, this)

        this.game.input.onUp.add(function(pointer) {
            swipeCoordX2 = pointer.clientX
            swipeCoordY2 = pointer.clientY
            if(swipeCoordX2 < swipeCoordX - swipeMinDistance){
                //console.log("left")
                swipeLeft=true
            }
            else if(swipeCoordX2 > swipeCoordX + swipeMinDistance){
                //console.log("right")
                swipeRight=true
            }
        }, this)

    //  Length, xAnchor, yAnchor
    createRope(5, 280, 885)
    lastRect = null
    createRope(5, 572, 744)
    lastRect = null
    createRope(5,539,590)
    lastRect=null
    createRope(5,232,690)
    lastRect=null
    createRope(5,314,525)
    lastRect=null
    createRope(5,466,395)
    lastRect=null
    createRope(5,293,170)
    lastRect=null
    createRope(5,500,250)
    lastRect=null

     },
     update: function() {

        if(isGameRunning){
            //detect monkey and ground collision
            //game.physics.arcade.collide(this.monkey, this.ground)

            //console.log(this.monkey.body.touching.down)
            //if(timer<=0 || (isJumped && this.monkey.body.touching.down) ){
            if(timer<=0 || (isJumped && touchingGround) ){
                //Game Over
                console.log("game over")
                isGameRunning = false

                this.game.add.tween(this.monkey).to({angle: right? -90:90}, 100).start()
                gameOverText = game.add.text(
                    game.world.width / 2,
                    game.world.height / 2,
                    "Game Over",
                    {
                        font: '32px Comic Sans MS',
                        fill: '#fff',
                        stroke: '#430',
                        strokeThickness: 4,
                        align: 'center'
                    }
                )
                gameOverText.fixedToCamera = true
                gameOverText.cameraOffset.setTo(100, 200)

                this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this, 1, 1, 1)
                this.button.anchor.setTo(.5,-1)
                this.button.scale.setTo(.6,.6)
                this.button.onInputUp.add(this.up, this)
                this.button.fixedToCamera = true
                this.button.cameraOffset.setTo(180,240)
                clearInterval(interval)

            }

            if(timerText!=null)timerText.destroy()
                  timerText = game.add.text(
                        10,
                        10,
                        "Time: "+timer+"s",
                        {
                            font: '24px Comic Sans MS',
                            fill: '#fff',
                            stroke: '#000',
                            strokeThickness: 2,
                            align: 'center'
                        })
            timerText.fixedToCamera = true
            timerText.cameraOffset.setTo(10, 10)

            counter++

            //commented for testing purpose, it will allow the monkey to jump infinitely
            //if (cursors.up.isDown && this.monkey.body.touching.down){
            this.monkey.body.setZeroVelocity()
            if (swipeLeft || swipeRight || cursors.up.isDown ){
                //console.log("up")
                isJumped = true
                touchingGround = false
                this.monkey.body.moveUp(700)
                this.monkey.body.thrust(500)
                this.monkey.frame = 1
            }
            if (swipeLeft || cursors.left.isDown){
                //console.log("left")
                this.monkey.body.moveLeft(700)
                this.monkey.animations.play('game')
                if(right) {right =  false
                this.monkey.scale.x*=-1
                }
            }
            else if (swipeRight || cursors.right.isDown){
                //console.log("right")
                this.monkey.body.moveRight(700)
                if(!right) {
                    right =  true
                    this.monkey.scale.x *= -1
                }

                this.monkey.animations.play('game')
            }
            else{
                this.monkey.animations.stop()
                this.monkey.frame = 5
            }

            if(counter>20){
                counter=0
                swipeLeft=swipeRight=false
            }
            if((300<=this.monkey.body.x && this.monkey.body.x<450) && (50<=this.monkey.body.y && this.monkey.body.y <=130)){
                //console.log("Home Win!")
                isGameRunning=false
                this.monkey.destroy()
                gameOverText = game.add.text(
                    game.world.width / 2,
                    game.world.height / 2,
                    "Level Complete",
                    {
                        font: '32px Comic Sans MS',
                        fill: '#fff',
                        stroke: '#430',
                        strokeThickness: 4,
                        align: 'center'
                    }
                )
                gameOverText.fixedToCamera = true
                gameOverText.cameraOffset.setTo(60, 200)

                this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this)
                this.button.anchor.setTo(.5,-1)
                this.button.scale.setTo(.6,.6)
                this.button.onInputUp.add(this.up, this)
                this.button.fixedToCamera = true
                this.button.cameraOffset.setTo(180,240)
                clearInterval(interval)

            }
        }
        else{

        }

    },
    render: function() {

    //game.debug.cameraInfo(game.camera, 32, 32)
    game.debug.spriteCoords(this.monkey, 0, 32)
   },
    up: function() {
        //start main state
        this.game.state.add('main', mainState)
        this.game.state.start('main')

    },
     actionOnClick: function(){

    },
    tick: function(){
        timer-=1
    }

}

var button
var background

var welcomeScreenState = {
    preload: function() {
    this.game.load.spritesheet('button', 'assets/btn.png', 193, 71)
    this.game.load.image('background','assets/screen.png')
    },

    create: function() {
        fullScreenMode()
        this.game.stage.backgroundColor = '#182d3b'
        this.background = this.game.add.tileSprite(0, 0, 900, 1200, 'background')

        this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this, 2, 1, 0)
        this.button.anchor.setTo(.5,-1)
        this.button.scale.setTo(.5,.5)
        //this.button.onInputOver.add(this.over, this)
        //this.button.onInputOut.add(this.out, this)
        this.button.onInputUp.add(this.up, this)
    },

    up: function() {
        //start main state
        this.game.state.add('main', mainState)
        this.game.state.start('main')

    },
     actionOnClick: function(){
    },
}

game.state.add('welcomeScreen',welcomeScreenState)
game.state.start('welcomeScreen')

function createRope(length, xAnchor, yAnchor) {

    var height = 20;        //  Height for the physics body - your image height is 8px
    var width = 16;         //  This is the width for the physics body. If too small the rectangles will get scrambled together.
    var maxForce = 20000;   //  The force that holds the rectangles together.

    for (var i = 0; i <= length; i++)
    {
        var x = xAnchor;                    //  All rects are on the same x position
        var y = yAnchor + (i * height);     //  Every new rect is positioned below the last

        if (i % 2 === 0)
        {
            //  Add sprite (and switch frame every 2nd time)
            newRect = game.add.sprite(x, y, 'chain', 1)

        }
        else
        {
            newRect = game.add.sprite(x, y, 'chain', 1);
            lastRect.bringToTop();
        }

        //  Enable physicsbody
        game.physics.p2.enable(newRect, false);

        //  Set custom rectangle
        //newRect.body.setCollisionGroup(this.ropeCollisionGroup)
        newRect.body.setRectangle(width, height)

        if (i === 0)
        {
            newRect.body.static = true;
        }
        else
        {
            //  Anchor the first one created
            newRect.body.velocity.x = 400;      //  Give it a push :) just for fun

            newRect.body.mass = length / i;     //  Reduce mass for evey rope element
        }

        //  After the first rectangle is created we can add the constraint
        if (lastRect)
        {
            game.physics.p2.createRevoluteConstraint(newRect, [0, -10], lastRect, [0, 10], maxForce);
        }

        lastRect = newRect;

    }

}

function fullScreenMode(){
    //make the GAME full screen
        this.game.scale.fullScreenScaleMode = Phaser.ScaleManager.SHOW_ALL
        this.game.scale.scaleMode = Phaser.ScaleManager.SHOW_ALL
        this.game.scale.refresh()
}

function isGrounded(){

        touchingGround = true

}<commit_msg>Successfully detected monkey ground collision :v:<commit_after>var game = new Phaser.Game(400,450, Phaser.AUTO, 'gameDiv')
var timer = 60
var cursors
var right = true
var counter=0
var swipeLeft=false,swipeRight=false, isGameRunning=true
var timerText=null
var swipeCoordX, swipeCoordY, swipeCoordX2, swipeCoordY2, swipeMinDistance = 100
var isJumped = false, touchingGround = true
var flipper=true
var lastRect

//collisions for P2 Physics
var monkeyCollisionGroup
var ropeCollisionGroup
var groundCollisionGroup

var mainState = {
    preload: function() {
         this.game.load.image('tree', 'assets/tree.png')
         this.game.stage.backgroundColor = "#ffffff"
         this.game.load.spritesheet('monkey','assets/jumpy.png',82,108)
         this.game.load.image('sky','assets/sky.png')
         this.game.load.image('platform','assets/platform.png')
         this.game.load.image('sky','assets/sky.png')
         this.game.load.spritesheet('chain', 'assets/chain.png', 16, 26)
         this.game.load.spritesheet('chain', 'assets/btn.png', 193, 71)
         this.game.load.spritesheet('chain', 'assets/chain.png', 16, 26)
    },

    create: function() {
        //makes phaser state go Full Screen
        fullScreenMode()

        //initialization of global variables
        isGameRunning = true
        right = true
        timer = 60
        isJumped = false
        touchingGround = true

        //start the system
        this.game.physics.startSystem(Phaser.Physics.P2JS)

        this.game.physics.p2.setImpactEvents(true)
        this.game.physics.p2.restitution = 0.8
        this.game.physics.p2.gravity.y = 12000

        //collisions for P2 Physics
        monkeyCollisionGroup = game.physics.p2.createCollisionGroup()
        ropeCollisionGroup = game.physics.p2.createCollisionGroup()
        groundCollisionGroup = game.physics.p2.createCollisionGroup()

        //add preloaded sprites to the game
        this.sky = this.game.add.sprite(0,0,"sky")
        this.tree = this.game.add.sprite(0,0,"tree")
        this.ground = this.game.add.sprite(0,1200,'platform')
        this.monkey = this.game.add.sprite(400,1000,'monkey')

        //apply physics on the objects
        this.game.physics.p2.enable(this.monkey)
        this.game.physics.p2.enable(this.ground)
        this.monkey.body.fixedRotation = true
        this.monkey.body.setRectangle(40, 40)

        //timer ticks interval 1s per tick
        interval=setInterval(function(){timer -= 1},1000)

        //create animations
        this.monkey.animations.add('game',[3, 0, 1, 2], 5, true)

        //start animation
        this.monkey.animations.play('game')

         //scales and anchors
        this.monkey.anchor.setTo(.5, .5)
        this.monkey.scale.setTo(.8, .8)
        this.sky.scale.setTo(2, 2)
        this.ground.scale.setTo(4, 1.8)
        this.ground.body.setRectangle(2000,100)

        this.monkey.body.gravity.y = 1300
        this.ground.body.gravity.y = 0
        this.ground.body.immovable = true
        this.ground.body.static = true

        //update world bounds with the new constraints
        //this.game.physics.p2.updateBoundsCollisionGroup()
        //this.monkey.body.setCollisionGroup(monkeyCollisionGroup)
        //this.ground.body.setCollisionGroup(groundCollisionGroup)
        //this.monkey.body.collides([groundCollisionGroup,ropeCollisionGroup])

        // stop falling from the world's bound
        this.monkey.body.collideWorldBounds = true
        this.ground.body.collideWorldBounds = true
        this.ground.body.onBeginContact.add(isGrounded, this)

        //camera bounds and activate follow
        this.game.world.setBounds(0, 0, 900, 1200)
        game.camera.follow(this.monkey)

        //keyboard inputs
        cursors = this.game.input.keyboard.createCursorKeys()

        //swipe co-ordinates
        this.game.input.onDown.add(function(pointer) {
            swipeCoordX = pointer.clientX
            swipeCoordY = pointer.clientY
        }, this)

        this.game.input.onUp.add(function(pointer) {
            swipeCoordX2 = pointer.clientX
            swipeCoordY2 = pointer.clientY
            if(swipeCoordX2 < swipeCoordX - swipeMinDistance){
                //console.log("left")
                swipeLeft=true
            }
            else if(swipeCoordX2 > swipeCoordX + swipeMinDistance){
                //console.log("right")
                swipeRight=true
            }
        }, this)

    //  Length, xAnchor, yAnchor
    createRope(5, 280, 885)
    lastRect = null
    createRope(5, 572, 744)
    lastRect = null
    createRope(5,539,590)
    lastRect=null
    createRope(5,232,690)
    lastRect=null
    createRope(5,314,525)
    lastRect=null
    createRope(5,466,395)
    lastRect=null
    createRope(5,293,170)
    lastRect=null
    createRope(5,500,250)
    lastRect=null

     },
     update: function() {

        if(isGameRunning){
            //detect monkey and ground collision
            //game.physics.arcade.collide(this.monkey, this.ground)

            //console.log(this.monkey.body.touching.down)
            //if(timer<=0 || (isJumped && this.monkey.body.touching.down) ){
            if(timer<=0 || (isJumped && touchingGround) ){
                //Game Over
                console.log("game over")
                isGameRunning = false

                this.game.add.tween(this.monkey).to({angle: right? -90:90}, 100).start()
                gameOverText = game.add.text(
                    game.world.width / 2,
                    game.world.height / 2,
                    "Game Over",
                    {
                        font: '32px Comic Sans MS',
                        fill: '#fff',
                        stroke: '#430',
                        strokeThickness: 4,
                        align: 'center'
                    }
                )
                gameOverText.fixedToCamera = true
                gameOverText.cameraOffset.setTo(100, 200)

                this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this, 1, 1, 1)
                this.button.anchor.setTo(.5,-1)
                this.button.scale.setTo(.6,.6)
                this.button.onInputUp.add(this.up, this)
                this.button.fixedToCamera = true
                this.button.cameraOffset.setTo(180,240)
                clearInterval(interval)

            }

            if(timerText!=null)timerText.destroy()
                  timerText = game.add.text(
                        10,
                        10,
                        "Time: "+timer+"s",
                        {
                            font: '24px Comic Sans MS',
                            fill: '#fff',
                            stroke: '#000',
                            strokeThickness: 2,
                            align: 'center'
                        })
            timerText.fixedToCamera = true
            timerText.cameraOffset.setTo(10, 10)

            counter++

            //commented for testing purpose, it will allow the monkey to jump infinitely
            //if (cursors.up.isDown && this.monkey.body.touching.down){
            this.monkey.body.setZeroVelocity()
            if (swipeLeft || swipeRight || cursors.up.isDown ){
                //console.log("up")
                isJumped = true
                touchingGround = false
                this.monkey.body.moveUp(700)
                this.monkey.body.thrust(500)
                this.monkey.frame = 1
            }
            if (swipeLeft || cursors.left.isDown){
                //console.log("left")
                this.monkey.body.moveLeft(700)
                this.monkey.animations.play('game')
                if(right) {right =  false
                this.monkey.scale.x*=-1
                }
            }
            else if (swipeRight || cursors.right.isDown){
                //console.log("right")
                this.monkey.body.moveRight(700)
                if(!right) {
                    right =  true
                    this.monkey.scale.x *= -1
                }

                this.monkey.animations.play('game')
            }
            else{
                this.monkey.animations.stop()
                this.monkey.frame = 5
            }

            if(counter>20){
                counter=0
                swipeLeft=swipeRight=false
            }
            if((300<=this.monkey.body.x && this.monkey.body.x<450) && (50<=this.monkey.body.y && this.monkey.body.y <=130)){
                //console.log("Home Win!")
                isGameRunning=false
                this.monkey.destroy()
                gameOverText = game.add.text(
                    game.world.width / 2,
                    game.world.height / 2,
                    "Level Complete",
                    {
                        font: '32px Comic Sans MS',
                        fill: '#fff',
                        stroke: '#430',
                        strokeThickness: 4,
                        align: 'center'
                    }
                )
                gameOverText.fixedToCamera = true
                gameOverText.cameraOffset.setTo(60, 200)

                this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this)
                this.button.anchor.setTo(.5,-1)
                this.button.scale.setTo(.6,.6)
                this.button.onInputUp.add(this.up, this)
                this.button.fixedToCamera = true
                this.button.cameraOffset.setTo(180,240)
                clearInterval(interval)

            }
        }
        else{

        }

    },
    render: function() {

    //game.debug.cameraInfo(game.camera, 32, 32)
    game.debug.spriteCoords(this.monkey, 0, 32)
   },
    up: function() {
        //start main state
        this.game.state.add('main', mainState)
        this.game.state.start('main')

    },
     actionOnClick: function(){

    },
    tick: function(){
        timer-=1
    }

}

var button
var background

var welcomeScreenState = {
    preload: function() {
    this.game.load.spritesheet('button', 'assets/btn.png', 193, 71)
    this.game.load.image('background','assets/screen.png')
    },

    create: function() {
        fullScreenMode()
        this.game.stage.backgroundColor = '#182d3b'
        this.background = this.game.add.tileSprite(0, 0, 900, 1200, 'background')

        this.button = this.game.add.button(this.game.world.centerX, this.game.world.centerY, 'button', this.actionOnClick, this, 2, 1, 0)
        this.button.anchor.setTo(.5,-1)
        this.button.scale.setTo(.5,.5)
        //this.button.onInputOver.add(this.over, this)
        //this.button.onInputOut.add(this.out, this)
        this.button.onInputUp.add(this.up, this)
    },

    up: function() {
        //start main state
        this.game.state.add('main', mainState)
        this.game.state.start('main')

    },
     actionOnClick: function(){
    },
}

game.state.add('welcomeScreen',welcomeScreenState)
game.state.start('welcomeScreen')

function createRope(length, xAnchor, yAnchor) {

    var height = 20        //  Height for the physics body - your image height is 8px
    var width = 16         //  This is the width for the physics body. If too small the rectangles will get scrambled together.
    var maxForce = 20000   //  The force that holds the rectangles together.

    for (var i = 0; i <= length; i++)
    {
        var x = xAnchor                    //  All rects are on the same x position
        var y = yAnchor + (i * height)     //  Every new rect is positioned below the last

        if (i % 2 === 0)
        {
            //  Add sprite (and switch frame every 2nd time)
            newRect = game.add.sprite(x, y, 'chain', 1)

        }
        else
        {
            newRect = game.add.sprite(x, y, 'chain', 1)
            lastRect.bringToTop()
        }

        //  Enable physicsbody
        game.physics.p2.enable(newRect, false)

        //  Set custom rectangle
        //newRect.body.setCollisionGroup(this.ropeCollisionGroup)
        newRect.body.setRectangle(width, height)

        if (i === 0)
        {
            newRect.body.static = true
        }
        else
        {
            //  Anchor the first one created
            newRect.body.velocity.x = 400
            newRect.body.damping = 0
            newRect.body.restitution = 1
            newRect.body.gravity.x = 0
            newRect.body.gravity.y = 0      //  Give it a push :) just for fun
            newRect.body.mass = length / i     //  Reduce mass for evey rope element
        }

        //  After the first rectangle is created we can add the constraint
        if (lastRect)
        {
            game.physics.p2.createRevoluteConstraint(newRect, [0, -10], lastRect, [0, 10], maxForce)
        }

        lastRect = newRect

    }

}

function fullScreenMode(){
    //make the GAME full screen
        this.game.scale.fullScreenScaleMode = Phaser.ScaleManager.SHOW_ALL
        this.game.scale.scaleMode = Phaser.ScaleManager.SHOW_ALL
        this.game.scale.refresh()
}

function isGrounded(){

        touchingGround = true

}<|endoftext|>


<commit_before>
mit.main = function() {

  // rAF
  window.requestAnimationFrame = function() {
    return window.requestAnimationFrame ||
      window.webkitRequestAnimationFrame ||
      window.mozRequestAnimationFrame ||
      window.msRequestAnimationFrame ||
      window.oRequestAnimationFrame ||
      function(f) {
        window.setTimeout(f,1e3/60);
      }
  }();

  // cAF
  window.cancelAnimationFrame = function() {
    return window.cancelAnimationFrame ||
      window.webkitCancelAnimationFrame ||
      window.mozCancelAnimationFrame ||
      window.msCancelAnimationFrame ||
      window.oCancelAnimationFrame ||
      function(f) {
        window.setTimeout(f,1e3/60);
      }
  }();

  var config = mit.config = {

  };

  var ui = mit.ui = {
    body: $('body'),
    score_board: $('#score_board'),
    last_score: $('#last_score'),
    high_score: $('#high_score'),
    start_screen: $('#start_screen'),
    start_game: $('#start_game'),
    tweet: $('#tweet'),
    fb: $('#fb'),
    fps_count: $('#fps_count'),
    invincible_timer: $('#invincible_timer'),
    invincible_loader: $('#invincible_loader')
  };

  /*
  Basic Canvas Inits
  */

  // Main Canvas

  var canvas = document.querySelector('#game_main');
  var ctx = canvas.getContext('2d');

  var W = canvas.width = ui.body.width();
  var H = canvas.height = ui.body.height();

  // Width x Height capped to 1000 x 500
  if (canvas.width > 1000) {
    W = canvas.width = 1000;
  }
  if (canvas.height > 500) {
    H = canvas.height = 500;
  }

  // Resizing Width/Height
  if (canvas.height < 500) {
    canvas.width = canvas.height * 1000/500;
  }
  if (canvas.width < 1000) {
    canvas.height = canvas.width * 500/1000;
  }

  // BG Canvas
  var bg_canvas = document.querySelector('#game_bg');
  var bg_ctx = bg_canvas.getContext('2d');

  bg_canvas.width = canvas.width;
  bg_canvas.height = canvas.height;

  var music = document.getElementById("start");
  music.volume = 0.2;

  var isMute = false;

  // Mute the game if button is clicked
  $("#mute").click(function() {
    if(isMute == false) {
      $(this).css("backgroundPosition", "0px -40px");
      music.volume = 0;
      isMute = true;
    }

    else {
      $(this).css("backgroundPosition", "0px 0px");
      music.volume = 0.2;
      isMute = false;
    }

    return false;
  });

  /*
    Game Start Screen and Lolz
  */
  mit.game_started = 0;
  mit.game_over = 0;
  mit.start_btn_clicked = 0;

  ui.start_screen.css('width', canvas.width + 'px');
  ui.start_screen.css('height', canvas.height + 'px');

  // Start Button
  var startGame = function() {
    // Play the awesome music! Really awesome
    music.play();
    flap.pause();

    // Hide the Start Screen
    ui.start_screen.fadeOut();

    // Start btn has been clicked
    // Game hasnt started. Game will
    // start on flight.
    mit.start_btn_clicked = 1;
    mit.game_started = 0;

    mit.Backgrounds.common_bg_speed = 1;
    mit.Backgrounds.resetAllSpeed();

    // Reset all accelerations and make
    // pappu stationary
    mit.Pappu.drawStatic(ctx);
    mit.ax = 0; mit.ay = 0;
    mit.vx = 0; mit.vy = 0;

    // if game over due to hitting someone
    // he'll rotate a lot. so need ta reset
    // on restart
    mit.Pappu.rotate_angle = 0;

    // reset score
    mit.score = 0;

    // Nuke all forks
    mit.ForkUtils.forks = [];
    // Nuke all branches
    mit.BranchUtils.branches = [];
    // Nuke all collectibles
    mit.CollectibleUtils.collecs = [];
    // Nuke all pakias and cur_pakia
    mit.PakiaUtils.pakias = [];
    mit.PakiaUtils.cur_pakia = false;
  };

  ui.start_game.on('mousedown', function() {
    startGame();

    return false;
  });

  // startGame();

  // Share links
  var tweet = document.getElementById("tweet");
  tweet.href='http://twitter.com/share?url=http://khele.in/pappu-pakia/&text=I am playing Pappu Pakia, a cute HTML5 game on khele.in!&count=horiztonal&via=_rishabhp&related=solitarydesigns';

  var facebook = document.getElementById("fb");
  facebook.href='http://facebook.com/sharer.php?s=100&p[url]=http://khele.in/pappu-pakia/&p[title]=I am playing Pappu Pakia, a cute HTML5 game on khele.in!';

  // Score Board
  mit.score = 0;
  try {

    mit.highScore = JSON.parse(localStorage.getItem("highScore"));
    if (mit.highScore)
      ui.high_score.text("High Score: "+ mit.highScore);

  } catch (e) {}

  ui.score_board.css('width', canvas.width + 'px');
  ui.score_board.css('height', canvas.height + 'px');

  // Set Canvas Width/Height in Config
  mit.config.canvas_width = mit.W = W;
  mit.config.canvas_height = mit.H = H;

  // Gravity
  mit.gravity = 0.7;

  // Velocity x,y
  mit.vx = 0;
  mit.vy = 0;

  // Velocity cap on either sides of the
  // number system.
  //
  // You can console.log velocities in drawing methods
  // and from there decide what to set as the cap.
  mit.v_cap = 6.5;

  // Accelaration x,y
  mit.ax = 0;
  mit.ay = 0;

  // Flying up ?
  mit.flying_up = 0;

  mit.ascend = function() {
    if (!mit.start_btn_clicked)
      return;

    if (!mit.game_started) {
      mit.game_started = 1;
      mit.game_over = 0;
    }

    mit.ay = -1.5;
    mit.flying_up = 1;
  };

  mit.descend = function() {
    if (!mit.start_btn_clicked)
      return;

    mit.ay = 0;
    mit.flying_up = 0;
  };

  // Game play on mouse clicks too!
  window.addEventListener('mousedown', function(e) {
    mit.ascend();
  }, false);

  window.addEventListener('mouseup', function(e) {
    mit.descend();
  }, false);

  // Game play on touch too!
  window.addEventListener('touchstart', function(e) {
    mit.ascend();
  }, false);

  window.addEventListener('touchend', function(e) {
    mit.descend();
  }, false);

  // ... and keyzz...
  window.addEventListener('keydown', function(e) {

    if (e.keyCode === 38) {
      mit.ascend();

      e.preventDefault();
    }

    if (e.keyCode === 32 || e.keyCode === 13) {
      startGame();

      e.preventDefault();
    }

  }, false);

  window.addEventListener('keyup', function(e) {

    if (e.keyCode === 38) {
      mit.descend();

      e.preventDefault();
    }
  }, false);

  /*
    Performing some game over tasks
  */
  mit.gameOver = function() {
    ui.start_screen.fadeIn();

    // High Score
    if (mit.score > mit.highScore) {
      mit.highScore = parseInt(mit.score);
      localStorage.setItem("highScore", JSON.stringify(parseInt(mit.score)));

      ui.high_score.text("High Score: "+ mit.highScore);
    }

    // Show last_score
    ui.last_score.text("Last Score: " + parseInt(mit.score));

    ui.start_game.html('re-start');
    ui.tweet.html('tweet score');
    ui.fb.html('post on fb');

    mit.descend();

    // Stop background
    mit.Backgrounds.common_bg_speed = 0;
    mit.Backgrounds.ground_bg_move_speed = 0;
    mit.Backgrounds.fps = 0;

    mit.game_over = 1;
    mit.start_btn_clicked = 0;

    // Pappu if invincible will be no morez
    mit.Pappu.undoInvincible();

    // Nuke all clones
    mit.Pappu.clones.length = 0;

    // Share
    var tweet = document.getElementById("tweet");
    tweet.href='http://twitter.com/share?url=http://khele.in/pappu-pakia/&text=I just scored ' +Math.floor(mit.score)+ ' points in Pappu Pakia!&count=horiztonal&via=_rishabhp&related=solitarydesigns';

    var facebook = document.getElementById("fb");
    facebook.href='http://facebook.com/sharer.php?s=100&p[url]=http://khele.in/pappu-pakia/&p[title]=I just scored ' +Math.floor(mit.score)+ ' points in the Pappu Pakia!';

  };

  mit.last_time = new Date();
  setInterval(function() {
    mit.ui.fps_count.html(mit.fps.toFixed(0) + ' FPS');
  }, 1000);

  // Initializations
  mit.Backgrounds.init(ctx);
  mit.ForkUtils.init();
  mit.BranchUtils.init();
  mit.CollectibleUtils.init();
  mit.Pappu.init();
  mit.PakiaUtils.init();

  (function renderGame() {
    window.requestAnimationFrame(renderGame);

    // Draw Backgrounds on BG Canvas
    mit.Backgrounds.draw(bg_ctx);

    ctx.clearRect(0, 0, W, H);

    // Draw Digs (holds forks)
    // I am fine without Digs, but Kushagra
    // just WANTS me to do this extra work :/
    // mit.ForkUtils.drawDigs(ctx);

    // Draw Grass on Main Canvas
    // mit.Backgrounds.drawGrass(ctx);

    if (mit.flying_up || !mit.game_started)
      mit.Pappu.updateFlyFrameCount();
    else
      mit.Pappu.updateFlyFrameCount(0);

    // Game over on reaching any boundary
    if (mit.Pappu.hasReachedBoundary(W, H)) {
      // Performing some game over tasks
      mit.gameOver();
      return;
    }

    //mit.ForkUtils.draw(ctx);
    //mit.BranchUtils.draw(ctx);

    //mit.ForkUtils.checkCollision();

    // Send over Pakias (Enemies)
    // mit.PakiaUtils.render(ctx);

    // Collectibles
    // mit.CollectibleUtils.draw(ctx);

    // mit.Pappu.createClones(3);

    if (mit.game_started) {

      // Drawin stuff
      mit.ForkUtils.draw(ctx);
      mit.BranchUtils.draw(ctx);
      mit.CollectibleUtils.draw(ctx);
      mit.Pappu.drawClones(ctx);

      // Check Collisions with pappu
      if (!mit.Pappu.invincible) {
        mit.ForkUtils.checkCollision();
        mit.BranchUtils.checkCollision();
        mit.PakiaUtils.checkCollision();
      }
      mit.CollectibleUtils.checkCollision();
      mit.Pappu.checkCloneCollision();

      // Send over Pakias (Enemies)
      if (mit.score > 199)
        mit.PakiaUtils.render(ctx);

      // Update score
      if (!mit.game_over) {
        mit.score = mit.score += 0.1;
        ui.score_board.text(parseInt(mit.score));
      }

      // Acceleration + Gravity
      // mit.ay = mit.ay + mit.gravity;

      // Velocity
      if (!mit.game_over) {
        if (
          (mit.vy < mit.v_cap && mit.ay+mit.gravity > 0) ||
          (mit.vy > -mit.v_cap && mit.ay+mit.gravity < 0)
          ) {

          // console.log(mit.ay);
          mit.vy += mit.ay;
          mit.vy += mit.gravity;
        }

        // console.log(vy, ay)

        mit.Pappu.x += mit.vx;
        mit.Pappu.y += mit.vy;

        if (mit.vy > mit.v_cap) {
          mit.vy = mit.v_cap;
        }
      }
      else {
        // on game over, he's gravity is unstoppable
        mit.vy += mit.gravity;
        mit.Pappu.y += mit.vy;
      }

      mit.Pappu.draw(ctx);
    }
    else {
      mit.Pappu.drawStatic(ctx);
    }

    // Calculate FPS
    mit.cur_time = new Date;
    mit.fps = 1e3 / (mit.cur_time - mit.last_time);
    mit.last_time = mit.cur_time;

    return;
  }());

};<commit_msg>game over was executing even after game over - no need really. lets save memory power<commit_after>
mit.main = function() {

  // rAF
  window.requestAnimationFrame = function() {
    return window.requestAnimationFrame ||
      window.webkitRequestAnimationFrame ||
      window.mozRequestAnimationFrame ||
      window.msRequestAnimationFrame ||
      window.oRequestAnimationFrame ||
      function(f) {
        window.setTimeout(f,1e3/60);
      }
  }();

  // cAF
  window.cancelAnimationFrame = function() {
    return window.cancelAnimationFrame ||
      window.webkitCancelAnimationFrame ||
      window.mozCancelAnimationFrame ||
      window.msCancelAnimationFrame ||
      window.oCancelAnimationFrame ||
      function(f) {
        window.setTimeout(f,1e3/60);
      }
  }();

  var config = mit.config = {

  };

  var ui = mit.ui = {
    body: $('body'),
    score_board: $('#score_board'),
    last_score: $('#last_score'),
    high_score: $('#high_score'),
    start_screen: $('#start_screen'),
    start_game: $('#start_game'),
    tweet: $('#tweet'),
    fb: $('#fb'),
    fps_count: $('#fps_count'),
    invincible_timer: $('#invincible_timer'),
    invincible_loader: $('#invincible_loader')
  };

  /*
  Basic Canvas Inits
  */

  // Main Canvas

  var canvas = document.querySelector('#game_main');
  var ctx = canvas.getContext('2d');

  var W = canvas.width = ui.body.width();
  var H = canvas.height = ui.body.height();

  // Width x Height capped to 1000 x 500
  if (canvas.width > 1000) {
    W = canvas.width = 1000;
  }
  if (canvas.height > 500) {
    H = canvas.height = 500;
  }

  // Resizing Width/Height
  if (canvas.height < 500) {
    canvas.width = canvas.height * 1000/500;
  }
  if (canvas.width < 1000) {
    canvas.height = canvas.width * 500/1000;
  }

  // BG Canvas
  var bg_canvas = document.querySelector('#game_bg');
  var bg_ctx = bg_canvas.getContext('2d');

  bg_canvas.width = canvas.width;
  bg_canvas.height = canvas.height;

  var music = document.getElementById("start");
  music.volume = 0.2;

  var isMute = false;

  // Mute the game if button is clicked
  $("#mute").click(function() {
    if(isMute == false) {
      $(this).css("backgroundPosition", "0px -40px");
      music.volume = 0;
      isMute = true;
    }

    else {
      $(this).css("backgroundPosition", "0px 0px");
      music.volume = 0.2;
      isMute = false;
    }

    return false;
  });

  /*
    Game Start Screen and Lolz
  */
  mit.game_started = 0;
  mit.game_over = 0;
  mit.start_btn_clicked = 0;

  ui.start_screen.css('width', canvas.width + 'px');
  ui.start_screen.css('height', canvas.height + 'px');

  // Start Button
  var startGame = function() {
    // Play the awesome music! Really awesome
    music.play();
    flap.pause();

    // Hide the Start Screen
    ui.start_screen.fadeOut();

    // Start btn has been clicked
    // Game hasnt started. Game will
    // start on flight.
    mit.start_btn_clicked = 1;
    mit.game_started = 0;

    mit.Backgrounds.common_bg_speed = 1;
    mit.Backgrounds.resetAllSpeed();

    // Reset all accelerations and make
    // pappu stationary
    mit.Pappu.drawStatic(ctx);
    mit.ax = 0; mit.ay = 0;
    mit.vx = 0; mit.vy = 0;

    // if game over due to hitting someone
    // he'll rotate a lot. so need ta reset
    // on restart
    mit.Pappu.rotate_angle = 0;

    // reset score
    mit.score = 0;

    // Nuke all forks
    mit.ForkUtils.forks = [];
    // Nuke all branches
    mit.BranchUtils.branches = [];
    // Nuke all collectibles
    mit.CollectibleUtils.collecs = [];
    // Nuke all pakias and cur_pakia
    mit.PakiaUtils.pakias = [];
    mit.PakiaUtils.cur_pakia = false;
  };

  ui.start_game.on('mousedown', function() {
    startGame();

    return false;
  });

  // startGame();

  // Share links
  var tweet = document.getElementById("tweet");
  tweet.href='http://twitter.com/share?url=http://khele.in/pappu-pakia/&text=I am playing Pappu Pakia, a cute HTML5 game on khele.in!&count=horiztonal&via=_rishabhp&related=solitarydesigns';

  var facebook = document.getElementById("fb");
  facebook.href='http://facebook.com/sharer.php?s=100&p[url]=http://khele.in/pappu-pakia/&p[title]=I am playing Pappu Pakia, a cute HTML5 game on khele.in!';

  // Score Board
  mit.score = 0;
  try {

    mit.highScore = JSON.parse(localStorage.getItem("highScore"));
    if (mit.highScore)
      ui.high_score.text("High Score: "+ mit.highScore);

  } catch (e) {}

  ui.score_board.css('width', canvas.width + 'px');
  ui.score_board.css('height', canvas.height + 'px');

  // Set Canvas Width/Height in Config
  mit.config.canvas_width = mit.W = W;
  mit.config.canvas_height = mit.H = H;

  // Gravity
  mit.gravity = 0.7;

  // Velocity x,y
  mit.vx = 0;
  mit.vy = 0;

  // Velocity cap on either sides of the
  // number system.
  //
  // You can console.log velocities in drawing methods
  // and from there decide what to set as the cap.
  mit.v_cap = 6.5;

  // Accelaration x,y
  mit.ax = 0;
  mit.ay = 0;

  // Flying up ?
  mit.flying_up = 0;

  mit.ascend = function() {
    if (!mit.start_btn_clicked)
      return;

    if (!mit.game_started) {
      mit.game_started = 1;
      mit.game_over = 0;
    }

    mit.ay = -1.5;
    mit.flying_up = 1;
  };

  mit.descend = function() {
    if (!mit.start_btn_clicked)
      return;

    mit.ay = 0;
    mit.flying_up = 0;
  };

  // Game play on mouse clicks too!
  window.addEventListener('mousedown', function(e) {
    mit.ascend();
  }, false);

  window.addEventListener('mouseup', function(e) {
    mit.descend();
  }, false);

  // Game play on touch too!
  window.addEventListener('touchstart', function(e) {
    mit.ascend();
  }, false);

  window.addEventListener('touchend', function(e) {
    mit.descend();
  }, false);

  // ... and keyzz...
  window.addEventListener('keydown', function(e) {

    if (e.keyCode === 38) {
      mit.ascend();

      e.preventDefault();
    }

    if (e.keyCode === 32 || e.keyCode === 13) {
      startGame();

      e.preventDefault();
    }

  }, false);

  window.addEventListener('keyup', function(e) {

    if (e.keyCode === 38) {
      mit.descend();

      e.preventDefault();
    }
  }, false);

  /*
    Performing some game over tasks
  */
  mit.gameOver = function() {
    ui.start_screen.fadeIn();

    // High Score
    if (mit.score > mit.highScore) {
      mit.highScore = parseInt(mit.score);
      localStorage.setItem("highScore", JSON.stringify(parseInt(mit.score)));

      ui.high_score.text("High Score: "+ mit.highScore);
    }

    // Show last_score
    ui.last_score.text("Last Score: " + parseInt(mit.score));

    ui.start_game.html('re-start');
    ui.tweet.html('tweet score');
    ui.fb.html('post on fb');

    mit.descend();

    // Stop background
    mit.Backgrounds.common_bg_speed = 0;
    mit.Backgrounds.ground_bg_move_speed = 0;
    mit.Backgrounds.fps = 0;

    mit.game_over = 1;
    mit.start_btn_clicked = 0;

    // Pappu if invincible will be no morez
    mit.Pappu.undoInvincible();

    // Nuke all clones
    mit.Pappu.clones.length = 0;

    // Share
    var tweet = document.getElementById("tweet");
    tweet.href='http://twitter.com/share?url=http://khele.in/pappu-pakia/&text=I just scored ' +Math.floor(mit.score)+ ' points in Pappu Pakia!&count=horiztonal&via=_rishabhp&related=solitarydesigns';

    var facebook = document.getElementById("fb");
    facebook.href='http://facebook.com/sharer.php?s=100&p[url]=http://khele.in/pappu-pakia/&p[title]=I just scored ' +Math.floor(mit.score)+ ' points in the Pappu Pakia!';

  };

  mit.last_time = new Date();
  setInterval(function() {
    mit.ui.fps_count.html(mit.fps.toFixed(0) + ' FPS');
  }, 1000);

  // Initializations
  mit.Backgrounds.init(ctx);
  mit.ForkUtils.init();
  mit.BranchUtils.init();
  mit.CollectibleUtils.init();
  mit.Pappu.init();
  mit.PakiaUtils.init();

  (function renderGame() {
    window.requestAnimationFrame(renderGame);

    // Draw Backgrounds on BG Canvas
    mit.Backgrounds.draw(bg_ctx);

    ctx.clearRect(0, 0, W, H);

    // Draw Digs (holds forks)
    // I am fine without Digs, but Kushagra
    // just WANTS me to do this extra work :/
    // mit.ForkUtils.drawDigs(ctx);

    // Draw Grass on Main Canvas
    // mit.Backgrounds.drawGrass(ctx);

    if (mit.flying_up || !mit.game_started)
      mit.Pappu.updateFlyFrameCount();
    else
      mit.Pappu.updateFlyFrameCount(0);

    // Game over on reaching any boundary
    if (mit.Pappu.hasReachedBoundary(W, H)) {
      if (mit.game_over)
        return;

      // Performing some game over tasks
      mit.gameOver();
      return;
    }

    //mit.ForkUtils.draw(ctx);
    //mit.BranchUtils.draw(ctx);

    //mit.ForkUtils.checkCollision();

    // Send over Pakias (Enemies)
    // mit.PakiaUtils.render(ctx);

    // Collectibles
    // mit.CollectibleUtils.draw(ctx);

    // mit.Pappu.createClones(3);

    if (mit.game_started) {

      // Drawin stuff
      mit.ForkUtils.draw(ctx);
      mit.BranchUtils.draw(ctx);
      mit.CollectibleUtils.draw(ctx);
      mit.Pappu.drawClones(ctx);

      // Check Collisions with pappu
      if (!mit.Pappu.invincible) {
        mit.ForkUtils.checkCollision();
        mit.BranchUtils.checkCollision();
        mit.PakiaUtils.checkCollision();
      }
      mit.CollectibleUtils.checkCollision();
      mit.Pappu.checkCloneCollision();

      // Send over Pakias (Enemies)
      if (mit.score > 199)
        mit.PakiaUtils.render(ctx);

      // Update score
      if (!mit.game_over) {
        mit.score = mit.score += 0.1;
        ui.score_board.text(parseInt(mit.score));
      }

      // Acceleration + Gravity
      // mit.ay = mit.ay + mit.gravity;

      // Velocity
      if (!mit.game_over) {
        if (
          (mit.vy < mit.v_cap && mit.ay+mit.gravity > 0) ||
          (mit.vy > -mit.v_cap && mit.ay+mit.gravity < 0)
          ) {

          // console.log(mit.ay);
          mit.vy += mit.ay;
          mit.vy += mit.gravity;
        }

        // console.log(vy, ay)

        mit.Pappu.x += mit.vx;
        mit.Pappu.y += mit.vy;

        if (mit.vy > mit.v_cap) {
          mit.vy = mit.v_cap;
        }
      }
      else {
        // on game over, he's gravity is unstoppable
        mit.vy += mit.gravity;
        mit.Pappu.y += mit.vy;
      }

      mit.Pappu.draw(ctx);
    }
    else {
      mit.Pappu.drawStatic(ctx);
    }

    // Calculate FPS
    mit.cur_time = new Date;
    mit.fps = 1e3 / (mit.cur_time - mit.last_time);
    mit.last_time = mit.cur_time;

    return;
  }());

};<|endoftext|>


<commit_before>(function() {

    var btn = document.getElementById('calc');

    btn.onclick = function(){

        var startHour = parseInt(document.getElementById('start-hour').value),
            startMinute = parseInt(document.getElementById('start-minute').value),
            startAmPm = document.querySelector('input[name = start-am-pm]:checked').value,
            endHour = parseInt(document.getElementById('end-hour').value),
            endMinute = parseInt(document.getElementById('end-minute').value),
            endAmPm = document.querySelector('input[name = end-am-pm]:checked').value,
            lunchTaken = document.querySelector('input[name = lunch]:checked').value,

            startToMinutes = 0,
            endToMinutes = 0,
            minutesDiff = 0,
            hourFinal = 0,
            minuteFinal = 0,
            hourOutput = "",
            minuteOutput = "";

            // Allows for AM/PM calculation
            if (startAmPm === "pm" && startHour != 12) {
                startHour += 12;
            }

            // Allows for AM/PM calculation
            if (endAmPm === "pm" && endHour != 12) {
                endHour += 12;
            }

            // Convert to total minutes
            startToMinutes = ((startHour * 60) + startMinute);
            endToMinutes = ((endHour * 60) + endMinute);

            minutesDiff = (endToMinutes - startToMinutes);

            // Removes 30 minutes if lunch was taken
            if (lunchTaken === "yes") {
                minutesDiff -= 30;
            }

            hourFinal = Math.floor(minutesDiff / 60);
            minuteFinal = (minutesDiff % 60);

            // Determines proper output of hour/hours and minute/minutes
            if (hourFinal === 1) {
                hourOutput = "hour";
            } else {
                hourOutput = "hours";
            }

            if (minuteFinal === 1) {
                minuteOutput = "minute";
            } else {
                minuteOutput = "minutes";
            }

            var ans = document.getElementById("answer");
            ans.innerHTML = "
Total time is " + hourFinal + " " + hourOutput +
            " and " + minuteFinal + " " + minuteOutput + "
";

        return false;
    };

    var clr = document.getElementById('clear');

    clr.onclick = function(){

        //remove empty field warnings
        window.location.reload();
    };

})();<commit_msg>Minor tweaks of little value<commit_after>(function() {

    var btn = document.getElementById('calc');

    btn.onclick = function(e){

        var startHour = parseInt(document.getElementById('start-hour').value),
            startMinute = parseInt(document.getElementById('start-minute').value),
            startAmPm = document.querySelector('input[name = start-am-pm]:checked').value,
            endHour = parseInt(document.getElementById('end-hour').value),
            endMinute = parseInt(document.getElementById('end-minute').value),
            endAmPm = document.querySelector('input[name = end-am-pm]:checked').value,
            lunchTaken = document.querySelector('input[name = lunch]:checked').value,
            startToMinutes,
            endToMinutes,
            minutesDiff,
            hourFinal,
            minuteFinal,
            hourOutput,
            minuteOutput;

            // Allows for AM/PM calculation
            if (startAmPm === "pm" && startHour != 12) {
                startHour += 12;
            }

            // Allows for AM/PM calculation
            if (endAmPm === "pm" && endHour != 12) {
                endHour += 12;
            }

            // Convert to total minutes
            startToMinutes = ((startHour * 60) + startMinute);
            endToMinutes = ((endHour * 60) + endMinute);

            minutesDiff = (endToMinutes - startToMinutes);

            // Removes 30 minutes if lunch was taken
            if (lunchTaken === "yes") {
                minutesDiff -= 30;
            }

            hourFinal = Math.floor(minutesDiff / 60);
            minuteFinal = (minutesDiff % 60);

            // Determines proper output of hour/hours and minute/minutes
            if (hourFinal === 1) {
                hourOutput = "hour";
            } else {
                hourOutput = "hours";
            }

            if (minuteFinal === 1) {
                minuteOutput = "minute";
            } else {
                minuteOutput = "minutes";
            }

            var ans = document.getElementById("answer");
            ans.innerHTML = "
Total time is " + hourFinal + " " + hourOutput +
            " and " + minuteFinal + " " + minuteOutput + "." + "
";

        e.preventDefault();
    };

    var clr = document.getElementById('clear');

    clr.onclick = function(){

        // Removes previous output
        window.location.reload();
    };

})();<|endoftext|>


<commit_before>$(function(){
  var canvas = $('#game_canvas')[0];
  var ctx = canvas.getContext("2d");
  sceneManager.goto(new MenuScene()); //first scene //TODO game menu scene
  ;(function(fps){
    var interval = 1000 / fps;
    var prevTime = Date.now();
    ;(function loop(){
      window.requestAnimFrame(loop);
      var now = Date.now();
      var delta = now - prevTime;
      if (delta < interval) return;
      var deltaRatio = delta / interval; //經過的時間與預計的時間的比例。數字越高代表越LAG。
      prevTime += delta - (delta % interval); //若requestAnimFrame是60FPS時，delta會是16ms的倍數。要減掉delta % interval否則會多算時間。
      Input.update();
      sceneManager.update(deltaRatio);
      ctx.clearRect(0, 0, canvas.width, canvas.height);
      sceneManager.render(canvas);
    })();
  }(40));
});
//-------------------------------------
//  MenuScene
//-------------------------------------
function MenuScene(){
  return {
    update: function(deltaRatio){
      if (Input.pressed(Input.KEYS.ENTER)){
        //TODO sound && animation?
        sceneManager.goto(new MapScene());
      }
    },
    render: function(canvas){
      var ctx = canvas.getContext("2d");
      imageCacher.ifloaded('images/menu.jpg', function(image){
        var width = image.width * (canvas.height / image.height);
        ctx.drawImage(image, (canvas.width - width) / 2, 0, width, canvas.height);
      });
    }
  };
}
//-------------------------------------
//  MapScene
//-------------------------------------
function MapScene(){
  var BASE_Y = 80;
  var player = (function(){
    var vx = 0, vy = 0;
    return characterFoctory.create('images/characters/wolf.png', 0, BASE_Y, function(){
      if (Input.pressed(Input.KEYS.RIGHT)) vx = 6;
      else if (Input.pressed(Input.KEYS.LEFT)) vx = 3;
      else vx = 4;
      if (Input.pressed(Input.KEYS.UP) && player.y == BASE_Y) vy = 15;
      if (player.y > BASE_Y){
        vy -= 1; //gravity
      }
      player.x += vx;
      player.y += vy;
      if (player.y < BASE_Y){
        player.y = BASE_Y;
        vy = 0;
      }
    });
  })();
  var nextEnemyRespawnAt = 50;
  var enemy;
  return {
    update: function(deltaRatio){
      if (player.x > nextEnemyRespawnAt){
        if (enemy) enemy.destroy();
        enemy = characterFoctory.create('images/characters/enemy.png', player.x + 1000, 80);
        nextEnemyRespawnAt = player.x + 1100 + Math.rand(200);
      }
      _.each(characterFoctory.characters, function(character){
        character.update();
      });
    },
    render: function(canvas){
      var ctx = canvas.getContext("2d");
      var viewX = player.x - 80;
      function drawImageWithXRepeat(ratio, path){
        imageCacher.ifloaded(path, function(image){
          var width = image.width * (canvas.height / image.height);
          var dx = -(viewX * ratio) % width;
          if (dx > 0) dx -= width;
          while(dx < canvas.width){
            ctx.drawImage(image, dx, 0, width, canvas.height);
            dx += width;
          }
        });
      }
      drawImageWithXRepeat(0.1, 'images/background.jpg');
      drawImageWithXRepeat(1.0, 'images/ground.png');
      _.each(characterFoctory.characters, function(character){
        imageCacher.ifloaded(character.path, function(image){
          var x = character.x - viewX;
          var y = canvas.height - character.y - image.height;
          var sx = character.getPattern() / character.maxPattern * image.width;
          var sy = 0;
          var width = image.width / character.maxPattern;
          var height = image.height;
          ctx.drawImage(image, sx, sy, width, height, x, y, width, height);
        });
      });
    }
  };
}
//-------------------------------------
//  Character
//-------------------------------------
var characterFoctory = new function(){
  var MAX_PATTERNS = {
    "images/characters/wolf.png": 4,
    "images/characters/enemy.png": 4
  };
  function getMaxPattern(path){ return MAX_PATTERNS[path] || 1; }
  var characters = {}, counter = 0;
  return {
    characters: characters,
    create: function(path, x, y, preUpdateFunc){
      var cid = (counter += 1);
      var pattern = 0, patternCounter = 0, patternAnimeSpeed = 12;
      var character = {
        x: x,
        y: y,
        path: path,
        getPattern: function(){ return pattern; },
        maxPattern: getMaxPattern(path),
        update: function(){
          if (preUpdateFunc) preUpdateFunc();
          patternCounter += patternAnimeSpeed;
          if (patternCounter > 100){
            patternCounter -= 100;
            pattern = (pattern + 1) % character.maxPattern;
          }
        },
        destroy: function(){
          delete characters[cid];
        }
      };
      return characters[cid] = character;
    }
  }
}

<commit_msg>use constant: VIEWPORT_X<commit_after>$(function(){
  var canvas = $('#game_canvas')[0];
  var ctx = canvas.getContext("2d");
  sceneManager.goto(new MenuScene()); //first scene //TODO game menu scene
  ;(function(fps){
    var interval = 1000 / fps;
    var prevTime = Date.now();
    ;(function loop(){
      window.requestAnimFrame(loop);
      var now = Date.now();
      var delta = now - prevTime;
      if (delta < interval) return;
      var deltaRatio = delta / interval; //經過的時間與預計的時間的比例。數字越高代表越LAG。
      prevTime += delta - (delta % interval); //若requestAnimFrame是60FPS時，delta會是16ms的倍數。要減掉delta % interval否則會多算時間。
      Input.update();
      sceneManager.update(deltaRatio);
      ctx.clearRect(0, 0, canvas.width, canvas.height);
      sceneManager.render(canvas);
    })();
  }(40));
});
//-------------------------------------
//  MenuScene
//-------------------------------------
function MenuScene(){
  return {
    update: function(deltaRatio){
      if (Input.pressed(Input.KEYS.ENTER)){
        //TODO sound && animation?
        sceneManager.goto(new MapScene());
      }
    },
    render: function(canvas){
      var ctx = canvas.getContext("2d");
      imageCacher.ifloaded('images/menu.jpg', function(image){
        var width = image.width * (canvas.height / image.height);
        ctx.drawImage(image, (canvas.width - width) / 2, 0, width, canvas.height);
      });
    }
  };
}
//-------------------------------------
//  MapScene
//-------------------------------------
function MapScene(){
  var VIEWPORT_X = 90;
  var BASE_Y = 80;
  var player = (function(){
    var vx = 0, vy = 0;
    return characterFoctory.create('images/characters/wolf.png', 0, BASE_Y, function(){
      if (Input.pressed(Input.KEYS.RIGHT)) vx = 6;
      else if (Input.pressed(Input.KEYS.LEFT)) vx = 3;
      else vx = 4;
      if (Input.pressed(Input.KEYS.UP) && player.y == BASE_Y) vy = 15;
      if (player.y > BASE_Y){
        vy -= 1; //gravity
      }
      player.x += vx;
      player.y += vy;
      if (player.y < BASE_Y){
        player.y = BASE_Y;
        vy = 0;
      }
    });
  })();
  var nextEnemyRespawnAt = 50;
  var enemy;
  return {
    update: function(deltaRatio){
      if (player.x > nextEnemyRespawnAt){
        if (enemy) enemy.destroy();
        enemy = characterFoctory.create('images/characters/enemy.png', player.x + 1000, BASE_Y);
        nextEnemyRespawnAt = player.x + 1100 + Math.rand(200);
      }
      _.each(characterFoctory.characters, function(character){
        character.update();
      });
    },
    render: function(canvas){
      var ctx = canvas.getContext("2d");
      var viewX = player.x - VIEWPORT_X;
      function drawImageWithXRepeat(ratio, path){
        imageCacher.ifloaded(path, function(image){
          var width = image.width * (canvas.height / image.height);
          var dx = -(viewX * ratio) % width;
          if (dx > 0) dx -= width;
          while(dx < canvas.width){
            ctx.drawImage(image, dx, 0, width, canvas.height);
            dx += width;
          }
        });
      }
      drawImageWithXRepeat(0.1, 'images/background.jpg');
      drawImageWithXRepeat(1.0, 'images/ground.png');
      _.each(characterFoctory.characters, function(character){
        imageCacher.ifloaded(character.path, function(image){
          var x = character.x - viewX;
          var y = canvas.height - character.y - image.height;
          var sx = character.getPattern() / character.maxPattern * image.width;
          var sy = 0;
          var width = image.width / character.maxPattern;
          var height = image.height;
          ctx.drawImage(image, sx, sy, width, height, x, y, width, height);
        });
      });
    }
  };
}
//-------------------------------------
//  Character
//-------------------------------------
var characterFoctory = new function(){
  var MAX_PATTERNS = {
    "images/characters/wolf.png": 4,
    "images/characters/enemy.png": 4
  };
  function getMaxPattern(path){ return MAX_PATTERNS[path] || 1; }
  var characters = {}, counter = 0;
  return {
    characters: characters,
    create: function(path, x, y, preUpdateFunc){
      var cid = (counter += 1);
      var pattern = 0, patternCounter = 0, patternAnimeSpeed = 12;
      var character = {
        x: x,
        y: y,
        path: path,
        getPattern: function(){ return pattern; },
        maxPattern: getMaxPattern(path),
        update: function(){
          if (preUpdateFunc) preUpdateFunc();
          patternCounter += patternAnimeSpeed;
          if (patternCounter > 100){
            patternCounter -= 100;
            pattern = (pattern + 1) % character.maxPattern;
          }
        },
        destroy: function(){
          delete characters[cid];
        }
      };
      return characters[cid] = character;
    }
  }
}

<|endoftext|>