jQuery(document).ready(function() {

  // Open every link with a rel="external" in a new window.
  jQuery('a[rel=external]').attr('target', '_blank');

  // display watermarks for the login form
  // they are placed here because they have to be replaced on all pages
  jQuery.watermark.className = 'watermark';
  jQuery('input#login-email').watermark( __('E-mail'));

  // handle watermarks differently in Opera since it ruins tab/form order
  if (navigator.appName.indexOf('Opera') != -1) {
    jQuery('input#login-password').addClass('watermark').val(__('Password')).focus(function () {
      jQuery(this).val('');
    });
  } else {
    jQuery('input#login-password').watermark(__('Password'));
  }

  // fade in errors and messages
  jQuery('p.success').fadeIn(1000);
  jQuery('p.error').fadeIn(1000);

  // settings for colorbox
  jQuery.fn.colorbox.settings.iframe = true;
  jQuery.fn.colorbox.settings.resize = true;
  jQuery.fn.colorbox.settings.width = 700;
  jQuery.fn.colorbox.settings.height = 600;
  jQuery.fn.colorbox.settings.overlayClose = true;
  jQuery.fn.colorbox.settings.opacity = 0.5;
  jQuery.fn.colorbox.settings.close = '';
  jQuery.fn.colorbox.settings.transition = 'elastic';

  jQuery('a.colorbox').colorbox();
  jQuery('a.reloadparent').bind('click', null, reloadParent);

  if (typeof fullscreen == 'function') {
    jQuery('a.fullscreen').fullscreen();
  }

  // process all queued events when the DOM is ready
  jQuery(init_queue).each(function () { this(); });

  // show elements with the class 'hidecolorbox', this prevents opening the url in the whole browser insted of the lighbox.
  // this happens when the page isn't completely loaded and the user presses on href with the class colorbox
  jQuery('.hidecolorbox').show();

});

/* START WATERMARK FUNCTIONS */

// display watermarks on the signup page
function watermarkSignup()
{
  jQuery('input#signup-email').watermark(__('E-mail'));

  // handle watermarks differently in Opera since it ruins tab/form order
  if (navigator.appName.indexOf('Opera') != -1) {
    jQuery('input#signup-password').addClass('watermark').val(__('Password')).focus(function () {
      jQuery(this).val('');
    });
  } else {
    jQuery('input#signup-password').watermark(__('Password'));
  }

  // handle watermarks differently in Opera since it ruins tab/form order
  if (navigator.appName.indexOf('Opera') != -1) {
    jQuery('input#signup-password2').addClass('watermark').val(__('Repeat password')).focus(function () {
      jQuery(this).val('');
    });
  } else {
    jQuery('input#signup-password2').watermark(__('Repeat password'));
  }
}

// display watermarks on password reset screen
function watermarkPasswordReset()
{
  jQuery('input#reset-email').watermark(__('E-mail'));
}

// display watermark on profile page
function watermarkProfile()
{
  jQuery('input#startnewsubject').watermark(__('Enter the name of the course or an invitation code'));
}

// display watermark on profile page
function watermarkISBN()
{
  jQuery('input#isbn_search').watermark( __('Enter ISBN-10 or ISBN-13 number'));
}

function watermarkToctree()
{
  // the first text input has to be watermarked
  jQuery('#navigation input:text').each(function(i, element) {
    if (!jQuery(element).hasClass('disabled') && jQuery(element).val() == '') {
      jQuery(element).watermark('If there are no (sub)chapters or paragraph headers, please continue.');
      return false;
    }
  });

}

/* END WATERMARK FUNCTIONS */

// helper functions for the spinner
function startSpinner(spinner_id)
{
    if (typeof spinner_id != 'undefined') {
      jQuery('img#' + spinner_id).show();
    } else {
      jQuery('img.spinner').show();
    }
    jQuery('body').css('cursor', 'wait');
}

function stopSpinner(spinner_id)
{
    if (typeof spinner_id != 'undefined') {
      jQuery('img#' + spinner_id).hide();
    } else {
      jQuery('img.spinner').hide();
    }
    jQuery('body').css('cursor', 'auto');
}

function showRehearsalTree(toc_no){
	jQuery('#navigation').treeview({
      collapsed: true,
      unique: true
    });
    
    var toc_base;

    toc_base = toc_no.substr(0, toc_no.indexOf('.'));

    jQuery('#navigation li').each(function() {

      var classes = jQuery(this).attr('class');

      // open correct nodes below current node
      if (classes.indexOf('toc_' + toc_base) != -1) {

        // work around a treeview bug to properly display the - icon
        jQuery(this).children('div.open-hitarea').removeClass('expandable-hitarea').addClass('collapsable-hitarea');

        // background color for currently active nodes
        //jQuery(this).children(':text').addClass('current');
      }

      // display tooltip for '+' icon
      // node number
      var node = classes.match("toc_([0-9.]+).");
      node = node[1];
      var text = __('Add more chapters/paragraphs to ') + node;
      var tooltip = '<a href="#" class="tooltip" onclick="javascript:return false;" title="' + text + '">&nbsp;</a>';
      jQuery(this).children('div.expandable-hitarea').html(tooltip);
    });
    
    jQuery('#navigation').show();
    jQuery('#navigation .quicknav').show();
    
    // enable edit title link
    jQuery('#navigation a.reviewlink').die();
    jQuery('#navigation a.reviewlink').live('click', function(event) {

      event.preventDefault();
		
	  window.parent.location = jQuery(this).attr('href');
      parent.jQuery.fn.colorbox.close();
    });
}

/**
 *  display the TOC tree widget. Default state is hidden and auto-collapsed
 *
 *  @param: toc_no string, current toc_no
 *  @param: disable, text inputs editable or not
 */
function showTocTree(toc_no, disable)
{
  jQuery('#navigation').treeview({
      collapsed: true,
      unique: false
    });

  // if we received a toc_no, we will disable the parts of the tree that are not
  // below the specified toc_no
  if (disable || typeof toc_no != 'undefined' && toc_no !== '') {

    var toc_base;

    toc_base = toc_no.substr(0, toc_no.indexOf('.'));

    jQuery('#navigation li').each(function() {

      var classes = jQuery(this).attr('class');

      // open correct nodes below current node
      if (classes.indexOf('toc_' + toc_base) != -1) {

        // work around a treeview bug to properly display the - icon
        jQuery(this).children('div.open-hitarea').removeClass('expandable-hitarea').addClass('collapsable-hitarea');

        // background color for currently active nodes
        jQuery(this).children(':text').addClass('current');
      }

      // display tooltip for '+' icon
      // node number
      var node = classes.match("toc_([0-9.]+).");
      node = node[1];
      var text = __('Add more chapters/paragraphs to ') + node;
      var tooltip = '<a href="#" class="tooltip" onclick="javascript:return false;" title="' + text + '">&nbsp;</a>';
      jQuery(this).children('div.expandable-hitarea').html(tooltip);

      // if the source is locked, chapters can't be edited anymore.
      if (disable) {
        jQuery(this).children('input:text').attr('readonly', 'readonly').addClass('disabled');
      }

      // this is not the part of the tree we want to open; disable it
      // workaround to distinguish eg. 'toc_1 ' and 'toc_10 '
      if (!disable && classes.indexOf('toc_' + toc_no + '.') == -1) {

        jQuery(this).children('input:text').attr('readonly', 'readonly').addClass('disabled');
        jQuery(this).children(':checkbox').hide();
      }
      
      if (disable){
      	jQuery('#toc_description_'+toc_no).addClass('currentTocNo');
      }
      
    });
  }

  // create initial 'more' links
  toctreeAddMoreLinks(disable);

  jQuery('#navigation').show();
  watermarkToctree();
  
  // mouseover edit/start links for filled chapters
  jQuery('#navigation input.toc_description').die();
  jQuery('#navigation input.toc_description').live('mouseover', function(event) {
  
    // hide previously displayed hover menus
    jQuery('#navigation .quicknav').each(function(i, elm) {
      jQuery(elm).hide();
    });

    // enable current item
    jQuery(this).siblings('.quicknav').show();
  });

  // enable start title link
  jQuery('#navigation a.startlink').die();
  jQuery('#navigation a.startlink').live('click', function(event) {

    event.preventDefault();

    var href = jQuery(this).attr('href');

    jQuery.get(href, { time: new Date().getTime() }, function(data) {
      window.parent.jQuery('#studyContainer').html(data);
      parent.jQuery.fn.colorbox.close();
    });
  });

  if (!disable) {
	base_toc_no = toc_no;
	
    // append dummy '+' icons on non-expandable nodes
    jQuery('#navigation li').not('.expandable').each(function (i, elm) {

      var css_li = 'expandable';
      var css_div = 'expandable-hitarea';
      if (jQuery(elm).hasClass('last')) {
        css_li = 'expandable lastExpandable';
        css_div = 'lastExpandable-hitarea';
      }
      jQuery(elm).addClass(css_li);

      toc_no = jQuery(elm).attr('class');
      toc_no = toc_no.match("toc_([0-9.]+).");
      new_toc_no = toc_no[1];

      jQuery(elm).prepend('<div class="dummy hitarea -hitarea closed-hitarea toc_' + new_toc_no + '0 ' + css_div + '"/>');
    });

    // click handler for 'more' buttons
    // appends N dummy items
    jQuery('#navigation a.link').die();
    jQuery('#navigation a.link').live('click', function(event) {
      event.preventDefault();
      addBlankTocFields(jQuery(this), null, base_toc_no);
    });

    jQuery('#navigation .quicknav').unbind('click');

    // enable edit title link
    jQuery('#navigation a.editlink').die();
    jQuery('#navigation a.editlink').live('click', function(event) {

      event.preventDefault();

      var classes = jQuery(this).attr('class');
      var node = classes.match("edit_([0-9(.)?]+)");
      node = node[1].replace(/\./g,'_');

      // open correct nodes below current node
      jQuery('#toc_description_' + node).removeClass('disabled');
      jQuery('#toc_description_' + node).removeAttr('readonly');
      jQuery('#toc_description_' + node).focus();
      
      // show the corresponding checkbox
      jQuery(escape_id('toc_checkbox_' + node.replace(/_/g,'.'))).show();
      
      // and show the corresponding checkbox
      jQuery('#toc_checkbox_'+node).show();
    });
  }
  
  // show 'more' links that are hidden by default
  jQuery('#navigation a.link').show();
}

/**
 *  Gets the content of an Url and places it in the target
 */

function ajaxGet(url, targetId)
{
  startSpinner();

  jQuery.get(url, { time: new Date().getTime() }, function(data) {
    stopSpinner();
    jQuery('#' + targetId).html(data);
  });

  return false;
}


