

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/COntentPanel.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Basisklasse für die einzelnen ContentPanels (Inhalte der Reiter).
 *
 * Die erweiterten, abgeleitetn Klassen befinden sich in den Dateien CP_xyz.class.js,
 * wobei xyz für den den Namen des Reiters steht.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig
/**
 * Basisklasse für die einzelnen ContentPanels (Inhalte der Reiter).
 * Die erweiterten, abgeleitetn Klassen befinden sich in den Dateien CP_xyz.class.js,
 * wobei xyz für den den Namen des Reiters steht.
 *
 * @constructor
 * @class
 * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Panels.
 * @param {Number} num Die Nummer des Panels.
 */
var ContentPanel = function(el, num)
{
  /**
   * jQuery-Objekt für das ContentPanel.
   * @type {jQuery}
   */
  this.el = $(el);

  /**
   * jQuery-Objekt für die Submit-Buttons zum Absenden des Formulars.
   * @type {jQuery}
   */
  this.submitBtns = this.el.find("p.submitBtns input");

  /**
   * Die Nummer des Panels.
   * @type {Number}
   */
  this.index = num;
};

ContentPanel.prototype =
{
  /**
   * Panel einblenden.
   */
  showPanel: function()
  {
    this.el.show();
  },

  /**
   * Panel ausblenden.
   */
  hidePanel: function()
  {
    this.el.hide();
  },

  /**
   * Den "Änderungen übernehmen" Button einblenden.
   */
  showEditButton: function()
  {
    this.submitBtns.eq(0).hide();
    this.submitBtns.eq(1).hide();
    this.submitBtns.eq(2).show();
  },

  /**
   * Den "Änderungen übernehmen" Button ausblenden.
   */
  hideEditButton: function()
  {
    //console.log(this.submitBtns);

    // Beim Entscheider den Button "ausschließen" nicht anzeigen
    if (this.index != 3)
      this.submitBtns.eq(0).show();

    this.submitBtns.eq(1).show();
    this.submitBtns.eq(2).hide();
  },

  /**
   * Formular für AJAX-Absendung vorbereiten.
   */
  prepareForm: function()
  {
    this.el.find("form:first").ajaxForm(
    {
      dataType: "json",

      // Diese Funktion wird vor dem Absenden des Formulars ausgeführt.
      beforeSubmit: function(formData)
      {

        var sel = SelectionManager.getActive();

        formData.push({ name: "selNum", value: sel.index });

        if (SelectionManager.editChoiceMode)
        {
          formData.push({ name: "choiceNum", value: sel.getActiveChoice().index });
        }

      }.tie(this),

      // Diese Funktion wird nach erfolgreichem Absenden ausgeführt.
      success: function(data)
      {
        Exception.handle(data.exception);

        /**
         * Wenn erfolgreich
         */
        if (data.items && data.items.length > 0)
        {
          var sel = SelectionManager.getActive();

          if (SelectionManager.editChoiceMode)
          {
            sel.replaceChoice(data);
          }
          else
          {
            sel.createChoice(this.index, data);
          }


        }

        /**
         * Wenn Fehler
         */
         if (data.exception)
         {
          /**
           * Im Fall, wenn man versucht hat das Auswahlkriterium ohne zu ändern zu übernehmen,
           * wird das Formular nicht zurück gesetzt.
           */
           if(data.exception.type = 'error' && data.exception.code == '1')
           {
              /**
               * Formular bleit nicht resettet.
               */
           }
           else
           {
              this.resetForm();
           }

         }
         /**
          * Wenn kein Fehler, Formular zurück setzen.
          */
         else
         {
            this.resetForm();
         }



      }.tie(this)
    });
  },

  /**
   * Setzt das Formular des Reiters auf den Ausgangszustand zurück.
   */
  resetForm: function()
  {
    alert("Muss implementiert werden!");
  },

  /**
   * Beim Ändern eines Kriteriums werden die eingegbenen Formulardaten per AJAX vom Server aus
   * der Session geladen und damit das Formular des jeweiligen Reiters neu gesetzt/befüllt.
   * @param {Object} data Daten des Kriteriums.
   */
  setFormWithChoiceData: function(data)
  {
    alert("Muss implementiert werden!");
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/CP_Branches.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Branchen".
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig
/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Branchen".
 *
 * @constructor
 * @class
 * @extends ContentPanel
 * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Panels.
 * @param {Number} num Die Nummer des Panels.
 */
var CP_Branches = function(el, num)
{
  // Den Konstruktor von der Klasse ContentPanel aufrufen
  ContentPanel.call(this, el, num);

  /**
   * Gibt an, ob alle Select-Felder resettet wurden, d.h. nur das erste auswählbar ist.
   * @type {Boolean}
   */
  this.allSelectsResetted = true;

  /**
   * jQuery-Objekt für das Autocomplete-Feld.
   * @type {jQuery}
   */
  this.ac = null;

  /**
   * jQuery-Objekt für das Eingabefeld.
   * @type {jQuery}
   */
  this.branchTextField = this.el.find("#inputBranch");

  /**
   * jQuery-Objekt für das erste Select-Feld.
   * @type {jQuery}
   */
  this.branches1Field = this.el.find("#dropdownBranches1");

  /**
   * jQuery-Objekt für das zweite Select-Feld.
   * @type {jQuery}
   */
  this.branches2Field = this.el.find("#dropdownBranches2");

  /**
   * jQuery-Objekt für das dritte Select-Feld.
   * @type {jQuery}
   */
  this.branches3Field = this.el.find("#dropdownBranches3");

  // Listener-Funktionen an Events binden.
  this.bindEventListeners();

  // Formular für AJAX-Absendung vorbereiten
  this.prepareForm();

  // Autocpmplete-Feld initialisieren
  this.initAutoComplete();
};

// Vererbung der Eigenschaften/Methoden von der Klasse ContentPanel
CP_Branches.prototype = new ContentPanel();

$.extend(CP_Branches.prototype,
{
  /**
   * Listener-Funktionen an Events binden.
   */
  bindEventListeners: function()
  {
    this.branchTextField.bind("click", this.onClickBranchText);
    this.branchTextField.bind("keypress", this.onKeypressBranchText.evt(this));
    this.branches1Field.bind("change", this.onChangeBranches1.evt(this));
    this.branches2Field.bind("change", this.onChangeBranches2.evt(this));
    this.branches3Field.bind("change", this.onChangeBranches3.evt(this));
  },

  /**
   * Autocpmplete-Feld initialisieren.
   */
  initAutoComplete: function()
  {
    this.ac = this.branchTextField.autocomplete($_AJAX_URL + "?branches&act=autoCompleteBranches",
    {
      minChars: 3,
      delay: 800,
      matchSubset: false,
      matchContains: false,
      max: 0,
      mustMatch: false,
      width: 500,
      //autoFill: true,
      moreItems: false
    });

    this.ac.result(function(evt, data, formatted)
    {
      // Pfeile am Anfang entfernen
      var newStr = formatted.replace(/^(-)*>\s/, "");
      // Neuen String ins Textfeld schreiben
      $(this).val(newStr);
    });
  },

  /**
   * Auswahloptionen für Branchen der 2. Ebene laden und Select-Feld damit befüllen.
   * @param {Number} branch1Index Nummer der übergeordneten Branche aus der 1. Ebene.
   */
  initBranches2: function(branch1Index, branch1ID, preSelectValue)
  {
    var value = branch1ID || this.branches1Field.get(0).options[branch1Index].value;

    $.getJSON($_AJAX_URL + "?branches&act=loadBranches23", { bra_ID: value, level: 2  }, function(data)
    {

      var ddBranches2 = this.branches2Field.get(0);

      ddBranches2.options.length = 0;

      $.each(data, function(i, option)
      {
        if (option.value == preSelectValue)
        {
          ddBranches2.options[i] = new Option(option.text, option.value, true, true);
        }
        else
        {
          ddBranches2.options[i] = new Option(option.text, option.value);
        }
      });

      this.branches2Field.attr("disabled", "");

      if (typeof this.branches3Field.attr("disabled") == "undefined")
      {
        this.resetBranch(3);
      }

      ddBranches2.focus();

    }.tie(this));
  },

  /**
   * Auswahloptionen für Branchen der 3. Ebene laden und Select-Feld damit befüllen.
   * @param {Number} branch2Index Nummer der übergeordneten Branche aus der 2. Ebene.
   */
  initBranches3: function(branch2Index, branch2ID, preSelectValue)
  {
    var value = branch2ID || this.branches2Field.get(0).options[branch2Index].value;

    $.getJSON($_AJAX_URL + "?branches&act=loadBranches23", { bra_ID: value, level: 3  }, function(data)
    {

      var ddBranches3 = this.branches3Field.get(0);

      ddBranches3.options.length = 0;

      $.each(data, function(i, option)
      {
        if (option.value == preSelectValue)
        {
          ddBranches3.options[i] = new Option(option.text, option.value, true, true);
        }
        else
        {
          ddBranches3.options[i] = new Option(option.text, option.value);
        }
      });

      this.branches3Field.attr("disabled", "");

      //ddBranches3.focus();

    }.tie(this));
  },

  /**
   * Listener-Funktion für Click-Event auf das Eingabefeld.
   */
  onClickBranchText: function(evt)
  {
    if (this.value == "Branche")
      this.value = "";
  },

  /**
   * Listener-Funktion für Keypress-Event bei Eingabe in das Eingabefeld.
   */
  onKeypressBranchText: function(evt, el)
  {
    if (!this.allSelectsResetted)
    {
      this.resetSelects();
    }
  },

  /**
   * Listener-Funktion für Change-Event bei Änderung der Branche in Ebene 1.
   */
  onChangeBranches1: function(evt, el)
  {
    this.branchTextField.val("");

    if  (el.selectedIndex != 0)
    {
      this.initBranches2(el.selectedIndex);
      this.allSelectsResetted = false;
    }
    else
    {
      this.resetSelects();
    }
  },

  /**
   * Listener-Funktion für Change-Event bei Änderung der Branche in Ebene 2.
   */
  onChangeBranches2: function(evt, el)
  {
    this.branchTextField.val("");

    if  (el.selectedIndex != 0)
    {
      this.initBranches3(el.selectedIndex);
    }
    else
    {
      this.resetBranch(3);
    }

    this.allSelectsResetted = false;
  },

  /**
   * Listener-Funktion für Change-Event bei Änderung der Branche in Ebene 3.
   */
  onChangeBranches3: function(evt, el)
  {
    this.branchTextField.val("");
    this.allSelectsResetted = false;
  },

  /**
   * Select-Feld für Branchen einer Ebene deaktivieren.
   * @param {Number} num Branchenebene.
   */
  resetBranch: function(num)
  {
    switch (num)
    {
      case 1:
        var ddBranches = this.branches1Field;
      break;

      case 2:
        var ddBranches = this.branches2Field;
      break;

      case 3:
        var ddBranches = this.branches3Field;
      break;
    }

    ddBranches[0].options.length = 1;
    // Ausgrauen
    ddBranches.attr("disabled", "disabled");
  },

  /**
   * Select-Felder resetten.
   */
  resetSelects: function()
  {
    this.resetBranch(2);
    this.resetBranch(3);

    this.branches1Field[0].selectedIndex    = 0;

    this.allSelectsResetted = true;
  },

  /**
   * Formular resetten. Siehe auch ContentPanel#resetForm.
   */
  resetForm: function()
  {
    this.resetSelects();

    this.branchTextField.val("Branche");
  },

  /**
   * Formular mit Kriteriumdaten befüllen. Siehe auch ContentPanel#setFormWithChoiceData.
   * @param {Object} data Daten des Kriteriums.
   */
  setFormWithChoiceData: function(data)
  {
    this.resetForm();

    var branch1 = this.branches1Field.get(0);
    var branch2 = this.branches2Field.get(0);
    var branch3 = this.branches3Field.get(0);

    if (data.selects_bra_ID && data.selects_bra_ID.length == 3 && data.selects_bra_ID[0] > 0)
    {
      Util.selectOpt(branch1, data.selects_bra_ID[0]);

      this.initBranches2(null, data.selects_bra_ID[0], data.selects_bra_ID[1]);

      if (data.selects_bra_ID[1] > 0)
      {
        this.initBranches3(null, data.selects_bra_ID[1], data.selects_bra_ID[2]);
      }
    }
    else
    {
      if (data.bra_ID > 0 && data.bra_branch != "")
      {
        this.branchTextField.val(data.bra_branch);
      }
    }
  }
});;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/CP_CompanyCriterias.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Firmenbezogene Kriterien".
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Firmenbezogene Kriterien".
 *
 * @constructor
 * @class
 * @extends ContentPanel
 * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Panels.
 * @param {Number} num Die Nummer des Panels.
 */
var CP_CompanyCriterias = function(el, num)
{
  // Den Konstruktor von der Klasse ContentPanel aufrufen
  ContentPanel.call(this, el, num);

  /**
   * jQuery-Objekt für die Telefon-Checkbox.
   * @type {jQuery}
   */
  this.phoneField = this.el.find("#phoneNumber");

  /**
   * jQuery-Objekt für die Fax-Checkbox.
   * @type {jQuery}
   */
  this.faxField = this.el.find("#faxNumber");

  /**
   * jQuery-Objekt für die E-Mail-Checkbox.
   * @type {jQuery}
   */
  this.emailField = this.el.find("#emailAddress");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl der Gesellschaftsform.
   * @type {jQuery}
   */
  this.legalFormField = this.el.find("#legalForm");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl des Firmentyps.
   * @type {jQuery}
   */
  this.companyTypeField = this.el.find("#companyType");

  /**
   * jQuery-Objekt für das Eingabefeld zur Eingabe der minimalen Mitarbeiterzahl.
   * @type {jQuery}
   */
  this.employeeMinField = this.el.find("#numberOfEmployees_min");

  /**
   * jQuery-Objekt für das Eingabefeld zur Eingabe der maximalen Mitarbeiterzahl.
   * @type {jQuery}
   */
  this.employeeMaxField = this.el.find("#numberOfEmployees_max");

  // Listener-Funktionen an Events binden.
  this.bindEventListeners();

  // Formular für AJAX-Absendung vorbereiten
  this.prepareForm();
};

// Vererbung der Eigenschaften/Methoden von der Klasse ContentPanel
CP_CompanyCriterias.prototype = new ContentPanel();

$.extend(CP_CompanyCriterias.prototype,
{
  /**
   * Listener-Funktionen an Events binden.
   */
  bindEventListeners: function()
  {
    this.el.find("a.hardlyReadableText").bind("click", this.onClickInfoText.evt(this));
    this.el.find("label.hardlyReadableText").bind("click", this.onClickInfoText.evt(this));
  },

  /**
   * Listener-Funktion für Click-Event auf Info.
   */
  onClickInfoText: function(evt, el)
  {
    //evt.preventDefault();

    this.el.find("div.infoTextBox").show();

    return true;
  },

  /**
   * Formular resetten. Siehe auch ContentPanel#resetForm.
   */
  resetForm: function()
  {
    this.employeeMinField.val("");
    this.employeeMaxField.val("");

    this.legalFormField[0].selectedIndex   = 0;
    this.companyTypeField[0].selectedIndex = 0;

    this.phoneField[0].checked = false;
    this.faxField[0].checked   = false;
    this.emailField[0].checked = false;
  },

  /**
   * Formular mit Kriteriumdaten befüllen. Siehe auch ContentPanel#setFormWithChoiceData.
   * @param {Object} data Daten des Kriteriums.
   */
  setFormWithChoiceData: function(data)
  {
    this.resetForm();

    // DOM-Elemente holen
    var legalForm = this.legalFormField.get(0);
    var companyType = this.companyTypeField.get(0);
    var phone = this.phoneField.get(0);
    var fax = this.faxField.get(0);
    var email = this.emailField.get(0);

    // Mitabeiterzahlen befüllen
    if (data.numberOfEmployees_max == '-1')
    {
      if (data.numberOfEmployees_min == '0')
        this.employeeMinField.val('');
      else
        this.employeeMinField.val(data.numberOfEmployees_min);

      this.employeeMaxField.val('');
    }
    else
    {
      this.employeeMinField.val(data.numberOfEmployees_min);
      this.employeeMaxField.val(data.numberOfEmployees_max);
    }

    // Gesellschaftsform
    if (data.lfo_ID > 0)
    {
      Util.selectOpt(legalForm, data.lfo_ID);
    }

    // Firmentyp
    if (data.coty_ID > 0)
    {
      Util.selectOpt(companyType, data.coty_ID);
    }

    if (data.hasPhone)
    {
      phone.checked = true;
    }

    if (data.hasFax)
    {
      fax.checked = true;
    }

    if (data.hasEmail)
    {
      email.checked = true;
    }
  }
});;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/CP_Decider.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Entscheider".
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Entscheider".
 *
 * @constructor
 * @class
 * @extends ContentPanel
 * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Panels.
 * @param {Number} num Die Nummer des Panels.
 */
var CP_Decider = function(el, num)
{
  // Den Konstruktor von der Klasse ContentPanel aufrufen
  ContentPanel.call(this, el, num);

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl des Aufgabenbereichs.
   * @type {jQuery}
   */
  this.jobTaskField = this.el.find("#jobTask");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl der Funktion.
   * @type {jQuery}
   */
  this.jobTitleField = this.el.find("#jobTitle");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl der Qualifikation.
   * @type {jQuery}
   */
  this.acdTitleField = this.el.find("#academicTitle");

  /**
   * jQuery-Objekt für die Checkbox "Keine Geschäftsführer".
   * @type {jQuery}
   */
  this.noCeoField = this.el.find("#noCeo");

  /**
   * jQuery-Objekt für Eingabefeld "Max. Entscheider".
   * @type {jQuery}
   */
  this.inputMaxField = this.el.find("#inputMax");

  // Listener-Funktionen an Events binden.
  this.bindEventListeners();

  // Formular für AJAX-Absendung vorbereiten
  this.prepareForm();
};

// Vererbung der Eigenschaften/Methoden von der Klasse ContentPanel
CP_Decider.prototype = new ContentPanel();

$.extend(CP_Decider.prototype,
{
  /**
   * Listener-Funktionen an Events binden.
   */
  bindEventListeners: function()
  {
    this.jobTaskField.bind("change", this.onChangeJobTasks.evt(this));
  },

  /**
   * Auswahloptionen für Funktion laden und Select-Feld damit befüllen.
   * @param {Number} taskIndex Nummer des Aufgabenbereichs.
   */
  initJobTitles: function(taskIndex, preSelectValue)
  {
    if (taskIndex > 0)
    {
      var value = this.jobTaskField.get(0).options[taskIndex].value;
      var extraParams = { 'jta_ID': value  };
    }
    else
    {
      this.resetJobTitles(preSelectValue);
      return;
    }

    $.getJSON($_AJAX_URL + "?decider&act=loadJobTitles", extraParams, function(data)
    {

      var jobTitles = this.jobTitleField.get(0);

      jobTitles.options.length = 0;

      $.each(data, function(i, option)
      {
        if (option.value == preSelectValue)
        {
          jobTitles.options[i] = new Option(option.text, option.value, true, true);
        }
        else
        {
          jobTitles.options[i] = new Option(option.text, option.value);
        }
      });

      jobTitles.focus();

    }.tie(this));
  },

  /**
   * Listener-Funktion für Change-Event bei Auswahl eines Aufgabenbereichs.
   */
  onChangeJobTasks: function(evt, el)
  {
    this.initJobTitles(el.selectedIndex);
  },

  /**
   * Alle Funktionen anzeigen.
   */
  resetJobTitles: function(preSelectValue)
  {
    var options   = $_CACHE.allJobTitles;
    var jobTitles = this.jobTitleField[0];

    jobTitles.options.length = 0;

    $.each(options, function(i, option)
    {
      if (option.value == preSelectValue)
      {
        jobTitles.options[i] = new Option(option.text, option.value, true, true);
      }
      else
      {
        jobTitles.options[i] = new Option(option.text, option.value);
      }
    });
  },

  /**
   * Formular resetten. Siehe auch ContentPanel#resetForm.
   */
  resetForm: function()
  {
    this.jobTaskField[0].selectedIndex  = 0;
    this.resetJobTitles();

    this.noCeoField[0].checked = false;

    this.acdTitleField[0].selectedIndex = 0;

    this.inputMaxField.val("");
  },

  /**
   * Formular mit Kriteriumdaten befüllen. Siehe auch ContentPanel#setFormWithChoiceData.
   * @param {Object} data Daten des Kriteriums.
   */
  setFormWithChoiceData: function(data)
  {
    this.resetForm();

    // DOM-Elemente holen
    var jobTask  = this.jobTaskField.get(0);
    var jobTitle = this.jobTitleField.get(0);
    var acdTitle = this.acdTitleField.get(0);
    var noCeo    = this.noCeoField.get(0);
    var inputMax = this.inputMaxField.get(0);

    // Aufgabenbereich
    if (data.jta_ID > 0 && data.jti_ID == 0)
    {
      var jtaIndex = Util.selectOpt(jobTask, data.jta_ID);
      this.initJobTitles(jtaIndex);
    }
    else if (data.jta_ID > 0 && data.jti_ID > 0)
    {
      var jtaIndex = Util.selectOpt(jobTask, data.jta_ID);
      this.initJobTitles(jtaIndex, data.jti_ID);
    }
    else if (data.jti_ID > 0)
    {
      Util.selectOpt(jobTitle, data.jti_ID);
    }

    // Qualifikation
    if (data.acti_ID > 0)
    {
      Util.selectOpt(acdTitle, data.acti_ID);
    }

    // Keine Geschäftsführer
    if (data.noCeo)
    {
      noCeo.checked = true;
    }

    // Max. Entscheider
    if (data.inputMax)
    {
      this.inputMaxField.val(data.inputMax);
    }
  }
});;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/CP_Regional.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Regionale Auswahl".
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Erweiterte ContentPanel-Klasse für den Reiter "Regionale Auswahl".
 *
 * @constructor
 * @class
 * @extends ContentPanel
 * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Panels.
 * @param {Number} num Die Nummer des Panels.
 */
var CP_Regional = function(el, num)
{
  // Den Konstruktor von der Klasse ContentPanel aufrufen
  ContentPanel.call(this, el, num);

  /**
   * jQuery-Objekt für das Autocomplete-Feld (PLZ/Ort).
   * @type {jQuery}
   */
  this.ac = null;

  /**
   * Zusätzliche Parameter die bei Eingabe in das Autocomplete-Feld per AJAX übergeben werden.
   * @type {Object}
   */
  this.acParams =
  {
    selectedFederalState: "",
    selectedDistrict: ""
  };

  /**
   * jQuery-Objekt für die Auswahlbuttons "Bundesland", "Landkreis" und "PLZ/Umkreis".
   * @type {jQuery}
   */
  this.buttons = this.el.find(".switchBtns > li");

  /**
   * jQuery-Objekt für die zu den Auswahlbuttons gehörenden Inhalts-Panels.
   * @type {jQuery}
   */
  this.btnPanels = this.el.find(".btnPanels > div");

  /**
   * Nummer des aktiven Auswahlbutton.
   * @type {Number}
   */
  this.activeBtnIndex = -1;

  /**
   * Hier werden die Landkreise für ein ausgewähltes Bundesland zwischengespeichert, damit sie
   * nicht ständig per AJAX neu geladen werden müssen.
   * @type {Array}
   */
  this.districtCache = [];

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl des Bundeslandes.
   * @type {jQuery}
   */
  this.stateField = this.el.find("#dropdownStates");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl des Landkreises.
   * @type {jQuery}
   */
  this.districtField = this.el.find("#dropdownDistricts");

  /**
   * jQuery-Objekt für das Eingabefeld zur Eingabe des Orts.
   * @type {jQuery}
   */
  this.cityField = this.el.find("#inputPostalCodeCity");

  /**
   * jQuery-Objekt für das Select-Feld zur Auswahl des Umkreises.
   * @type {jQuery}
   */
  this.distanceField = this.el.find("#dropdownDistance");

  // Listener-Funktionen an Events binden.
  this.bindEventListeners();

  // Formular für AJAX-Absendung vorbereiten
  this.prepareForm();

  // Autocpmplete-Feld initialisieren
  //this.initAutoComplete();

  // Ersten Auswahlbutton auf aktiv setzen
  this.activateBtn(0);
};

// Vererbung der Eigenschaften/Methoden von der Klasse ContentPanel
CP_Regional.prototype = new ContentPanel();

$.extend(CP_Regional.prototype,
{
  /**
   * Listener-Funktionen an Events binden.
   */
  bindEventListeners: function()
  {
    this.el.find(".switchBtns").bind("click", this.onClickSwitchBtns.evt(this));
    this.stateField.bind("change", this.onChangeState.evt(this));
    this.districtField.bind("change", this.onChangeDistrict.evt(this));
  },

  /**
   * Autocpmplete-Feld initialisieren.
   */
  initAutoComplete: function()
  {
    this.ac = this.cityField.autocomplete($_AJAX_URL + "?regional&act=autoCompleteCity",
    {
      minChars: 1,
      delay: 800,
      matchSubset: false,
      matchContains: false,
      max: 0,
      mustMatch: false,
      width: 200,
      moreItems: false,
      extraParams: this.acParams
    });
  },

  /**
   * Listener-Funktion für Click-Event auf einen Auswahlbutton.
   */
  onClickSwitchBtns: function(evt, el)
  {
    evt.preventDefault();

    // get the parent <li> object of the event target (probably an <a> tag)
    var btn = $(evt.target).parent()[0];

    var btnIndex = this.buttons.index(btn);

    if (btnIndex != -1)
    {
      this.activateBtn(btnIndex);
    }
  },

  /**
   * Auswahlbutton auf aktiv setzen.
   * @param {Number} btnIndex Nummer des Button.
   */
  activateBtn: function(btnIndex)
  {
    btnIndex = parseInt(btnIndex);

    this.deactivateBtn();

    this.activeBtnIndex = btnIndex;

    this.buttons.eq(btnIndex).addClass("selected");

    this.btnPanels.eq(btnIndex).show();

    switch (btnIndex)
    {
      case 1:
        this.resetCity();
      break;

      case 2:
        this.resetState();
        this.resetDistrict();
      break;
    }
  },

  /**
   * Auswahlbutton auf inaktiv setzen.
   * @param {Number} btnIndex Nummer des Button.
   */
  deactivateBtn: function()
  {
    if (this.activeBtnIndex != -1)
    {
      this.buttons.eq(this.activeBtnIndex).removeClass("selected");
      this.btnPanels.eq(this.activeBtnIndex).hide();
      this.activeBtnIndex = -1;
    }
  },

  /**
   * Listener-Funktion für Change-Event bei Änderung des Bundeslandes.
   */
  onChangeState: function(evt, el)
  {
    if  (el.selectedIndex != "0")
    {
      this.getDistrictOptions();
    }
    else
    {
      if (countryCode != 'CH')
      {
        /* Landkreisbutton ausschalten */
        $(this.buttons[1]).hide();
      }

      this.acParams.selectedFederalState = "";

      this.destroyDistrictOptions();
    }

    //this.ac.trigger("flushCache");
  },

  /**
   * Listener-Funktion für Change-Event bei Änderung des Landkreises.
   */
  onChangeDistrict: function(evt, el)
  {
    if  (el.selectedIndex != 0)
    {
      var districts = $(el).get(0);

      /* Autocomplete mit neuem Landkreis aktualisieren */
      this.acParams.selectedDistrict = districts.options[districts.selectedIndex].value;
    }
    else
    {
      /* Autocomplete ohne Landkreis aktualisieren */
      this.acParams.selectedDistrict = "";
    }

    //this.ac.trigger("flushCache");
    this.cityField.get(0).value = "PLZ/Ort";
  },

  /**
   * Auswahloptionen für das Select-Feld zur Auswahl des Landkreises erzeugen.
   * @param {Array} data Die Daten für die Optionen.
   * @param {Number} preSelectIndex Die Nummer der Option die ausgewählt sein soll.
   */
  createDistrictOptions: function(data, preSelectValue)
  {
    var districts = this.districtField.get(0);

    districts.options.length = 0;

    $.each(data, function(i, option)
    {
      if (option.value == preSelectValue)
      {
        districts.options[i] = new Option(option.text, option.value, true, true);
      }
      else
      {
        districts.options[i] = new Option(option.text, option.value);
      }
    });
  },

  /**
   * Daten für Auswahloptionen (Landkreise) per AJAX oder aus dem Cache holen und damit
   * Select-Feld bauen.
   * @param {Number} preSelectIndex Die Nummer der Option die ausgewählt sein soll.
   */
  getDistrictOptions: function(preSelectValue)
  {
    var state = this.stateField.get(0);
    var stateIndex = state.selectedIndex;

    if (countryCode != 'CH')
    {
      var cache = this.districtCache[stateIndex] || false;

      if (cache !== false)
      {
        this.createDistrictOptions(cache, preSelectValue);
      }
      else
      {
        /* Laden/Aktualisieren Landkreisliste */
        $.getJSON($_AJAX_URL + "?regional&act=loadDistricts&selectedIndex=" + state.options[stateIndex].value, function(data)
        {

          this.createDistrictOptions(data, preSelectValue);
          this.districtCache[stateIndex] = data;

        }.tie(this));
      }

      this.cityField.val("PLZ/Ort");

      /* Landkreisbutton einschalten */
      $(this.buttons[1]).show();
    }

    this.acParams.selectedFederalState = state.options[stateIndex].value;
  },

  /**
   * Auswahloptionen (Landkreise) löschen.
   */
  destroyDistrictOptions: function()
  {
    var districts = this.districtField.get(0);
    districts.options.length = 0;
  },

  /**
   * Landkreis resetten.
   */
  resetState: function()
  {
    this.stateField[0].selectedIndex    = 0;

      /* Landkreisbutton ausschalten */
      $(this.buttons[1]).hide();
  },

  /**
   * Landkreis resetten.
   */
  resetDistrict: function()
  {
    this.districtField[0].selectedIndex = 0;
  },

  /**
   * PLZ/Umkreis resetten.
   */
  resetCity: function()
  {
    if ($_CNT_ID == '1')
      this.distanceField[0].selectedIndex = 0;

    this.cityField.val("PLZ/Ort");
  },

  /**
   * Formular resetten. Siehe auch ContentPanel#resetForm.
   */
  resetForm: function()
  {
    this.stateField[0].selectedIndex    = 0;
    this.resetDistrict();
    this.resetCity();

    $(this.buttons[1]).hide();
    // Ersten Auswahlbutton aktivieren
    this.activateBtn(0);
  },

  /**
   * Formular mit Kriteriumdaten befüllen. Siehe auch ContentPanel#setFormWithChoiceData.
   * @param {Object} data Daten des Kriteriums.
   */
  setFormWithChoiceData: function(data)
  {
    this.resetForm();

    var state = this.stateField.get(0);

    var activeBtn = 0;

    // Bundesland setzen
    if (data.fst_ID > 0)
    {
      Util.selectOpt(state, data.fst_ID);

      // Landkreise von diesem Bundesland holen
      this.getDistrictOptions(data.dst_ID);

      if (data.dst_ID > 0)
      {
        activeBtn = 1;
      }

      $(this.buttons[1]).show();
    }

    // Ort-Eingabefeld befüllen
    if (data.cit_city != "" || data.cit_postalCode != "")
    {
      var input = "";

      if (data.cit_city != "" && data.cit_postalCode != "")
      {
        input = data.cit_postalCode + " " + data.cit_city;
      }
      else if (data.cit_city == "" && data.cit_postalCode != "")
      {
        input = data.cit_postalCode;
        if (data.distance > 0)
        {
          $('#dropdownDistance').val(data.distance);
        }
      }
      else if (data.cit_city != "" && data.cit_postalCode == "")
      {
        input = data.cit_city;
      }

      this.cityField.get(0).value = input;

      activeBtn = 2;
    }

    this.activateBtn(activeBtn);
  }
});;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/Choice.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Objekt zum Verwalten einer Auswahl, T@M-Frontend mod_addresses
 *
 * Aus der Choice-Klasse wird für jedes Kriterium ein Choice-Objekt erzeugt.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig
/**
 * Aus der Choice-Klasse wird für jedes Kriterium ein Choice-Objekt erzeugt.
 *
 * @constructor
 * @class
 * @param {ChoiceBlock} choiceBlock Der Kriteriumblock, zu der dieses Kriterium gehört.
 * @param {Number} num Die Nummer des Kriteriums.
 * @param {String, Element} el CSS-Selektor oder DOM-Element des Kriteriums.
 * @param {Boolean} create Soll das DOM-Element des Kriteriums neu erzeugt werden ?
 * @param {Object} data Daten für die Erzeugung des DOM-Elements.
 */
var Choice = function(choiceBlock, num, el, create, data)
{
  /**
   * jQuery-Objekt des Kriteriums.
   * @type {jQuery}
   */
  this.el = (el) ? $(el) : null;

  /**
   * Hier wird die Nummer des Kriteriums gespeichert.
   * @type {Number}
   */
  this.index = num;

  /**
   * Das letzte Element (Zeile) des Kriteriums. Enthält die Trefferzahlen.
   * @type {jQuery}
   */
  this.lastItem = null;

  /**
   * Verweis auf den Kriteriumblock, in der sich dieses Kriterium befindet.
   * @type {ChoiceBlock}
   */
  this.choiceBlock = choiceBlock;

  // Neues DOM-Element für Kriterium erzeugen
  if (create && data)
  {
    this.create("add", data);
  }
  // Bestehendes DOM-Element verwenden
  else
  {
    this.lastItem = this.el.find("table tr:last");
  }
};

Choice.prototype =
{
  /**
   * Neues DOM-Element für Kriterium via HTML-Code erzeugen und anzeigen.
   * @param {String} mode Bei "replace" wird das vorhandene Kriterium-Element ersetzt.
   * @param {Object} data Die Daten des Kriteriums.
   */
  create: function(mode, data)
  {
    // Basis HTML-Code für das Kriterium
    var tpl = new $.Template(
      '<div choice="{num}" class="choiceStyle" style="display: none"{exclude}>',
        '<table  class="choice_list" cellpadding="0" cellspacing="0" border="0">',
        '</table>',
      '</div>'
    );

    // HTML-Code für eine Zeile
    var itemTpl = new $.Template(
      '<tr>',
        '<td colspan="3">{title}</td>',
      '</tr>'
    );

    // HTML-Code für die letzte Zeile (mit Info-Icon + Zahlen)
    var itemTpl_info = new $.Template(
      '<tr>',
        '<td class="col1">{title}</td>',
        (($_DEBUG == "1") ? '<td class="alignRight">{overallHits}</td>' : '<td class="alignRight">&nbsp;</td>'),
        (($_PERF != "normal") ? '<td >' : '<td class="chcInfoIcon">'),
        '<input type="hidden" value="{overallHits}" /><input type="hidden" value="{filteredHits}" /></td>',
      '</tr>'
    );

    var numStr = String(this.index);

    var exc = data.exclude ? ' exclude="true"' : '';

    var choiceEl = tpl.apply({ 'num': numStr, 'exclude': exc });

    var insertRows = choiceEl.find("table");

    var itemsHtml = "";
    // Alle Zeilen eines Kriteriums erstellen
    for (var i = 0; i < data.items.length; i++)
    {
      if (i == data.items.length - 1)
      {
        if (data.exclude)
        {
          data.items[i].title = '<span class="markChoiceExclude">*</span> ' + data.items[i].title;
          //console.log(data);
        }

        this.lastItem = itemTpl_info.apply({ 'title': data.items[i].title, 'overallHits': data.overallHits, 'filteredHits': data.filteredHits });

        insertRows.append(this.lastItem);
      }
      else
      {
        insertRows.append(itemTpl.apply(data.items[i]));
      }
    }

    // Kriterium ersetzen
    if (mode === "replace")
    {
      this.el.after(choiceEl);
      this.el.remove();
    }
    // Kriterium neu erstellen
    else
    {
      this.choiceBlock.el.append(choiceEl);
    }

    setTimeout(function()
    {

      this.el = choiceEl;
      this.el.show("middle");

    }.tie(this), 10);
  },

  /**
   * DOM-Element von diesem Kriterium ersetzen.
   * @param {Object} data Die neuen Daten des Kriteriums.
   */
  replace: function(data)
  {
    this.create("replace", data);
  },

  /**
   * Kriterium entsprechend markieren/hervorheben, wenn es dabei ist geändert zu werden.
   */
  enableEditStyle: function()
  {
    this.el.addClass("choiceStyleEdit");
  },

  /**
   * Markierung für das Ändern des Kriteriums wieder entfernen.
   */
  disableEditStyle: function()
  {
    this.el.removeClass("choiceStyleEdit");
  },

  /**
   * Kriterium markieren/hervorheben, wenn es ausgewählt (angeklickt) wurde.
   */
  setActive: function()
  {
    this.el.addClass("choiceStyleActive");
  },

  /**
   * Markierung für das Auswählen des Kriteriums wieder entfernen.
   */
  setInActive: function()
  {
    this.el.removeClass("choiceStyleEdit");
    this.el.removeClass("choiceStyleActive");
  },

  /**
   * Den direkten Vorgänger von diesem Kriterium ermitteln.
   * @return {Choice}
   */
  prevChoice: function()
  {
    var prevNum = this.index - 1;

    while (this.choiceBlock.choices[prevNum] === undefined && prevNum >= 0)
    {
      prevNum--;
    }

    return this.choiceBlock.choices[prevNum] || null;
  },

  /**
   * Den direkten Nachfolger von diesem Kriterium ermitteln.
   * @return {Choice}
   */
  nextChoice: function()
  {
    var nextNum = this.index + 1;

    while (this.choiceBlock.choices[nextNum] === undefined && nextNum < this.choiceBlock.choices.length)
    {
      nextNum++;
    }

    return this.choiceBlock.choices[nextNum] || null;
  },

  /**
   * Die Nummer von diesem Kriterium ändern (auch im DOM-Element).
   * @param {Number} newIndex Die neue Nummer.
   */
  changeIndex: function(newIndex)
  {
    this.index = parseInt(newIndex);

    newIndex = new String(newIndex);
    this.el.attr("choice", newIndex);
  },

  /**
   * Die Trefferzahlen von diesem Kriterium aktualisieren.
   * @param {Object} data Die neuen Trefferzahlen.
   */
  updateNumbers: function(data)
  {
    this.lastItem.find("td:nth(1)").text(data.overall);

    var info = this.lastItem.find("td:nth(2)");

    info.find("input:nth(0)").val(data.overall);
    info.find("input:nth(1)").val(data.filtered);
  },

  /**
   * Entfernt das DOM-Element von diesem Kriterium aus dem DOM-Baum
   * und lässt es damit vom Bildschirm verschwinden.
   */
  remove: function()
  {
    this.el.remove();
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/ChoiceBlock.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Objekt zum Verwalten einer Auswahl, T@M-Frontend mod_addresses
 *
 * Aus der ChoiceBlock-Klasse wird für jeden Kriteriumblock innerhalb einer Selektion
 * ein ChoiceBlock-Objekt erzeugt. Dieses kann wiederum beliebig viele Kriterien in Form
 * von Choice-Objekten (siehe Choice.class.js) enthalten.
 * Jeder Kriteriumblock steht für genau einen Reiter im Contentbereich und enthält jeweils nur
 * Kriterien, die über diesen zugehörigen Reiter erstellt wurden.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Aus der ChoiceBlock-Klasse wird für jeden Kriteriumblock innerhalb einer Selektion
 * ein ChoiceBlock-Objekt erzeugt. Dieses kann wiederum beliebig viele Kriterien in Form
 * von Choice-Objekten (siehe Choice.class.js) enthalten.
 * Jeder Kriteriumblock steht für genau einen Reiter im Contentbereich und enthält jeweils nur
 * Kriterien, die über diesen zugehörigen Reiter erstellt wurden.
 *
 * @constructor
 * @class
 * @param {Selection} selection Die Selektion, zu der dieser Kriteriumblock gehört.
 * @param {String, Element} el CSS-Selektor oder DOM-Element des Kriteriumblocks.
 * @param {Number} num Die Nummer des Kriteriumblocks.
 */
var ChoiceBlock = function(selection, el, num)
{
  /**
   * jQuery-Objekt des Kriteriumblocks.
   * @type {jQuery}
   */
  this.el = $(el);

  /**
   * Hier wird die Nummer des Kriteriumblocks gespeichert.
   * @type {Number}
   */
  this.index = num;

  /**
   * Verweis auf die Selektion, in der sich dieser Kriteriumblock befindet.
   * @type {Selection}
   */
  this.selection = selection;

  /**
   * Speichert die Kriterien in diesem Kriteriumblock.
   * @type {Array}
   */
  this.choices = [];

  // Kriteriumblock initialisieren
  this.init();
};

ChoiceBlock.prototype =
{
  /**
   * Kriterien aus DOM-Baum auslesen und speichern.
   */
  init: function()
  {
    var self = this;

    this.el.find("div[@choice]").each(function(i)
    {
      self.addChoice(this);
    });
  },

  /**
   * Im DOM-Baum bereits vorhandenes Kriterium diesem Kriteriumblock hinzufügen.
   * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Kriteriums.
   */
  addChoice: function(el)
  {
    var num = this.choices.length;
    this.choices.push(new Choice(this, num, el, false));
  },

  /**
   * Neues Kriterium erzeugen, darstellen und speichern.
   * @param {Object} data Die Kriteriumdaten.
   */
  createChoice: function(data)
  {
    if (data.items.length > 0)
    {
      var num = this.choices.length;

      if (this.el.css("display") == "none")
      {
        this.el.show("middle", function()
        {
          this.choices.push(new Choice(this, num, null, true, data));
        }.tie(this));
      }
      else
      {
        this.choices.push(new Choice(this, num, null, true, data));
      }
    }
  },

  /**
   * Gibt, falls vorhanden, das Kriterium mit der angegebenen Nummer zurück, ansonsten false.
   * @param {Number} num Die Nummer des Kriteriums.
   * @return {Choice, Boolean}
   */
  getChoice: function(num)
  {
    num = parseInt(num);

    if (this.choiceExists(num))
    {
      return this.choices[num];
    }

    return false;
  },

  /**
   * Prüft, ob ein Kriterium mit der angegebenen Nummer in diesem Kriteriumblock existiert.
   * @param {Number} num Die Nummer des Kriteriums.
   * @return {Boolean}
   */
  choiceExists: function(num)
  {
    if (num in this.choices && this.choices[num] !== undefined)
    {
      return true;
    }

    return false;
  },

  /**
   * Tauscht die Position von zwei Kriterien innerhalb von diesem Kriteriumblock.
   * @param {Choice} choiceOne Erstes Kriterium.
   * @param {Choice} choiceTwo Zweites Kriterium.
   */
  swapChoices: function(choiceOne, choiceTwo)
  {
    var numOne = choiceOne.index;
    var numTwo = choiceTwo.index;

    choiceOne.changeIndex(numTwo);
    choiceTwo.changeIndex(numOne);

    this.choices[numOne] = choiceTwo;
    this.choices[numTwo] = choiceOne;
  },

  /**
   * Löscht ein Kriterium aus diesem Kriteriumblock.
   * @param {Number} num Die Nummer des Kriteriums.
   */
  removeChoice: function(num)
  {
    if (this.choiceExists(num))
    {
      this.selection.deactivateChoice();

      this.choices[num].remove();
      this.choices.splice(num, 1);

      this.cleanupChoices(num);

      if (this.choices.length == 0)
      {
        this.selection.removeChoiceBlock(this.index);
      }
    }
  },

  /**
   * Muss ausgeführt werden, nachdem ein Kriterium gelöscht wurde, um sicherzustellen,
   * dass die verbliebenen Choice-Objekte die richtige Kriteriumnummer besitzen.
   * @param {Number} startNum Die Nummer des Kriteriums, ab der mit der Korrektur begonnen werden soll.
   */
  cleanupChoices: function(startNum)
  {
    for (var i = startNum; i < this.choices.length; i++)
    {
      this.choices[i].changeIndex(i);
    }
  },

  /**
   * Trefferzahlen von allen Kriterien in diesem Kriteriumblock aktualisieren.
   * @param {Array} data Die neuen Zahlendaten.
   */
  updateChoiceNumbers: function(data)
  {
    //console.log(data.length);

    for (var i = 0; i < data.length; i++)
    {
      this.choices[i].updateNumbers(data[i]);
    }
  },

  /**
   * Kriteriumblock ausblenden.
   */
  hide: function()
  {
    this.el.hide();
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/ContentManager.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Der ContentManager verwaltet die Inhalte und Funktionalität der einzelnen Reiter.
 *
 * Jedem Reiter ist ein erweitertes ContentPanel-Objekt zugeteilt (siehe CP_(.*).class.js).
 * Diese Objekte sind von der Basisklasse ContentPanel (siehe ContentPanel.class.js) abgeleitet,
 * d.h. die Methoden/Eigenschaften in ContentPanel stehen auch den erweiterten Objekten zur Verfügung.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig
/**
 * Der ContentManager verwaltet die Inhalte und Funktionalität der einzelnen Reiter.
 * Jedem Reiter ist ein erweitertes ContentPanel-Objekt zugeteilt (siehe CP_(.*).class.js).
 * Diese Objekte sind von der Basisklasse ContentPanel (siehe ContentPanel.class.js) abgeleitet,
 * d.h. die Methoden/Eigenschaften in ContentPanel stehen auch den erweiterten Objekten zur Verfügung.
 *
 * @class
 * @static
 */
var ContentManager =
{
  /**
   * Speichert die jQuery-Objekte der Reiter-Buttons
   * @type {Array}
   */
  tabs: [],

  /**
   * Speichert die jQuery-Objekte der Reiter-Inhaltsboxen
   * @type {Array}
   */
  contentPanels: [],

 /**
  * Nummer des aktiven Reiter
  * @type {Number}
  */
  activePanelIndex: -1,

  /**
  * ContentManager initialisieren
  */
  init: function()
  {
    this.tabs = $("#tabs > li");

    var panels = $("#contentPanels > div");

    // Die erweiterten ContentPanel-Objekte erzeugen und speichern.
    this.contentPanels.push(new CP_Regional(panels[0], 0));
    this.contentPanels.push(new CP_Branches(panels[1], 1));
    this.contentPanels.push(new CP_CompanyCriterias(panels[2], 2));
    this.contentPanels.push(new CP_Decider(panels[3], 3));

    // Aktiven Reiter setzen.
    // Beim Laden der Seite steht in der globalen Variable $_ACTIVE_TAB die Nummer
    // des Reiters, der ausgewählt/aktiv sein soll.
    this.activatePanel($_ACTIVE_TAB);

    // Listener-Funktion für Click-Event registrieren.
    $("#tabs").bind("click", this.onClick.evt(this));

    // Listener-Funktion für Click-Event auf Länderauswahl registrieren.
    $("#countrySelectionSmall").bind("click", this.onClickCountryFlag.evt(this));
  },

  /**
   * Listener-Funktion für Click-Event auf Länderauswahl
   */
  onClickCountryFlag: function(evt, el)
  {
    // Standardaktionen bei Klick verhindern.
    evt.preventDefault();

    // Element, auf das geklickt wurde.
    var target = $(evt.target);

    // Nur ausführen, wenn target ein Bild ist
    if (target.is("img"))
    {
      var country = target.parents("div:first");

      if (country.size() > 0)
      {
        // Land auf das geklickt wurde.
        var cnt = country.attr("title");

        // Dialog öffnen
        DialogManager.get("changeCountry").show(cnt);
      }
    }
  },

  /**
   * Listener-Funktion für Click-Event
   */
  onClick: function(evt, el)
  {
    evt.preventDefault();

    var tab = $(evt.target).parent("li")[0];

    var tabIndex = this.tabs.index(tab);

    if (tabIndex != -1)
    {
      this.activatePanel(tabIndex, true);
    }
  },

  /**
   * Aktiviert einen Reiter und zeigt den zugehörigen Inhalt an.
   * @param {Number} num Die Nummer des Reiters
   */
  activatePanel: function(num, resetActiveChoice)
  {
    num = parseInt(num);

    if (resetActiveChoice)
    {
      SelectionManager.getActive().deactivateChoice();
    }

    this.deactivatePanel();

    this.activePanelIndex = num;
    var tabNr = num + 1;

    this.tabs.eq(num).addClass("selected");

    this.contentPanels[num].showPanel();
  },

  /**
   * Deaktiviert den aktuell aktivierten Reiter.
   */
  deactivatePanel: function()
  {
    if (this.activePanelIndex != -1)
    {
      this.tabs.eq(this.activePanelIndex).removeClass("selected");
      this.contentPanels[this.activePanelIndex].hidePanel();
      this.activePanelIndex = -1;
    }
  },

  /**
   * Gibt die derzeit aktivierte Reiter-Inhaltsbox zurück
   * @return {CP_Regional, CP_Branches, CP_CompanyCriterias, CP_Decider}
   */
  getActivePanel: function()
  {
    return this.contentPanels[this.activePanelIndex];
  },

  /**
   * Setzt die Formulare in allen Reitern auf den Ursprungszustand zurück.
   */
  resetAllForms: function()
  {
    for (var i = 0; i < this.contentPanels.length; i++)
    {
      this.contentPanels[i].resetForm();
    }

    // Auf Regionale Auswahl springen
    this.activatePanel(0);
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/DialogManager.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Verwaltet alle Dialoge.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Verwaltet alle Dialoge.
 *
 * @class
 * @static
 */
var DialogManager =
{
  /**
   * Hier werden alle Dialoge gespeichert.
   * @type {Array}
   */
  dialogs: [],

  /**
   * Erstellt alle Dialoge und speichert sie.
   */
  init: function()
  {
    // Login Dialog
    this.add("login", "#dialog-0", function(btn, customUrl)
    {
      if (btn == "yes")
      {
        var url = customUrl || $_BASE + "login/" + $_QSID;
        window.location = url;
      }

      this.hide();
    });

    // Dialog bei Selektion löschen
    this.add("deleteSelection", "#dialog-1", function(btn)
    {
      if (btn == "yes")
      {
        var selNum = SelectionManager.getActive().index;

        window.location = $_BASE + "?do=deleteSelection&selNum=" + selNum + $_ASID;
      }

      this.hide();
    });

    // Dialog bei ALLE Selektionen löschen
    this.add("deleteAllSelections", "#dialog-2", function(btn)
    {
      if (btn == "yes")
      {
        window.location = $_BASE + "?do=deleteSelection" + $_ASID;
      }

      this.hide();
    });

    // Dialog für die Länderauswahl
    this.add("changeCountry", "#dialog-3", function(btn, cnt)
    {
      if (btn == "yes")
      {
        window.location = $_BASE + "?do=saveSelections&country_to_change=" + cnt + $_ASID;
      }
      else if (btn == "no")
      {
        window.location = $_BASE + "?do=deleteSelection&country=" + cnt + $_ASID;
      }

      this.hide();
    });

    // Dialog für die Länderauswahl
    this.add("hasLoadedSel", "#dialog-4", function(btn)
    {
      if (btn == "insert")
      {
        window.location = $_BASE + "ordering/?do=offerCrossSection&loadedSelSaveMode=insert" + $_ASID;
      }
      else if (btn == "update")
      {
        window.location = $_BASE + "ordering/?do=offerCrossSection&loadedSelSaveMode=update" + $_ASID;
      }

      this.hide();
    });

    // Dialog für die Länderauswahl
    this.add("noCalc", "#dialog-5", function(btn)
    {
      this.hide();
    });

    // Dialog / Hinweis wiederholung des Kriteriums
    this.add("noMultiple", "#dialog-6", function(btn)
    {
      this.hide();
    });
  },

  /**
   * Neuen Dialog hinzufügen.
   * @param {String} dialogName Name des Dialogs. Damit wird er dann später aufgerufen.
   * @param {String, Element} el CSS-Selektor oder DOM-Element für den Dialog.
   * @param {Function} [clickHandler] Callback-Funktion die aufgerufen wird, sobald ein Button im Dialog geklick wurde.
   */
  add: function(dialogName, el, clickHandler)
  {
    var h = clickHandler || this._defaultHandler;

    var dialog = { 'name': dialogName, 'obj': new Dialog(el, h) };

    this.dialogs.push(dialog);
  },

  /**
   * Auf einen bestimmten Dialog zugreifen.
   * @param {String} dialogName Name des Dialogs.
   */
  get: function(dialogName)
  {
    for (var i = 0; i < this.dialogs.length; i++)
    {
      if (this.dialogs[i].name == dialogName)
        return this.dialogs[i].obj;
    }

    return null;
  },

  /**
   * Standard Callback-Funktion.
   */
  _defaultHandler: function(btn)
  {
    //console.log(btn);
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/Exception.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Statische Klasse für Fehlerbehandlung. Insbesondere für AJAX-Abfragen.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Statische Klasse für Fehlerbehandlung. Insbesondere für AJAX-Abfragen.
 *
 * @class
 * @static
 */
var Exception =
{
  noticeMessageIdPrefix: "notification-message-",

  errorMessageIdPrefix: "error-message-",

  /**
   * Fehler verarbeiten und Meldung anzeigen.
   * @param {Object} e Fehler-Objekt.
   */
  handle: function(e)
  {
    if (!e || !e.type || !e.code)
      return false;

    var show_message = true;

    switch (e.type)
    {
      case "notice":

        var msgEl = $("#" + this.noticeMessageIdPrefix + e.code);

      break;

      case "error":

        var msgEl = $("#" + this.errorMessageIdPrefix + e.code);


        /**
         * Wenn mehrfaches kriterium, dialog Zeigen.
         */
        if (e.code == "1")
        {
          show_message = false;
          $_allow_unblock_screen = false; // gesetzt in initApp.js
          DialogManager.get("noMultiple").show();
        }

        if (e.code == "0")
        {
          console.log("AJAX-Fehler:");
          console.log(e.data);
        }

      break;
    }

    /**
     * Wenn nichts die Anzeige der Meldung hindert, zeigen
     */
    if (show_message)
    {
      msgEl.fadeIn("slow", function()
      {
        (function() { msgEl.fadeOut("slow"); }).delay(5000);
      });
    }

  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/Selection.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Aus der Selection-Klasse wird für jede sichtbare Selektion eine Selection-Objekt erzeugt.
 * Die jeweilige Selektion wird dann über dieses Objekt angesprochen und verwaltet.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Aus der Selection-Klasse wird für jede sichtbare Selektion eine Selection-Objekt erzeugt.
 * Die jeweilige Selektion wird dann über dieses Objekt angesprochen und verwaltet.
 *
 * @constructor
 * @class
 * @param {String, Element} el CSS-Selektor oder DOM-Element der Selektion.
 * @param {Number} num Die Nummer der Selektion.
 */
var Selection = function(el, num)
{
  /**
   * jQuery-Objekt der Selektion.
   * @type {jQuery}
   */
  this.el = $(el);

  /**
   * Hier wird die Nummer der Selektion gespeichert. Über diese Nummer kann man die Selektion auch
   * über den SelectionManager ansprechen. Außerdem steht die gleiche Nummer auch im id-Attribut
   * des DOM-Elements von dieser Selektion.
   * @type {Number}
   */
  this.index = num;

  /**
   * Speichert das gerade aktive/ausgewählte Kriterium.
   * @type {Choice}
   */
  this.activeChoice = null;

  /**
   * Alle Kriteriumblöcke werden hier gespeichert.
   * @type {Array}
   */
  this.choiceBlocks = [];

  /**
   * jQuery-Objekt zum Zugriff auf das, den Selektionsnamen umgebene, DOM-Element.
   * @type {jQuery}
   */
  this.selectionTitle = this.el.find(".selectionTitle:first");

  /**
   * jQuery-Objekt zum Zugriff auf das, Max. gewünscht umgebene, DOM-Element.
   * @type {jQuery}
   */
  this.maxTotalHits = this.el.find(".maxTotalHits:first");

  /**
   * jQuery-Objekt zum Zugriff auf das, Max. Entscheider umgebene, DOM-Element.
   * @type {jQuery}
   */
  this.maxDecider = this.el.find(".maxDecider:first");

  // Selektion initialisieren
  this.init();

  // Listener-Funktionen an Events binden.
  this.bindEventListeners();

  // Formulare in dieser Selektion für AJAX-Absendung vorbereiten
  this.initForms();
};

Selection.prototype =
{
  /**
   * Kriteriumblöcke auslesen und speichern
   */
  init: function()
  {
    var self = this;

    this.el.find(".active div[@choiceblock]").each(function(i)
    {
      var num = parseInt($(this).attr("choiceblock"));
      self.addChoiceBlock(this, num);
    });
  },

  /**
   * Listener-Funktionen an Events binden.
   */
  bindEventListeners: function()
  {
    this.selectionTitle.find("div:last a").bind("click", this.onClickTitle.evt(this));

    this.maxTotalHits.find("td:nth(1) a").bind("click", this.onClickMaxTotalHits.evt(this));
    this.maxDecider.find("td:nth(1) a").bind("click", this.onClickMaxDecider.evt(this));

    this.el.find(".active").bind("click", this.onClickChoice.evt(this));

    this.el.find(".active").bind("mouseover", this.onMouseOverChoice.evt(this));
    this.el.find(".active").bind("mouseout", this.onMouseOutChoice.evt(this));

    this.el.find(".inActive").bind("mouseover", this.onMouseOverInActive.evt(this));
    this.el.find(".inActive").bind("mouseout", this.onMouseOutInActive.evt(this));
  },

  /**
   * Formulare in dieser Selektion für AJAX-Absendung vorbereiten
   */
  initForms: function()
  {
    var self = this;

    this.selectionTitle.find("form").ajaxForm(
    {
      dataType: "json",
      beforeSubmit: function(formData)
      {
        formData.push({ name: "selNum", value: self.index });
      },
      success: function(data)
      {
        self.changeTitle(data.title);
      }
    });

    this.maxDecider.find("form").ajaxForm(
    {
      dataType: "json",
      beforeSubmit: function(formData)
      {
        formData.push({ name: "selNum", value: self.index });
      },
      success: function(data)
      {
        var max = self.maxDecider;
        var maxDeciderStr = String(data.maxDecider);

        max.find("td:nth(1) span").text(maxDeciderStr);
        max.find("form > input:text").val(maxDeciderStr);

        max.find("td:nth(2)").hide("fast", function()
        {
          max.find("td:nth(1)").show();
        });

        self.changeNumHits(undefined, data.totalHitsPersons);
      }
    });

    this.maxTotalHits.find("form").ajaxForm(
    {
      dataType: "json",
      beforeSubmit: function(formData)
      {
        formData.push({ name: "selNum", value: self.index });
      },
      success: function(data)
      {
        var max = self.maxTotalHits;
        var maxHitsStr = String(data.maxHits);

        self.el.find(".inActive:first li:last").text(maxHitsStr);

        max.find("td:nth(1) span").text(maxHitsStr);
        max.find("form > input:text").val(maxHitsStr);

        max.find("td:nth(2)").hide("fast", function()
        {
          max.find("td:nth(1)").show();
        });

        if (data.maxHits <= 0)
				{
			    self.changeNumHits(data.totalHitsFirms, data.totalHitsPersons);
		    }
      }
    });
  },

  /**
   * Listener-Funktion für Click-Event auf das Icon "Selektionsname ändern".
   */
  onClickTitle: function(evt, el)
  {
    evt.preventDefault();

    var selTitle = this.selectionTitle;

    selTitle.find("div:last").hide("fast", function()
    {
      selTitle.find("div:first").show();
    });
  },

  /**
   * Listener-Funktion für Click-Event auf das Icon "Max. gewünscht ändern".
   */
  onClickMaxTotalHits: function(evt, el)
  {
    evt.preventDefault();

    var max = this.maxTotalHits;

    max.find("td:nth(1)").hide("fast", function()
    {
      max.find("td:nth(2)").show();
    });
  },

  /**
   * Listener-Funktion für Click-Event auf das Icon "Max. Entscheider ändern".
   */
  onClickMaxDecider: function(evt, el)
  {
    evt.preventDefault();

    var max = this.maxDecider;

    max.find("td:nth(1)").hide("fast", function()
    {
      max.find("td:nth(2)").show();
    });
  },

  /**
   * Listener-Funktion für Click-Event auf ein Kriterium.
   */
  onClickChoice: function(evt, el)
  {
    //evt.preventDefault();

    var target = $(evt.target);
    var choiceDom = target.parents("div[@choice]:first");

    // Nur ausführen, wenne es sich um ein Kriterium handelt
    if (choiceDom.size() == 1)
    {
      var choiceBlockDom = choiceDom.parents("div[@choiceblock]:first");
      var blockNum = parseInt(choiceBlockDom.attr("choiceblock"));
      var choiceNum = parseInt(choiceDom.attr("choice"));

      var choice = this.getChoiceBlock(blockNum).getChoice(choiceNum);

      if (choice === this.activeChoice)
      {
        this.deactivateChoice();
      }
      else
      {
        this.activateChoice(choice);
      }
    }
  },

  /**
   * Listener-Funktion für Mouseover-Event über das Info-Icon rechts neben jedem Kriterium.
   */
  onMouseOverChoice: function(evt, el)
  {
    evt.preventDefault();

    var tooltip = TooltipManager.get("choiceInfo");

    if (!tooltip.isDisplayed)
    {
      var target = $(evt.target);
      var choice = target.parents("div[@choice]:first");
      var infoIcon = target.is("td.chcInfoIcon:first");

      if (infoIcon)
      {
        var offset = target.offset();

        var left = offset.left + TooltipManager.defaultLeft;
        var top = offset.top + TooltipManager.defaultTop;

        tooltip.show(left, top, target, choice);
      }
      else if (choice.size() == 1)
      {
        //console.log(choice);
        choice.addClass("choiceStyleOver");
      }
    }
  },

  /**
   * Listener-Funktion für Mouseout-Event bei Verlassen des Info-Icon rechts neben jedem Kriterium.
   */
  onMouseOutChoice: function(evt, el)
  {
    evt.preventDefault();

    var target = $(evt.target);
    var choice = target.parents("div[@choice]:first");
    var infoIcon = target.is("td.chcInfoIcon:first");

    var tooltip = TooltipManager.get("choiceInfo");

    if (infoIcon && tooltip.isDisplayed)
    {
      tooltip.hide();
    }
    else if (choice.size() == 1)
    {
      //console.log(choice);
      choice.removeClass("choiceStyleOver");
    }
  },

  /**
   * Listener-Funktion für Mouseover-Event über eine inaktive Selektion.
   */
  onMouseOverInActive: function(evt, el)
  {
    evt.preventDefault();

    var tooltip = TooltipManager.get("selectionTitle");

    if (!tooltip.isDisplayed)
    {
      var target = $(evt.target);

      if (target.is("li.showSelName"))
      {
        var offset = target.offset();

        var left = offset.left;
        var top = offset.top - 30;

        tooltip.show(left, top, this.selectionTitle);
      }
    }
  },

  /**
   * Listener-Funktion für Mouseout-Event bei Verlassen einer inaktiven Selektion.
   */
  onMouseOutInActive: function(evt, el)
  {
    evt.preventDefault();

    var target = $(evt.target);

    var tooltip = TooltipManager.get("selectionTitle");

    if (target.is("li.showSelName") && tooltip.isDisplayed)
    {
      tooltip.hide();
    }
  },

  /**
   * Stellt diese Selektion als aktiv/ausgewählt dar. Um zu garantieren, dass immer genau eine
   * Selektion aktiv ist sollte diese Funktion nicht direkt verwendet werden, sondern
   * SelectionManager#setActive.
   */
  setActive: function()
  {
    var active = this.el.find(".active");

    this.el.find(".inActive").hide("middle", function()
    {
      active.show("middle");
    });
  },

  /**
   * Stellt diese Selektion als inaktiv/abgewählt dar.
   */
  setInActive: function()
  {
    this.deactivateChoice();

    var inActive = this.el.find(".inActive");

    this.el.find(".active").hide("middle", function()
    {
      inActive.show("middle");
    });
  },

  /**
   * Falls ein Kriterium aktiv/ausgewählt ist wird true zurückgegeben, sonst false.
   * @return {Boolean}
   */
  isChoiceActive: function()
  {
    if (this.activeChoice !== null)
    {
        return true;
    }

    return false;
  },

  /**
   * Falls vorhanden, wird das aktive Kriterium zurückgegeben, ansonsten false.
   * @return {Choice, Boolean}
   */
  getActiveChoice: function()
  {
    if (this.isChoiceActive())
    {
      return this.activeChoice;
    }

    return false;
  },

  /**
   * Gibt den Kriteriumblock mit der angegebenen Nummer zurück oder false, falls er nicht existiert.
   * @param {Number} num Die Nummer des Kriteriumblocks.
   * @return {ChoiceBlock, Boolean}
   */
  getChoiceBlock: function(num)
  {
    num = parseInt(num);

    if (this.blockExists(num))
    {
      return this.choiceBlocks[num];
    }

    return false;
  },

  /**
   * Diese Funktion wird nach Klick auf "ändern" in der Toolbox ausgeführt.
   */
  editChoice: function()
  {
    // Wurde überhaupt eine Auswahl aktiviert/ausgewählt
    if (this.isChoiceActive())
    {
      // Aktive Auswahl holen
      var choice = this.getActiveChoice();
      var url = $_AJAX_URL + "?selection&act=getChoice" + $_ASID;

      // Erstmal die Daten der aktiven Auswahl vom Sever aus der Session holen
      $.getJSON(url, { "selNum": this.index, "chcBlockNum": choice.choiceBlock.index, "choiceNum": choice.index }, function(data)
      {
        // Wählt den richtigen Reiter für das Kriteriums aus und befüllt das
        // Formular des Reiters mit den Daten.
        ContentManager.activatePanel(choice.choiceBlock.index);

        //console.log(data.choice);

        ContentManager.getActivePanel().setFormWithChoiceData(data.choice);

        SelectionManager.enableEditMode();
      });
    }
  },

  /**
   * Diese Funktion wird nach Klick auf "nach oben/unten" in der Toolbox ausgeführt.
   * @param {String} direction Die Richtung in der geschoben wird.
   */
  moveChoice: function(direction)
  {
    // Wurde überhaupt eine Auswahl aktiviert
    if (this.isChoiceActive())
    {
      // Aktive Auswahl holen
      var choice = this.getActiveChoice();

      if (direction == "up")
      {
        var neighbourChoice = choice.prevChoice();
      }
      else
      {
        var neighbourChoice = choice.nextChoice();
      }

      if (neighbourChoice)
      {
        // Erstmal die Daten der aktiven Auswahl vom Sever aus der Session holen
        $.getJSON($_AJAX_URL + "?selection&act=moveChoice" + $_ASID, { "selNum": this.index, "chcBlockNum": choice.choiceBlock.index, "choiceNum": choice.index, "direction": direction }, function(data)
        {
          choice.choiceBlock.swapChoices(choice, neighbourChoice);

          if (direction == "up")
          {
            choice.el.insertBefore(neighbourChoice.el);
          }
          else
          {
            choice.el.insertAfter(neighbourChoice.el);
          }
        });
      }
    }
  },

  /**
   * Diese Funktion wird nach Klick auf "Kriterium -> löschen" in der Toolbox ausgeführt.
   */
  deleteChoice: function()
  {
    // Wurde überhaupt eine Auswahl aktiviert
    if (this.isChoiceActive())
    {
      // Aktive Auswahl holen
      var choice = this.getActiveChoice();

      // Erstmal die Daten der aktiven Auswahl vom Sever aus der Session holen
      $.getJSON($_AJAX_URL + "?selection&act=deleteChoice" + $_ASID, { "selNum": this.index, "chcBlockNum": choice.choiceBlock.index, "choiceNum": choice.index }, function(data)
      {

        choice.choiceBlock.removeChoice(choice.index);

        if (data.changed)
        {
          this.updateChoiceNumbers(data.changed);
        }

        this.changeNumHits(data.totalHitsFirms, data.totalHitsPersons);

        this.el.find(".selLoadedFromOrderIcon").css('display','none');

      }.tie(this));
    }
  },

  /**
   * Ein Kriterium auf aktiv setzen.
   * @param {Choice} choice Kriterium.
   */
  activateChoice: function(choice)
  {
    this.deactivateChoice();

    this.activeChoice = choice;
    this.activeChoice.setActive();

    ToolBox.activateChoice();
  },

  /**
   * Das gerade aktive Kriterium deaktivieren.
   */
  deactivateChoice: function()
  {
    if (this.isChoiceActive())
    {
      SelectionManager.disableEditMode();

      this.activeChoice.setInActive();
      this.activeChoice = null;

      ToolBox.deactivateChoice();
    }
  },

  /**
   * Änderung des Selektionsnamens sichtbar machen.
   * @param {String} title Neuer Selektionsname.
   */
  changeTitle: function(title)
  {
    var selTitle = this.selectionTitle;

    selTitle.find("div:last > strong").text(title);
    selTitle.find("form > input:text").val(title);

    selTitle.find("div:first").hide("fast", function()
    {
      selTitle.find("div:last").show();
    });
  },

  /**
   * Neues Kriterium dieser Selektion hinzufügen.
   * @param {Number} blockNum Die Nummer des Kriteriumblocks, in den das neue Kriterium eingefügt werden soll.
   * @param {Object} data Die Daten des Kriteriums.
   */
  createChoice: function(blockNum, data)
  {
    if (data)
    {
      this.getChoiceBlock(blockNum).createChoice(data);

      if (blockNum == 3)
      {
        this.el.find(".maxDecider:first").show();
      }

      if (data.changed)
      {
        this.updateChoiceNumbers(data.changed);
      }
      this.changeNumHits(data.totalHitsFirms, data.totalHitsPersons);

      this.el.find(".selLoadedFromOrderIcon").css('display','none');
    }
  },

  /**
   * Anhängig von $cfg['app']['performance'](etc/config.php) Ergebniszeilen
   * ein- / ausblenden;
   */
  hideResultlineBySpeedup2: function(totalHitsFirms, totalHitsPersons)
  {
    //console.log('totalHitsFirms: ' + totalHitsFirms);
    //console.log('totalHitsPersons: ' + totalHitsPersons);

    var $perf = (typeof($_PERF) == 'string') ? $_PERF : 'undefined';

    if($perf == 'speedup2')
    {

      if (totalHitsFirms == "" || totalHitsFirms == undefined)
      {
        this.el.find(".active:first .totalHitsFirms").css('display','none');
      }
      else
      {
        this.el.find(".active:first .totalHitsFirms").css('display','block');
      }

      if (String(totalHitsPersons) == "" || totalHitsPersons == undefined)
      {
        this.el.find(".active:first .totalHitsPersons").css('display','none');
      }
      else
      {
        this.el.find(".active:first .totalHitsPersons").css('display','block');
      }


    }
  },

  /**
   * Trefferzahlen aktualisieren (Gefundene Firmen und Gefundene Entscheider).
   * @param {Number} totalHitsFirms Die Trefferzahl für die Firmen.
   * @param {Number} [totalHitsPersons] Die Trefferzahl für die Personen/Entscheider.
   */
  changeNumHits: function(totalHitsFirms, totalHitsPersons)
  {

  /**
   * Bei 'speedup2' Ergebniszeilen ausblenden;
   */
   this.hideResultlineBySpeedup2(totalHitsFirms, totalHitsPersons);

   if (totalHitsFirms != undefined)
   {
     var totalHitsFirmsStr = String(totalHitsFirms);

     this.el.find(".inActive:first li:nth(1)").text(totalHitsFirmsStr);
     this.el.find(".active:first .totalHitsFirms:first td:nth(1)").text(totalHitsFirmsStr);
   }

   if (totalHitsPersons != undefined)
   {
     if (totalHitsPersons < 0)
       var totalHitsPersonsStr = '';
     else
       var totalHitsPersonsStr = String(totalHitsPersons);

     this.el.find(".inActive:first li:nth(1)").text(totalHitsPersonsStr);
     this.el.find(".active:first .totalHitsPersons:first td:nth(1)").text(totalHitsPersonsStr);
   }
  },

  /**
   * Kriterium ersetzten/überschreiben. Wird bei Änderung eines Kriteriums eingesetzt.
   * @param {Object} data Kriteriumdaten.
   */
  replaceChoice: function(data)
  {
    if (this.isChoiceActive())
    {
      this.activeChoice.replace(data);
      this.deactivateChoice();

      if (data.changed)
      {
        this.updateChoiceNumbers(data.changed);
      }

      this.changeNumHits(data.totalHitsFirms, data.totalHitsPersons);

      this.el.find(".selLoadedFromOrderIcon").css('display','none');
    }
  },


  /**
   * Prüft, ob ein Kriteriumblock mit der angegebenen Nummer existiert.
   * @param {Number} num Kriteriumblocknummer.
   * @return {Boolean}
   */
  blockExists: function(num)
  {
    if (num in this.choiceBlocks && this.choiceBlocks[num] !== undefined)
    {
      return true;
    }

    return false;
  },

  /**
   * Neuen Kriteriumblock dieser Selektion hinzufügen.
   * @param {Striing, Element} el CSS-Selektor oder DOM-Element des Kriteriumblocks.
   * @param {Number} num Kriteriumblocknummer.
   */
  addChoiceBlock: function(el, num)
  {
    this.choiceBlocks[num] = new ChoiceBlock(this, el, num);
  },

  /**
   * Kriteriumblock aus dieser Selektion löschen.
   * @param {Number} num Kriteriumblocknummer.
   */
  removeChoiceBlock: function(num)
  {
    if (this.blockExists(num))
    {
      this.choiceBlocks[num].hide();

      if (num == 3)
      {
        this.el.find(".maxDecider:first").hide();
      }
    }
  },

  /**
   * Trefferzahlen von allen Kriterien in dieser Selektion aktualisieren.
   * @param {Array} data Die neuen Zahlendaten.
   */
  updateChoiceNumbers: function(data)
  {
    // Branchen
    if (data[1])
    {
      this.choiceBlocks[1].updateChoiceNumbers(data[1]);
    }

    // Firmenbezogene Kriterien
    if (data[2])
    {
      this.choiceBlocks[2].updateChoiceNumbers(data[2]);
    }

    // Entscheider
    if (data[3])
    {
      this.choiceBlocks[3].updateChoiceNumbers(data[3]);
    }
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/SelectionManager.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Der SelectionManager verwaltet alle Selektionen.
 * Jede Selektion wird in einem Selection-Objekt (siehe Selection.class.js) festgehalten
 * und im SelectionManager gespeichert.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Der SelectionManager verwaltet alle Selektionen.
 * Jede Selektion wird in einem Selection-Objekt (siehe Selection.class.js) festgehalten
 * und im SelectionManager gespeichert.
 *
 * @class
 * @static
 */
var SelectionManager =
{
  /**
   * Speichert die aktive, ausgewählte Selektion.
   * @type {Selection}
   */
  active: null,

  /**
   * Hier sind alle Selektionen gespeichert
   * @type {Array}
   */
  selections: [],

  /**
   * Diese Eigenschaft gibt an, ob gerade ein Kriterium geändert/editiert wird (true) oder nicht (false)
   * @type {Boolean}
   */
  editChoiceMode: false,

  /**
   * SelectionManager initialisieren
   */
  init: function()
  {
    // Bei Laden der kompletten Seite werden die Selektion aus dem HTML-Code ausgelesen
    // und dem SelectionManager hinzugefügt.
    $("#selection .selectionItem").each(function(i)
    {
      SelectionManager.add(this);
    });

    // Listener-Funktion für Click-Event registrieren.
    $("#selection").bind("click", this.onClick.evt(this));

    // Aktive Selektion setzen.
    // Beim Laden der Seite steht in der globalen Variable $_ACTIVE_SELECTION_NUM die Nummer
    // der Selektion, die ausgewählt/aktiv sein soll.
    this.active = this.getSelection($_ACTIVE_SELECTION_NUM);
  },

  /**
   * Selektion hinzufügen.
   * @param {Element, String} el HTML-Element oder '#id' der Selektion
   */
  add: function(el)
  {
    // Nummer der neuen Selektion
    var num = this.selections.length;
    // Neues Selection-Objekt erzeugen dem Array SelectionManager#selections anfügen
    this.selections.push(new Selection(el, num));
  },

  /**
   * Listener-Funktion für Click-Event
   */
  onClick: function(evt, el)
  {
    // Element, auf das geklickt wurde.
    var target = $(evt.target);

    var selection = target.parents(".inActive:first");

    // Nur ausführen, wenn Selektion inaktiv
    if (selection.size() == 1)
    {
      // Selektionsnummer auslesen
      var num = parseInt(selection.parents(".selectionItem").attr("id").split("-")[1]);
      // Selektion aktivieren
      this.setActive(num);
    }
  },

  /**
   * Editiermodus aktivieren.
   * Vor dem Ändern eines Kriteriums wird diese Funktion ausgeführt.
   */
  enableEditMode: function()
  {
    if (!this.editChoiceMode)
    {
      this.editChoiceMode = true;

      this.getActive().activeChoice.enableEditStyle();

      ContentManager.getActivePanel().showEditButton();

      ToolBox.choiceMenuItems.eq(0).removeClass("active");
      ToolBox.choiceMenuItems.eq(1).removeClass("active");
      ToolBox.choiceMenuItems.eq(2).removeClass("active");
      ToolBox.choiceMenuItems.eq(3).removeClass("active");
    }
  },

  /**
   * Editiermodus deaktivieren.
   * Nach dem Ändern eines Kriteriums wird diese Funktion ausgeführt.
   */
  disableEditMode: function()
  {
    if (this.editChoiceMode)
    {
      this.editChoiceMode = false;

      this.getActive().activeChoice.disableEditStyle();

      var activePanel = ContentManager.getActivePanel();

      activePanel.hideEditButton();
      activePanel.resetForm();

      ToolBox.choiceMenuItems.eq(0).addClass("active");
      ToolBox.choiceMenuItems.eq(1).addClass("active");
      ToolBox.choiceMenuItems.eq(2).addClass("active");
      ToolBox.choiceMenuItems.eq(3).addClass("active");
    }
  },

  /**
   * Eine bestimmte Selektion holen.
   * @param {Number} num Die Nummer der Selektion
   * @return {Selection, Boolean}
   */
  getSelection: function(num)
  {
    num = parseInt(num);

    if (this.selectionExists(num))
    {
      return this.selections[num];
    }

    return false;
  },

  /**
   * Gibt die gerade aktive Selektion zurück.
   * @return {Selection}
   */
  getActive: function()
  {
    return this.active;
  },

  /**
   * Prüft, ob eine Selektion existiert.
   * @param {Number} num Die Nummer der Selektion
   * @return {Boolean}
   */
  selectionExists: function(num)
  {
    if (num in this.selections && this.selections[num] !== undefined)
    {
      return true;
    }

    return false;
  },

  /**
   * Eine Selektion aktivieren.
   * @param {Number} num Die Nummer der Selektion
   */
  setActive: function(num)
  {
    if (this.selectionExists(num))
    {
      if (this.active !== null)
      {
        this.active.setInActive();
      }

      this.active = this.getSelection(num);
      this.active.setActive();
    }
  },

  recalculateActiveSelection: function()
  {
    if (this.active !== null)
    {
      // Seite blocken
      $.blockUI();
      $("#ajaxIndicator").css("display", "block");
      $("#indicator_1").css("display", "block");

      var selNum = SelectionManager.getActive().index;
      window.location = $_BASE + "?do=recalculateSelection&selNum=" + selNum + $_ASID;
    }
  }

};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/ToolBox.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Die gesamte Funktionalität der Toolbox (Panel) ist hier gebündelt.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Die gesamte Funktionalität der Toolbox (Panel) ist hier gebündelt.
 *
 * @class
 * @static
 */
var ToolBox =
{
  /**
   * jQuery-Objekt der Toolbox.
   * @type {jQuery}
   */
  el: null,

  /**
   * jQuery-Objekt der Menüpunkte unter "Kriterium".
   * @type {jQuery}
   */
  choiceMenuItems: null,

  /**
   * jQuery-Objekt der Menüpunkte unter "Selektion".
   * @type {jQuery}
   */
  selectionMenuItems: null,

  /**
   * jQuery-Objekt der Menüpunkte unter "Alles".
   * @type {jQuery}
   */
  allMenuItems: null,

  /**
   * Toolbox initialisieren
   */
  init: function()
  {
    this.el = ($_TOOLBOX_VIEW == "big") ? $("#panelBig-active") : $("#panel-active");

    //console.log(this.el);

    this.el.bind("click", this.onClick.evt(this));

    this.choiceMenuItems    = this.el.find(".choiceMenuItems li a");
    this.selectionMenuItems = this.el.find(".selectionMenuItems li a");
    this.allMenuItems       = this.el.find(".allMenuItems li a");
  },

  /**
   * Menüpunkte aktivieren, wenn ein Kriterium ausgewählt wurde.
   */
  activateChoice: function()
  {
    this.choiceMenuItems.eq(0).addClass("active");
    this.choiceMenuItems.eq(1).addClass("active");
    this.choiceMenuItems.eq(2).addClass("active");
    this.choiceMenuItems.eq(3).addClass("active");
  },

  /**
   * Menüpunkte wieder deaktivieren, wenn ein Kriterium abgewählt wurde.
   */
  deactivateChoice: function()
  {
    this.choiceMenuItems.eq(0).removeClass("active");
    this.choiceMenuItems.eq(1).removeClass("active");
    this.choiceMenuItems.eq(2).removeClass("active");
    this.choiceMenuItems.eq(3).removeClass("active");
  },

  showLoadIndicator: function(nr)
  {
     $('#ajaxIndicator').css("display", "block");
     $('#indicator_1').css("display", "none");
     $('#indicator_2').css("display", "none");
     $('#indicator_3').css("display", "none");


     $('#indicator_' + nr).css("display", "block");
  },

  checkSelectionNames: function()
  {
    var i;
    var ret_val = true;
    var sel_names = $(".selectionTitle strong");

    for (i=0 ; i < sel_names.length ; i++)
    {
      if ($(sel_names[i]).text() == '')
      {
        ret_val = false;
      }
    }

    return ret_val;
  },

  /**
  * Listener-Funktion für Click-Event auf einen Menüpunkt.
  * Steuert die Aktionen, wenn ein Menüpunkt angegklickt wurde.
  */
  onClick: function(evt, el)
  {
    evt.preventDefault();

    var target = $(evt.target);

    if (target.is("a.active"))
    {
      var doAct = target.parent().attr("class");

      switch (doAct)
      {
        /**
         * Der Menüpunkt 'Auswahl -> hinzufügen' wurde geklickt
         */
        case "choiceAdd":

          ContentManager.getActivePanel().sendForm(false);

        break;

        /**
         * Der Menüpunkt 'Auswahl -> ausschließen' wurde geklickt
         */
        case "choiceExclude":

          ContentManager.getActivePanel().sendForm(true);

        break;

        /**
         * Der Menüpunkt 'Auswahl -> ändern' wurde geklickt
         */
        case "choiceEdit":

          SelectionManager.getActive().editChoice();

        break;

        /**
         * Der Menüpunkt 'Auswahl -> löschen' wurde geklickt
         */
        case "choiceDelete":

          SelectionManager.getActive().deleteChoice();

        break;

        /**
         * Der Menüpunkt 'Auswahl -> nach oben' wurde geklickt
         */
        case "choiceMoveUp":

          SelectionManager.getActive().moveChoice("up");

        break;

        /**
         * Der Menüpunkt 'Auswahl -> nach unten' wurde geklickt
         */
        case "choiceMoveDown":

          SelectionManager.getActive().moveChoice("down");

        break;

        /**
         * Der Menüpunkt 'Selektion -> hinzufügen' wurde geklickt
         */
        case "addSelection":

          window.location = $_BASE + "?do=addSelection" + $_ASID;

        break;

        /**
         * Der Menüpunkt 'Selektion -> laden' wurde geklickt
         */
        case "listSelections":

          var url = $_BASE + "?do=listSelections" + $_ASID;

          if ($_USER.auth == "yes")
          {
            window.location = url;
          }
          else
          {
            DialogManager.get("login").show(url);
          }

        break;

        /**
         * Der Menüpunkt 'Selektion -> speichern' wurde geklickt
         */
        case "saveSelection":

          var selNum = SelectionManager.getActive().index;
          var url    = $_BASE + "?do=saveSelections&selNum=" + selNum + $_ASID;

          if ($_USER.auth == "yes")
          {
            window.location = url;
          }
          else
          {
            DialogManager.get("login").show(url);
          }

        break;

        /**
         * Der Menüpunkt 'Selektion -> löschen' wurde geklickt
         */
        case "deleteSelection":

          DialogManager.get("deleteSelection").show();

        break;

        /**
         * Der Menüpunkt 'Alles -> kalkulieren' wurde geklickt
         */
        case "calculatePrices":

          //nach oben springen
          if (document.URL.search(/#top/) != -1)
          {
            window.location.href = document.URL;
          }
          else
          {
            window.location.href = document.URL + '#top';
          }

          $.blockUI();

          $.ajax({
            url: $_AJAX_URL + "?selection&act=canCalculate" + $_ASID,
            dataType: "json",
            global: false,
            success: function(data)
            {
              if (data.canCalculate)
              {
                if (data.hasLoadedSelection)
                {
                  DialogManager.get("hasLoadedSel").show();
                }
                else
                {
                  var load_indicator_nr = (ToolBox.checkSelectionNames()) ? 3 : 1;
                  ToolBox.showLoadIndicator(load_indicator_nr);

                  window.location = $_BASE + "ordering/?do=offerCrossSection" + $_ASID;
                }
              }
              else
              {
                DialogManager.get("noCalc").show();
              }
            }
          });

        break;

        /**
         * Der Menüpunkt 'Alles -> speichern' wurde geklickt
         */
        case "saveAll":

          var url = $_BASE + "?do=saveSelections" + $_ASID;

          if ($_USER.auth == "yes")
          {
            window.location = url;
          }
          else
          {
            DialogManager.get("login").show(url);
          }

        break;

        /**
         * Der Menüpunkt 'Alles -> löschen' wurde geklickt
         */
        case "deleteAll":

          DialogManager.get("deleteAllSelections").show();

        break;

        case "panelDisplay-active":

          window.location = $_BASE + "changeToolboxView/?tab=" + ContentManager.activePanelIndex + $_ASID;

        break;
      }
    }
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/Tooltip.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Jeder Tooltip im System besitzt eine Instanz dieser Klasse und kann darüber gesteuert werden.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Jeder Tooltip im System besitzt eine Instanz dieser Klasse und kann darüber gesteuert werden.
 *
 * @constructor
 * @class
 * @param {String, Element} el CSS-Selektor oder DOM-Element des Tooltips.
 * @param {Function} showHandler Callback-Funktion die aufgerufen wird, bevor der Tooltip angezeigt wird.
 */
var Tooltip = function(el, showHandler)
{
  /**
   * jQuery-Objekt des Dialogs.
   * @type {jQuery}
   */
  this.el = $(el);

  /**
   * Die Callback-Funktion. Über die Funktion show können ihr beliebige viele Parameter übergeben werden.
   * @type {Function}
   */
  this.showHandler = showHandler;

  /**
   * Gibt an, ob das Tooltip angezeigt wird.
   * @type {Boolean}
   */
  this.isDisplayed = false;

  if ($.fn.bgiframe)
  {
    this.el.bgiframe();
  }
};

Tooltip.prototype =
{
  /**
   * Gibt Maße (Höhe, Breite etc.) des Fensters (nur sichtbarer Bereich) zurück.
   * @return {Object}
   */
  viewport: function viewport()
  {
    return {
      x: $(window).scrollLeft(),
      y: $(window).scrollTop(),
      cx: $(window).width(),
      cy: $(window).height()
    };
  },

  /**
   * Tooltip einblenden.
   */
  show: function(left, top)
  {
    if (!this.isDisplayed)
    {
      var result = this.showHandler.apply(this, Array.slice(arguments, 2));

      if (result === false)
        return;

      this.isDisplayed = true;

      this.el.removeClass("tooltip-hide").addClass("tooltip-show");

      this.el.css({
        "left": left + 'px',
        "top": top + 'px'
      });

      var v = this.viewport();
      h = this.el[0];
      // check horizontal position
      if((v.x + v.cx) < (h.offsetLeft + h.offsetWidth))
      {
        left -= h.offsetWidth + 20 + this.left;
        this.el.css({ "left": left + 'px' });
      }
      // check vertical position
      if((v.y + v.cy) < (h.offsetTop + h.offsetHeight))
      {
        top -= h.offsetHeight + 20 + this.top;
        this.el.css({ "top": top + 'px' });
      }
    }
  },

  /**
   * Tooltip ausblenden.
   */
  hide: function()
  {
    if (this.isDisplayed)
    {
      this.isDisplayed = false;
      this.el.removeClass("tooltip-show").addClass("tooltip-hide");
    }
  }
};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/TooltipManager.class.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Verwaltet alle Tooltips.
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Verwaltet alle Tooltips.
 *
 * @class
 * @static
 */
var TooltipManager =
{
  /**
   * Hier werden alle Tooltips gespeichert.
   * @type {Array}
   */
  tooltips: [],

  /**
   * Gibt an, um wieviel Pixel ein Tooltip standardmäßig von seinem Zielelement aus
   * nach rechts geschoben wird.
   * @type {Number}
   */
  defaultLeft: 15,

  /**
   * Gibt an, um wieviel Pixel ein Tooltip standardmäßig von seinem Zielelement aus
   * nach unten geschoben wird.
   * @type {Number}
   */
  defaultTop: 15,

  /**
   * Gibt an, um wieviel Pixel ein Tooltip standardmäßig von seinem Zielelement aus
   * nach rechts geschoben wird.
   * @type {Number}
   */
  Toolbox_Left: -200,

  /**
   * Gibt an, um wieviel Pixel ein Tooltip standardmäßig von seinem Zielelement aus
   * nach unten geschoben wird.
   * @type {Number}
   */
  Toolbox_Top: 20,

  /**
   * Erstellt alle Tooltips und speichert sie.
   */
  init: function()
  {
    // Blendet bei jedem Kriterium die genauen Trfferzahlen ein
    this.add("choiceInfo", "#tooltip-0", function(target, choice)
    {
      var fullNum = target.find("input:nth(0)").val();
      var depNum = target.find("input:nth(1)").val();

      if (choice.attr("exclude") == "true")
      {
        this.el.find("span:nth(1)").text("Abgezogene Treffer:");
      }
      else
      {
        this.el.find("span:nth(1)").text("Treffer mit vorherigem gefiltert:");
      }

      this.el.find("strong:nth(0)").text(fullNum);
      this.el.find("strong:nth(1)").text(depNum);
    });

    // Blendet den Selektionsnamen von geschlossenen Selektionen ein
    this.add("selectionTitle", "#tooltip-1", function(selTitleEl)
    {
      var title = selTitleEl.find("div:last > strong").text();

      if (title.length > 0)
      {
        this.el.text(title);
      }
      else
      {
        return false;
      }
    });

    this.addAndBind("tooltip_maxGewuenscht", "#tooltip_maxGewuenscht_content");
    this.addAndBind("tooltip_maxGewuenscht_button", "#tooltip_maxGewuenscht_button");
    this.addAndBind("tooltip_maxEntscheider_button", "#tooltip_maxEntscheider_button");
    this.addAndBind("tooltip_selName_button", "#tooltip_selName_button");

    /**
     * Tooltips des Toolboxes
     */
    this.addAndBind_at_Toolbox("tooltipChoiceEdit", "#tooltipChoiceEdit");
    this.addAndBind_at_Toolbox("tooltipChoiceDelete", "#tooltipChoiceDelete");
    this.addAndBind_at_Toolbox("tooltip_ChoiceMoveUp", "#tooltip_ChoiceMoveUp");
    this.addAndBind_at_Toolbox("tooltip_ChoiceMoveDown", "#tooltip_ChoiceMoveDown");

    this.addAndBind_at_Toolbox("tooltipAddSelection", "#tooltipAddSelection");
    this.addAndBind_at_Toolbox("tooltipListSelections", "#tooltipListSelections");
    this.addAndBind_at_Toolbox("tooltipSaveSelection", "#tooltipSaveSelection");
    this.addAndBind_at_Toolbox("tooltipDeleteSelection", "#tooltipDeleteSelection");
    this.addAndBind_at_Toolbox("tooltipCalculatePrices", "#tooltipCalculatePrices");
    this.addAndBind_at_Toolbox("tooltipSaveAll", "#tooltipSaveAll");
    this.addAndBind_at_Toolbox("tooltipDeleteAll", "#tooltipDeleteAll");
  },

  /**
   * Neuen Tooltip hinzufügen.
   * @param {String} tooltipName Name des Tooltips. Damit wird er dann später aufgerufen.
   * @param {String, Element} el CSS-Selektor oder DOM-Element für den Tooltip.
   * @param {Function} [showHandler] Callback-Funktion die aufgerufen wird, bevor der Tooltip angezeigt wird.
   */
  add: function(tooltipName, el, showHandler)
  {
    var h = showHandler || this._defaultHandler;

    var tooltip = { 'name': tooltipName, 'obj': new Tooltip(el, h) };

    this.tooltips.push(tooltip);
  },

  /**
   * Auf einen bestimmten Tooltip zugreifen.
   * @param {String} tooltipName Name des Tooltips.
   */
  get: function(tooltipName)
  {
    for (var i = 0; i < this.tooltips.length; i++)
    {
      if (this.tooltips[i].name == tooltipName)
      {
        return this.tooltips[i].obj;
      }
    }

    return null;
  },

  /**
   * Standard Callback-Funktion.
   */
  _defaultHandler: function()
  {

  },

  addAndBind: function(css_class,el)
  {
     var tooltipName = css_class;
     this.add(tooltipName,el);

     $('.' + css_class).bind('mouseover',this.overCSSClass)
     $('.' + css_class).bind('mouseout',this.outCSSClass)
  },

  addAndBind_at_Toolbox: function(css_class,el)
  {
     var tooltipName = css_class;
     this.add(tooltipName,el);

     $('.' + css_class).bind('mouseover',this.overCSSClass_at_Toolbox)
     $('.' + css_class).bind('mouseout',this.outCSSClass)
  },

  overCSSClass: function(evt)
  {
    var i, tooltip;
    var selection = $(evt.target);

    if (tooltip = TooltipManager.getTooltipFromClass(selection))
    {
      var el_offset = selection.offset();
      var top = TooltipManager.defaultTop + el_offset.top;
      var left = TooltipManager.defaultLeft + el_offset.left;

      tooltip.show(left,top);
//      console.log(tooltip);
    };
  },

  overCSSClass_at_Toolbox: function(evt)
  {
    var i, tooltip;
    var selection = $(evt.target);

    if (tooltip = TooltipManager.getTooltipFromClass(selection))
    {
      var el_offset = selection.offset();
      var top = TooltipManager.Toolbox_Top + el_offset.top;
      var left = TooltipManager.Toolbox_Left + el_offset.left;

      tooltip.show(left,top);
//      console.log(tooltip);
    };
  },

  outCSSClass: function(evt)
  {
    var selection = $(evt.target);
    if (tooltip = TooltipManager.getTooltipFromClass(selection))
    {
        tooltip.hide();
    }
  },

  getTooltipFromClass: function(selection){

    var target_selection;
    var tooltip = null;

    var sel_classes = selection.attr("class");

    if (sel_classes != undefined) {
      var classes = sel_classes.split(' ');
      for (i = 0; i < classes.length; i++) {

        if (tooltip = TooltipManager.get(classes[i])) {
          break;
        }
      }
    }

    target_selection = selection.parent();

    if ( target_selection && tooltip === null) {

      tooltip =  TooltipManager.getTooltipFromClass(target_selection);
    }

    return tooltip;
  }

};;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/initApp.js
--------------------------------------------------------------------------*/
//<?php - diese Zeile für PHP-Documentor notwendig
/**
 * Hier wird die Adressauswahl initialisiert und gestartet
 *
 * @author klickwerk GmbH <support@klickwerk.de>
 * @version 1.0
 * @package frontend
 * @subpackage mod_addresses
 */
// ?>  - diese Zeile für PHP-Documentor notwendig

/**
 * Hier wird die Adressauswahl initialisiert und gestartet
 */
$(document).ready(function(evt)
{

  /**
   * Screen frei geben Variable setzen
   */
  $_allow_unblock_screen = true;

  /**
   * Ajaxindicator Standardwert setzen
   */
  $_type_of_ajax_indicator = 1;

  /**
   * An submit buttons onClick Aktion binden
   */
  $('.button-style-add').bind("click", function(){
    $_type_of_ajax_indicator = 2;
  });
  $('.button-style-exclude').bind("click", function(){
    var selection = SelectionManager.getActive();
    console.log(selection);
    if (typeof selection != "undefined")
    {
      $('#markChoiceExclude_hint_' + selection.index ).css('display', 'block');
    }
    $_type_of_ajax_indicator = 2;

  });
  $('.button-style-edit').bind("click", function(){
    $_type_of_ajax_indicator = 2;
  });
  $('.tooltipChoiceDelete').bind("click", function(){
    $_type_of_ajax_indicator = 2;
  });



  if ($_CNT_ID > 0 && $_MODULE == "addresses")
  {
    // Einstellungen für das Blocken der Seite bei AJAX-Abfragen
    $.extend($.blockUI.defaults.overlayCSS, { opacity: "0.5" });
    $.extend($.blockUI.defaults.pageMessageCSS, { width: "auto", border: "none", textAlign: "left", backgroundColor: "transparent", margin: "0", top: "0", left: "0" });
    $.blockUI.defaults.pageMessage = "";

    // Seite blocken
    $.blockUI();

    // Bei AJAX-Abfragen wird dieses Element angezeigt (Daten werden geladen...)
    var ajaxIndicator = $("#ajaxIndicator");

    // Nach Beendigung von AJAX-Abfragen wird folgendes ausgeführt
    ajaxIndicator.ajaxStop(function()
    {
      /**
       * Es kann sein, dass nicht immer nach ajax-Auffruf der Screen sofort freigegeben werden soll.
       */
      if ($_allow_unblock_screen)
      {
        // Seite freigeben
        $.unblockUI();
      }
      else
      {
        /**
         * wenn diesmal verhindert, trotzdem auf erlaubt setzen.
         */
        $_allow_unblock_screen = true;
      }

      // ajaxIndicator ausblenden
      $(this).css("display", "none");
    });

    // Bei Fehlerhaften AJAX-Abfragen Meldung anzeigen
    ajaxIndicator.ajaxError(function()
    {
      Exception.handle({ type: "error", code: "0", data: arguments });
    });

    // Toolbox (Panel) initialisieren
    ToolBox.init();

    // Selektionen initialisieren
    SelectionManager.init();

    // Inhalt links (Reiter) initialisieren
    ContentManager.init();

    // Dialoge initialisieren
    DialogManager.init();

    // Tooltips initialisieren
    TooltipManager.init();

    // Seite freigeben
    $.unblockUI();

    // Vor Beginn einer AJAX-Abfrage wird folgendes ausgeführt
    ajaxIndicator.ajaxSend(function()
    {
      // Seite blocken
      $.blockUI();

      var type_1 = $(this).find('#indicator_1');
      var type_2 = $(this).find('#indicator_2');

      type_1.css("display", "none");
      type_2.css("display", "none");

      // je nach Typ Indikator Zeigen
      switch($_type_of_ajax_indicator)
      {
        case 1:
          type_1.css("display", "block");
          break;

        case 2:
          //nach oben springen
          if (document.URL.search(/#top/) != -1)
          {
            window.location.href = document.URL;
            type_2.css("display", "block");
          }
          else
          {
            window.location.href = document.URL + '#top';
            type_2.css("display", "block");
          }
          break;

        default:
          type_1.css("display", "block");
      }

      // Indikator auf standard setzen
      $_type_of_ajax_indicator = 1;

      // ajaxIndicator einblenden
      $(this).css("display", "block");
    });
  }
});;

/*--------------------------------------------------------------------------
 /app.frontend/mod_addresses/scr/jscript/default/__src__/tabs_tooltips.js
--------------------------------------------------------------------------*/
/**
 * @author jburov
 */
$(document).ready(function(evt)
{
  $('.tab_tooltip_1').bind("mouseover", onOverTooltip1);
  $('.tab_tooltip_2').bind("mouseover", onOverTooltip2);
  $('.tab_tooltip_3').bind("mouseover", onOverTooltip3);
  $('.tab_tooltip_4').bind("mouseover", onOverTooltip4);
  $('#tooltip_noCeo').bind("mouseover", onOverTooltip);
  //$('.tooltip_maxGewuenscht').bind("mouseover", onOverTooltipMaxGewuenscht);

  $('.button-style-add').bind("mouseover", onOverTooltipSearchBtn);
  $('.button-style-exclude').bind("mouseover", onOverTooltipSearchBtn_2);

  $('.tab_tooltip_1').bind("mouseout", onOutTooltip1);
  $('.tab_tooltip_2').bind("mouseout", onOutTooltip2);
  $('.tab_tooltip_3').bind("mouseout", onOutTooltip3);
  $('.tab_tooltip_4').bind("mouseout", onOutTooltip4);
  $('#tooltip_noCeo').bind("mouseout", onOutTooltip);
  //$('.tooltip_maxGewuenscht').bind("mouseout", onOutTooltipMaxGewuenscht);

  $('.button-style-add').bind("mouseout", onOutTooltipSearchBtn_1);
  $('.button-style-exclude').bind("mouseout", onOutTooltipSearchBtn_2);

}
);

function onOutTooltip(evt)
{

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#' + target_id + '_content');

  var top = -1000;
  var left = -1000;

      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px'
      });

  tooltip_content.hide();
}

function onOverTooltip(evt)
{
  var all_contents_offset = $('#all-contents').offset();

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#' + target_id + '_content');

  var top = offset.top - 40;
  var left = offset.left - all_contents_offset.left + 15;


      tooltip_content.removeClass("tooltip-hide").addClass("tooltip-show");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px',
        "width": '300px'
      });

       tooltip_content.show('slow');
}

function onOutTooltipSearchBtn(evt)
{

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#' + target_id + '_content');

  var top = -1000;
  var left = -1000;

      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px'
      });

  tooltip_content.hide();
}

function onOutTooltipSearchBtn_1(evt)
{

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#tooltip_button_exclude_content');

  var top = -1000;
  var left = -1000;

      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px'
      });

  tooltip_content.hide();
}

function onOutTooltipSearchBtn_2(evt)
{

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#tooltip_button_add_content');

  var top = -1000;
  var left = -1000;

      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px'
      });

  tooltip_content.hide();
}

function onOverTooltipSearchBtn(evt)
{
  var all_contents_offset = $('#all-contents').offset();

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#tooltip_button_exclude_content');

  var top = offset.top - 25;
  var left = offset.left - all_contents_offset.left - 120;


      tooltip_content.removeClass("tooltip-hide").addClass("tooltip-show");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px',
        "width": '300px'
      });

       tooltip_content.show('slow');
}


function onOverTooltipSearchBtn_2(evt)
{
  var all_contents_offset = $('#all-contents').offset();

  var target = $(evt.target);
  var target_id = target.attr('id');
  var offset = target.offset();

  var tooltip_content = $('#tooltip_button_add_content');

  var top = offset.top - 25;
  var left = offset.left - all_contents_offset.left - 70;


      tooltip_content.removeClass("tooltip-hide").addClass("tooltip-show");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px',
        "width": '300px'
      });

       tooltip_content.show('slow');
}


// Verworfen
//
//function onOverTooltipMaxGewuenscht(evt)
//{
//
//  var all_contents_offset = $('#all-contents').offset();
//
//  var target = $(evt.target);
//  var target_id = target.attr('id');
//  var offset = target.offset();
//
//  var tooltip_content = $('#tooltip_maxGewuenscht_content');
//
//  var top = offset.top - 50;
//  var left = offset.left - all_contents_offset.left + 15;
//
//
//      tooltip_content.removeClass("tooltip-hide").addClass("tooltip-show");
//
//      tooltip_content.css({
//        "left": left + 'px',
//        "top": top + 'px',
//        "width": '180px'
//      });
//
//       tooltip_content.show('slow');
//}
//
//function onOutTooltipMaxGewuenscht(evt)
//{
//
//  var target = $(evt.target);
//  var target_id = target.attr('id');
//  var offset = target.offset();
//
//  var tooltip_content = $('#tooltip_maxGewuenscht_content');
//
//  var top = -1000;
//  var left = -1000;
//
//      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");
//
//      tooltip_content.css({
//        "left": left + 'px',
//        "top": top + 'px'
//      });
//
//  tooltip_content.hide();
//  //console.log(tooltip_content);
//}

function onOverTooltip1(evt)
{
  var tab_nr = 1;
  onOverTooltipTanNr(evt,tab_nr);
}

function onOverTooltip2(evt)
{
  var tab_nr = 2;
  onOverTooltipTanNr(evt,tab_nr);
}

function onOverTooltip3(evt)
{
  var tab_nr = 3;
  onOverTooltipTanNr(evt,tab_nr);
}

function onOverTooltip4(evt)
{
  var tab_nr = 4;
  onOverTooltipTanNr(evt,tab_nr);
}

function onOverTooltipTanNr(evt,tab_nr)
{


  var all_contents_offset = $('#all-contents').offset();

  var target = $(evt.target);
  selection_class = target.parents("li:first").attr('class');
  var searchStr = /selected/g;

  if (!searchStr.exec(selection_class) || evt.target.tagName == 'IMG')
  {
      var offset = target.offset();
      var tooltip_content = $('#tab_tooltip_' + tab_nr +'_content');

      var top = offset.top - 15;
      var left = offset.left - all_contents_offset.left + 15;


      tooltip_content.removeClass("tooltip-hide").addClass("tooltip-show");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px',
        "width": '300px'
      });

       tooltip_content.show('slow');

  }




    //console.log(tooltip_content);
}


function onOutTooltipTabNr(tab_nr)
{
  var tooltip_content = $('#tab_tooltip_' + tab_nr +'_content');

  var top = -1000;
  var left = -1000;

      tooltip_content.removeClass("tooltip-show").addClass("tooltip-hide");

      tooltip_content.css({
        "left": left + 'px',
        "top": top + 'px'
      });

  tooltip_content.hide();
  //console.log(tooltip_content);
}

function onOutTooltip1()
{
  var tab_nr = 1;
  onOutTooltipTabNr(tab_nr)
}
function onOutTooltip2()
{
  var tab_nr = 2;
  onOutTooltipTabNr(tab_nr);
}
function onOutTooltip3()
{
  var tab_nr = 3;
  onOutTooltipTabNr(tab_nr);
}
function onOutTooltip4()
{
  var tab_nr = 4;
  onOutTooltipTabNr(tab_nr);
};
