<?php
/**
 * @copyright (c) Kufer Software GmbH, Loisachstrasse 4, D-84453 Mühldorf
 */


class ToolFirma extends ToolBase
{
  
  private $_dbwBelegung;
  private $_user;

  
  protected $_debugStorno;

  public function __construct()
  {
    parent::__construct();
    $this->toolTitle = 'gebuchte Seminare';

    
    $dbwbelegung = new DBWorkBelegung();
    $dbwbelegung->newSearch();
    $dbwbelegung->fromobject->kurs->semester = $this->toolSettings->semlist;
    $dbwbelegung->toobject->kurs->semester = '';
    $dbwbelegung->dbwkurse->justNoAusfall = $this->toolSettings->keineAusgefallenenKurse;
    $dbwbelegung->setOrderBySettings($this->toolSettings);

    

    $searchAPI = new KurssuchAPIwSearch(false);
    $searchAPI->getSearchParamsFromReqToSession('tool' . $this->toolId);

    
    
    $dbwbelegung->fromobject->kurs = $searchAPI->getFromObjectBySession($dbwbelegung->fromobject->kurs, 'tool' . $this->toolId);
    $dbwbelegung->toobject->kurs = $searchAPI->getToObjectBySession($dbwbelegung->toobject->kurs, 'tool' . $this->toolId);

    
    if ($this->toolSettings->tnStatusFa == '') {
      $tnStatusFa = 'FSZ';
    } else {
      $tnStatusFa = $this->toolSettings->tnStatusFa;
    }
    $dbwbelegung->fromobject->status = $tnStatusFa;
    $dbwbelegung->dbwkurse->beruecksichtigeKurstagRaumanzeige = $this->toolSettings->versteckeKurstageWieImRaumanzeigeprogramm;

    $this->_dbwBelegung = $dbwbelegung;
    $this->_user = SessionOperations::getCurrentWebToolsUser();

    $this->_debugStorno = false;
    if (DBWorkBASysSettings::isBlak()) {
      $this->_debugStorno = true;
    }
  }

  
  protected function doByBrowserRefresh()
  {
    $this->_isRefresh = true;
    $_POST = array();
    $_SERVER['REQUEST_METHOD'] = 'GET';
  }

  
  public function init($pPageId)
  {
    
    $this->checkBrowserReload();

    $page = null;
    switch ($pPageId) {
      default:
      case 305: 
        $page = $this->_handleKursuebersicht($pPageId);
        break;
      case 306: 
        break;
       case 313: 
        $page = $this->_handleAlleTermine();
        break;
         
      case 312: 


        $dbwKursTage = new DBWorkKurseTage();

        $vonDatum = DateTimeOperations::getValidDateString(GetOperations::getVarValue('von', ''));
        $bisDatum = DateTimeOperations::getValidDateString(GetOperations::getVarValue('bis', ''));

        
        $termiplanFormat = GetOperations::getVarValue('terminplanformat', '');
        
        $terminBereich = GetOperations::getVarValue('terminbereich', '');

        if (GetOperations::isDefined('nr')) {
          
          
          $selectedBelegungsIds = GetOperations::getVarValue('nr');
          $belIdAry = explode(':', $selectedBelegungsIds);

          $this->_dbwBelegung->fromobject->status = 'F';
          $belegungenStatusF = $this->_dbwBelegung->getBelegungenByIds($belIdAry);

          $knrAryMitF = ArrayOperations::mapAttribut($belegungenStatusF, 'knr');
          $kursNrAry = $this->_dbwBelegung->getKursNrWhereFirmaAngemeldet($knrAryMitF, SessionOperations::getCurrentWebToolsTeilnehmer()->id);
          if (count($kursNrAry) == 0) {
            $data = array();
          } else {
            
            
            $dbwKursTage->newSearch();
            $dbwKursTage->fromobject->datum = $vonDatum;
            $dbwKursTage->toobject->datum = $bisDatum;
            $data = $dbwKursTage->getKurstageByTnLimit($this->_user->tnr, null, 0, true, $kursNrAry);
          }
        } elseif (GetOperations::isDefined('ktnr')) {
          $ktnr = GetOperations::getVarValue('ktnr');
          $ktNrAry = explode(':', $ktnr);

          $kursTageAlle = $dbwKursTage->getKurseTageByIds($ktNrAry);
          if (SessionOperations::isAdmin()) {
            $data = $kursTageAlle;
          } else {
            $data = $this->_filterKurstageAngemeldeteKurseFirma($kursTageAlle, SessionOperations::getCurrentWebToolsTeilnehmer()->id);
          }
        }

        $page = new PageTnMeineKurseTerminplan('meine Kurse', $pPageId, $this, $data, $vonDatum, $bisDatum, $termiplanFormat, $this->_user->tnr, $terminBereich);
        break;
      case 319:
        
        $belid = GetOperations::getVarValue('belid');
        $page = new PageTnMeineKurseStammBlatt('TNKursstammblatt', $pPageId, $this, $belid);
        break;
      case 336:  
        $page = $this->_handleKursdetails();
        break;
      case 360: 
        $dbwbelegung = new DBWorkBelegung();
        $belid = GetOperations::getVarValue('belid');
        $data = $dbwbelegung->getBelegung($belid);
        $page = $this->_handleStorno($data, $pPageId);
        break;
      case 479:
        $page = $this->_handleNotenDerMitarbeiter($pPageId);
        break;
      case 480: 
        $knr = GetOperations::getVarValue('nr');
        $page = PageHandlerAPI::handleKursAnw($this, $pPageId, $knr, $pPageId . '.0.1', null, false, $this->_user->tnr);
        break;
    }
    if ($page == null) {
      throw new Exception('ungültige PageId');
    }
    $this->currentPage = $page;
  }

  
  private function _filterKurstageAngemeldeteKurseFirma($pKurstage, $pFirma)
  {
    $kursNrAlle = ArrayOperations::mapAttribut($pKurstage, 'knr');

    $this->_dbwBelegung->fromobject->status = '-ATP';
    $kursNrAngemeldet = $this->_dbwBelegung->getKursNrWhereFirmaAngemeldet($kursNrAlle, $pFirma);

    return array_filter($pKurstage, function($pKurstag) use ($kursNrAngemeldet) {
      return in_array($pKurstag->knr, $kursNrAngemeldet);
    });
  }

  
  protected function fillIcsSettingsInSession()
  {
    SessionOperations::setVarValueWTIntern(
      'icsSetting_versteckeKurstageWieImRaumanzeigeprogramm',
      $this->toolSettings->versteckeKurstageWieImRaumanzeigeprogramm
    );
  }

  
  private function _handleKursuebersicht($pPageId = 305)
  {
    $this->updateAndGetSelectedIds();

    
    if (DBWorkBASysSettings::isMDS()) {
      $blaetterBelId = RequestOperations::getVarValue('blid');
      $pageLinks = array();
      if ($blaetterBelId != '') {
        $blaetterForward = RequestOperations::getVarValue('dir') != 'back';
        $startBelegung = new Belegung();
        $startBelegung->id = $blaetterBelId;
      } else {
        $startBelegung = null;
        $blaetterForward = true;
      }
      
      
      $ohneStornoStatus = false; 
      $data = $this->_dbwBelegung->getBelegungenbyTeilnehmerNRLimit(
        $this->_user->id,
        $startBelegung,
        $this->toolSettings->kurseproseite,
        $blaetterForward,
        $ohneStornoStatus,
        true
      );

      $count = count($data);
      if ($this->_dbwBelegung->countBefore > 0 && $count > 0) {
        $pageLinks['backward'] = '&blid=' . $data[0]->id . '&dir=back';
      }
      if ($this->_dbwBelegung->countBehind > 0 && $count > 0) {
        $pageLinks['forward'] = '&blid=' . $data[$count - 1]->id . '&dir=forw';
      }
    } 
    else {
      
      $alleIds = $this->getAlleIdsBelegungen($this->_dbwBelegung);
      $data = $this->getData($this->_dbwBelegung, $alleIds, $this->toolSettings->kurseproseite);
      $anzahlAllerBelegungsIdsDesTeilnehmers = count($alleIds);
    }

    $userid = $this->_user->getIdentifier();

    
    $pageLinks['termineall'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.1');
    
    $pageLinks['terminplan'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.2');
    
    $pageLinks['termineics'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.3');
    
    $pageLinks['filter'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.4');
    
    $pageLinks['print'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.5');
    
    $pageLinks['showmitarbeiter'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.7');
    
    $pageLinks['showmitarbeiterkurse'] = \SecurityOperations::privilegAllowed($userid, $this->getToolId(), $pPageId . '.0.8');
    

    

    if ($this->_showDetailsAllowed($userid, $pPageId)) {
      
      $pageLinks['details'] = $this->getUrlParamsForFile(array('toolsection_id' => 336));
    }


    $pageLinks['self'] = $this->getUrlParamsForFile(array('toolsection_id' => $pPageId)); 
    
    if (DBWorkBASysSettings::isBlak()) {
      
      foreach ($data as $key => $belegung) {
        if ($belegung->kurs->kursauswahl2 == 'W') {
          $data[$key]->kurs->gebuehr = BLAK_NOT_SHOW_WSS;
          $data[$key]->kurs->geb_erm = BLAK_NOT_SHOW_WSS;
          $data[$key]->entgelt = BLAK_NOT_SHOW_WSS;
          $data[$key]->bet_offen = BLAK_NOT_SHOW_WSS;
          $data[$key]->bezahlt = BLAK_NOT_SHOW_WSS;
        }
      }

      $page = new PageFaMeineKurseUebersichtBLAK(
        'gebuchte Seminare',
        $pPageId,
        $this,
        $data,
        'meine Anmeldungen',
        $this->_dbwBelegung,
        $anzahlAllerBelegungsIdsDesTeilnehmers,
        $this->toolSettings->kurseproseite
      );
    
    } elseif (DBWorkBASysSettings::isMDS()) {
      unset($pageLinks['showmitarbeiter'], $pageLinks['showmitarbeiterkurse']);

      
      $page = new PageFaMeineKurseUebersichtMDS(
        'gebuchte Seminare',
        $pPageId,
        $this,
        $data,
        'verfügbare Seminare:',
        $this->_dbwBelegung,
        $anzahlAllerBelegungsIdsDesTeilnehmers,
        $this->toolSettings->kurseproseite
      );
    } else {
      $page = new PageFaMeineKurseUebersicht(
        'gebuchte Seminare',
        $pPageId,
        $this,
        $data,
        'Aktuell von uns gebuchte Seminare mit folgenden Mitarbeitern:',
        $this->_dbwBelegung,
        $anzahlAllerBelegungsIdsDesTeilnehmers,
        $this->toolSettings->kurseproseite
      );
    }
    $page->setLinks($pageLinks);

    return $page;
  }

  
  protected function _showDetailsAllowed(\Kufer\Web\Classes\Identifier\Identifier $pUserId, $pPageId)
  {
    
    return (\SecurityOperations::privilegAllowed($pUserId, $this->getToolId(), $pPageId . '.0.6') == 2
       && $this->rechteOR(array('336.1.1', '336.1.2', '336.1.3', '336.1.4' . '336.1.5',
                             '336.1.6', '336.1.7')));
  }

  
  private function _handleKursdetails($pPageId = 336)
  {
    $alleIds = $this->getAlleIdsBelegungen($this->_dbwBelegung);
    $data = $this->getData($this->_dbwBelegung, $alleIds, 1, GetOperations::getVarValue('belid'));
    
    $data = $data[0];
    $kursNr = $data->knr;
    $belid = $data->id;

    $dbwKurseBase = new DBWorkKurseBase();
    
    $dozenten = $dbwKurseBase->getDozentenForKurse(array($kursNr));

    $pageTitle = 'gebuchte Seminare';

    $title = '';
    if (count($dozenten[$kursNr]) > 1) {
      $title .= 'Information an die Dozenten';
    } elseif (count($dozenten[$kursNr]) == 1) {
      if ($dozenten[$kursNr][0]->geschlecht == 'W') {
        $title = 'Information an die Dozentin';
      } else {
        $title = 'Information an den Dozenten';
      }
    }

    
    if (GetOperations::getVarValue('showFormular', '') == 'info') {
      $pageLinks = array();
      $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
      $pageLinks['action'] = $this->getUrlParamsForFile(array('toolsection_id' => $pPageId, 'belid' => $belid, 'sendInfo' => 'doz'));
      if (count($dozenten) == 0) {
        $page = new PageKeinKontakt($pageTitle, $pPageId, $this, $title);
      } else {
        $betreff = $data->kurs->getVarValue('titel_zeile1') . ' - ' . $this->_user->name . ' ' . $this->_user->vorname;
        $page = new PageKontaktKursAnDozenten($pageTitle, $pPageId, $this, $title, $betreff, 'Ihre Nachricht:', $data->kurs, $dozenten);
      }
      $page->setLinks($pageLinks);
    } elseif (GetOperations::getVarValue('showFormular', '') == 'feedback') {
      $pageLinks = array();
      $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
      $pageLinks['action'] = $this->getUrlParamsForFile(array('toolsection_id' => $pPageId, 'belid' => $belid, 'sendInfo' => 'vhs'));
      $ueberschrift = 'Feedback - Kurs ' . $data->kurs->id . ': ' . $data->kurs->getVarValue('titel_zeile1');
      $betreff = $data->kurs->getVarValue('titel_zeile1') . ' - ' . $this->_user->name . ' ' . $this->_user->vorname;
      $page = new PageKontakt($pageTitle, $pPageId, $this, $ueberschrift, $betreff);
      $page->setLinks($pageLinks);
    }

    
    elseif (GetOperations::getVarValue('showFormular', '') == 'kursortsms') {
      
      
      $tab = GetOperations::getVarValue('tab', '');
      
      $page = SmsUserAPI::getSMSPage4Kursort($data, $this, $pageTitle, $pPageId, $this->toolSettings->showSmsBetreff, $tab, false);
    }
    
    elseif (GetOperations::getVarValue('sendInfo', '') != '' && GetOperations::getVarValue('sendInfo', '') == 'kursortsms') {
      $tab = GetOperations::getVarValue('tab', '');
      
      $page = SmsUserAPI::getSMSPage4Kursort($data, $this, $pageTitle, $pPageId, $this->toolSettings->showSmsBetreff, $tab, true);
    }

    
    elseif (GetOperations::getVarValue('sendInfo', '') != '') {
      $pageLinks = array();
      $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
      $versendet = array();
      $nichtVersendet = array();

      if (GetOperations::getVarValue('sendInfo', '') == 'doz') {
        

        
        $teilnehmer = SessionOperations::getCurrentWebToolsTeilnehmer();
        $senderEmailData = ToolsAPI::getSenderEmailAddressAndName($teilnehmer, 'Andere');

        foreach (PostOperations::getVarValue('doz') as $value) {
          $dbwDozent = new DBWorkDozenten();
          $doz = $dbwDozent->getDozent($value);
          $mailAdress = $doz->getVarValueEx('email', 'kommunikation');
          $email = new smtpMail();
          $email->SetVar2Value('from', $senderEmailData['email']);
          $email->SetVar2Value('sendername', $senderEmailData['name']);
          $email->SetVar2Value('reply', $senderEmailData['reply']);
          $email->SetVar2Value('replyname', $senderEmailData['replyname']);
          $email->SetVar2Value('to', $mailAdress);
          $email->SetVar2Value('contenttype', SMTP_CONTENTTYPE_TEXT);
          $email->SetVar2Value('doNotSplitHTMLBody', true);
          $email->subject = PostOperations::getVarValue('betreff');
          $email->body = PostOperations::getVarValue('info');
          if ($email->sendMail()) {
            $versendet[] = $doz;
          } else {
            $nichtVersendet[] = $doz;
          }
        }
        $ueberschrift = $title . ' - Kurs ' . $data->knr . ': ' . $data->kurs->getVarValue('titel_zeile1');
        $page = new PageNachrichtErfolgreichGesendetPerson($pageTitle, $pPageId, $this, $ueberschrift, $versendet, $nichtVersendet);
        $page->setLinks($pageLinks);
      } elseif (GetOperations::getVarValue('sendInfo', '') == 'vhs') {
        
        $allgsettings = AllgSettingsAPI::getAllgSettings();

        
        $teilnehmer = SessionOperations::getCurrentWebToolsTeilnehmer();
        $senderEmailData = ToolsAPI::getSenderEmailAddressAndName($teilnehmer);

        $mailAddress = EmailOperations::getToolEmailAddressForVhs($this->toolSettings->vhsEmailTool21Section336);
        $email = new smtpMailTools();
        $email->SetVar2Value('from', $senderEmailData['email']);
        $email->SetVar2Value('sendername', $senderEmailData['name']);
        $email->SetVar2Value('reply', $senderEmailData['reply']);
        $email->SetVar2Value('replyname', $senderEmailData['replyname']);
        $email->SetVar2Value('to', $mailAddress);
        $email->SetVar2Value('contenttype', SMTP_CONTENTTYPE_TEXT);
        $email->SetVar2Value('doNotSplitHTMLBody', true);
        $email->subject = PostOperations::getVarValue('betreff');
        $email->body = PostOperations::getVarValue('info');
        $email->setFooter('Feedback zu einem Kurs', $this->_user, $data->kurs);

        if ($email->sendMail()) {
          $versendet[] = $allgsettings->vhsname;
        } else {
          $nichtVersendet[] = $allgsettings->vhsname;
        }
        $ueberschrift = 'Feedback - Kurs ' . $data->knr . ': ' . $data->kurs->getVarValue('titel_zeile1');
        $page = new PageNachrichtErfolgreichGesendetFeedback($pageTitle, $pPageId, $this, $ueberschrift, $versendet, $nichtVersendet);
        $page->setLinks($pageLinks);
      }
    }
    
    elseif (GetOperations::isDefined('showForum')) {
      $pageLinks = array();
      
      $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
      $page = new PageTnForum($this, $pPageId);
      $page->setLinks($pageLinks);
    }
    
    else {
      
      if (!is_numeric($belid) || $belid < 1) {
        
        $page = new PageWTDefault($pageTitle, $pPageId, $this);
        $page->setContent('<h2>Ungültige Parameter, bitte manipulieren Sie die URL nicht!</h2>');
      } else {
        
        if ($this->_user->tnr != $data->tnr) {
          
          $page = new PageWTDefault($pageTitle, $pPageId, $this);
          $page->setContent('<h2>Sie sind nicht berechtigt sich diese Informationen anzusehen!</h2>');
        } else {
          if (GetOperations::getVarValue('showAbmeldung', '--') != '--') {
            
            $page = $this->_getPage4Storno($pPageId, $data);
          } else { 
            $page = $this->_showStandardKursdetails($data);
          }
        }
      }
    }

    return $page;
  }

  

  
  protected function _checkWeitereStornoHindernisse($pGruende, $pData)
  {
    return $pGruende;
  }

  protected function _getBelegAryAndUmmeldInfo()
  {
    $belegAry4Firma = array();
    $belegungenZumStornieren = array();
    $ummeldeInfo = array();

    
    
    $jsonObject = JsonOperations::getFromString(PostOperations::getVarValue('jsonData'));

    $vars = get_object_vars($jsonObject);
    $belegungenZumUmmelden = array();

    
    
    foreach ($vars as $value) {
      
      $belegAry4Firma[] = $value->belegung->id;
      if (isset($value->belegung->status) && $value->belegung->status == 'S') {
        
        $belegungenZumStornieren[] = $value->belegung->id;
      } else {
        
        $belegungenZumUmmelden[] = $value->belegung->id;
        $teilnehmerNeu = isset($value->teilnehmer) ? $value->teilnehmer : null;
        if (!is_null($teilnehmerNeu)) {
          if (isset($teilnehmerNeu->id) && $teilnehmerNeu->id != '') {
            
          }
          $ummeldeInfo[$value->belegung->id] = $teilnehmerNeu;
        }
      }
      $belegAry4Firma = array_merge($belegungenZumStornieren, $belegungenZumUmmelden);
    }

    return array(
        'belegAry4Firma' => $belegAry4Firma,
        'belegungenZumStornieren' => $belegungenZumStornieren,
        'ummeldeInfo' => $ummeldeInfo
    );
  }

  protected function _getStornoHinderungsGruende($pKomplettAbmelden, $pData, $pBelegAry4Firma, $pFirmenBelegungen)
  {
    
    $gruende = array();
    $dbwZahlung = new DBWorkZahlung();

    
    if ($pData->status != 'F') {
      $gruende[] = 'Die Firma ist nicht mit Status F angemeldet im Kurs.';
    }

    
    $nurMitarbeiterAufWartelisteStornieren = $this->haveBelegungenNurStatusW($pFirmenBelegungen);
    if (!$nurMitarbeiterAufWartelisteStornieren) {
      if (!$pKomplettAbmelden) {
        $gruende[] = 'Es sollen nicht alle Teilnehmer storniert werden.';
      }


      
      if (!$dbwZahlung->isStornoBzglZahlungOkForBelegung($pData->id)) {
        $gruende[] = 'Aufgrund bereits erfolgter Zahlungen/Rechnungen ist eine Stornierung nicht möglich.';
      }

      
      $gruende = $this->_checkWeitereStornoHindernisse($gruende, $pData);

      
      
      if ($pData->kurs->beginn_dat != '' && DateTimeOperations::isDatebeforeNow($pData->kurs->beginn_dat)) {
        $gruende[] = 'Der Kurs hat bereits am ' . $pData->kurs->beginn_dat . ' begonnen.';
      }

      if ($pData->kurs->anm_ende != '') {
        $anmende = DateTimeOperations::getTimestampByDatestring($pData->kurs->anm_ende);
        $akttime = gmmktime(0, 0, 0);
        if ($anmende < $akttime) {
          
          $kursbeginndat = $pData->kurs->beginn_dat;
          if ($kursbeginndat !== '') { 
            $kursbeginn = DateTimeOperations::getTimestampByDatestring($kursbeginndat);
            if ($kursbeginn < $akttime) {
              $gruende[] = 'Der Anmeldeschluss ist bereits erreicht (' . $pData->kurs->anm_ende . ')';
            }
          }
        }
      }
    }

    $firmenBelegungen = $this->_getFirmenBelegungen($pKomplettAbmelden, $pBelegAry4Firma);

    
    foreach ($firmenBelegungen as $mitarbeiterBelegung) {
      if (!$dbwZahlung->isStornoBzglZahlungOkForBelegung($mitarbeiterBelegung->id)) {
        $gruende[] = 'Aufgrund bereits erfolgter Zahlungen/Rechnungen bei ' . $mitarbeiterBelegung->teilnehmer->name_vorname
          . ' ist eine Stornierung nicht möglich.';
      }

      if ($mitarbeiterBelegung->entgelt != '0,00') {
        $gruende[] = 'Das Entgelt bei ' . $mitarbeiterBelegung->teilnehmer->name_vorname . ' ist ungleich 0.';
      }
    }

    $anzahlFreiwerdenderPlaetze = $this->_getAnzahlFreiWerdenderPlaetze($firmenBelegungen);
    
    if ($anzahlFreiwerdenderPlaetze > 0 && $pData->kurs->getVarValue('teil_min') > $pData->kurs->getVarValue('anmeldungen') - $anzahlFreiwerdenderPlaetze) {
      $gruende[] = 'Durch eine Abmeldung würde die Mindestteilnehmerzahl unterschritten (minimal ' . $pData->kurs->getVarValue('teil_min')
        . ' - derzeit ' . $pData->kurs->getVarValue('anmeldungen') . ' - abzumelden ' . $anzahlFreiwerdenderPlaetze . ')';
    }

    return $gruende;
  }

  
  protected function _getFirmenBelegungen($pKomplettAbmelden, $pBelegAry4Firma)
  {
    if ($pKomplettAbmelden) {
      return $pBelegAry4Firma;
    } else {
      return $this->_dbwBelegung->getBelegungenByIds($pBelegAry4Firma);
    }
  }

  
  protected function _getAnzahlFreiWerdenderPlaetze($pFirmenBelegungen)
  {
    $anzahlFreiwerdenderPlaetze = 0;
    foreach ($pFirmenBelegungen as $mitarbeiterBelegung) {
      if (in_array($mitarbeiterBelegung->status, array('A', ' ', '', 'P'))) {
        $anzahlFreiwerdenderPlaetze++;
      }
    }

    return $anzahlFreiwerdenderPlaetze;
  }

  
  protected function _getMaInformationen($pKomplettAbmelden, $pFirmenBelegungen, $pBelegungenZumStornieren, $pUmmeldeInfo)
  {
    $maInformationen = array();
    
    if (!$pKomplettAbmelden) {
      foreach ($pFirmenBelegungen as $belegung) {
        $nachrichtBeginn = 'Die Belegung für ' . $belegung->teilnehmer->name . ', ' . $belegung->teilnehmer->vorname
            . ' (Nr. ' . $belegung->tnr . ', derzeit Status ' . $belegung->status . ') soll ';
        if (in_array($belegung->id, $pBelegungenZumStornieren)) {
          $maInformationen[] = $nachrichtBeginn . 'storniert werden.';
        } else {
          $maInformationen[] = $nachrichtBeginn . "ersetzt werden durch:\n "
              . $this->getNeuMaInfo($pUmmeldeInfo[$belegung->id]);
        }
      }
    }

    return $maInformationen;
  }

  
  protected function logStorno($pData, $pHinderungsGruende, $pKomplettAbmelden, $pHaveBelegungenNurStatusW, $pMaInfos, $pZusatzHinweis = '')
  {
    if ($this->_debugStorno) {
      $stornoMessage = 'Firma ' . $pData->teilnehmer->namevorname . ' (' . $pData->tnr . ') ';
      $stornoMessage .= 'möchte sich vom Kurs ' . $pData->kurs->kurzbez . ' (' . $pData->knr . ') abmelden.' . "\n";
      if (!$pKomplettAbmelden) {
        $stornoMessage .= 'Die Firma meldet sich nicht komplett ab:' . "\n";
        $additionalInfoWarteliste = $pHaveBelegungenNurStatusW ? ' (von Warteliste storniert)' : '';
        foreach ($pMaInfos as $maInfo) {
          $stornoMessage .= $maInfo . $additionalInfoWarteliste . "\n";
        }
      } else {
        $stornoMessage .= 'Die Firma möchte sich komplett abmelden.' . "\n";
      }

      if (count($pHinderungsGruende) != 0) {
        $stornoMessage .= 'Folgende Gründe sprechen gegen ein automatisches Stornieren:' . "\n";
        foreach ($pHinderungsGruende as $grund) {
          $stornoMessage .= $grund . "\n";
        }
      } else {
        $stornoMessage .= 'Es sprechen keine Gründe gegen ein SimpleStorno.' . "\n";
      }
      $stornoMessage .= $pZusatzHinweis;
      Logger::Logg($stornoMessage, 100);
    }
  }

  
  protected function _handleStornoDmz($pData, $pKomplettAbmelden, $pMaInformationen, $pAnzahlFreiwerdenderPlaetze, $pFirmenBelegungen, $pPageId)
  {
    $stornogrund = '';
    $belApi = new BelegungAPI();
    try {
      $haveBelegungenNurStatusW = $this->haveBelegungenNurStatusW($pFirmenBelegungen);
      $this->logStorno($pData, array(), $pKomplettAbmelden, $haveBelegungenNurStatusW, $pMaInformationen, 'Die Stornierung erfolgt per DMZ.' . "\n");

      $page = new PageWTDefault('meine Kurse', 336, $this);
      if (DBWorkBASysSettings::isBlak()) {
        $page = $this->_setBLAKStornoPage($page, $pData);
      } else {
        $page->setContentHeader('Die Stornierung wurde durchgeführt.');
      }
      if ($haveBelegungenNurStatusW) {
        $storniertenTnNamen = $this->getBelegteTnNamenStringListe($pFirmenBelegungen);
        if (!DBWorkBASysSettings::isBlak()) {
          $page->setContent('<p class="singledetailcontent">Die TeilnehmerInnen wurden erfolgreich vom Kurs "' . CleanOperations::cleanStringForHtml($pData->kurs->getVarValue('kurzbez_titel')) . '" abgemeldet.'
                . BR_WT . BR_WT . $storniertenTnNamen . BR_WT . '<a class="singledetailcontent" href="' . CleanOperations::cleanStringForHtml($this->getUrlParamsForFile(array('toolsection_id' => 336, 'belid' => $pData->id))) . '" title="zu den Kursdetails">Zurück</a></p>');
        }

        $result = $belApi->storniereBelegungDMZ($pData->id, 'S', $stornogrund, $pAnzahlFreiwerdenderPlaetze, $this->_debugStorno, $pFirmenBelegungen);
        $this->_dbwBelegung->doStornoFirmenMitarbeiter($pData, $pFirmenBelegungen, $stornogrund, $this->tool0Settings->direktMaKuerzel);
      } else {
        $result = $belApi->storniereBelegungDMZ($pData->id, 'S', $stornogrund, $pAnzahlFreiwerdenderPlaetze, $this->_debugStorno);
        
        $this->_dbwBelegung->doFirmenStorno($pData, $stornogrund);
        if (!DBWorkBASysSettings::isBlak()) {
          $page->setContent('<p class="singledetailcontent">Sie wurden erfolgreich vom Kurs "' . CleanOperations::cleanStringForHtml($pData->kurs->getVarValue('kurzbez_titel')) . '" abgemeldet.'
                . BR_WT . BR_WT . '<a href="' . CleanOperations::cleanStringForHtml($this->getUrlParamsForFile(array('toolsection_id' => 336, 'belid' => $pData->id))) . '" title="zu den Kursdetails">Zurück</a></p>');
        }
      }
      
      $wartelistenSuccessAry = json_decode($result->reason, true);
      
      
      $wlInfo = $this->_benachrichtigeWarteliste($pData, $pAnzahlFreiwerdenderPlaetze, $wartelistenSuccessAry, true);
      
      $this->_sendSimpleStornoMail($pPageId, $pData, $pKomplettAbmelden, $wlInfo, $pFirmenBelegungen, $pAnzahlFreiwerdenderPlaetze);
    } catch (Exception $e) {
      
      $page = $this->_getPage4AbmeldeFailure($pData, $stornogrund, false);
      Logger::logg('Fehler der Stornierung über DMZ: ' . $e->getMessage(), 200);
    }

    return $page;
  }

  
  protected function _handleStornoDirekt($pData, $pKomplettAbmelden, $pMaInformationen, $pAnzahlFreiwerdenderPlaetze, $pFirmenBelegungen, $pPageId)
  {
    $stornogrund = '';
    $haveBelegungenNurStatusW = $this->haveBelegungenNurStatusW($pFirmenBelegungen);
    $this->logStorno($pData, array(), $pKomplettAbmelden, $haveBelegungenNurStatusW, $pMaInformationen, 'Die Stornierung erfolgt im Direktbetrieb.' . "\n");
    $page = new PageWTDefault('meine Kurse', 336, $this);
    try {
      $plaetzeFreiNachStorno = $pData->kurs->getTeilMax() - $pData->kurs->getVarValue('teil_akt') - $pAnzahlFreiwerdenderPlaetze;
      $anzahlZuInformieren = min(array($plaetzeFreiNachStorno, $pAnzahlFreiwerdenderPlaetze));
      if ($anzahlZuInformieren < 0) {
        $anzahlZuInformieren = 0;
      }
      $page->setContentHeader('Die Stornierung wurde durchgeführt.');
      if ($haveBelegungenNurStatusW) {
        $storniertenTnNamen = $this->getBelegteTnNamenStringListe($pFirmenBelegungen);
        $page->setContent('<p class="singledetailcontent">Die TeilnehmerInnen wurden erfolgreich vom Kurs "' . CleanOperations::cleanStringForHtml($pData->kurs->getVarValue('kurzbez_titel')) . '" abgemeldet.'
                . BR_WT . BR_WT . $storniertenTnNamen . BR_WT . '<a class="singledetailcontent" href="' . CleanOperations::cleanStringForHtml($this->getUrlParamsForFile(array('toolsection_id' => 336, 'belid' => $pData->id))) . '" title="zu den Kursdetails">Zurück</a></p>');

        $this->_dbwBelegung->doStornoFirmenMitarbeiter($pData, $pFirmenBelegungen, $stornogrund, $this->tool0Settings->direktMaKuerzel);
        $wlInfo = array();
      } else {
        $page->setContent('<p class="singledetailcontent">Sie wurden erfolgreich vom Kurs "' . CleanOperations::cleanStringForHtml($pData->kurs->getVarValue('kurzbez_titel')) . '" abgemeldet.'
                . BR_WT . BR_WT . '<a href="' . CleanOperations::cleanStringForHtml($this->getUrlParamsForFile(array('toolsection_id' => 336, 'belid' => $pData->id))) . '" title="zu den Kursdetails">Zurück</a></p>');

        $this->_dbwBelegung->doFirmenStorno($pData, $stornogrund, $this->tool0Settings->direktMaKuerzel);
        $wlInfo = $this->_benachrichtigeWarteliste($pData, $anzahlZuInformieren);
      }
      $this->_sendSimpleStornoMail($pPageId, $pData, $pKomplettAbmelden, $wlInfo, $pFirmenBelegungen, $pAnzahlFreiwerdenderPlaetze);
    } catch (Exception $e) {
      $page = $this->_getPage4AbmeldeFailure($pData, $stornogrund, false);
      Logger::logg('Fehler der Stornierung im Direktbetrieb: ' . $e->getMessage(), 200);
    }

    return $page;
  }

  
  protected function _handleStornoPerMail($pData, $pGruende, $pKomplettAbmelden, $pMaInformationen, $pFirmenBelegungen, $pPageId)
  {
    $stornogrund = '';
    $haveBelegungenNurStatusW = $this->haveBelegungenNurStatusW($pFirmenBelegungen);
    $this->logStorno($pData, $pGruende, $pKomplettAbmelden, $haveBelegungenNurStatusW, $pMaInformationen, 'Die Stornierung wird per E-Mail versendet.' . "\n");

    $mailAnMaAry = array();
    $mailAnMaAry['VerwMa'] = $this->toolSettings->stornoBenachrichtigungsMailAnVerwMa;
    
    
    
    $mailAdressAry = ToolsAPI::getEmailAdressForKursMA($pData->kurs, $this->toolId, $pPageId, $mailAnMaAry);
    $email = \ArrayOperations::firstValue($mailAdressAry);
    if ($email != '') {
      $betreff = 'Abmeldung von Firma ' . $pData->teilnehmer->namevorname . ' von Kurs ' . $pData->knr . ' (' . $pData->kurs->getVarValue('kurzbez_titel') . ')';
      $body = 'Firma ' . $pData->teilnehmer->namevorname . ' (interne Teilnehmer-Nr. ' . $pData->teilnehmer->id . ')'
        . ' möchte sich vom Kurs "' . $pData->kurs->getVarValue('kurzbez_titel') . '" (Kurs-Nr. ' . $pData->knr . ') ' . ($pKomplettAbmelden ? 'mit allen Mitarbeitern ' : '') . 'abmelden.' . "\n";
      if ($stornogrund != '') {
        $body .= "\n" . 'Dabei wurde vom Teilnehmer folgender Grund angegeben: ' . "\n" . $stornogrund;
      }
      $gruendeCount = count($pGruende);
      if ($gruendeCount > 0) {
        $body .= "\n";
        $body .= 'Eine automatische Abmeldung konnte ';
        $body .= 'aus folgende' . ($gruendeCount == 1 ? 'm Grund' : 'n Gründen');
        $body .= ' nicht durchgeführt werden:';
        foreach ($pGruende as $grund) {
          $body .= "\n- $grund";
        }
      }
      if (count($pMaInformationen) > 0) {
        $body .= "\n\nDie Belegungen der Mitarbeiter sollen wie folgt geändert werden:";
        foreach ($pMaInformationen as $info) {
          $body .= "\n- $info";
        }
      }
      $body .= "\n\n" . 'Diese E-Mail wurde am ' . DateTimeOperations::getDateNow() . ' um ' . DateTimeOperations::getTimeNow() . ' aus den ' . KUFERTOOLS . ' versandt.';

      
      $teilnehmer = SessionOperations::getCurrentWebToolsTeilnehmer();
      $senderEmailData = ToolsAPI::getSenderEmailAddressAndName($teilnehmer);
      $mailVersandt = smtpMailTools::sendStandardTextMailWithFooter(
        $email,
        $betreff,
        $body,
        'Stornierung eines Kurses',
        SessionOperations::getCurrentWebToolsUser(),
        $pData->kurs,
        $senderEmailData['email'],
        $senderEmailData['name'],
        $senderEmailData['reply'],
        $senderEmailData['replyname']
      );
    } else {
      $mailVersandt = false;
    }

    return $this->getPage4StornoMailversandt($mailVersandt, $pData, $stornogrund);
  }

  private function getPage4StornoMailversandt($mailVersandt, $pData, $stornogrund)
  {
    $page = new PageWTDefault('meine Kurse', 336, $this);
    
    if ($mailVersandt) {
      if (DBWorkBASysSettings::isBlak()) {
        $page = $this->_setBLAKStornoPage($page, $pData);
      } else {
        $sprachsettings = new SprachSettingsObject();
        $page->setContentHeader('Eine Nachricht mit Ihrem Abmeldewunsch wurde an die Einrichtung versendet.');
        $page->setContent(
          '<p class="singledetailcontent">Ihre Bitte um Stornierung ' . CleanOperations::cleanStringForHtml($sprachsettings->Kurs['Singular_mit_Artikel']['Genitiv']) . ' "'
          . $pData->kurs->getVarValue('kurzbez_titel') . '" haben wir erhalten. Sie bekommen in Kürze eine Bestätigung.'
          . $this->_getKomplizierteAbmeldungTextEnde()
          . BR_WT . BR_WT . '<a href="' . CleanOperations::cleanStringForHtml(ToolsAPI::getHistoryEntry(2)) . '" title="zu den Kursdetails">Zurück</a></p>'
        );
      }
    } else {
      
      $page = $this->_getPage4AbmeldeFailure($pData, $stornogrund);
    }

    return $page;
  }

  
  private function getBelegteTnNamenStringListe($pBelegungen)
  {
    $tnListe = '';
    foreach ($pBelegungen as $belegung) {
      $tnListe .= '<ul><li>' . CleanOperations::cleanStringForHtml($belegung->teilnehmer->namevorname) . '</li></ul>' . "\n";
    }

    return $tnListe;
  }

  
  private function haveBelegungenNurStatusW($pBelegungen)
  {
    foreach ((array)$pBelegungen as $belegung) {
      if ($belegung->status != 'W') {
        return false;
      }
    }

    return true;
  }

  
  protected function _handleStorno($pData, $pPageId)
  {
    if (!PostOperations::isDefined('abmeldenRadio')) {
      
      return $this->getPage4StornoMailversandt(true, $pData, '');
    }


    $komplettAbmelden = (PostOperations::getVarValue('abmeldenRadio') == 'alle') || (PostOperations::getVarValue('alleChecked') == 'allselected');
    $belegungenZumStornieren = array();
    
    
    
    $ummeldeInfo = array();

    
    if ($komplettAbmelden) {
      $belegAry4Firma = $this->_dbwBelegung->getTeilnehmerBelegungenByFirmaKurs($pData->tnr, $pData->knr);
    
    } else {
      $infoAry = $this->_getBelegAryAndUmmeldInfo();
      $belegAry4Firma = $infoAry['belegAry4Firma'];
      $belegungenZumStornieren = $infoAry['belegungenZumStornieren'];
      $ummeldeInfo = $infoAry['ummeldeInfo'];
    }

    $firmenBelegungen = $this->_getFirmenBelegungen($komplettAbmelden, $belegAry4Firma);
    $anzahlFreiwerdenderPlaetze = $this->_getAnzahlFreiWerdenderPlaetze($firmenBelegungen);
    $maInformationen = $this->_getMaInformationen($komplettAbmelden, $firmenBelegungen, $belegungenZumStornieren, $ummeldeInfo);
    $gruende = $this->_getStornoHinderungsGruende($komplettAbmelden, $pData, $belegAry4Firma, $firmenBelegungen);

    $haveBelegungenNurStatusW = false;
    if (count($firmenBelegungen) > 0) {
      
      
      $haveBelegungenNurStatusW = $this->haveBelegungenNurStatusW($firmenBelegungen);
    }

    if (($komplettAbmelden || $haveBelegungenNurStatusW)
            && count($gruende) == 0
            && (!SessionOperations::isReplikat() || SessionOperations::isDmzBetrieb())) {
      if (SessionOperations::isDmzBetrieb()) {
        return $this->_handleStornoDmz($pData, $komplettAbmelden, $maInformationen, $anzahlFreiwerdenderPlaetze, $firmenBelegungen, $pPageId);
      } else {
        return $this->_handleStornoDirekt($pData, $komplettAbmelden, $maInformationen, $anzahlFreiwerdenderPlaetze, $firmenBelegungen, $pPageId);
      }
    } else {
      return $this->_handleStornoPerMail($pData, $gruende, $komplettAbmelden, $maInformationen, $firmenBelegungen, $pPageId);
    }
  }

  

  
  protected function _setBLAKStornoPage($pPage, $pData)
  {
    $sprachsettings = new SprachSettingsObject();
    $content = BR_WT . 'Lieber Fortbildungsteilnehmer,' . BR_WT . BR_WT;
    $content .= 'Ihre Stornierung des Kurses ' . CleanOperations::cleanStringForHtml($pData->kurs->kurzbez) . ' haben wir erhalten.' . BR_WT;
    $content .= 'Schade, dass Sie an diesem Kurs nicht teilnehmen k&ouml;nnen. ' . BR_WT;
    $content .= 'Sollten in Ihrem Fall Stornogeb&uuml;hren anfallen, wird das '
                . 'von Ihnen angegebene Konto mit der f&auml;lligen Geb&uuml;hr belastet. '
                . '&Uuml;ber die Teilnahmebedingungen und die anfallenden Stornogeb&uuml;hren '
                . 'k&ouml;nnen Sie sich auf der '
                . '<a href="http://www.blak.de/d/items/teilnahmebedingungen.html" target="_blank">
                                             Website der BLAK</a> informieren.' . BR_WT . BR_WT;
    $content .= 'Gerne stehen wir Ihnen bei R&uuml;ckfragen jederzeit zur Verf&uuml;gung' . BR_WT . BR_WT;
    $content .= 'Ihre Abteilung Fortbildung der BLAK' . BR_WT;
    $content .= 'Telefon 089/ 92 62 63 / 64' . BR_WT;
    $content .= 'E-Mail: <a href="mailto:fortbildung@blak.aponet.de">fortbildung@blak.aponet.de</a>';
    $content .= BR_WT . BR_WT . '<a href="' . CleanOperations::cleanStringForHtml($this->getUrlParamsForFile(array('toolsection_id' => 336, 'belid' => $pData->id))) . '" title="zu den ' . CleanOperations::cleanStringForHtml($sprachsettings->KursZusammengesetzt['Singular']['Nominativ']) . 'details">Zurück</a></p>';

    $pPage->setContentHeader('Ihre Stornierung wurde an BLAK versendet.');
    $pPage->setContent($content);

    return $pPage;
  }

  
  protected function _getKomplizierteAbmeldungTextEnde()
  {
    return '';
  }

  
  protected function getNeuMaInfo($pTnInfo)
  {
    $result = "$pTnInfo->titel $pTnInfo->name, $pTnInfo->vorname ";
    if ($pTnInfo->id != '') {
      $result .= "(Nr. $pTnInfo->id) ";
    }
    $result .= "Geschlecht: $pTnInfo->geschlecht ";

    
    $result .= $this->_getBerufsgruppe($pTnInfo);

    if (isset($pTnInfo->email->wert) && $pTnInfo->email->wert != '') {
      $result .= ', E-Mail: ' . $pTnInfo->email->wert;
    }
    if (isset($pTnInfo->tel->wert) && $pTnInfo->tel->wert != '') {
      $result .= ', Telefon: ' . $pTnInfo->tel->wert;
    }
    if (isset($pTnInfo->mobil->wert) && $pTnInfo->mobil->wert != '') {
      $result .= ', Mobil: ' . $pTnInfo->mobil->wert;
    }

    return trim($result);
  }

  
  protected function _getBerufsgruppe($pTnInfo)
  {
    return '';
  }

  
  protected function _getStornoPage4Tool($pPageId, $pData)
  {
    return new PageFaMeineKurseAbmeldung($this, $pPageId, $pData);
  }

  
  protected function _getPage4Storno($pPageId, $pData)
  {
    $page = $this->_getStornoPage4Tool($pPageId, $pData);
    $pageLinks = array();
    $pageId4Storno = 360;
    $pageLinks['stornoaction'] = $this->getUrlParamsForFile(array('toolsection_id' => $pageId4Storno, 'belid' => $pData->id));
    $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
    $page->setLinks($pageLinks);

    return $page;
  }

  
  protected function _getPage4AbmeldeFailure($pData, $pStornogrund = '', $pMailVersandGescheitert = true)
  {
    $pageId = 336;
    $page = $this->_getStornoPage4Tool($pageId, $pData);
    if ($pMailVersandGescheitert) {
      $page->mailVersandGescheitert = true;
    } else { 
      $page->stornoGescheitert = true;
    }
    $page->stornoGrund = $pStornogrund;
    $pageLinks = array();

    
    $pageLinks['stornoaction'] = '';
    
    $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
    $page->setLinks($pageLinks);

    return $page;
  }

  
  protected function _sendSimpleStornoMail($pPageId, $pBelegung, $pKomplettAbmelden, $pWarteListeBenachrichtigtAry, $pFirmenBelegungen, $pFreiwerdendePlaetze)
  {
    if ($this->toolSettings->stornoImmerBenachrichtigungsMail) {
      $text = 'Die Firma ' . $pBelegung->teilnehmer->namevorname . " ($pBelegung->tnr) hat " . ($pKomplettAbmelden ? 'sich komplett und damit ' : '')
              . 'folgende Teilnehmer vom Kurs "' . $pBelegung->kurs->getVarValue('kurzbez_titel')
              . '" (' . $pBelegung->knr . ') abgemeldet:' . "\n";

      foreach ($pFirmenBelegungen as $mitarbeiterBelegung) {
        $text .= $mitarbeiterBelegung->teilnehmer->namevorname . " (Teilnehmernr.: $mitarbeiterBelegung->tnr, $mitarbeiterBelegung->status_lang) \n";
      }
      $text .= "\n";
      if (count($pWarteListeBenachrichtigtAry) > 0) {
        foreach ($pWarteListeBenachrichtigtAry as $wlBenachrichtigt) {
          $text .= "Teilnehmer $wlBenachrichtigt->namevorname ($wlBenachrichtigt->tnr) von der Warteliste ";
          if ($wlBenachrichtigt->benachrichtigt) {
            $text .= 'wurde per E-Mail über '
                     . (($wlBenachrichtigt->anzahl == 1) ? 'einen Platz' : $wlBenachrichtigt->anzahl . ' Plätze') . ' benachrichtigt';
          } else {
            $text .= 'konnte nicht benachrichtigt werden';
          }

          
          if ($wlBenachrichtigt->sendereplikathinweis) {
            $text .= '; für diesen Teilnehmer ist dies auf dem Replikat erst nach der nächsten Übertragung ersichtlich.';
          } else {
            $text .= '.';
          }
          $text .= "\n";
        }
      } else {
        if ($pFreiwerdendePlaetze > 0) {
          $text .= 'Warteliste war leer.' . "\n";
        } else {
          $text .= 'Keine frei werdenden Plätze.' . "\n";
        }
      }
      $text .= "\n" . 'Diese Nachricht wurde automatisch von den KuferTools generiert.';

      $mailAnMaAry = array();
      $mailAnMaAry['VerwMa'] = $this->toolSettings->stornoBenachrichtigungsMailAnVerwMa;
      
      

      $mailAdressAry = ToolsAPI::getEmailAdressForKursMA($pBelegung->kurs, $this->toolId, $pPageId, $mailAnMaAry);
      $emailAdress = \ArrayOperations::firstValue($mailAdressAry);
      smtpMail::sendStandardTextMail($emailAdress, 'Kurs Storno', $text);
    }
  }

  
  protected function _benachrichtigeWarteliste($pBelegung, $pAnzahl, $pWartelistenAry = null, $pIsDMZ = false)
  {
    $kursIstBeendet = DateTimeOperations::isDatebeforeNow($pBelegung->kurs->ende_dat);

    if ($kursIstBeendet) {
      return null; 
    }

    $dbwBel = new DBWorkBelegung();
    
    
    
    $wlLaenge = $dbwBel->getCountTNinWartelisteByKurs($pBelegung->knr);

    
    
    $wartelistenBelIds = null;

    if (is_array($pWartelistenAry)) {
      $wartelistenBelIds = array();

      
      
      foreach ($pWartelistenAry as $wartelistenAryObj) {
        $wartelistenBelIds[] = $wartelistenAryObj['belid'];
      } 
    } 
    $wlBelIdCount = count($wartelistenBelIds);

    
    $anzahlFreiPlaetze = $pAnzahl;
    if ($pIsDMZ) {
      
      
      $anzahlFreiPlaetze = $wlBelIdCount;  
    }

    if ($this->_debugStorno) {
      $wlNachrichtenMessage = 'Es sind ' . $wlLaenge . ' Teilnehmer auf der Warteliste eingetragen. Davon wurden ' . $anzahlFreiPlaetze
                              . ' Teilnehmer benachrichtigt';
      Logger::Logg($wlNachrichtenMessage, 101);
    }

    if ($wlLaenge == 0 || $anzahlFreiPlaetze == 0) {
      return null;
    }

    $bearbeiterKürzel = 'WT';
    
    if ($pIsDMZ) {
      
      
      $warteListenBelegungsAry = $dbwBel->getBelegungenByIds($wartelistenBelIds);
    } else {
      
      $warteListenBelegungsAry = $dbwBel->getWartelistenBelegungen($pBelegung->knr, $anzahlFreiPlaetze, $pBelegung->tnr);
    }
    $teilnehmerNrAry = array();
    $teilnehmerObjAry = array();
    
    
    $infoStatRepAry = array();

    
    $wlBelArycount = count($warteListenBelegungsAry);
    $maxWLBelCount = max(array($wlBelArycount, $wlBelIdCount));
    
    for ($i = 0;$i < $maxWLBelCount;$i++) {
      
      $wlBelegung = $warteListenBelegungsAry[$i];
      $wlBelegungDMZ = $pWartelistenAry[$i];  

      
      
      
      
      if ($pIsDMZ && ($wlBelegung->tnr != $wlBelegungDMZ['tnr'] || $wlBelegung->status != $wlBelegungDMZ['status_1']
                      || $wlBelegung->knr != $pBelegung->knr)) {
        if ($wlBelegungDMZ['firma'] > 0) { 
          $tnr = $wlBelegungDMZ['firma'];
        } else {
          $tnr = $wlBelegungDMZ['tnr'];
        }

        
        
        $teilnehmerObjAry[$tnr] = $wlBelegungDMZ;
        
        
        $infoStatRepAry[$tnr] = array('changeWLStatusAllowed' => false, 'sendeReplikatHinweis' => true);
      }
      
      else {
        if ($wlBelegung->firma > 0) { 
          $tnr = $wlBelegung->firma;
        } else {
          $tnr = $wlBelegung->tnr;
        }
        
        
        
        
        
        
        
        
        
        $infoStatRepAry[$tnr] = array('changeWLStatusAllowed' => true, 'sendeReplikatHinweis' => false);
      } 
      $teilnehmerNrAry[] = $tnr;
    } 

    
    
    $countAry4Tnr = array_count_values($teilnehmerNrAry);

    
    
    $WlBenachrichtigungsAry = array();
    $dbwTeilnehm = new DBWorkTeilnehmer();

    foreach ($countAry4Tnr as $tnr => $anzahl) {
      $teilnehm = $dbwTeilnehm->getTeilnehm($tnr);
      
      $result = new WartelistenBenachrichtigungFirma();
      $infoStatRep = $infoStatRepAry[$tnr];
      $result->sendereplikathinweis = $infoStatRep['sendeReplikatHinweis'];

      
      if (!is_null($teilnehm->id) && $teilnehm->id >= 0) {
        $result->namevorname = $teilnehm->namevorname;
        $result->tnr = $teilnehm->id;
        $email = $teilnehm->getVarValueEx('email', 'kommunikation');
      } else {
        
        
        
        $teilnehmWLObj = $teilnehmerObjAry[$tnr];
        $result->namevorname = $teilnehmWLObj['name'] . ', ' . $teilnehmWLObj['vorname'];
        $result->tnr = $teilnehmWLObj['tnr'];
        $email = $teilnehmWLObj['email'];

        
        
        $teilnehm->ansprache = $teilnehmWLObj['ansprache'];
        $teilnehm->anrede = $teilnehmWLObj['anrede'];
        $teilnehm->titel = $teilnehmWLObj['titel'];
        $teilnehm->geschlecht = $teilnehmWLObj['geschlecht'];
        $teilnehm->name = $teilnehmWLObj['name'];
      }
      
      $ansprache = $teilnehm->getVarValue('ansprache_default');
      $result->anzahl = $anzahl;
      if ($email != '') {
        $text = '';
        if ($this->toolSettings->stornoWartelistenBenachrichtigungText != '') {
          $text = $this->toolSettings->stornoWartelistenBenachrichtigungText;
        } else {
          
          $text .= '{%t_ansprache%}';
          $text .= "\n\n";
          $text .= 'Im Kurs {%k_kurzbez_titel%} ({%k_id%}) {%platz%} frei geworden.' . "\n";
          $text .= 'Bitte geben Sie uns umgehend Bescheid, ob weiterhin Interesse besteht.';
          $text .= "\n\nMit freundlichen Grüßen\n";
          $text .= 'Ihre {%vhsname%}';
        }

        $platz = 'ist ein Platz';
        if ($anzahl > 1) {
          $platz = ' sind ' . $anzahl . ' Plätze ';
        }

        $mitarbeiter = $this->getMitarbeiter($pBelegung->kurs->hpm, $pBelegung->kurs->getVarValue('verwaltung_ma'));

        
        
        $vars = array('{%t_ansprache%}' => $ansprache, '{%k_kurzbez_titel%}' => $pBelegung->kurs->getVarValue('kurzbez_titel'),
          '{%k_titel%}' => $pBelegung->kurs->titel, '{%k_kurzbez%}' => $pBelegung->kurs->kurzbez, '{%k_titel_zeile1%}' => $pBelegung->kurs->getVarValue('titel_zeile1'),
          '{%k_titel_untertitel%}' => $pBelegung->kurs->getVarValue('titel_untertitel'), '{%k_id%}' => $pBelegung->kurs->id, '{%k_nrab%}' => $pBelegung->kurs->nrab,
          '{%k_beginn_dat%}' => $pBelegung->kurs->beginn_dat, '{%k_ende_dat%}' => $pBelegung->kurs->ende_dat, '{%k_ort%}' => $pBelegung->kurs->ort,
          '{%platz%}' => $platz, '{%vhsname%}' => $this->allgSettings->vhsname, '{%k_hpm_email%}' => $mitarbeiter->email,
          '{%k_hpm_nachname%}' => $mitarbeiter->name, '{%k_hpm_vorname%}' => $mitarbeiter->vorname, '{%k_hpm_tel%}' => $this->getTelMitarbeiter($mitarbeiter));
        foreach ($vars as $toSearch => $replacement) {
          $text = str_replace($toSearch, $replacement, $text);
        }
        $result->benachrichtigt = smtpMail::sendStandardTextMail($email, 'Ein Platz wurde frei', $text);

        
        
        
        
        if ($result->benachrichtigt) {
          
          
          $warteListenBelegungsAryPart4TN = $this->_getTNPartfromWarteListe($warteListenBelegungsAry, $tnr);

          
          foreach ($warteListenBelegungsAryPart4TN as $warteListenBelegung) {
            
            
            if ($infoStatRep['changeWLStatusAllowed']) {
              
              
              $dbwBel->changeWarteListenStatus($warteListenBelegung, $bearbeiterKürzel);
            }
          }
        } 
      } 
      $WlBenachrichtigungsAry[] = $result;
    } 

    return $WlBenachrichtigungsAry;
  }

  

  
  protected function getMitarbeiter($pMaKennungPlanend, $pMaKennungVerwaltend)
  {
    $dbwBasysUser = new DBWorkBASysUser();
    $maPlanend = $dbwBasysUser->getBASysUserByKennung($pMaKennungPlanend);
    if (trim($maPlanend->email) != '') {
      $mitarbeiter = $maPlanend;
    } else {
      $maVerwaltend = $dbwBasysUser->getBASysUserByKennung($pMaKennungVerwaltend);
      $mitarbeiter = $maVerwaltend;
    }

    return $mitarbeiter;
  }

  
  protected function getTelMitarbeiter($pMitarbeiter)
  {
    if (trim($pMitarbeiter->tel) != '') {
      $result = $pMitarbeiter->tel;
    } elseif (trim($pMitarbeiter->tel2) != '') {
      $result = $pMitarbeiter->tel2;
    } else {
      $result = $pMitarbeiter->tel3;
    }

    return $result;
  }

  
  private function _getTNPartfromWarteListe($pWarteListenBelegungsAry, $pTnr)
  {
    $warteListenTNPart = array();
    foreach ($pWarteListenBelegungsAry as $wlBelegung) {
      if ($wlBelegung->firma == 0) {
        if ($wlBelegung->tnr == $pTnr) {
          $warteListenTNPart[] = $wlBelegung;
        }
      } else { 
        
        if ($wlBelegung->firma == $pTnr) {
          $warteListenTNPart[] = $wlBelegung;
        }
      }
    }

    return $warteListenTNPart;
  }

  

  
  private function _showStandardKursdetails($pData)
  {
    $detailSightId = 336; 
    $reiterKursdetailsSightId = 307;
    $reiterTermineSightId = 309;
    $reiterDownloadsSightId = 310;
    $reiterJournalSightId = 311;
    $printSightId = 319;
    $notenDerMitarbeiterId = 479;
    $anwSightId = 480;


    

    $reiterSeite = new ReiterSeite($detailSightId, $this->toolSettings->reiterBeschriftung);

    $data = $pData;
    
    $seite1data = $data;

    
    if (DBWorkBASysSettings::isBlak()) {
      if ($data->kurs->kursauswahl2 == 'W') {
        $data->kurs->gebuehr = BLAK_NOT_SHOW_WSS;
        $data->kurs->geb_erm = BLAK_NOT_SHOW_WSS;
        $data->entgelt = BLAK_NOT_SHOW_WSS;
        $data->bet_offen = BLAK_NOT_SHOW_WSS;
        $data->bezahlt = BLAK_NOT_SHOW_WSS;

        
        $seite1data = unserialize(serialize($data)); 
        $seite1data->kurs->aussenst = BLAK_NOT_SHOW_WSS;
      }
    }



    
    $tabPage = $this->_getTabCollectionAndFirstTabPage($seite1data, $reiterSeite, $detailSightId);

    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Kursdetails'))) {
      $tabPage->addTabPage(new TabPageSightBuilderUebersicht($reiterSeite->getLabel('Kursdetails'), $data, $this->getToolId(), $reiterKursdetailsSightId));
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Inhalt'))) {
      $tabPage->addTabPage(new TabKursDetailsInhalt($reiterSeite->getLabel('Inhalt'), $data->kurs, $this->toolSettings->benutzteinfo));
    }
    
    
    $addUrlPart = 'belid=' . $data->id;
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Termine'))) {
      $termineTab = new TabKursDetailsTermine($reiterSeite->getLabel('Termine'), $data->kurs, $reiterTermineSightId, $addUrlPart, '', true);
      $termineTab->setLinks(array(
          'versteckeKurstageWieImRaumanzeigeprogramm' => $this->toolSettings->versteckeKurstageWieImRaumanzeigeprogramm,
          'termineDruck' => \SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterTermineSightId . '.0.1') == 2
          ));
      $tabPage->addTabPage($termineTab);
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Downloads'))) {
      $tabPage->addTabPage(new TabKursDetailsDownloadsTN($reiterSeite->getLabel('Downloads'), $data->knr, $this->getToolId(), $reiterDownloadsSightId, $this->_user->tnr));
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Fotos'))) {
      $tabPage->addTabPage(new TabKursDetailsFotos($reiterSeite->getLabel('Fotos'), $data->knr));
    }
    
    
    if (!DBWorkBASysSettings::isBlak() || $data->kurs->kursauswahl2 != 'W') {
      if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $reiterSeite->getRecht('Journal')) && $this->_isAllowed4Module()) {
        $tabPage->addTabPage(new TabKursDetailsJournal($reiterSeite->getLabel('Journal'), $data, $reiterJournalSightId));
      }
    }

    $page = $tabPage;
    $pageLinks = array();
    $pageLinks['self'] = $this->getUrlParamsForFile(array('toolsection_id' => $detailSightId));

    
    
    if (!in_array($data->status, array('S', 'Z')) && $this->_isAllowed4Module()
        && \SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.1')) {
      $pageLinks['abmelden'] = $this->getUrlParamsForFile(array('toolsection_id' => $detailSightId, 'belid' => $pData->id, 'showAbmeldung' => 1));
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.2') && $this->_isAllowed4Module()) {
      $pageLinks['forum'] = $this->getUrlParamsForFile(array('toolsection_id' => $detailSightId, 'belid' => $data->id, 'showForum' => 1));
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.3') && $this->_isAllowed4Module()) {
      $pageLinks['feedback'] = $this->getUrlParamsForFile(array('toolsection_id' => $detailSightId, 'belid' => $data->id, 'showFormular' => 'feedback'));
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.4') && $this->_isAllowed4Module()) {
      $pageLinks['infoAnDoz'] = $this->getUrlParamsForFile(array('toolsection_id' => $detailSightId, 'belid' => $data->id, 'showFormular' => 'info'));
    }
    $pageLinks['bescheinigung'] = '';
    $pageLinks['rechnung'] = '';
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.5') && $this->_isAllowed4Module()) {
      $pageLinks['druck_small'] = $this->getUrlParamsForFile(array('toolsection_id' => $printSightId, 'belid' => $data->id, 'nr' => $data->knr));
    }

    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.6') && $this->_isAllowed4Module()) {
      $pageLinks['noten_der_mitarbeiter'] = $this->getUrlParamsForFile(array('toolsection_id' => $notenDerMitarbeiterId, 'belid' => $data->id, 'nr' => $data->knr));
    }

    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $detailSightId . '.0.7') && $this->_isAllowed4Module()) {
      $pageLinks['anwesenheiten4kurs'] = $this->getUrlParamsForFile(array('toolsection_id' => $anwSightId, 'belid' => $data->id, 'nr' => $data->knr));
    }

    $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();

    $page->setLinks($pageLinks);

    return $page;
  }

  
  protected function _getTabCollectionAndFirstTabPage($pData, $pReiterSeite, $pDetailSightId)
  {
    $reiterSeite1 = 306;

    $tabPage = new TabCollectionKursdetails(
      'gebuchte Seminare',
      $pDetailSightId,
      $this,
      'unsere Anmeldung zum Kurs ' . $pData->knr . ': ' . $pData->kurs->getVarValue('titel_zeile1'),
      $pData,
      $pData->knr,
      '',
      null,
      1
    );
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pReiterSeite->getRecht('Belegungsdetails'))) {
      $tabPage->addTabPage(new TabPageSightBuilderUebersicht($pReiterSeite->getLabel('Belegungsdetails'), $pData, $this->getToolId(), $reiterSeite1, 'ersteSeite'));
    }

    return $tabPage;
  }

  
  protected function _isAllowed4Module()
  {
    return true;
  }

  
  private function _handleAlleTermine()
  {
    ToolsAPI::updateAndGetSelectedIds($this->getToolId());
    $pageId = 313;
    $dbwKursTage = new DBWorkKurseTageWT();

    $vonDatum = DateTimeOperations::getValidDateString(GetOperations::getVarValue('von', ''));
    $bisDatum = DateTimeOperations::getValidDateString(GetOperations::getVarValue('bis', ''));
    $dbwKursTage->newSearch();
    $dbwKursTage->fromobject->datum = $vonDatum;
    $dbwKursTage->toobject->datum = $bisDatum;
    $dbwKursTage->fromobject->kurs = $this->_dbwBelegung->fromobject->kurs;
    $dbwKursTage->toobject->kurs = $this->_dbwBelegung->toobject->kurs;

    $dbwKursTage->orderby = 'datum';
    $dbwKursTage->setOrderAktuellesSemester($this->toolSettings);

    if ($this->toolSettings->versteckeKurstageWieImRaumanzeigeprogramm) {
      $dbwKursTage->fromobject->ranzprognoanz = true;
    }

    if ($this->toolSettings->tnStatusFaTermine === '') {
      $this->toolSettings->tnStatusFaTermine = 'F';
    }

    $this->_dbwBelegung->fromobject->status = $this->toolSettings->tnStatusFaTermine;

    $belIdAry = $this->_dbwBelegung->getBelegungsIdsbyTeilnehmerNR($this->_user->tnr);
    $kursNrAry = $this->_dbwBelegung->getKursNrFromBelegungNrAry($belIdAry);

    if (count($kursNrAry) == 0) {
      $alleIds = array();
      $data = array();
    } else {
      $alleIds = $dbwKursTage->getKurstageIdsByTNOnlyDifferent($this->_user->tnr, $kursNrAry);
      $data = $this->getData($dbwKursTage, $alleIds, $this->toolSettings->kurstageproseite);
    }

    $this->setTotalData($alleIds);
    $termineGesamt = count($alleIds);

    $pageLinks = array();

    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pageId . '.0.1')) {
      if (count($data) == 0) {
        $pageLinks['terminenachoutlook'] = 'ics.php?usertype=TN&amp;von=' . $vonDatum . '&amp;bis=' . $bisDatum;
      } else {

        
        $kursNrAry = $dbwKursTage->getKurstageNrByTn($this->_user->tnr);
        
        $joinedKnrAry = implode(':', $kursNrAry);
        $count = count($data);
        $pageLinks['terminenachoutlook'] = 'ics.php?usertype=TN&amp;von=' . $data[0]->datum . '&amp;bis=' . $data[$count - 1]->datum . '&amp;terminnr=' . $joinedKnrAry;
      }
    }

    $pageLinks['terminplan'] = \SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pageId . '.0.5');

    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pageId . '.0.2')) {
      $pageLinks['filter'] = true;
    }
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pageId . '.0.3')) {
      $pageLinks['print'] = true;
    }

    $pageLinks['self'] = 'usertools.php?tool_id=21&amp;toolsection_id=313';
    
    if (\SecurityOperations::privilegAllowedCurrentUser($this->getToolId(), $pageId . '.0.4')
       && $this->rechteOR(array('336.1.1', '336.1.2', '336.1.3', '336.1.4', '336.1.5', '336.1.6',
                             '336.1.7'))) {
      $pageLinks['kursdetails'] = 'usertools.php?tool_id=21&amp;toolsection_id=336';
    }
    $pageLinks['back'] = ToolsAPI::getLastHistoryEntry();
    $page = new PageTnAlleTermine('meine Kurse', $pageId, $this, $data, $vonDatum, $bisDatum, $termineGesamt, $this->toolSettings->kurstageproseite);
    $page->setLinks($pageLinks);

    return $page;
  }

  public function getToolId()
  {
    return \ToolsAPI::TOOL_KURSUEBERSICHT_FA;
  }

  
  public function _handleNotenDerMitarbeiter($pPageId)
  {
    $belid = GetOperations::getVarValue('belid', -1);
    $dbwBelegung = new DBWorkBelegung(1, true);
    $firmenBelegung = $dbwBelegung->getBelegung($belid);


    if (!SessionOperations::isAdmin()) {
      $firmenTn = SessionOperations::getCurrentWebToolsTeilnehmer();
      if ($firmenTn->id != $firmenBelegung->tnr) {
        
        return new PageWTDefault('', '', $this);
      }
    }

    $tnStatus = $this->toolSettings->tnstatus;
    if ($this->toolSettings->tnstatus == '') {
      $tnStatus = 'ATP';
    }
    $tnStatus = \StringOperations::str_split($tnStatus);
    if (in_array('A', $tnStatus)) {
      $tnStatus = array_merge($tnStatus, array('', ' '));
    }

    $firmenMaBelegungen = $dbwBelegung->getTeilnehmerBelegungenByFirmaKurs($firmenBelegung->tnr, $firmenBelegung->knr, $tnStatus);
    $firmenMaBelegungIds = ArrayOperations::mapAttribut($firmenMaBelegungen, 'id');

    $dbwTnFach = new DBWorkTNFach(1, true);
    $dbwTnNoten = new DBWorkTNNoten(1, true);
    $dbwKursFach = new DBWorkKursFach(1, true);

    $data = new stdClass();
    $data->belegungen = $firmenMaBelegungen;
    $data->tnFaecher = $dbwTnFach->getTNFachByBelIds($firmenMaBelegungIds);
    $data->tnNoten = $dbwTnNoten->getTNNotenByBelIds($firmenMaBelegungIds);
    $data->kursFach = $dbwKursFach->getFaecherByKurs($firmenBelegung->knr);
    $data->backLink = ToolsAPI::getLastHistoryEntry();
    $data->kurs = $firmenBelegung->kurs;

    $data->ohneNotenloseFaecher = $this->toolSettings->notenOhneNotenloseFaecher;
    $data->ohneFaecherloseBelegungen = $this->toolSettings->notenOhneFaecherloseBelegungen;

    if ($this->toolSettings->notenOhneEinzelnoten) {
      $presenter = new NotenUebersichtEinfach();
    } else {
      $presenter = new NotenUebersicht();
    }

    return new PageFaMitarbeiterNoten($this, $pPageId, $data, $presenter);
  }
}