function addUpdateLinks(update_links_url)
{
  jQuery.get(update_links_url, { time: new Date().getTime() }, function(data) {
    parent.jQuery('#q-info').html(data);

    // show number of available questions in the QA step
    displayAvailableQuestions();
  });


  stopSpinner();
}

function removeUpdateLinks()
{
  jQuery('#q-info').empty();
}

// saves selected answers in the 'show questions' lightbox
function saveSelectedQuestions(parent_load_url)
{
  jQuery('#savequestions').click(function() {

  startSpinner();
  var postData = [];

  // gather selected questions
  jQuery('input[type=hidden]').each(function(i, elm) {

    if (jQuery(elm).attr('name') == 'question[]' && jQuery(elm).attr('value') !== '') {
    var tmp = {};
    tmp.name = jQuery(elm).attr('name');
    tmp.value = jQuery(elm).attr('value');
    postData.push(tmp);
    }
  });

  // gather selected answers
  jQuery('.answer_selected').each(function(i, elm) {
    var tmp = {};
    tmp.name = 'answer[]';
    tmp.value = jQuery(elm).attr('id');
    postData.push(tmp);
  });


  // gather newly added answers
  jQuery('.new_answer').each(function(i, elm) {

    var value = jQuery(elm).val();

    if (typeof value != 'undefined' && value !== '') {
    var tmp = {};
    question_id = jQuery(elm).attr('id').substr(12);
    tmp.name = 'new_answer[' + question_id + ']';
    tmp.value = value;
    postData.push(tmp);
    }
  });



  // gather newly added answers checkboxes
  jQuery('.new_answer_checkbox').each(function(i, elm) {

    var checked = jQuery(elm).attr('checked');


    if (checked) {

    var tmp = {};
    new_answer_checkbox_id = jQuery(elm).attr('id');
    question_id = new_answer_checkbox_id.substr(20);

    tmp.name = 'new_answer_checkbox[]';
    tmp.value = question_id;
    postData.push(tmp);
    }
  });

  // dunno why, but apparently we need this
  jQuery('.answer_selected').each(function(i, elm) {
    var tmp = {};
    question_id = jQuery(elm).attr('name').substr(9);
    tmp.name = 'selected_answer[' + question_id + ']';
    tmp.value = jQuery(elm).attr('id');
    postData.push(tmp);
  });

  jQuery.post(jQuery('#tocitemquestions').attr('action'), postData, function(data) {

    //jQuery('#ajaxresult').html(data);
    //return false;

    stopSpinner();
    jQuery.get(parent_load_url, { time: new Date().getTime()}, function(data) {

      parent.jQuery('#studyContainer').html(data);
      parent.jQuery.fn.colorbox.close();
    });
  });

  // I(FB) think this is not necessary, the studyContainer is reloaded just above this line.
  /*jQuery.get(parent_load_url, { time: new Date().getTime()}, function(data) {

    parent.jQuery('#studyContainer').html(data);
    parent.jQuery.fn.colorbox.close();
  });*/

  });

  return false;
}


function addQuestionToggle()
{
  jQuery('div.question a').click(function(event) {

    event.preventDefault();
    jQuery('.answers').hide();

    question = jQuery(this).parent();
    question_id = question.attr('id').substr(2);
    answer_id = 'a_' + question_id;

    jQuery('#' + answer_id).slideToggle('slow');
  });

  jQuery('.question_checkbox').click(function(event) {

    question_id = jQuery(this).attr('id').substr(18);
    answer_id = 'a_' + question_id;
    jQuery('.answers').hide();
    jQuery('#' + answer_id).slideToggle('slow');

    if (!jQuery(this).attr('checked')) {
        name = 'answer_q_' + question_id;
        jQuery('p[name=' + name + ']').removeClass('selected');
        jQuery('#new_answers_' + question_id).removeClass('answer-selected');
    }
  });
}

// select or deselect an answer in 'show questions' lightbox for use
function addAnswerSelect()
{
  // deal with answers that are already available
  jQuery('.selectable_answer').click(function() {

  // detect toggle on current answer
  if (!jQuery(this).hasClass('answer_selected')) {

    // disable all previous answers if we select a new answer
    jQuery(this).parent().children('.selectable_answer').each(function(i, elm) {
    jQuery(elm).removeClass('answer_selected');
    });
  }

  // toggle current answer so we can deselect it
  jQuery(this).toggleClass('answer_selected');

  // if current item is selected, we can set the checkbox for this question
  // eg. we want to use this question
  var question_id = jQuery(this).attr('name').substr(9);

  //deselect the new answer checkbox for the current question
  jQuery('#' + 'new_answer_checkbox_' + question_id).attr('checked', '');

  if (jQuery(this).hasClass('answer_selected')) {
    jQuery('#question_checkbox_' + question_id).attr('value', question_id);
  } else {
    jQuery('#question_checkbox_' + question_id).attr('value', '');
  }
  });

  // deal with new answer box
  jQuery('.new_answer').click(function() {

  new_answer_id = jQuery(this).attr('id');
  question_id = new_answer_id.substr(12);

  jQuery('p[name=' + 'answer_q_' + question_id  + ']').removeClass('selected');
  jQuery(this).addClass('answer-selected');

  jQuery('#question_checkbox_' + question_id).attr('checked', 'checked');
  });


  jQuery('.new_answer_checkbox').click(function() {

  // disable all previous answers if we select a new answer
  jQuery('.selectable_answer').each(function(i, elm) {
    jQuery(elm).removeClass('answer_selected');
  });

  new_answer_id = jQuery(this).attr('id');
  question_id = new_answer_id.substr(20);
  //jQuery('#question_checkbox_' + question_id).attr('value', question_id);
  //alert(question_id);
  });
}

/**
 *  binds an onclick event to the close button and overlay of the colorbox.
 *  The event reloads the parent.
 */
function reloadParent()
{
  jQuery('#cboxClose, #cboxOverlay').click(function(){
    // do it like this to prevent reposts
    window.parent.location = window.parent.location;
  });
}

// if the window is unloaded, reload the parent
function reloadParentOnUnload()
{
  jQuery(document).ready(function(){
    jQuery(window).bind('unload', function() {
        window.parent.location = window.parent.location;
    });
  });
}

function deleteTocItemStudyUnit(del_tocitem_studyunit_url, studyunit_id) {

  jQuery('.delete_tocitem_studyunit').die();
  jQuery('.delete_tocitem_studyunit').live('click', function(event) {
    // determine correct source ID (strip out the 'source_' prefix)
    id = jQuery(this).attr('id');
    id = id.substring(10, id.length);

    // delete item from studyunit table and alter right screen column
    url = del_tocitem_studyunit_url + '?studyunit_id=' + studyunit_id + '&tocitem_studyunit_id=' + id;

    jQuery.ajax({
      url: url,
      success: function(html) {
        jQuery('#studyunit').empty();
        jQuery('#studyunit').append(html);
      }
    });

    // also refresh the TOC tree when we removed an item from our study unit
    // we want to see the checkbox unchecked
    toc_tree_url = 'studyunit/toctree';
    id = jQuery(this).attr('rel');
    url = toc_tree_url + '?source_id=' + id + '&studyunit_id=' + studyunit_id;

    var html = jQuery.ajax({
      url: url,
      async: false
    }).responseText;

    jQuery('#toctree').html(html);
    showTocTree();

    return false;
  });
}

function carouselSourceToc(toc_tree_url, studyunit_id)
{
  jQuery('a.carousel_source').die();
  jQuery('a.carousel_source').live('click', function(event) {

    startSpinner('spinner_caroussel');

    // reset all previously selected a.selecteds
    jQuery('#source-carousel li a').each(function(elm) {
      jQuery(this).removeClass('selected');
    });
    // make this item selected
    jQuery(this).addClass('selected');

    // determine correct source ID (strip out the 'source_' prefix)
    id = jQuery(this).attr('id');
    id = id.substring(7, id.length);

    url = toc_tree_url + '?source_id=' + id + '&studyunit_id=' + studyunit_id;

    var html = jQuery.ajax({
      url: url,
      async: false
    }).responseText;

    jQuery('#toctree').html(html);

    stopSpinner('spinner_caroussel');
    showTocTree();
  });
}

// rotate through our sources
function addSourceCarousel()
{
  // firstly, remember first item
  // we need this because the carousel screws up the order
  var first_item = jQuery('#source-carousel li a:first');

  jQuery('#source-carousel').jCarouselLite ({
    circular: true,
    visible: 6,
    btnPrev: '#caroussel_prev',
    btnNext: '#caroussel_next'
  });
}

/**
 *  toggle between isbn and user input when adding a source.
 */
function toggleAddSource(enable, disable)
{
  jQuery('#toggle' + enable).attr('checked', 'checked');
  jQuery('#toggle' + disable).removeAttr('checked');

  // enable
  jQuery('#opt' + enable + ' :input').each(function(i, element) {
    jQuery(element).removeAttr('disabled').removeClass('disabled');
  });

  // disable
  jQuery('#opt' + disable + ' :input').each(function(i, element) {
    jQuery(element).attr('disabled', 'disabled').addClass('disabled');
  });
}

// append blank TOC fields to our tree
function addBlankTocFields(clicked, dummies, currentTocNo)
{
  // determine next toc_no position
  // for legacy reasons this can be on a href or a class
  var toc_no = jQuery(clicked).attr('href');

  if (typeof toc_no == 'undefined') {
    toc_no = jQuery(clicked).attr('class');
    toc_no = toc_no.match("toc_([0-9.]+).");
    toc_no = toc_no[1];
  }

  // strip off our anchor
  toc_no = toc_no.replace(/^.*#/, '');

  var parts = toc_no.split('.');
  var last = parseInt(parts.pop(), 10) + 1;
  var base = parts.join('.');

  // check if the new inputs have to get the class current
  var currentClass = '';
  if (currentTocNo == base){
  	currentClass = ' current ';
  }
  
  // if we actually have a base node, we append the missing '.'
  if (base !== '') {
    base += '.';
  }

  // append N blank items
  var output = '';
  var new_toc_no;
  var i;

  // our 'template' for new items
  var template = '<li class="closed toc_REPLACEME. CSS">' +
  'HITAREA REPLACEME ' +
  '<input id="toc_checkbox_REPLACEID" class="toc_checkbox" type="checkbox" value="REPLACEME" name="toc_checkbox[]" />' +
  '<input id="toc_description_REPLACEID" class="text toc_description '+ currentClass +'" type="text" value="" name="toc_description[REPLACEME]" /> ' +
  'MORELINK ' +
  '</li>';

  for (i = last; i < (last + 5); i++) {
    new_toc_no = base + i;
    
    // in the ID we don't want a . so replace it with _ 
    new_toc_no_id = new_toc_no.replace(/\./g,'_');

    // replace all correct toc_no
    temptemplate = template.replace(/REPLACEME/g, new_toc_no);
    output += temptemplate.replace(/REPLACEID/g, new_toc_no_id);

    // also replace extra CSS and HTML (last node only)
    if (i == (last + 5) - 1) {
      output = output.replace('CSS', 'expandable lastExpandable');
      output = output.replace('HITAREA', '<div class="dummy hitarea -hitarea closed-hitarea toc_' + new_toc_no + '.0 expandable-hitarea lastExpandable-hitarea "/>');
      output = output.replace('MORELINK', '<br /><a href="#' + new_toc_no + '" class="link">' + __('More') + '</a>');

    } else {

      output = output.replace('CSS', 'expandable');
      output = output.replace('HITAREA', '<div class="dummy hitarea -hitarea closed-hitarea toc_' + new_toc_no + '.0 expandable-hitarea "/>');
      output = output.replace('MORELINK', '');
    }
  }

  var parent = jQuery(clicked).parent();

  // append our new fields to our element
  if (dummies == true) {
  	
  	if (jQuery(clicked).hasClass('dummy')){
  		// only add dummies the first time it's clicked.

	    // move the 'more' link to the correct place
	    var morelink = jQuery(parent).children('a.link');
	    jQuery(morelink).remove();
	    jQuery(parent).append('<ul>' + output + '</ul>').append(morelink);
	}
  } else {
    jQuery(parent).after(output);
  }
  
  // remove 'last' class and 'more' link
  if (jQuery(clicked).hasClass('link')) {
    jQuery(parent).children('div').removeClass('lastExpandable-hitarea'); // it's not the last anymore
    jQuery(parent).children('div').addClass('expandable-hitarea'); // make it expendable again
    jQuery(parent).removeClass('last').removeClass('lastExpandable');
    jQuery(clicked).remove();
  } else {
    jQuery(clicked).removeClass('lastExpandable-hitarea').removeClass('dummy');
  }
}

// adds the 'more' links for the TOC step
function toctreeAddMoreLinks(disable) {

  if (!disable) {

    var morelink;

    // append to open items that are last in the tree
    jQuery('#navigation li').each(function(i, elm) {

      var classes = jQuery(elm).attr('class');

      // detect last items
      if (classes.indexOf('lastExpandable') != -1 || classes.indexOf('lastCollapsable') != -1 || classes.indexOf('last') != -1) {

        var toc_no = classes.match("toc_([0-9.]+).");
        toc_no = toc_no[1];

        // strip off last dot
        toc_no = toc_no.substring(0, toc_no.length - 1);
        morelink = '<br /><a href="#' + toc_no + '" class="link">' + __('More') + '</a>';
        jQuery(elm).append(morelink);
      }
    });
  }
}

//see http://docs.jquery.com/Frequently_Asked_Questions#How_do_I_select_an_element_that_has_weird_characters_in_its_ID.3F
function escape_id(myid)  { return '#'+myid.replace(/:/g,"\\:").replace(/\./g,"\\.");}

function checkTocitems() {

  jQuery('.toc_description').live('click', function() {

    toc_description_id = jQuery(this).attr('id');
    toc_no = toc_description_id.substr(16);
    toc_checkbox_id = 'toc_checkbox_' + toc_no;
    toc_checkbox_id = escape_id(toc_checkbox_id);
    jQuery(toc_checkbox_id).attr('checked', 'checked');
  });
}

// Toc tree function that only posts changed inputs
// It posts 'descriptions', selected checkboxes and unselected checkboxes.
function handleTocUpdate(deletetocitemstudyunit_url, redirect)
{
  var postDataCheckboxes   = new Array(); // holds the state of the changed checkbox
  var postData             = []; // data to be posted

  jQuery('#navigation').die();

  // bind keyup event to description fields
  // onchange is not supported in jQuery 1.3 Live
  jQuery('#navigation input.toc_description').live('keyup', function (e) {

    // if the description has changed we want to use it, so also add the checkbox.
    id = jQuery(this).attr('id');
    id = id.replace('toc_description_','');
    id = id.replace(/_/g, '.');

	// add the corresponding checkbox
    postDataCheckboxes[id] = 1;

    // also visually select the corresponding selectbox
    jQuery('#toc_checkbox_'+id.replace(/\./g,'_')).attr('checked', 'checked');
  });
  
  // bind onclick event to description fields
  jQuery('#navigation input.toc_description').live('click', function() {
    
    // also add the checkbox.
  	id = jQuery(this).attr('id');
    id = id.replace('toc_description_','');
    id = id.replace(/_/g, '.');
    
    // add the corresponding checkbox
    postDataCheckboxes[id] = 1;
    
    // also visually select the corresponding selectbox
    jQuery('#toc_checkbox_'+id.replace(/\./g,'_')).attr('checked', 'checked');
  });

  // bind click event to checkboxes for onClick(live can only be binded to one event)
  jQuery('#navigation input.toc_checkbox').die();
  jQuery('#navigation input.toc_checkbox').live('click', function (e) { // onchange is not supported in jQuery 1.3 Live

    if (typeof jQuery(this).attr('name') !== 'undefined') {
      if (jQuery(this).attr('value') !== ''){
        id = jQuery(this).attr('id');
        id = id.replace('toc_checkbox_','');

        if (jQuery(this).attr('checked')) {
          // turn it on

          // add checkbox to array if it's description is not watermarked
          if (jQuery('#toc_description_'+id.replace(/\./g,'_')).hasClass('watermark')){
            return false;
          } else {
            postDataCheckboxes[jQuery(this).attr('value')] = 1;
          }

        } else {
          // turn it off
          postDataCheckboxes[jQuery(this).attr('value')] = 0;
        }
      }
      }
  });

  // bind click event to checkboxes for onKeyup(live can only be binded to one event)
  jQuery('#navigation input.toc_checkbox').live('keyup', function (e) { // onchange is not supported in jQuery 1.3 Live
    if (typeof jQuery(this).attr('name') !== 'undefined') {
      if (jQuery(this).attr('value') !== ''){
        id = jQuery(this).attr('id');
        id = id.replace('toc_checkbox_','');

        if (jQuery(this).attr('checked')) {
          // turn it on

          // add checkbox to array if it's description is not watermarked
          if (jQuery('#toc_description_'+id.replace(/\./g,'_')).hasClass('watermark')){
            return false;
          } else {
            postDataCheckboxes[jQuery(this).attr('value')] = 1;
          }

        } else {
          // turn it off
          postDataCheckboxes[jQuery(this).attr('value')] = 0;
        }
      }
      }
  });

  // bind a click to the save button
  // with the existing postData and add some other fields to the postData
  jQuery('#save_toc_items_btn').die('click'); // specifically die the click event!!
  jQuery('#save_toc_items_btn').live('click', function(event) {
    event.preventDefault();

    // build the postData
    for ( var i in postDataCheckboxes){
    
      // add descriptions to postData if it's active and doesn't have the watermark class
      if (postDataCheckboxes[i] == 1){
      	  if (!jQuery('#toc_description_'+i.replace(/\./g,'_')).hasClass('watermark')){
		      var tmp = {};
		      tmp.name = 'toc_description['+i+']';
		      tmp.value = jQuery('#toc_description_'+i.replace(/\./g,'_')).val();
		      postData.push(tmp);
		  }
	  }

      // add (un)selected checkboxes to postData
      var tmp = {};

      if (postDataCheckboxes[i] == 1){
        tmp.name = 'toc_checkbox[]';
      } else {
        tmp.name = 'toc_checkbox_unselected[]';
      }
      tmp.value = i;
      postData.push(tmp);
    }

    // add hidden inputs to postData
    jQuery('#toc_items_form input[type=hidden]').each(function(i, el){
      var tmp = {};
      tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();

      // store studyunit_id to refresh the studyunit tab
      if (tmp.name == 'studyunit_id') {
        studyunit_id = tmp.value;
      }

      if (tmp.value !== '') {
        postData.push(tmp);
      }
    });

    // include the caller parameter in the post data
    // the action on the server won't return an updated
    // toctree if we're in the study flow because
    // this isn't displayed in the flow (save and close lightbox)
    if (redirect !== '') {
      obj = {};
      obj.name = 'caller';
      obj.value = 'study_flow';
      postData.push(obj);
    }
    
    // if a lot of items are changed, show a warning. postData is always at least 6 long.
    if (postData.length > 21){
		jQuery('#tocprogress').show();
	}

      // AJAX submit our formdata, save our updated TOC and return a new TOC tree
    jQuery.post(jQuery('#toc_items_form').attr('action'), postData, function(data) {
      stopSpinner('spinner_savetoc');

      // if we're in the studyflow (we have a redirect)
      // we want to close our TOC tree and redirect the user to the next step
      if (redirect !== '') {
        jQuery('#save_toc_items_btn').removeAttr('disabled');

        jQuery.get(redirect, { time: new Date().getTime()}, function(data) {
          parent.jQuery('#studyContainer').html(data);
          parent.jQuery.fn.colorbox.close();
        });
        return false;

      } else {
        jQuery('#studyContainer').html(data);
        jQuery('#save_toc_items_btn').removeAttr('disabled');

        // refresh studyunit tab
        jQuery.get(deletetocitemstudyunit_url + '?studyunit_id=' + studyunit_id, { time: new Date().getTime()} ,function(data){
          jQuery('#studyunit').html(data);
          jQuery('#items').sortable();
        });

        stopSpinner();
        return false;
      }
    });
    });
}

function getTocIndex(start_url){
  jQuery.get(start_url, { time: new Date().getTime()} , function(data){
    jQuery('#studyContainer').html(data);
  });

  return false;
}

/**
 *  Delete a Toc_Item
 *
 *  tocItemId = id of the tocItem in the database
 *  studyUnitId = id of node in the mindmap
 */
function deleteTocItem(tocItemId, studyUnitId)
{
  startSpinner();

  jQuery.post('toc/del', { tocitem_id: tocItemId},
    function(data) {
      stopSpinner();
      jQuery('#studyContainer').html(data);
      removeNode(studyUnitId);

      //save the xml to the filesystem
      saveXml();
    });
}

/*********** StudyUnitLanguage **************/

/**
 *  Add listener to the button to set the StudyUnitLanguage
 */
function saveStudyUnitLanguage()
{ 
  jQuery(document).ready(function() {
  	// show the save button when the page is loaded to prevent opening the 'Expectation' step in the popup.
  	jQuery('#save_language_btn').show();
  });
       
  jQuery('#save_language_btn').die();
  jQuery('#save_language_btn').live('click', function(event){

    jQuery('#save_language_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];
    jQuery('#save_language_form :input').each(function(i, el){
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);
    });

    jQuery.post(jQuery('#save_language_form').attr('action'), postData, function(data) {
        // close colorbox
        parent.jQuery.fn.colorbox.close();

        parent.jQuery('#studyContainer').html(data);
      });

    return false;
  });
}

/*********** Expectation **************/

/**
 *  Add listener to the button to add a new Expectation
 */
function saveExpectation()
{
  jQuery('#save_expectation_btn').die();
  jQuery('#save_expectation_btn').live('click', function(event){

    jQuery('#save_expectation_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];
    var expectationText = '';

    jQuery('#add_expectation_form :input').each(function(i, el) {
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);

        // get the text for the expectation cloud.
        if (this.type == 'textarea') {
          expectationText = jQuery(el).val();
        }
    });

    jQuery.post(jQuery('#add_expectation_form').attr('action'), postData,
      function(data) {

        // first get the info for the expectation cloud.
        showExpectation(jQuery('#tocItemStudyUnitId').val(), expectationText);

        stopSpinner();

        // remove handler
        jQuery('#save_expectation_btn').die('click');

        // insert the new html
        jQuery('#studyContainer').html(data);
      });

    return false;
  });
}

/*********** Relation **************/

/**
 *  Add listener to the button to add a new Relation
 */
function saveRelation()
{
  jQuery('#save_relation_btn').die();
  jQuery('#save_relation_btn').live('click', function(event){

    jQuery('#save_relation_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];
    jQuery('#add_relation_form :input').each(function(i, el){
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);
    });

    jQuery.post(jQuery('#add_relation_form').attr('action'), postData,
      function(data){

        stopSpinner();

        // remove handler
        jQuery('#save_expectation_btn').die('click');

        jQuery('#studyContainer').html(data);
      });

    return false;
  });
}

/*********** Question **************/

/**
 *  Add listener to the button to add a new Question/Answer
 */
function saveQuestion()
{
  //jQuery('#save_question_btn').die();
  //jQuery('#save_question_btn').live('click', function(event){

    jQuery('#save_question_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];
    jQuery('#add_question_form :input').each(function(i, el){
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);
    });

    jQuery.post(jQuery('#add_question_form').attr('action'), postData,
      function(data) {

        stopSpinner();

        // remove handler
        jQuery('#save_question_btn').die('click');

        jQuery('#studyContainer').html(data);
      });

    return false;
  //});
}

function checkQuestion(url)
{
  var content = true;
  jQuery('#add_question_form textarea').each(function(i, el) {
    if (jQuery(el).val() !== '') {
      content = false;
    }
  });

  if (!content) {
    jQuery('#questiondialog').dialog('open');
  } else {
    saveXml();
    ajaxGet(url, 'studyContainer'); removeUpdateLinks(); saveXml();
  }

  return false;
}

function checkQuestionDialog(url)
{
  var yes = __('Yes');
  var cancel = __('Cancel');

  var conf, buttons;

  conf = [
    {
      name: __('Yes'),
      callback: function () {
        ajaxGet(url, 'studyContainer'); removeUpdateLinks(); saveXml();
        jQuery(this).dialog('close');
      }
    },
    {
      name: __('Cancel'),
      callback: function() {
        jQuery(this).dialog('close');
      }
    }
  ];

  buttons = {};

  for (var i = 0; i < conf.length; i++) {
    buttons[conf[i].name] = conf[i].callback;
  }

  jQuery('#questiondialog').dialog({
    autoOpen: false,
    bgiframe: true,
    resizable: false,
    height: 140,
    modal: true,
    overlay: {
      backgroundColor: '#000',
      opacity: 0.5
    },
    buttons: buttons
  });
}

/*********** Note **************/

/**
 *  save Note (belonging to TocItem_StudyUnit)
 */
function saveNote()
{
    jQuery('#save_note_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];
    var expectationText = '';

    jQuery('#add_note_form :input').each(function(i, el) {
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);
    });

    jQuery.post(jQuery('#add_note_form').attr('action'), postData,
      function(data) {

        stopSpinner();

        // remove handler
        jQuery('#save_note_btn').die('click');

        // insert the new html
        jQuery('#studyContainer').html(data);
      });

    return false;
}

function dontSplit()
{
  jQuery.get('expectation', { time: new Date().getTime()} , function(data){
      jQuery('#studyContainer').html(data);
    });
}

/**
 *  Create words that are clickable
 */
function createKeywords(question_data, answer_data)
{
  // unbind any previous handlers we might have on the keywords
  // we can't do this in the plugin because we need the handler twice
  // and a die(); live(); combo will result in events for the last element only
  jQuery('#question').find('span').die();
  jQuery('#answer').find('span').die();

  jQuery('#question').keywords({}, question_data);
  jQuery('#answer').keywords({}, answer_data);
}

/**
 *  Create words that are clickable in the comarequestions step
 */
function createCompareQuestionsKeywords()
{
  // unbind any previous handlers we might have on the keywords
  // we can't do this in the plugin because we need the handler twice
  // and a die(); live(); combo will result in events for the last element only
  jQuery('#keywords').find('span').die();

  jQuery('#keywords').keywords({'link':false});
}

/**
 *
 */
function saveKeywords()
{
  jQuery('#save_keywords_btn').die();
  jQuery('#save_keywords_btn').live('click', function(event){

    event.preventDefault();

    jQuery('#save_keywords_btn').attr('disabled', 'disabled');
    startSpinner();

    var postData = [];

    var tmp = {};
    tmp.name = 'tocitemquestion_id';
    tmp.value = jQuery('#question_id').val();
    postData.push(tmp);

    tmp = {};
    tmp.name = 'tocitemanswer_id';
    tmp.value = jQuery('#answer_id').val();
    postData.push(tmp);

    tmp = {};
    tmp.name = 'question_keywords';
    tmp.value = jQuery('#question').getkeywords();
    postData.push(tmp);

    tmp = {};
    tmp.name = 'answer_keywords';
    tmp.value = jQuery('#answer').getkeywords();
    postData.push(tmp);

    jQuery.post(jQuery('#save_keyword_form').attr('action'), postData,
      function(data) {

        stopSpinner();

        // remove handler
        jQuery('#save_keywords_btn').die('click');

        jQuery('#studyContainer').html(data);
      });

    return false;
  });
}

function keywordToMindmap(elementId)
{
  jQuery('#keywords li').click(function(event) {

    jQuery('#keyworderror').hide();

    //var selectedNode = getNode();
    var selectedNode = thisMovie('mindmap').getNode();

    if (selectedNode) {

      word = this.innerHTML;
      keywordId = 'K_' + this.id;

      addNode(keywordId, selectedNode.id, word.replace(/\\/, ''));
      jQuery(this).remove();

      saveXml();
    } else {
      jQuery('#keyworderror').show();
    }
  });
}

/**
 *  Hides keywords in an answer, and shows them when given the right answer.
 */
function createRehearsal()
{
  // hide the keywords
  jQuery('#rehearsal').rehearsals(data);
  // check the input of the user
  jQuery('#keyword').checkInput(data, jQuery('#rehearsal'), finishedPos);

  jQuery('#rehearsal').show();
}

function getHintRehearsal()
{
  // first get the keyword which are still hidden.
  // in the array 'finishedPos' are the keywords are that are already filled in.
  if (typeof data.keywords != 'undefined' && jQuery('#keywordsLeft').val() > 0) {
    var whatsLeft = [];

    for (var i = 0; i < data.keywords.length; i++) {

      if (jQuery.inArray(data.keywords[i].pos, finishedPos) == -1){
        whatsLeft.push(data.keywords[i]);
      }
    }

    var randHint = whatsLeft[Math.floor(Math.random() * whatsLeft.length)];

    // show keyword
    jQuery('#rehearsal').html(showKeyword(jQuery('#rehearsal').text(),randHint.pos, randHint.word));

    // add effect to the keyword
    jQuery('#k_' + randHint.pos).fadeIn().fadeOut().fadeIn().fadeOut().fadeIn();

    // lower the number of keywords left to fill in
    if (jQuery('#keywordsLeft').val() > 1) {
      jQuery('#keywordsLeft').val(jQuery('#keywordsLeft').val() - 1);
    } else {
      jQuery('#keywordsLeft').val(0);
    }

    // add this word to the finished positions array
    finishedPos.push(randHint.pos);

    if (jQuery('#keywordsLeft').val() == 0) {
      jQuery('#getHintButton').hide();
      jQuery('#giveUpButton').hide();
      jQuery('#inputContainer').hide();
      jQuery('#wrongButton').show();
    }
  }
}

function giveUpRehearsal()
{
  if (typeof data.keywords != 'undefined') {
    for (var i = 0; i < data.keywords.length; i++) {

      if (jQuery.inArray(data.keywords[i].pos, finishedPos) == -1) {
        // show keyword

        jQuery('#rehearsal').html(showKeyword(jQuery('#rehearsal').text(), data.keywords[i].pos, data.keywords[i].word));

        // lower the number of keywords left to fill in.
        if (jQuery('#keywordsLeft').val() > 1) {
          jQuery('#keywordsLeft').val(jQuery('#keywordsLeft').val() - 1);
        } else {
          jQuery('#keywordsLeft').val(0);
        }

        // add this word to the finished positions array
        finishedPos.push(data.keywords[i].pos);
      }
    }

    if (jQuery('#keywordsLeft').val() == 0) {
      jQuery('#getHintButton').hide();
      jQuery('#giveUpButton').hide();
      jQuery('#inputContainer').hide();
      jQuery('#wrongButton').show();
    }
  }
}

// if a user presses on Enter when in the ISBN field, the form gets submitted
function handleISBNSubmit()
{
  jQuery('#isbn_input').keypress(function(e) {
    if (e.which == 13) {
      jQuery('#isbnsubmit').trigger('click');
      e.preventDefault();
    }
  });
}

/**
 * processes the Json when a search for Source is done.
 *
 */
function processSourceSearch()
{
  // reset all variables
  jQuery('#id').val('');
  jQuery('#isbn_name').val('');
  jQuery('#isbn').val('');
  jQuery('#isbn13').val('');
  jQuery('#isbn_author').val('');
  jQuery('#isbn_version').val('');
  jQuery('#image').val('');
  jQuery('#cover').attr('src', 'images/default_cover.jpg');
  jQuery('#isbnsource-submit').addClass('hide');
  jQuery('#textTitle').html('');
  jQuery('#textAuthor').html('');
  jQuery('#textVersion').html('');
  
  // hide notices
  jQuery('.success').addClass('hide');
  jQuery('.error').addClass('hide');

  // if we found a non-empty result in div#ajax_result, we can display data
  if (jQuery('#ajax_result').html() != '[]' ) {

    var data = eval('(' + jQuery('#ajax_result').html() + ')');

    if (data.name) {
      jQuery('#id').val(data.id);
      jQuery('#isbnsource-submit').removeClass('hide');
    } else {
      jQuery('#id').val('');
      jQuery('#cover').attr('src', 'images/default_cover.jpg');
      jQuery('#isbnsource-submit').addClass('hide');
    }

    // fill spans
    var shorttitle = data.name;
    var originaltitle = data.name;
    if (shorttitle.length > 80) {
      shorttitle = shorttitle.substr(0, 76) + ' ...';
    }

    jQuery('#textTitle').html(shorttitle);
    jQuery('#textTitle').attr({title : originaltitle});
    jQuery('#textAuthor').html(data.author_text);
    jQuery('#textVersion').html(data.publisher_text);

    jQuery('#isbn').val(data.isbn);
    jQuery('#isbn13').val(data.isbn13);

    // fill hidden fields when searched for ISBN
    jQuery('#isbn_name').val(data.name);
    jQuery('#isbn_author').val(data.author_text);
    jQuery('#isbn_version').val(data.publisher_text);

    if (data.cover !== '') {
      jQuery('#cover').attr('src', data.cover);
      jQuery('#image').val(data.cover);
    }

  } else {
    // no data found; reset everything and display default cover image
    jQuery('#id').val('');
    jQuery('#cover').attr('src', 'images/default_cover.jpg');
    jQuery('#image').val('');
    jQuery('#isbnsource-submit').addClass('hide');
    
    // add notice
	jQuery('h1').before('<p class="error">' + __('ISBN Not found') + '</p>');
  }
}


function addSource(add_source_url, subject_id, source_url, subject_sources_url)
{
  jQuery('#isbn-searchform').submit(function(event) {

    event.preventDefault();
	
	// hide notice
	jQuery('.success').addClass('hide');

    // make sure our radio button is set
     if (jQuery('#toggle0').attr('checked') != true) {
      return;
     }

    startSpinner();

    source_url += '?subject_id=' + subject_id;
    subject_sources_url += '?subject_id=' + subject_id;

    add_source_url += '?subject_id=' + subject_id;
    add_source_url += '&search=' + jQuery('#isbn').val() + '&isbn13=' + jQuery('#isbn13').val();

    jQuery.get(add_source_url, function(data) {
    
      // add notice
	  jQuery('h1').before('<p class="success">'+data+'</p>');
	  
      jQuery.get(subject_sources_url, function(data) {
        jQuery('#subjectsources').html(data);        
      });
    });

    stopSpinner();
  });
}


// Handle language switch on the top right
function changeLanguage()
{

  // because chrome2 doesn't properly submit the form we have to hack it a bit
  jQuery('#lang').submit(function(event) {

    // chrome(2) specific hack, because it doesn't want to properly submit our form (submit action gets triggered but not executed)
    if ((navigator.userAgent.toLowerCase().indexOf('chrome') > -1)) {


      var location = window.location.href;

      var target = jQuery('#language').val();
      var source = (target == 'en' ? '/nl/' : '/en/');
      target = '/' + target + '/';

      location = location.replace(source, target);
      window.location=location;
      return false;
    }
  });

  jQuery('#language').change(function() {
    jQuery(this).closest('form').submit();
  });
}

/*
 * START AUTOCOMPLETE FUNCTIONS
 */

// reset institution and degree if we change the country on the profile/confirmation page
function resetAutocompleteProfile()
{
  jQuery('#profile-country').change(function() {
    jQuery('#profile-institution').val('').flushCache();
    jQuery('#profile-education-level').val('').flushCache();
  });
}

// autocomplete the degrees (user screen)
function ajaxAutocompleteDegrees(url)
{
  jQuery('#profile-education-level').autocomplete(url, {
    matchContains: true,
    extraParams: {
      country: function() { return jQuery('#profile-country').val(); }
    }
  });
}

// autocomplete the institutions (user screen)
function ajaxAutocompleteInstitutions(url)
{
  jQuery('#profile-institution').autocomplete(url, {
    matchContains: true,
    extraParams: {
      country: function() { return jQuery('#profile-country').val(); }
    }
  });
}

// autocomplete the studies (user screen)
function ajaxAutocompleteStudies(url)
{
  jQuery('#profile-study1').autocomplete(url, {
    matchContains: true,
    extraParams: {
      institution: function() { return jQuery('#profile-institution').val(); }
    }
  });

  jQuery('#profile-study2').autocomplete(url, {
    matchContains: true,
    extraParams: {
      institution: function() { return jQuery('#profile-institution').val(); }
    }
  });

  jQuery('#profile-study3').autocomplete(url, {
    matchContains: true,
    extraParams: {
      institution: function() { return jQuery('#profile-institution').val(); }
    }
  });
}

// autocomplete the book titles
function ajaxAutocompleteBooktitles(url)
{
  jQuery('#name').autocomplete(url, {matchContains: true});
}

// autocomplete the book authors
function ajaxAutocompleteBookauthors(url)
{
  jQuery('#author').autocomplete(url, {
    matchContains: true,
    extraParams: {
      title: function() { return jQuery('#name').val(); }
    }
  });
}

// autocomplete the book versions
function ajaxAutocompleteBookversions(url)
{
  jQuery('#version').autocomplete(url, {
    matchContains: true,
    extraParams: {
      title: function() { return jQuery('#name').val(); }
    }
  });
}

// autocomplete the TOC suggestions
function ajaxAutocompleteTocSuggestions(url)
{
  var toc_no;
  var source_id = jQuery('input[name=source_id]').val();

  // add autocomplete to all editable TOC nodes
  jQuery('#navigation li input.toc_description').not('.disabled').each(function() {

    toc_no = jQuery(this).siblings('input:checkbox').val();

    jQuery(this).autocomplete(url, {
      matchContains: true,
      extraParams: {
        source_id: source_id,
        toc_no: toc_no
      }
    });
  });
}


/*
 * END AUTOCOMPLETE FUNCTIONS
 */


// retrieve base href, is used in the movie players
function getBaseHref()
{
    var thebase = document.getElementsByTagName('base');
    return thebase[0].href;
}

// sort the items in the study unit
function storeStudyUnitOrder(studyunit_url, subject_id, studyunit_id )
{
  jQuery('#items').sortable();

  jQuery('#return').click(function(event) {

    startSpinner();

    var serialized_items = jQuery('#items').sortable('serialize');

    url =
      studyunit_url +
      '?studyunit_id=' + studyunit_id +
      '&subject_id=' + subject_id;

    jQuery.ajax({
      type: 'POST',
      url: url,
      data: serialized_items
    });

    if (jQuery('p.success').length) {
      jQuery('p.success').fadeOut().wrap(__('Settings saved')).fadeIn(1000);
    } else {
      jQuery('div#msg').wrap('<p class="success hide">' + __('Settings saved') + '</p>');
      jQuery('p.success').fadeIn(1000);
    }

    stopSpinner();
    event.preventDefault();
  });
}

// sort the items in the study unit
function storeStudyUnitItemOrder(studyunit_url, subject_id, studyunit_id )
{
  jQuery('#items').sortable();

  jQuery('#return').click(function(event) {

    startSpinner();

    var serialized_items = jQuery('#items').sortable('serialize');

    url =
      studyunit_url +
      '?studyunit_id=' + studyunit_id +
      '&subject_id=' + subject_id;

    jQuery.ajax({
      type: 'POST',
      url: url,
      data: serialized_items
    });


    stopSpinner();
    event.preventDefault();

    // trigger the hidden href to start studying in fullscreen mode
    window.location = jQuery('#startstudybutton').attr('href');
  });
}

// display the intro movie on the homepage
function displayMovie(image, video)
{
    var basehref = getBaseHref();
    var flashvars = {};
    var params = {};

    params.allowfullscreen = 'true';
    params.allowscriptaccess = 'always';
    params.wmode = 'transparent';

    if (image != '') {
      flashvars.image = basehref + image;
    }

    flashvars.file = basehref + video;

    flashvars.backcolor = 'e6e6e6';
    flashvars.screencolor = 'ffffff';
    flashvars.controlbar = 'over';

    swfobject.embedSWF('swf/player.swf', 'movie', '465', '261', '9.0.0', 'swf/expressInstall.swf', flashvars, params);
}

// helper function for the timer bar
function leadingZero(n) {
  return (n !== null && n < 10 && n >= 0 ? '0' : '') + n;
}

// display timer bar on study page
function startTimer(studyinterval, pauseinterval, stopinterval, concentrationinterval, skip_studytips)
{
  // times in seconds
  var inactivity_counter = 0;

  // appropriately set pause and stopinterval
  pauseinterval += studyinterval;

  // detect inactivity with keyups and mousedowns
  jQuery(document).keyup(function(event) {
    inactivity_counter = 0;
  });

  jQuery(document).mousedown(function(event) {
    inactivity_counter = 0;
  });

  // display progress bar
  jQuery('#progressbar').progressbar();

  // init time interval bar below
  var centerminutes = leadingZero(Math.floor((stopinterval / 2) / 60));
  var stopminutes = leadingZero(Math.floor(stopinterval / 60));

  // display start, median and end time below the timer bar
  var intervals = '<span class="left">0 min.</span>' +
                  '<span class="center">' + centerminutes + ' min.</span>' +
                  '<span class="right">' + stopminutes + ' min.</span>';

  jQuery('#timerintervals').html(intervals);

  // add timer to progressbar
  jQuery('#progressbar').everyTime(1000, 'timer', function (i) {

      // detect inactivity and notify the user
      // and don't display these notifications in pause mode
      if (inactivity_counter > 0 && (inactivity_counter % concentrationinterval === 0) &&
          (i < studyinterval || i > pauseinterval)) {

          concentrationNotification(skip_studytips);
      }
      inactivity_counter += 1;

      if (i == studyinterval) {
          pauseStudy();
      }
      if (i == pauseinterval) {

          // unblock pause mode if necessary
          jQuery.unblockUI();

          // offer user option to go to rehearsal mode
          rehearseStudy();
      }

      // keep counter running until the end
      if (i <= stopinterval) {
          var value = Math.round((i * 100) / stopinterval );
          jQuery('#progressbar').progressbar('option', 'value', value);

          // calculate time display
          var elapsed = '';

          var hours = leadingZero(Math.floor(i / 3600));
          var minutes = leadingZero(Math.floor(i / 60));
          var seconds = leadingZero(i % 60);

          // display hours, if we have 1 hour or more
          if (hours > 1) {
            elapsed += hours + ':';
          }
          // display minutes and seconds
          elapsed += minutes + ':' + seconds;

          jQuery('#elapsed').html(elapsed );
      } else {
          jQuery.growlUI(__("Time's up!"), '<p>' + __('Your time is up...') + '</p>', 5000);
          jQuery(this).stopTime('timer');
      }
  });
}

// display fullscreen notification
function displayFullscreenNotification()
{
  var isNav = (navigator.appName == 'Netscape') ? 1 : 0;
  var isIE = (navigator.appName.indexOf('Microsoft') != -1) ? 1 : 0;
  var isChrome = (navigator.userAgent.toLowerCase().indexOf('chrome') > -1) ? 1 : 0;
  var isSafari = (!isChrome && navigator.userAgent.toLowerCase().indexOf('safari') > -1) ? 1 : 0;
  var isOldChrome = (isChrome && parseFloat(navigator.appVersion) == 1) ? 1 : 0;

  // notify the user that you can go to fullscreen mode with F11
  if ((isIE && document.documentElement.clientHeight < screen.height) ||
      (window.innerHeight < screen.height)) {

    if (!(isOldChrome || isSafari)) {
      jQuery.growlUI(__('Switch to fullscreen'), '<p>' + __('Please press F11 to study in fullscreen mode.') + '</p>', 5000);
    }
  }
}


// display the mindmap
function displayMindmap(saveUrl, xlmFileName, xmlPath)
{

    basehref = getBaseHref();

    var flashvars = {};
    var params = {};

    params.allowfullscreen = 'true';
    params.allowscriptaccess = 'always';
    params.wmode = 'transparent';

    flashvars.fvNodesXml = xmlPath; //'swf/nodes.xml';
    flashvars.fvSaveUrl = saveUrl;
    flashvars.fvXmlFilename = xlmFileName;
    flashvars.fvFontXml = 'swf/xml/font.xml';
    //flashvars.fvDebug = 'true';

    swfobject.embedSWF('swf/mindmap.swf', 'mindmap', '100%', '100%', '9.0.0', 'swf/expressInstall.swf', flashvars, params);
}

/**
 *  gets the dimension of the window. Returns an array with Width and Height
 */
function getWindowDimensions()
{
  var winWidth, winHeight, d = document;

  if (typeof window.innerWidth !== 'undefined') {
    winWidth = window.innerWidth;
    winHeight = window.innerHeight;
  } else if (d.documentElement && typeof d.documentElement.clientWidth !== 'undefined' && d.documentElement.clientWidth !== 0) {
    winWidth = d.documentElement.clientWidth;
    winHeight = d.documentElement.clientHeight;
  } else if (d.body && typeof d.body.clientWidth !== 'undefined') {
    winWidth = d.body.clientWidth;
    winHeight = d.body.clientHeight;
  }

  return [winWidth, winHeight];
}

// change the height of the mindmap and sidebar panel to their maximum size
function changeFullscreenBoxes()
{
  windowDimensions = getWindowDimensions();
  var availHeight = windowDimensions[1];

  // margin top (10) + navbar (41) + navbar margin (9) + sidebar_top (12) + sidebar_bottom (11) + margin bottom (10)
  var usedHeightPanel = 93 + 3;
  var usedHeightMindmap = 93 - 7 + 3;

  // resize to new max height, or (if not enough space), reset to minimum height
  // minimum usable height of sidepanel is 612px
  if (availHeight - usedHeightPanel >= 612) {
    jQuery('#sidepanel').height(availHeight - usedHeightPanel);
  } else {
    jQuery('#sidepanel').height(612);
  }

  // resize to new max height, or (if not enough space), reset to minimum height
  // minimum usable height of the mindmap is 618px
  if (availHeight - usedHeightMindmap >= 618) {
    jQuery('#map-container').height(availHeight - usedHeightMindmap);
  } else {
    jQuery('#map-container').height(618);
  }

  // remove left and right margins from the breadcrumb bar
  var breadcrumb_width = jQuery('div.map-wrapper').width() - 11 - 12;
  jQuery('div.breadCrumb').width(breadcrumb_width);
}


// do a resize of the mindmap and sidebar panel when the browser size changes
// also saves the mindmap XML on window close
function handleFullscreenResize()
{
  // when window is closed, we save the mindmap
  jQuery(window).unload(function() {
    saveXml();
  });

  jQuery(window).resize(function() {
    changeFullscreenBoxes();
  });
}

// toggle the wiki box
function toggleStudyPlugins()
{
  // handle study overlay close button
  jQuery('#wikiclose').die();
  jQuery('#wikiclose').bind('click', function (event) {
    jQuery('#study-options-tab').slideToggle();
    event.preventDefault();
  });

  jQuery('#study-options a').click(function (event) {
      var target = jQuery(this).attr('href');
      jQuery('#study-options-tab div.inner div').each(function() {
        jQuery(this).hide();
      });

      jQuery('#container_' + target).show();

      if (jQuery('#study-options-tab').css('display') == 'none'){
        jQuery('#study-options-tab').slideToggle();
      }

      event.preventDefault();
  });
}


// handle the translation plugin
function pluginTranslateWords()
{

  jQuery('#translation_source').watermark( __('Enter text to translate'));

  jQuery('#plugin_translation').submit(function (event) {

      // source and target language
      var sourceLang = jQuery('#plugin_translation select[name=from] option:selected').val() || 'en';
      var targetLang = jQuery('#plugin_translation select[name=to] option:selected').val() || 'nl';
      var callbacks = { start: function() { startSpinner('spinner_translate'); }, complete:   function() { stopSpinner('spinner_translate'); }, error:  function() { stopSpinner('spinner_translate'); } };

      jQuery('#translation_source').translate(sourceLang, targetLang, callbacks);
      event.preventDefault();
  });

}

function pluginWikiSearch()
{
  jQuery('#wikisearch_term').watermark(__('Enter term to search for'));

  jQuery('#wikisearch_explanation li a').die();
  jQuery('#wikisearch_explanation li a').live('click', function(event) {
    var term = jQuery(this).html();

    jQuery('#plugin_wikisearch input[name=prevterm]').val(jQuery('#wikisearch_term').val());
    jQuery('#wikisearch_term').val(term);
    jQuery('#plugin_wikisearch').trigger('submit');
    event.preventDefault();
  });

  jQuery('#plugin_wikisearch').submit(function (event) {

    startSpinner('spinner_wikisearch');
    jQuery('#wikisearch_explanation').hide();

    var searchterm =jQuery('#wikisearch_term').val();
    var language = jQuery('#plugin_wikisearch input[name=language]').val();
    var basehref = getBaseHref();

    jQuery.get(basehref + '/searchwiki.php', {lang: language, searchterm: searchterm, time: new Date().getTime()}, function(data) {

      var prevterm = jQuery('#plugin_wikisearch input[name=prevterm]').val();
      if (prevterm !== '') {

        data += '<br /><br /><li>Back to <a class="wikiterm" href="' + prevterm +'">' + prevterm + '</a></li>';
        jQuery('#plugin_wikisearch input[name=prevterm]').val('');
      }

      jQuery('#wikisearch_explanation').html(data).slideToggle();
      stopSpinner('spinner_wikisearch');
    });
    event.preventDefault();
  });
}

// handle submit of notepad entries
function pluginNotepad()
{
  jQuery('#save_notepad_btn').die();
  jQuery('#save_notepad_btn').live('click', function(event) {

    event.preventDefault();

    jQuery('#save_notepad_btn').attr('disabled', 'disabled');
    startSpinner('spinner_notepad');

    var postData = [];
    jQuery('#plugin_notepad :input').each(function(i, el){
        var tmp = {};
        tmp.name = jQuery(el).attr('name');
        tmp.value = jQuery(el).val();
        postData.push(tmp);
    });

    jQuery.post(jQuery('#plugin_notepad').attr('action'), postData,
      function(data) {

        stopSpinner('spinner_notepad');
        jQuery('#save_notepad_btn').removeAttr('disabled');
        jQuery('#study-options-tab').slideUp();
      });

    return false;
  });
}

// execute a Google Image Search
function startImageSearch(type, node_id, text, studyunit_id, user_id, source_id)
{
    var searchResult = document.getElementById('searchControl');

    // create a left, right search control
    // create a custom search form
    this.searchResult = new google.search.SearchControl();
    // set up for large result sets
    this.searchResult.setResultSetSize(GSearch.LARGE_RESULTSET);

    // configure control
    var searcher = new google.search.ImageSearch();
    searcher.setRestriction(google.search.Search.RESTRICT_SAFESEARCH, google.search.Search.SAFESEARCH_MODERATE);

    var options = new google.search.SearcherOptions();
    options.setExpandMode(google.search.SearchControl.EXPAND_MODE_OPEN);
    this.searchResult.addSearcher(searcher, options);

    var drawOptions = new google.search.DrawOptions();

    this.searchResult.setNoResultsString(GSearchControl.NO_RESULTS_DEFAULT_STRING);
    this.searchResult.draw(searchResult, drawOptions);

    // add some efaqt styling to the Google form using jQuery
    jQuery('input.gsc-input').addClass('text').val(text);
    jQuery('input.gsc-search-button').addClass('button');

    // add click handler to the images so we can pass the URL of the thumbnail to the mindmap
    jQuery('.gsc-resultsbox-visible').die();
    jQuery('.gsc-resultsbox-visible').live('click', function(elm) {
      elm.preventDefault();
      var thumb = jQuery(elm.target).attr('src');
      var original = jQuery(elm.target).parent().attr('href');

      // ignore non-existant images and google's browse buttons
      if (typeof thumb == 'undefined') {
        return;
      }

      // depending on type (either 'mindmap' or 'question') we either add a node
      // to the mindmap or return the URL of the selected image
      if (type == 'mindmap') {

        // download image locally
        jQuery.get('study/downloadfile?url=' + escape(thumb) + '&user_id=' + user_id + '&type=mindmap', { time: new Date().getTime()}, function(data) {

          if (data !== 'NOK') {
            // add image to mindmap
            setNodeIcon(data, node_id);

            // close colorbox
            parent.jQuery.fn.colorbox.close();
          }
        });

      } else {

          // download image locally
          jQuery.get('study/downloadfile?url=' + escape(thumb) + '&source_id=' + source_id + '&type=question' + '&original=' + original, { time: new Date().getTime()}, function(data) {

          // update our DOM
          window.location=window.location;
        });
      }
    });
}


function addTocBackButton(back_url)
{
  jQuery('#back_toc_items_btn').die();
  jQuery('#back_toc_items_btn').live('click', function() {
    jQuery.get(back_url, { time: new Date().getTime()}, function(data) {

      parent.jQuery('#studyContainer').html(data);
      parent.jQuery.fn.colorbox.close();
    });

  });
}

function openSubject(url)
{
  jQuery('<a />').colorbox({href: url, open: true});
  reloadParent();
}


function openTocItemQuestions(url)
{
  jQuery('<a />').colorbox({href: url, open: true});
}

// open the TOC tree lightbox within the study proces
function openStudyUnitTocTreePopup(url, nextUrl)
{
  // open colorbox
  jQuery('<a />').colorbox({href: url, open: true, overlayClose: false});
  
  // disable the Esc from closing the colorbox
  jQuery().unbind("keydown.cbox_close");

  jQuery('#cboxClose, #cboxOverlay').click(function(){
    // when the close button is pressed, go to the next step.
    jQuery.get(nextUrl, { time: new Date().getTime()}, function(data) {
      parent.jQuery('#studyContainer').html(data);

      // restore the close action on the close button
      jQuery('#cboxClose, #cboxOverlay').unbind('click');
      jQuery('#cboxClose, #cboxOverlay').click(function(){
        parent.jQuery.fn.colorbox.close();
      });
    });
  });
}

// opens a popup where the user can select the studyunit language
function openStudyUnitLanguagePopup(url){
	// open colorbox
  	jQuery('<a />').colorbox({href: url, open: true, overlayClose: false});
		 
  	// hide close button
    jQuery('#cboxClose').hide();
    
    // disable the Esc from closing the colorbox
    jQuery().unbind("keydown.cbox_close");
}

// opens a popup where the user can select the studyunit language
function openCompareQuestionsPopup(url){
	// open colorbox
  	jQuery('<a />').colorbox({href: url, open: true, overlayClose: false});
		 
  	// hide close button
    jQuery('#cboxClose').hide();
    
    // disable the Esc from closing the colorbox
    jQuery().unbind("keydown.cbox_close");
}

// report selected keywords as irrelevant.
function reportIrrelevantKeywords(url){

	// report button event
    jQuery('#reportKeywordsButton').die();
  	jQuery('#reportKeywordsButton').live('click', function(event){
		event.preventDefault();
	
	    jQuery('#reportKeywordsButton').attr('disabled', 'disabled');
	    startSpinner();
	    
	    var postData = [];
	
	    var tmp = {};
	    tmp.name = 'keywords';
	    tmp.value = jQuery('p.keywords').getkeywords();
	    postData.push(tmp);
	    
	    var tmp = {};
	    tmp.name = 'tocitemid';
	    tmp.value = jQuery('#tocitemid').val();
	    postData.push(tmp);
	
	    jQuery.post(jQuery('#reportKeywordsForm').attr('action'), postData, function(data) {
			//alert(data);
			stopSpinner();
	    });
	});
  
  	// go back to the questions step
    jQuery('#reportKeywordsBackButton').die();
  	jQuery('#reportKeywordsBackButton').live('click', function(event){		
  		jQuery.get(jQuery('#backUrl').val(), { time: new Date().getTime()}, function(data) {
	      parent.jQuery('#studyContainer').html(data);
	      parent.jQuery.fn.colorbox.close();
	    });
  	});
  	
  	// go to the keyword step
  	jQuery('#reportKeywordsNextButton').die();
  	jQuery('#reportKeywordsNextButton').live('click', function(event){
  		jQuery.get(jQuery('#nextUrl').val(), { time: new Date().getTime()}, function(data) {
	      parent.jQuery('#studyContainer').html(data);
	      parent.jQuery.fn.colorbox.close();
	    });
  	});
}

function checkSpelling(language, id)
{
  if (typeof id != 'undefined') {
    jQuery('#' + id).spellcheck({ lang: language, events: 'keypress blur paste' });
  } else {
    jQuery('#quest').spellcheck({ lang: language, events: 'keypress blur paste' });
    jQuery('#ans').spellcheck({ lang: language, events: 'keypress blur paste' });
    }
}


function doDatepicker()
{
  // get previous date
  var prevdate = jQuery('#datepicker').val() || '01-01-1970';

  jQuery('#datepicker').datepicker({
    showOn: 'button',
    buttonImage: 'images/datepicker.gif',
    buttonImageOnly: true,
    showAnim: 'fadeIn',
    dateFormat: 'dd-mm-yy',
    changeYear: true,
    yearRange: '1940:2000',
    defaultDate: prevdate
    });
}

/*************  Breadcrumb functions   ***************************************/

function addBreadcrumb(text, url)
{

  var descr = text;
  var exists = false;

  // truncate texts that are too long
  if (text.length > 25) {
    text = text.substr(0, 25) + '...';
  }

  // parse all nodes to do some cleanup and to prevent double nodes
  jQuery('#breadcrumbs li a').each(function() {

    // exit if we already have a similar named node
    if (jQuery(this).text() == text) {
      exists = true;
    }
  });

  if (!exists) {

    // parse all nodes to do some cleanup and to prevent double nodes
    jQuery('#breadcrumbs li a').each(function() {
      // remove class=final from all previous li's
      jQuery(this).removeClass('final');
    });

    jQuery('#breadcrumbs li:last').removeClass('inactive');
    jQuery('#breadcrumbs li:last a').addClass('final');

    // append new node
    var new_link = '<a href="javascript:;" onclick="saveXml();ajaxGet(\'' + url + '\', \'studyContainer\');" title="' + descr + '">' + text + '</a>';

    jQuery('#breadcrumbs').append('<li class="inactive">' + new_link + '</li>');
  }
}

function resetBreadcrumb(text, url, position)
{
  // remove all breadcrumb notes from position specified
  jQuery('#breadcrumbs li').each(function(i)  {
    if (i >= position) {
      jQuery(this).remove();
    }
  });

  // layout last node
  jQuery('#breadcrumbs li:last a').addClass('final');

  addBreadcrumb(text, url);
}

/*************  Mindmap functions ***************************************/

function continueStudying(node_id) {

  // we only accept numeric nodes
  if (node_id == 0 || node_id.match(/^\d+$/) == null) {
    jQuery.growlUI(__('Function not available'), '<p>' + __('This function is only available for chapter titles, not for keywords.') + '</p>');
    return;
  }

  ajaxGet('study/continuestudying?id=' + node_id, 'studyContainer');
}

// open a lightbox with Google Image Search and allow a user to append
// an image to the current node specified by node_id
function mindmapImageLightbox(node_id, text)
{
  // open colorbox
  var url = 'study/imagesearch?node_id=' + node_id + '&text=' + text;
  jQuery('<a />').colorbox({href: url, open: true});
}

// open a lightbox with node info and allow a user to append
// an image to the current node specified by node_id
function mindmapInfoLightbox(node_id)
{
  // we only accept numeric nodes
  if (node_id == 0 || node_id.match(/^\d+$/) == null) {
    jQuery.growlUI(__('Function not available'), '<p>' + __('This function is only available for chapter titles, not for keywords.') + '</p>');
    return;
  }

  // open colorbox
  var url = 'study/info?node_id=' + node_id;
  jQuery('<a />').colorbox({href: url, open: true});
}

function thisMovie(movieName, lightbox)
{
  // normal window
  if (!lightbox) {
    if (navigator.appName.indexOf('Microsoft') != -1) {
        return window[movieName];
    } else {
        return document[movieName];
    }
  }

  // lightbox; access parent window
  if (navigator.appName.indexOf('Microsoft') != -1) {
      return window.parent[movieName];
  } else {
      return parent.document[movieName];
  }
}

function addNode(id, parentId, text)
{
  jQuery(document).ready(function() {
    var node = {};
    node.id = id;
    node.text = text;
    node.children = [];
    try {
      thisMovie('mindmap').addNode(node, parentId);
    } catch (err) {}

  });
}

function removeNodeById(id)
{
  thisMovie('mindmap').removeNodeById(id);
}

function getNode()
{
  return thisMovie('mindmap').getNode();
}

function setNodeText(text)
{
  thisMovie('mindmap').setNodeText(text);
}

function setNodeIcon(img, node_id)
{
  thisMovie('mindmap', true).setNodeIcon(img, node_id);
}

function getXml()
{
  alert(thisMovie('mindmap').getXml());
}

function saveXml()
{
  if (typeof(thisMovie('mindmap')) != 'undefined') {
    thisMovie('mindmap').saveXml();
  }
}

function showRelationArrow(id)
{
  try{
    thisMovie('mindmap').showRelationArrow(id);
  } catch(err) {
  	// try again every 3 seconds, the mindmap may not be loaded yet
  	setTimeout("showRelationArrow("+id+")",3000);
  }
}

function hideRelationArrow(id)
{
  thisMovie('mindmap').hideRelationArrow(id);
}

function showExpectation(id, text)
{
  try{
    thisMovie('mindmap').showCloud(id, text.replace(/\\/,''));
  } catch(err) {}
}

function mindmapReady()
{
  jQuery(init_mindmap_queue).each(function () { this(); });
}

/*********************************************************************/


/*************  Translation functions ***************************************/

// helper function to handle translations
function __(s)
{
  if (typeof(i18n)!='undefined' && i18n[s]) {
    return i18n[s];
  }
  return s;
}

// open a colorbox on our AJAX pages
function liveColorbox()
{
  jQuery('.colorbox').die();
  jQuery('.colorbox').live('click', function() {
    jQuery(this).colorbox({open:true});
    return false;
  });
}


// when file browser popup is closed, update data
function handleFilebrowser(url, postUrl, redirectUrl)
{
  // handle clicks on selected images in our directory
  jQuery('#file-box').click(function(elm) {
    elm.preventDefault();

    // retrieve URL from our a href
    // because there are also icons in here, we might have to look at the previous element
    var upload = jQuery(elm.target).attr('href');
    if (upload === '' || typeof upload == 'undefined') {
      upload = jQuery(elm.target).closest('a.file-image').attr('href');
    }

    if (!postUrl) {
      // add file to a new question.
      storeFileBrowserData(upload, url, true);
    } else {
      // the user is editing a question, now the url of the image has to be posted
      $.post(postUrl, { upload: upload },
        function(data){
        window.location = redirectUrl;
        });

    }
  });
}

// handle our selected file and update the DOM
function storeFileBrowserData(upload, url, closelightbox)
{
  // call special symfony action to store selected upload for this user/source_id combo
  url += '?upload=' + upload;

  jQuery.get(url, { time: new Date().getTime()}, function(data) {
    parent.jQuery('#question-options').html(data);

    if (closelightbox === true) {
      parent.jQuery.fn.colorbox.close();
      
      // Focus 'cause of an IE bug. Sometimes when the popup is closed you can't type in the textarea.
      parent.jQuery('#quest').focus();
    }
  });
}

// remove user uploaded file for a question
// just empties the hidden input and removes the display of uploaded file
function removeUploadedFile()
{
  jQuery('#remove_uploaded_file').click(function(event) {
    event.preventDefault();
    jQuery('#input_uploaded_file').attr('value', '');
    jQuery('#display_uploaded_file').remove();
    jQuery('#remove_uploaded_file').remove();
  });
}

// display concentration notification
function concentrationNotification(skip_studytips)
{
  // play notification sound
  swfobject.embedSWF('swf/playsound.swf?playSound=var_play', 'soundeffect', '0', '0', '9.0.0', 'swf/expressInstall.swf', '', {loop: false});

  var content = '<p>' + __('If you are having problems concentrating, read the study tips for help.') + '</p>';

  // showing studytips is a user configurable setting
  if (skip_studytips == 1) {

    // append studytip container and retrieve a random studytip through AJAX
    // somehow we can't call getStudytip() here because it doesn't return any data...
    jQuery.get('ajax/getstudytip', { time: new Date().getTime()}, function(data) {

      // FIXME: this is a nasty way to circumvent AJAX asynchronous race conditions
      if (data !== '') {
        content += '<hr /><div id="studytip">' + data + '</div>';
        jQuery.growlUI(__('Are you still studying?'), content, 8000);
      } else {
        jQuery.growlUI(__('Are you still studying?'), content, 8000);
      }

    });

  } else {
    jQuery.growlUI(__('Are you still studying?'), content, 8000);
  }

  return true;
}


// block the screen during study pause and display tips
function pauseStudy()
{
  // offer user option to go to rehearsal mode
  rehearseStudy();

  jQuery.blockUI({message: jQuery('#studytips'), css: {
                  left: '30%',
                  width: '40%',
                  top: '20%',
                  padding: '0px 5px',
                  background: '#444444',
                  opacity: '0.9',
                  borderColor: '#444444',
                  cursor: 'auto'
                  }
                });

  jQuery('.close-studytip').one('click', function(event) {
    jQuery.unblockUI();
    event.preventDefault();
  });

  // fill with first studytip
  getStudytip();

  // add handler to 'next tip' block
  jQuery('#getnexttip').bind('click', function(event) {
    event.preventDefault();
    getStudytip();
  });
}

// screen that will be displayed after pause mode, offers rehearsal option
function rehearseStudy()
{
  jQuery.blockUI({message: jQuery('#rehearsal'), css: {
                  left: '30%',
                  width: '40%',
                  top: '20%',
                  padding: '0px 5px',
                  background: '#444444',
                  opacity: '0.9',
                  borderColor: '#444444',
                  cursor: 'auto'
                  }
                });

  // close button
  jQuery('.close-studytip').bind('click', function(event) {
    jQuery.unblockUI();
    event.preventDefault();
  });

  // rehearsal button
  jQuery('#rehearse_yes').one('click', function(event) {

    var url = jQuery(this).attr('href');

    jQuery.unblockUI();
    startSpinner();

    jQuery.get(url, { time: new Date().getTime()}, function(data) {
      stopSpinner();
      parent.jQuery('#studyContainer').html(data);
    });

    event.preventDefault();
  });

  // resume button
  jQuery('#rehearse_no').one('click', function(event) {
    jQuery.unblockUI();
    event.preventDefault();
  });

}

// retrieves a new study tip and places it into div#studytip
function getStudytip()
{
  jQuery.get('ajax/getstudytip', { time: new Date().getTime()}, function(data) {
    jQuery('#studytip').html(data);
  });
}

// retrieves a new study tip and places it into div#studytip
function displayExplanation()
{
  jQuery('a.explanation-link').die();
  jQuery('a.explanation-link').live('click', function(e) {

    jQuery('.explanation-text').slideToggle();

    // we hide the list of own questions on the question module because of lack of space
    if (jQuery('#quest').length) {
      jQuery('#myquestions').toggle();
    }

    e.preventDefault();
  });
}

function round_number(number,dec_places) {
  // Version 2.0 (c) Copyright 2008, Russell Walker, Netshine Software Limited. www.netshinesoftware.com
  var new_number = '';
  var i = 0;
  var sign = '';
  number = number.toString();
  number=number.replace(/^\s+|\s+$/g,'');

  if (number.charCodeAt(0) == 45) {
    sign = '-';
    number = number.substr(1).replace(/^\s+|\s+$/g,'');
  }

  dec_places = dec_places * 1;
  dec_point_pos = number.lastIndexOf('.');

  if (dec_point_pos === 0) {
    number= '0' + number;
    dec_point_pos = 1;
  }

  if (dec_point_pos == -1 || dec_point_pos == number.length - 1) {

    if (dec_places > 0) {
      new_number = number + '.';
      for (i = 0;i < dec_places; i++) {
        new_number += '0';
      }
      if (new_number === 0) {
        sign = '';
      }
      return sign + new_number;
    } else {
      return sign + number;
    }
  }

  var existing_places = (number.length - 1) - dec_point_pos;

  if (existing_places == dec_places) {
    return sign + number;
  }
  if (existing_places < dec_places) {
    new_number = number;

    for (i = existing_places; i < dec_places; i++) {
      new_number += '0';
    }

    if (new_number === 0) {
        sign = '';
    }

    return sign + new_number;
  }

  var end_pos = (dec_point_pos * 1) + dec_places;
  var round_up = false;
  if ((number.charAt(end_pos + 1) * 1) > 4) {
    round_up = true;
  }

  var digit_array = [];
  for (i = 0;i <= end_pos; i++) {
    digit_array[i] = number.charAt(i);
  }

  for (i = digit_array.length - 1; i >= 0; i--) {
    if (digit_array[i] == '.') {
      continue;
    }

    if (round_up) {
      digit_array[i]++;
      if (digit_array[i] < 10) {
        break;
      }
    } else {
      break;
    }
  }

  for (i = 0; i <= end_pos; i++) {
    if (digit_array[i] == '.' || digit_array[i] < 10 || i === 0) {
      new_number += digit_array[i];
    } else {
      new_number += '0';
    }
  }

  if (dec_places === 0) {
      new_number = new_number.replace('.', '');
  }
  if (new_number === 0) {
      sign = '';
  }
  return sign+new_number;
}

// gives cost indication in money, based on credits
// used in buycredits and transfercredits
function calculateCosts(credits, eurcreditvalue, dollarfactor, poundfactor, rpfactor, chffactor)
{
  var eurvalue = round_number(credits * eurcreditvalue, 2);

  // initial situation: display values
  var costs = __('Roughly equivalent to') + ' ' +
              '&euro;' + eurvalue + ', ' +
              '$' + round_number(eurvalue * dollarfactor, 2) + ', ' +
              '&pound;' + round_number(eurvalue * poundfactor, 2) + ', ' +
              'Rp.' + round_number(eurvalue * rpfactor, 2) + ', ' +
              'CHF' + round_number(eurvalue * chffactor, 2);
  return costs;
}

function displayCreditCosts(bindto, eurcreditvalue, dollarfactor, poundfactor, rpfactor, chffactor)
{
  // on start, display credits as well
  var elm = '#' + bindto;
  var credits = jQuery(elm + ' option:selected').text();
  credits = credits.match(/\d+/);

  jQuery('#curval').html(calculateCosts(credits, eurcreditvalue, dollarfactor, poundfactor, rpfactor, chffactor));

  // on change calculate new values
  jQuery(elm).change(function() {
    credits = jQuery(elm + ' option:selected').text();
    credits = credits.match(/\d+/);
    jQuery('#curval').html(calculateCosts(credits, eurcreditvalue, dollarfactor, poundfactor, rpfactor, chffactor));
  });
}

// display link to 'buy questions' on Q/A page
function displayAvailableQuestions()
{
  var available = jQuery('#available_questions').text();
  available = parseInt(available, 0);

  // because of asynchronous javascript in the updatelinks block
  // we might not have values here
  // therefore we just exit here and call displayAvailableQuestions in
  // addUpdateLinks() as well
  if (isNaN(available)) {
    return;
  }

  if (available > 0) {
    var href = jQuery('#buy_questions_link').attr('href');
    var text = available + ' ' + __('new questions available');
    href = '<a href="' + href + '" class="link colorbox floatr">' + text + '</a>';
    jQuery('#new_questions_available').html(href);
  } else {
    // when there are no questions, empty the container.
    jQuery('#new_questions_available').html('');
  }
}

/**
* Function : dump()
* Arguments: The data - array,hash(associative array),object
* The level - OPTIONAL
* Returns  : The textual representation of the array.
* This function was inspired by the print_r function of PHP.
* This will accept some data as the argument and return a text that will be a more readable version of the array/hash/object that is given.
*/
function dump(arr,level)
{
  var dumped_text = '';
  if (!level) {
    level = 0;
  }

  // The padding given at the beginning of the line.
  var level_padding = '';
  for (var j = 0;j < level + 1; j++) {
    level_padding += '  ';
  }

  // Array/Hashes/Objects
  if (typeof(arr) == 'object') {

    for (var item in arr) {
      var value = arr[item];

      // If it is an array
      if (typeof(value) == 'object') {
        dumped_text += level_padding + "'" + item + "' ...\n";
        dumped_text += dump(value,level + 1);
      } else {
        dumped_text += level_padding + "'" + item + "' => \"" + value + "\"\n";
      }
    }
  // Strings/Chars/Numbers etc.
  } else {
    dumped_text = '===>' + arr + '<===(' + typeof(arr) + ')';
  }
  return dumped_text;
}

// when buying/using questions check if a question has a question and if so turn on the icon.
function toggleImageIcon(){
	// get all the answers with the class 'editquestion'. 
	jQuery('.editquestion').each(function(i, element) {	
		// get the id of the quesiton container. Replace the a from answer to q.
		parentId = jQuery(element).parent().attr('id');
		questionContainerId = parentId.replace(/\a/g,'q');
		
		// show the icon that indicates that a question has an image.
		jQuery('#'+questionContainerId+' .questionwithimage').each(function(j, container){
			jQuery(container).removeClass('hide');			
		});
	});
}

// rate questions
function addStarRating(postUrl){
	jQuery('.auto-submit-star').rating({ 
		callback: function(value, link){
			// disable when clicked on
			jQuery(this).rating('disable');
			
			questionId = jQuery(this).attr('name').replace(/star_/g,'');
				
			var postData = [];
		    var tmp = {};
		    tmp.name = 'questionId';
		    tmp.value = questionId;
		    postData.push(tmp);
		    
		    var tmp = {};
		    tmp.name = 'value';
		    tmp.value = value;
		    postData.push(tmp);
  			
			jQuery.post(postUrl, postData, function(data) {
			
		  	});
		  	
		  	// change text
		  	jQuery(this).siblings('.used').html('&nbsp;&nbsp;'+__('Thank you for your rating.'));
		} 
	});
	
	// disable ratings
	//jQuery('.ratingdisabled').rating('disable');
}