[CLASS] Abfahrtstafeln von bahn.de auslesen

Hi zusammen,

wie so oft habe ich mal wieder eine Idee aufgegriffen und für mich „optimiert“, d.h. entsprechend meinen Bedürfnissen angepasst. Dabei ist folgendes OneScript bei rausgekommen :smiley:

Aussehen tut das so …

und das Script im bekannten selbst-erklärendem-installierendem Format hier …


<? 
################################################################################
# Scriptbezeichnung: Internet.Travel.ips.php
# Version: 1.0.20180224
# Author:  Heiko Wilknitz (@Pitti)
#          Original von sysrun (16.05.2010)
#
# Abfahrtstafeln von bahn.de
# ===========================
#
# Dieses Skript liest die An-und Abfahrtszeiten der Deutschen Bahn aus.
#
# Installation:
# -------------
#
# Dieses Skript richtet automatisch alle nötigen Objekte bei manueller
# Ausführung ein. Eine weitere manuelle Ausführung setzt alle benötigten Objekte
# wieder auf den Ausgangszustand.
#
# - Neues Skript erstellen
# - Diesen PHP-Code hineinkopieren
# - Abschnitt 'Konfiguration' den eigenen Gegebenheiten anpassen 
# - Skript Abspeichern
# - Skript Ausführen
#
# ------------------------------ Konfiguration ---------------------------------
#
# Schrittweite bzw. Offset der Startzeit konfigurierbar machen
# von Jetzt bis max. 12 Stunden in der Zukunft, sollte reichen
# Nur im Notfall anpassen ;-)
#
$min 	= 0;		// Jetzt 
$max 	= 720; 		// 12 Stunden 
$step 	= 5;  		// kleine Schrittweite
$jump 	= 60;		// große Schrittweite
$suffix = "min";	// min = Minuten
#
# Startzeit Offset Profil 
#
$time = array(
	array($min-3, "Jetzt", 		"", 0x0000FF),
	array($min-2, "--",	 		"", -1),
	array($min-1, "-", 	 		"", -1),
	array($min, "%d ".$suffix, 	"", 0x00FF00),
	array($max+1, "+", 			"", -1),
	array($max+2, "++",			"", -1)
);
#
# Ankunft & Abfahrt Profil
#
$arrdep = array(
	array(0, "Abfahrt",	"", 0x00FF00),
	array(1, "Ankunft",	"", 0xFFFF00),
	array(2, "Beides",	"", 0x0000FF)
);
#
# Stationen Profil
# ACHTUNG: Hier die eigenen Stationen eintragen bzw. Ändern und Erweitern!!
#
$stations = array(
	array(8001825, "Erding",			"", 0xFF8000),
	array(8003879, "Markt Schwaben",	"", 0xFF8000),
	array(8004252, "Neubiberg",			"", 0xFF8000)
);
#
# Suchen 
#
$search = array(
  array(0, '>', '', -1),
  array(1, 'Suchen', '', 0x008000)
);
#
################################################################################

// INSTALLATION
if ($_IPS['SENDER']=='Execute') {
	$pos = 0;
	// Startzeit
	$vpn = "Travel.Time";
	$vid = CreateVariableByName($_IPS['SELF'], "Startzeit", 1);
	CreateProfileInteger($vpn, 'Clock', '', '', $min, $max, 0, 0, $time);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, $min-3);	
	// Wegzeit bzw. Laufweg
	$vpn = "Travel.AwayTime";
	$vid = CreateVariableByName($_IPS['SELF'], "Laufweg", 1);
	CreateProfileInteger($vpn, 'Hourglass', '', ' min', 0, 60, 5, 0, NULL);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);	
	// Abfahrt und Ankunft
	$vpn = "Travel.ArrivalsDeparture";
	$vid = CreateVariableByName($_IPS['SELF'], "Abfahrt und Ankunft", 1);
	CreateProfileInteger($vpn, 'Distance', '', '', 0, 0, 0, 0, $arrdep);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);	
	// Stationen
	$vpn = "Travel.Stations";
	$vid = CreateVariableByName($_IPS['SELF'], "Bahnhof/Haltestelle", 1);
	CreateProfileInteger($vpn, 'Flag', '', '', 0, 0, 0, 0, $stations);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, $stations[0][0]);	
	// Suchen
	$vpn = "Travel.Search";
	$vid = CreateVariableByName($_IPS['SELF'], "Reise", 1);
	CreateProfileInteger($vpn, 'Script', '', '', 0, 0, 0, 0, $search);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);
	// Fahrplan
	$vid = CreateVariableByName($_IPS['SELF'], "Fahrplan ", 3);
	IPS_SetVariableCustomProfile($vid, '~HTMLBox');
	IPS_SetIcon($vid, "Database");
	IPS_SetPosition($vid, $pos++);
}
// AKTION VIA WEBFRONT
else if($_IPS['SENDER'] == "WebFront") {
	$name = IPS_GetName($_IPS['VARIABLE']);
	switch ($name) {
    	case 'Startzeit':  
			switch($_IPS['VALUE']) {
		    	case $min-3:
					SetValue($_IPS['VARIABLE'], 0); 
					break;
		    	case $min-2:
		          	$_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $jump;
		          	if($_IPS['VALUE'] <= 0) {
						$_IPS['VALUE'] = -3;
						SetValue($_IPS['VARIABLE'], 0); 
		          	}
		          	break;
		    	case $min-1:
		          	$_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $step;
		          	if($_IPS['VALUE'] <= 0) {
						$_IPS['VALUE'] = -3;
						SetValue($_IPS['VARIABLE'], 0); 
		          	}
		          	break;
		       	case $max+1:
		          	$_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $step);
		         	break;
		       	case $max+2:
		          	$_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $jump);
		         	break;
		        default:
		            return;
				break;
	    	}
			break;
	    case 'Reise':
			// Daten holen 
			$vid = CreateVariableByName($_IPS['SELF'], "Startzeit", 1);
			$start = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Laufweg", 1);
			$time = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Abfahrt und Ankunft", 1);
			$mode = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Bahnhof/Haltestelle", 1);
			$station = GetValue($vid); //Formatted
			// Fahrplan rendern
			$vid = CreateVariableByName($_IPS['SELF'], "Fahrplan ", 3);
			SetValue($vid, GenerateTimetable($start, $time, $mode, $station));		
			// Update Button zurückstellen
			$_IPS['VALUE'] = 0;
        	break;
	}
    // Speichern
    SetValue($_IPS['VARIABLE'], $_IPS['VALUE']);
}

# -------------------------------- FUNKTIONEN ----------------------------------

// Daten von bahne.de holen und rendern
function GenerateTimetable($start, $time, $mode, $station) 
{
    // Anzeige aufbereiten 
	$style = "";
	$style = $style.'<style type="text/css">';
	$style = $style.'table  {border-collapse: collapse; font-size: 14px; width: 100%; }';
	$style = $style.'td.fst {vertical-align: middle; text-align: center; width: 30px; padding: 5px; border-left: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.mid {vertical-align: middle; text-align: left; line-height: 20px; padding: 5px; border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.lst {vertical-align: middle; text-align: left; width: 350px; line-height: 20px; padding: 5px; border-right: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'tr:last-child {border-bottom: 1px solid rgba(255, 255, 255, 0.2); }';
	$style = $style.'tr:nth-child(even) {  background-color: rgba(0, 0, 0, 0.2); }';	  
	$style = $style.'.th { color: rgb(255, 255, 255); background-color: rgb(160, 160, 0); font-weight:bold; background-image: linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -o-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -moz-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -webkit-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -ms-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); }';
	$style = $style.'</style>';

	// Startzeit berechnen
	$dateTime = new DateTime();
	if ($start > 0) {
		$dateTime->modify('+'.$start.' minutes');
	}

	// Hier werden Verkehrsmittel ausgeschlossen 
	/* 
	$bahn->TypeBUS(false); 
	$bahn->TypeTRAM(false); 
	$bahn->TypeICE(false); 
	$bahn->TypeIC(false); 
	$bahn->TypeRE(false); 
	$bahn->TypeSBAHN(false); 
	$bahn->TypeUBAHN(false); 
	$bahn->TypeFAEHRE(false); 
	*/ 
	// Abfahrt
	$departure = '';
	if ($mode == 0 || $mode == 2) {
		// Parameter 1 ist der Bahnhof oder die Haltestelle 
		// (es muss kein Bahnhof sein, Bushaltestelle gehen auch) 
		// Parameter 2 ist die Art der Tafel: "Abfahrt" oder "Ankunft" 
		$bahn=new Bahn($station, "abfahrt"); 
		// Hier werden Datum und Zeit gesetzt. 
		// Werden die nicht gesetzt wird die/das aktuelle Zeit/Datum genommen
		$bahn->datum($dateTime->format('d.m.Y')); 
		$bahn->zeit($dateTime->format("H:i"));
		// Jetzt das Ergebniss holen! 
		$status=$bahn->fetch(); 
		if($status){ 
		    // Array mit den Informationen ausgeben: 
		    $departure = RenderHTML($bahn, "Abfahrt", $time); 
		} 
	} 
	// Ankunft
	$arrivals = '';
	if ($mode == 1 || $mode == 2) {
		// Parameter 1 ist der Bahnhof oder die Haltestelle 
		// (es muss kein Bahnhof sein, Bushaltestelle gehen auch) 
		// Parameter 2 ist die Art der Tafel: "Abfahrt" oder "Ankunft" 
		$bahn=new Bahn($station, "ankunft"); 
		// Hier werden Datum und Zeit gesetzt. 
		// Werden die nicht gesetzt wird die/das aktuelle Zeit/Datum genommen
		$bahn->datum($dateTime->format('d.m.Y')); 
		$bahn->zeit($dateTime->format("H:i")); 
		// Jetzt das Ergebniss holen! 
		$status=$bahn->fetch(); 
		if($status){ 
		    // Array mit den Informationen ausgeben: 
		    $arrivals = RenderHTML($bahn, "Ankunft", 0); 
		} 
	}
	// HTML zusammenbauen	
	$html = $style;
	$html = $html.$departure;
	if (!empty($departure)) $html = $html.'<br />'; 
	$html = $html.$arrivals;
	// fertiges HTML zurueck
	return $html;
}

// anzeige aufbereiten in eine html box 
// $bahn - ergebnis der class.bahn.php 
// $wegezeit - eine wegezeit in minuten zum bahnhof. oder =0 
function RenderHTML($bahn, $typ, $wegezeit) 
{ 
	$str = '';  
	$str .= '<table>';
    $str .= '<tr><td class="fst th" style="width:30px;"></td><td class="mid th"  style="width:80px;">Zug</td><td class="mid th" style="width:50px;">'.$typ.'</td><td class="mid th" style="width:50px;">Diff.</td><td class="mid th" style="width:200px;">Richtung</td><td class="mid th" style="width:40px;">Gleis</td><td class="lst th">Aktuelles</td></tr>'; 

    $pos = 0; 
    for($i=0; $i<sizeof($bahn->timetable); $i++) 
    { 
        //$eintrag = explode(";", $bahn->timetable[$i]); 
        $caller = $bahn->timetable[$i]["type"]; 
        $eintrag[0] = "<img src=/user/bahn/".strtolower($caller)."_24x24.gif>"; 
        $colour="white"; // yellow or red, white ist der normalfall 
        $eintrag[1] = $bahn->timetable[$i]["train"]; 
        $eintrag[2] = $bahn->timetable[$i]["time"]; 
        // differenz zur aktuellen zeit ausrechnen. 
        $timestampField = strtotime($bahn->timetable[$i]["time"]); 
        $timestampNow = time();//+1*60*60; 
        $diff = $timestampField - $timestampNow; 
        //echo $diff." * "; 
        if ($diff >0) { 
            $eintrag[3] = $uhrzeit = date("H:i",$diff-1*60*60); 
            if ($diff > $wegezeit*60) { 
               $colour="white"; 
            } 
            else { 
               $colour="yellow"; 
               $eintrag[3]="<font color='#FFFF00'>".$eintrag[3]; 
            } 
        } 
        else { 
          // nicht mehr zu schaffen da zeit abgelaufen 
          $eintrag[3] = "--:--"; 
          if ($wegezeit <>0) 
              $eintrag[3]="<font color='#FF0000'>".$eintrag[3]; 
        } 
        $eintrag[4] = $bahn->timetable[$i]["route_ziel"]; 
        $eintrag[5] = $bahn->timetable[$i]["platform"]; 
        $eintrag[6] = $bahn->timetable[$i]["ris"]; 

        $str .= "<tr>"; 
		
		$count = count( $eintrag );
		for ( $e = 0; $e < $count; $e++ )
		{
		    if ( $e == 0 ) $class = 'fst'; 
		    else if ( $e == $count - 1 ) $class = 'lst'; 
			else $class = 'mid'; 
            $str .= '<td class="'.$class.'">'.$eintrag[$e].'</td>'; 
		}			
        $str .= "</tr>"; 

        $pos++; 

        if($pos >= 6) 
            break; 
    } 
    $str .= "</table>"; 

    return $str; 
} 

// Erzeugt eine Variable unterhalb {id} mit dem Namen {name} vom Typ [type}
// Existiert die Variable schon wird diese zurückgeliefert.
// Types: 0 = Boolean, 1 = Integer, 2 = Float, 3 = String
function CreateVariableByName($id, $name, $type) 
{ 
   $vid = @IPS_GetVariableIDByName($name, $id); 
   if($vid===false) { 
      $vid = IPS_CreateVariable($type); 
      IPS_SetParent($vid, $id); 
      IPS_SetName($vid, $name); 
   }
   return $vid; 
}

// Erzeugt ein Variablenprofil vom Typ {type} mit Name n{name} 
function CreateProfile($name, $type)
{
	if(!IPS_VariableProfileExists($name)) {
		IPS_CreateVariableProfile($name, $type);
	} 
	else {
	  $profile = IPS_GetVariableProfile($name);
	  if($profile['ProfileType'] != $type)
	    throw new Exception("Variable profile type does not match for profile ".$name);
	}
}

// Erzeugt ein Integer-Variablenprofil
function CreateProfileInteger($name, $icon, $prefix, $suffix, $minvalue, $maxvalue, $step, $digits, $asso = NULL)
{
	CreateProfile($name, 1);

	IPS_SetVariableProfileIcon($name, $icon);
	IPS_SetVariableProfileText($name, $prefix, $suffix);
	IPS_SetVariableProfileDigits($name, $digits);
	
	if(sizeof($asso) !== 0){
	  $minvalue = 0;
	  $maxvalue = 0;
	} 
	IPS_SetVariableProfileValues($name, $minvalue, $maxvalue, $step);
	
	if(sizeof($asso) !== 0){
	  foreach($asso as $ass) {
	    IPS_SetVariableProfileAssociation($name, $ass[0], $ass[1], $ass[2], $ass[3]);
	  }
	}         
}

# --------------------------------- KLASSE BAHN --------------------------------
# 
#	Author: Frederik Granna (sysrun) 
#	Version 0.1 
# 
# ------------------------------------------------------------------------------
class Bahn
{ 
    var $_BASEURL="https://reiseauskunft.bahn.de/bin/bhftafel.exe/dn?maxJourneys=20"; 
    var $_PARAMS=array(); 
    var $timetable=array(); 
    var $bahnhof=false; 
    var $_FETCHMETHOD; 

    function Bahn($bahnhof=null,$type="abfahrt"){ 
       $type=strtolower($type); 
       if(!$bahnhof) 
          $bahnhof="008003280"; 
        $this->_init($bahnhof); 
        $this->fetchMethodCURL(true); 
        $this->boardType($type);
    } 

    function TypeBUS($state=true){$this->_PARAMS['GUIREQProduct_5'] = ($state) ? "on" : false;} 
    function TypeICE($state=true){$this->_PARAMS['GUIREQProduct_0'] = ($state) ? "on" : false;} 
    function TypeIC($state=true){$this->_PARAMS['GUIREQProduct_1'] = ($state) ? "on" : false;} 
    function TypeRE ($state=true){$this->_PARAMS['GUIREQProduct_3'] = ($state) ? "on" : false;} // NV genannt 
    function TypeSBAHN ($state=true){$this->_PARAMS['GUIREQProduct_4'] = ($state) ? "on" : false;} 
    function TypeFAEHRE ($state=true){$this->_PARAMS['GUIREQProduct_6'] = ($state) ? "on" : false;}   // UBAHN 
    function TypeTRAM ($state=true){$this->_PARAMS['GUIREQProduct_8'] = ($state) ? "on" : false;}   // STrassenbahn 
    function TypeUBAHN ($state=true){$this->_PARAMS['GUIREQProduct_7'] = ($state) ? "on" : false;}   // UBAHN 

    function boardType($type){ 
        if($type=="ankunft") 
            $this->_PARAMS['boardType']="arr"; 
        else 
            $this->_PARAMS['boardType']="dep";
    } 

    function datum($datum){ 
        $this->_PARAMS['date']=$datum; 
    } 

    function zeit($zeit){ 
        $this->_PARAMS['time']=$zeit; 

    } 

    function fetch($html=null){ 
       if($html){ 
          return $this->_parse($html); 
       }else if($this->_FETCHMETHOD=="CURL"){ 
            return $this->_queryCurl(); 
        } 
    } 

    function _queryCurl(){ 
        $this->buildQueryURL(); 
        $result=$this->_call(); 
        return $this->_parse($result); 
    } 

    function buildQueryURL(){ 
       $fields_string=""; 
        foreach($this->_PARAMS as $key=>$value){ 
           if($value) 
                $fields_string .= $key.'='.urlencode($value).'&'; 
        }; 
        rtrim($fields_string,'&'); 

        $this->_URL=$this->_BASEURL.$fields_string; 
        return $this->_URL; 
    } 

    function _parse($data){ 
        $dom = new DOMDocument(); 
        @$dom->loadHTML($data); 

        $select=$dom->getElementById("rplc0"); 
        if($select->tagName=="select"){ 
            $options=$select->getElementsByTagName("option"); 
            foreach($options AS $op){ 
                echo utf8_decode($op->getAttribute("value")."-".$op->nodeValue)."n"; 
            } 
            return false; 
        }else{ 
           $this->bahnhof=utf8_decode($select->getAttribute("value")); 
            $this->_process_dom($dom); 
            return true; 
        } 
    } 

    function _process_dom($dom){ 
        $test=$dom->getElementById("sqResult")->getElementsByTagName("tr"); 
        $data=array(); 
        foreach($test as $k=>$t){ 
            $tds=$t->getElementsByTagName("td"); 
            foreach($tds AS $td){ 
               $dtype=$td->getAttribute("class"); 
                switch($dtype){ 
                    case 'train': 
                        if($a=$td->getElementsByTagName("a")->item(0)){ 
                            $data[$k]['train']=str_replace(" ","",$a->nodeValue); 
                            if($img=$a->getElementsByTagName("img")->item(0)){
                                if (preg_match('%/([a-z]*)_24%', $img->getAttribute("src"), $regs)) {
                                   switch($regs[1]){ 
                                      case 'EC': 
                                         $data[$k]['type']="IC"; 
                                      break; 
                                        default: 
                                            $data[$k]['type']=strtoupper($regs[1]); 
                                        break; 
                                    } 
                                } 
                            } 
                        } 
                    break; 
                    case 'route': 
                       if($span=@$td->getElementsByTagName("span")->item(0)){ 
                          $data[$k]['route_ziel']=$span->nodeValue; 
                        } 
                        preg_match_all('/(.*)s*([0-9:]{5})/', $td->nodeValue, $result, PREG_PATTERN_ORDER); 
                        $tmp=array(); 
                        foreach($result[1] AS $rk=>$rv){ 
                        	$tmp[$result[2][$rk]]=utf8_decode(trim(html_entity_decode(str_replace("n","",$rv)))); 
                        } 
                        $data[$k]['route']=$tmp; 
                    break; 
                    case 'time': 
                    case 'platform': 
                    case 'ris': 
                       $data[$k][$dtype]=$td->nodeValue; 
                    break; 
                } 
            } 
        } 
        foreach($data AS $d){ 
            if(array_key_exists("train",$d)){ 
               foreach($d AS $dk=>$dv) 
                  if(!is_array($dv)) 
                      $d[$dk]=ltrim(str_replace("
","",utf8_decode(trim(html_entity_decode($dv)))),"-"); 
                $d['route_start']=$this->bahnhof; 
                $this->timetable[]=$d; 
         	} 
        } 
    } 

    function fetchMethodCURL($state){ 
        if($state){ 
            $this->_FETCHMETHOD="CURL"; 
        }else{ 
            $this->_FETCHMETHOD="OTHER"; 
        } 
    } 

    function _call(){ 
        $this->_CH = curl_init(); 
        curl_setopt($this->_CH,CURLOPT_RETURNTRANSFER,true); 
        curl_setopt($this->_CH,CURLOPT_URL,$this->_URL); 
        $result = curl_exec($this->_CH); 
        curl_close($this->_CH); 
        return $result; 
    } 

    function _init($bahnhof) { 
        $this->_PARAMS=array( 
            'country'=>'DEU', 
            'rt'=>1, 
            'GUIREQProduct_0'=>'on',	// ICE 
            'GUIREQProduct_1'=>'on',	// Intercity- und Eurocityzüge 
            'GUIREQProduct_2'=>'on',	// Interregio- und Schnellzüge 
            'GUIREQProduct_3'=>'on',	// Nahverkehr, sonstige Züge 
            'GUIREQProduct_4'=>'on',	// S-Bahn 
            'GUIREQProduct_5'=>'on',	// BUS 
            'GUIREQProduct_6'=>'on',	// Schiffe 
            'GUIREQProduct_7'=>'on',	// U-Bahn 
            'GUIREQProduct_8'=>'on',	// Strassenbahn 
            'REQ0JourneyStopsSID'=>'', 
            'REQTrain_name'=>'', 
            'REQTrain_name_filterSelf'=>'1', 
            'advancedProductMode'=>'', 
            'boardType'=>'dep',			// dep oder arr 
            'date'=>date("d.m.Y"), 
            'input'=>$bahnhof, 
            'start'=>'Suchen', 
            'time'=>date("H:i") 
        ); 
    } 
} 
# ------------------------------------------------------------------------------ 
?>

Viel Spaß
Pitti

PS: die Icons muss man wie hier im Thread beschrieben runterladen und entsprechend ablegen!

Funktioniert prinzipiell, aber er vergisst die voreingestellten Stationen nicht und nimmt auch keine neuen an. :confused:

Als Button wird es umgesetzt*, aber das Suchergebnis bleibt bei Erding & Co.

  • zumindest, wenn ich eine andere Station ins Array schreibe - wenn ich den Eintrag nur auskommentiere, dann wird es nicht gelöscht

Grüße
galleto

Hi galleto,

verstehe gerade nur Bahnhof :smiley:

Hast Du nur den Namen oder auch die ID geändert?

array(8001825, „Erding“, „“, 0xFF8000),

8001825 => Id der Haltestelle (muss man aus der echten Website extrahieren, stand auch oben irgendwo)
Erding => Anzeigename

Hilft das?
Ciao Pitti

Könnte bitte nochmal jemand reinstellen, wo man die Icons der Bahn herbekommt und wie man die StationsID der Bahnhöfe ermittelt. Habe zwar den ganzen Faden gelesen aber diese Infos nicht gefunden. Kann auch Blindheit oder Blödheit sein, freu mich aber doch über Hilfe.

In Post 24 (3.Seite) ganz unten hängt ein Zip dran!

Ablegen muss man sie unter „/var/lib/symcon/webfront/user/bahn/“

Die Stations-ID habe ich wie folgt ermittelt (geht vielleicht auch anders):

  • Seite direkt aufgerufen
  • Name eingegeben (meist kommt durch Suggestion die richtige Station/Name)
  • dann einfach Suchen klicken
  • im Browser F12 (Debug Console) öffnen
  • Das Inputfeld auswählen und den Wert rauskopieren

Bissle doof, aber man macht das ja nur ein mal!

Ciao Pitti

Danke Pitti,

dann kann ich ja mal etwas zurückgeben:
Habe eine öffentliche Liste der Bahn gefunden, in dr alle 6.600 Stationen verzeichnet sind. Leider wenig systematisch und recht umfangreich, aber mit Geodaten.

Habe das in eine Exceltabelle umgearbeitet und selktierbar gemacht.
DB_Stationsnummern_2017-09.zip (463 KB)
Die Felder Laenge und Breite habe ich mit einem Suchfilter für meinen Wohnort mit ± 0,2 Länge/Breite vergeben und oala: die Stationen in meiner Umgebung. In der ersten Spalte kann ich dann z.B. ein „x“ als Selektor eintragen, damit ich die gewünschten Stationen später besser wiederfinde.

Viel Spaß damit.

Irgendwie stelle ich mich schon wieder zu dappig an.
Habe eine Kategorie „DB“ angelegt und darunter das Skript, ebenfalls mit dem Namen „DB“ angelegt, gespeichert und ausgeführt. Dann werden unter dem Skript (nicht wirklich geschickt) die Variablen angelegt

. Mir wäre es ja lieber, das Skript selber wäre unsichtbar und die Variablen unterhalb eines Dummy-Moduls.

Beim ausführen aus dem Skripteditor gibt es keine Fehlermeldung. Aber im Webfront kommt, sobald man auf eine der Schaltflächen klickt, die Meldung „X Fehler“. Wenn ich das skript aus dem Webfront heraus ausführe, kommt eine ganze Liste von Fehlern:

25.02.2018 19:16:04 | PHP | Error: Notice: Undefined index: VARIABLE
   Error in Script E:\IP-Symcon\scripts\22069.ips.php on Line 139
  134 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger.inc.php (call IPSLogger_Out)
   44 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger_PhpErrorHandler.inc.php (call IPSLogger_Err)
  139 in scripts\22069.ips.php (call IPSLogger_PhpErrorHandler)
25.02.2018 19:16:04 | PHP | Error: Notice: Undefined index: VARIABLE
   Error in Script E:\IP-Symcon\scripts\22069.ips.php on Line 189
  134 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger.inc.php (call IPSLogger_Out)
   44 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger_PhpErrorHandler.inc.php (call IPSLogger_Err)
  189 in scripts\22069.ips.php (call IPSLogger_PhpErrorHandler)
25.02.2018 19:16:04 | PHP | Error: Notice: Undefined index: VALUE
   Error in Script E:\IP-Symcon\scripts\22069.ips.php on Line 189
  134 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger.inc.php (call IPSLogger_Out)
   44 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger_PhpErrorHandler.inc.php (call IPSLogger_Err)
  189 in scripts\22069.ips.php (call IPSLogger_PhpErrorHandler)
25.02.2018 19:16:04 | PHP | Error: Warning: Variable #0 existiert nicht
   Error in Script E:\IP-Symcon\scripts\22069.ips.php on Line 189
  134 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger.inc.php (call IPSLogger_Out)
   37 in scripts\IPSLibrary\app\core\IPSLogger\IPSLogger_PhpErrorHandler.inc.php (call IPSLogger_Err)
      in IPSLogger_PhpErrorHandler
  189 in scripts\22069.ips.php (call SetValue)

Benötigt das skript noch irgendwelche Bibliotheken, die am Anfang des Threads mal erwähnt waren?

 # Zeilen 137 bis 190 in denen der Fehler auftritt:
// AKTION VIA WEBFRONT
else if($_IPS['SENDER'] == "WebFront") {
    $name = IPS_GetName($_IPS['VARIABLE']); #139, hier tritt der erste Fehler auf
    switch ($name) {
        case 'Startzeit':  
            switch($_IPS['VALUE']) {
                case $min-3:
                    SetValue($_IPS['VARIABLE'], 0); 
                    break;
                case $min-2:
                      $_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $jump;
                      if($_IPS['VALUE'] <= 0) {
                        $_IPS['VALUE'] = -3;
                        SetValue($_IPS['VARIABLE'], 0); 
                      }
                      break;
                case $min-1:
                      $_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $step;
                      if($_IPS['VALUE'] <= 0) {
                        $_IPS['VALUE'] = -3;
                        SetValue($_IPS['VARIABLE'], 0); 
                      }
                      break;
                   case $max+1:
                      $_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $step);
                     break;
                   case $max+2:
                      $_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $jump);
                     break;
                default:
                    return;
                break;
            }
            break;
        case 'Reise':
            // Daten holen 
            $vid = CreateVariableByName($_IPS['SELF'], "Startzeit", 1);
            $start = GetValue($vid);
            $vid = CreateVariableByName($_IPS['SELF'], "Laufweg", 1);
            $time = GetValue($vid);
            $vid = CreateVariableByName($_IPS['SELF'], "Abfahrt und Ankunft", 1);
            $mode = GetValue($vid);
            $vid = CreateVariableByName($_IPS['SELF'], "Bahnhof/Haltestelle", 1);
            $station = GetValue($vid); //Formatted
            // Fahrplan rendern
            $vid = CreateVariableByName($_IPS['SELF'], "Fahrplan ", 3);
            SetValue($vid, GenerateTimetable($start, $time, $mode, $station));        
            // Update Button zurückstellen
            $_IPS['VALUE'] = 0;
            break;
    }
    // Speichern
    SetValue($_IPS['VARIABLE'], $_IPS['VALUE']); #190 Hier treten die anderen Fehler auf
}

Hi Tango,

komme gerade aus der Kneipe, also vielleicht nicht mehr alles 100tig bei mir :wink:

Aber was macht die IPSLibrary da bei diesem Script??? Also mein Script hat damit nix zu tun, ich nutze sie nicht!
Hast Du da was verändert?

PS: Ich finde die Variablen unterhalb des Scripts geschickt :wink: :wink: :wink:

Die Variablen werden jedenfalls korrekt angelegt!

Ciao Pitti

Hallo Pitti,

bin nochmal an die Sache gegangen und habe „mein“ Skript (ich hatte nur die Bahnhöfe geändert) und alle Variablen rausgelöscht und das Skript von oben nochmal völlig rein und sauber in ein neues Skript bei mir reinkopiert, nix geändert, gespeicher und einmal ausgeführt. Das lief, wie bei mir, ohne Fehler durch. Das Skript habe ich auf nicht sichbar gesetzt.

Dann habe ich separat ein Dummy-Modul angelegt und darunter Links der Variablen gesetzt und die wieder so sortiert, wie Du es gemacht hast.

Im Webfront wird also alles wieder angezeigt, allerdings werden bei den Bahnhöfen nicht nur Deine drei angezeigt, sondern auch die sieben, die ich gestern bei mir angelegt hatte, also werden jetzt ???10 Stationen??? gezeigt. Wo merkt denn der sich das?

Wenn ich eine Änderung an den Voreinstellungen im Webfront mache kommt wieder „+ Fehler“. Es hat sich also nix geändert. Der Fahrplan wird nicht angezeigt.

Wenn ich das Skript im Webfront sichtbar mache und von dort ausführe, kommt wieder die Fehlermeldung, dass er den Index ‚VARIABLE‘ nicht kennt (Zeile 126 und 176), sowie einen undefinierten Index ‚VALUE‘ habe und die Variable #0 nicht existieren würde (Zeile 176).

Any Ideas?

Haha, das merkt er sich im Profil der Variable :frowning: Bitte händisch löschen - Profil „Travel.Stations“ !!!

Die anderen Themen muss ich mir später mal durchdenken bzw. wir chatten, skypen, telefonieren mal!

Ciao Pitti

Danke Pitti, das hat mich auf die richtige Spur gebracht. Wichtig ist, alle führenden Nullen der ID zu löschen; das können auch drei sein, dann ist das Format halt kürzer.

Für meine „Dorfhaltestelle“ bekomme ich noch folgende Fehlermeldung:

26.02.2018 11:49:49 | PHP | Error: Notice: Undefined index: platform
Error in Script C:\IP-Symcon\scripts\54560.ips.php on Line 298

Wahrscheinlich stolpert das Skript über die Gleis-Angabe. Kannst Du das abfangen?

Grüße
galleto

Versuch mal die Zeile mit dem hier zu ersetzen


$eintrag[5] = isset($bahn->timetable[$i]["platform"]) ? $bahn->timetable[$i]["platform"] : ''; 

Hi Pitti,

geniales Script!

Einen Fehler bekomme ich leider immer wieder angezeigt.

2018-02-26 16_06_49-IPSView Windows.png

Dabei wird das Icon „ec_ic_24x24.gif“ nicht geladen.

Eine Idee was das sein kann?

Gruß
Kai

Hi Kai,

habe es mir mal auf die Schnelle angeschaut, eigentlich sollte es funzen!

Das Icon „ec_ic_24x24.gif“ wird nicht geladen weil der TYPE vorher anscheinend nicht gesetzt worden ist. Warum das so ist kann ich im Moment nicht sagen! Passieren muss das zwischen Zeile 472 und 488 in der Klasse, welche ja nicht von mir ist :wink:

Ich schaue es mir aber heute Abend nochmal an!

Ciao Pitti

Funktioniert! Vielen Dank!

Grüße
galleto

Habs :smiley:

Bitte Zeile 476 durch das hier ersetzen:


                                if (preg_match('%/([a-z_]*)_24%', $img->getAttribute("src"), $regs)) {

Das [a-z_] macht den Unterschied, also der „_“!

Ich poste demnächst nochmal das gesamte Script mit all den Patches!

Ciao Heiko

Hi Pitti,

genial!!! :smiley:

Vielen Dank.

Besteht die Möglichkeit, dass man sich in der HTML-Box mehr als 6 Zeilen (Einträge) anzeigen lassen kann?

Beste Grüße
Kai

Hi zusammen,

hier mal ein Update mit den gemachten Änderung entsprechend dem Feedback hier im Forum.

Ein neuer Konfigurationsparameter ($rows) ist hinzugekommen (Gruß an @KaiS), damit kann man jetzt steuern wieviel Zeilen der Fahrplan darstellen soll (maximal 20 sind möglich).

Viel Spaß
Pitti


<? 
################################################################################
# Scriptbezeichnung: Online.Travel.ips.php
# Version: 1.1.20180226
# Author:  Heiko Wilknitz (@Pitti)
#          Original von sysrun (16.05.2010)
#
# Abfahrtstafeln von bahn.de
# ===========================
#
# Dieses Skript liest die An-und Abfahrtszeiten der Deutschen Bahn aus.
#
# Installation:
# -------------
#
# Dieses Skript richtet automatisch alle nötigen Objekte bei manueller
# Ausführung ein. Eine weitere manuelle Ausführung setzt alle benötigten Objekte
# wieder auf den Ausgangszustand.
#
# - Neues Skript erstellen
# - Diesen PHP-Code hineinkopieren
# - Abschnitt 'Konfiguration' den eigenen Gegebenheiten anpassen 
# - Skript Abspeichern
# - Skript Ausführen
#
# ------------------------------ Konfiguration ---------------------------------
#
# Anzahl Zeilen in Fahrplantabelle (maximal 20 möglich)
$rows = 10; 
#
# Schrittweite bzw. Offset der Startzeit konfigurierbar machen
# von Jetzt bis max. 12 Stunden in der Zukunft, sollte reichen
# Nur im Notfall anpassen ;-)
#
$min 		= 0;		// Jetzt 
$max 		= 720; 	// 12 Stunden 
$step 	= 5;  	// kleine Schrittweite
$jump 	= 60;		// große Schrittweite
$suffix 	= "min";	// min = Minuten
#
# Startzeit Offset Profil 
#
$time = array(
	array($min-3, "Jetzt", 		"", 0x0000FF),
	array($min-2, "--",	 		"", -1),
	array($min-1, "-", 	 		"", -1),
	array($min, "%d ".$suffix, 	"", 0x00FF00),
	array($max+1, "+", 			"", -1),
	array($max+2, "++",			"", -1)
);
#
# Ankunft & Abfahrt Profil
#
$arrdep = array(
	array(0, "Abfahrt",	"", 0x00FF00),
	array(1, "Ankunft",	"", 0xFFFF00),
	array(2, "Beides",	"", 0x0000FF)
);
#
# Stationen Profil
# ACHTUNG: Hier die eigenen Stationen eintragen bzw. Ändern und Erweitern!!
#		int => Stations ID
#		string => Anzeigename
#	 	hex => Farbcode
#
$stations = array(
	array(8001825, "Erding",			"", 0xFF8000),
	array(8003879, "Markt Schwaben",	"", 0xFF8000),
	array(8004252, "Neubiberg",			"", 0xFF8000)
);
#
# Suchen 
#
$search = array(
  array(0, '>', '', -1),
  array(1, 'Suchen', '', 0x008000)
);
#
################################################################################

// INSTALLATION
if ($_IPS['SENDER']=='Execute') {
	$pos = 0;
	// Startzeit
	$vpn = "Travel.Time";
	$vid = CreateVariableByName($_IPS['SELF'], "Startzeit", 1);
	CreateProfileInteger($vpn, 'Clock', '', '', $min, $max, 0, 0, $time);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, $min-3);	
	// Wegzeit bzw. Laufweg
	$vpn = "Travel.AwayTime";
	$vid = CreateVariableByName($_IPS['SELF'], "Laufweg", 1);
	CreateProfileInteger($vpn, 'Hourglass', '', ' min', 0, 60, 5, 0, NULL);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);	
	// Abfahrt und Ankunft
	$vpn = "Travel.ArrivalsDeparture";
	$vid = CreateVariableByName($_IPS['SELF'], "Abfahrt und Ankunft", 1);
	CreateProfileInteger($vpn, 'Distance', '', '', 0, 0, 0, 0, $arrdep);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);	
	// Stationen
	$vpn = "Travel.Stations";
	$vid = CreateVariableByName($_IPS['SELF'], "Bahnhof/Haltestelle", 1);
	CreateProfileInteger($vpn, 'Flag', '', '', 0, 0, 0, 0, $stations);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, $stations[0][0]);	
	// Suchen
	$vpn = "Travel.Search";
	$vid = CreateVariableByName($_IPS['SELF'], "Reise", 1);
	CreateProfileInteger($vpn, 'Script', '', '', 0, 0, 0, 0, $search);
	IPS_SetVariableCustomProfile($vid, $vpn);
	IPS_SetVariableCustomAction($vid, $_IPS['SELF']);
	IPS_SetPosition($vid, $pos++);
	SetValue($vid, 0);
	// Fahrplan
	$vid = CreateVariableByName($_IPS['SELF'], "Fahrplan ", 3);
	IPS_SetVariableCustomProfile($vid, '~HTMLBox');
	IPS_SetIcon($vid, "Database");
	IPS_SetPosition($vid, $pos++);
}
// AKTION VIA WEBFRONT
else if($_IPS['SENDER'] == "WebFront") {
	$name = IPS_GetName($_IPS['VARIABLE']);
	switch ($name) {
    	case 'Startzeit':  
			switch($_IPS['VALUE']) {
		    	case $min-3:
					SetValue($_IPS['VARIABLE'], 0); 
					break;
		    	case $min-2:
		          	$_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $jump;
		          	if($_IPS['VALUE'] <= 0) {
						$_IPS['VALUE'] = -3;
							SetValue($_IPS['VARIABLE'], 0); 
		          	}
		          	break;
		    	case $min-1:
		          	$_IPS['VALUE'] = GetValue($_IPS['VARIABLE']) - $step;
		          	if($_IPS['VALUE'] <= 0) {
						$_IPS['VALUE'] = -3;
							SetValue($_IPS['VARIABLE'], 0); 
		          	}
		          	break;
		       	case $max+1:
		          	$_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $step);
		         	break;
		       	case $max+2:
		          	$_IPS['VALUE'] = min($max, max(0, GetValue($_IPS['VARIABLE'])) + $jump);
		         	break;
		        default:
		            return;
				break;
	    	}
			break;
	    case 'Reise':
			// Daten holen 
			$vid = CreateVariableByName($_IPS['SELF'], "Startzeit", 1);
			$start = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Laufweg", 1);
			$time = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Abfahrt und Ankunft", 1);
			$mode = GetValue($vid);
			$vid = CreateVariableByName($_IPS['SELF'], "Bahnhof/Haltestelle", 1);
			$station = GetValue($vid); //Formatted
			// Fahrplan rendern
			$vid = CreateVariableByName($_IPS['SELF'], "Fahrplan ", 3);
			SetValue($vid, GenerateTimetable($start, $time, $mode, $station, $rows));		
			// Update Button zurückstellen
			$_IPS['VALUE'] = 0;
        	break;
	}
   // Speichern
	SetValue($_IPS['VARIABLE'], $_IPS['VALUE']);
}

# -------------------------------- FUNKTIONEN ----------------------------------

// Daten von bahne.de holen und rendern
function GenerateTimetable($start, $time, $mode, $station, $rows) 
{
    // Anzeige aufbereiten 
	$style = "";
	$style = $style.'<style type="text/css">';
	$style = $style.'table  {border-collapse: collapse; font-size: 14px; width: 100%; }';
	$style = $style.'td.fst {vertical-align: middle; text-align: center; width: 30px; padding: 5px; border-left: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.mid {vertical-align: middle; text-align: left; line-height: 20px; padding: 5px; border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'td.lst {vertical-align: middle; text-align: left; width: 350px; line-height: 20px; padding: 5px; border-right: 1px solid rgba(255, 255, 255, 0.2); border-top: 1px solid rgba(255, 255, 255, 0.1); }';
	$style = $style.'tr:last-child {border-bottom: 1px solid rgba(255, 255, 255, 0.2); }';
	$style = $style.'tr:nth-child(even) {  background-color: rgba(0, 0, 0, 0.2); }';	  
	$style = $style.'.th { color: rgb(255, 255, 255); background-color: rgb(160, 160, 0); font-weight:bold; background-image: linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -o-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -moz-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -webkit-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); background-image: -ms-linear-gradient(top,rgba(0,0,0,0) 0,rgba(0,0,0,0.3) 50%,rgba(0,0,0,0.3) 100%); }';
	$style = $style.'</style>';

	// Startzeit berechnen
	$dateTime = new DateTime();
	if ($start > 0) {
		$dateTime->modify('+'.$start.' minutes');
	}

	// Hier werden Verkehrsmittel ausgeschlossen 
	/* 
	$bahn->TypeBUS(false); 
	$bahn->TypeTRAM(false); 
	$bahn->TypeICE(false); 
	$bahn->TypeIC(false); 
	$bahn->TypeRE(false); 
	$bahn->TypeSBAHN(false); 
	$bahn->TypeUBAHN(false); 
	$bahn->TypeFAEHRE(false); 
	*/ 
	// Abfahrt
	$departure = '';
	if ($mode == 0 || $mode == 2) {
		// Parameter 1 ist der Bahnhof oder die Haltestelle 
		// (es muss kein Bahnhof sein, Bushaltestelle gehen auch) 
		// Parameter 2 ist die Art der Tafel: "Abfahrt" oder "Ankunft" 
		$bahn=new Bahn($station, "abfahrt"); 
		// Hier werden Datum und Zeit gesetzt. 
		// Werden die nicht gesetzt wird die/das aktuelle Zeit/Datum genommen
		$bahn->datum($dateTime->format('d.m.Y')); 
		$bahn->zeit($dateTime->format("H:i"));
		// Jetzt das Ergebniss holen! 
		$status=$bahn->fetch(); 
		if($status){ 
		    // Array mit den Informationen ausgeben: 
		    $departure = RenderHTML($bahn, "Abfahrt", $time, $rows); 
		} 
	} 
	// Ankunft
	$arrivals = '';
	if ($mode == 1 || $mode == 2) {
		// Parameter 1 ist der Bahnhof oder die Haltestelle 
		// (es muss kein Bahnhof sein, Bushaltestelle gehen auch) 
		// Parameter 2 ist die Art der Tafel: "Abfahrt" oder "Ankunft" 
		$bahn=new Bahn($station, "ankunft"); 
		// Hier werden Datum und Zeit gesetzt. 
		// Werden die nicht gesetzt wird die/das aktuelle Zeit/Datum genommen
		$bahn->datum($dateTime->format('d.m.Y')); 
		$bahn->zeit($dateTime->format("H:i")); 
		// Jetzt das Ergebniss holen! 
		$status=$bahn->fetch(); 
		if($status){ 
		    // Array mit den Informationen ausgeben: 
		    $arrivals = RenderHTML($bahn, "Ankunft", 0, $rows); 
		} 
	}
	// HTML zusammenbauen	
	$html = $style;
	$html = $html.$departure;
	if (!empty($departure)) $html = $html.'<br />'; 
	$html = $html.$arrivals;
	// fertiges HTML zurueck
	return $html;
}

// anzeige aufbereiten in eine html box 
// $bahn - ergebnis der class.bahn.php
// $typ - "Ankunft" oder "Abfahrt"  
// $wegezeit - eine wegezeit in minuten zum bahnhof. oder =0
// $zeilen - maximale Anzahl von Zeilen pro Tabelle
function RenderHTML($bahn, $typ, $wegezeit, $zeilen) 
{
	$str = '';  
	$str .= '<table>';
	$str .= '<tr><td class="fst th" style="width:30px;"></td><td class="mid th"  style="width:80px;">Zug</td><td class="mid th" style="width:50px;">'.$typ.'</td><td class="mid th" style="width:50px;">Diff.</td><td class="mid th" style="width:200px;">Richtung</td><td class="mid th" style="width:40px;">Gleis</td><td class="lst th">Aktuelles</td></tr>'; 

	$pos = 0; 
	$journeys = count($bahn->timetable);
	for($i=0; $i<$journeys; $i++) { 
		//$eintrag = explode(";", $bahn->timetable[$i]); 
		$caller = $bahn->timetable[$i]["type"]; 
		$eintrag[0] = "<img src=/user/bahn/".strtolower($caller)."_24x24.gif>"; 
		$colour="white"; // yellow or red, white ist der normalfall 
		$eintrag[1] = $bahn->timetable[$i]["train"]; 
		$eintrag[2] = $bahn->timetable[$i]["time"]; 
		// differenz zur aktuellen zeit ausrechnen. 
		$timestampField = strtotime($bahn->timetable[$i]["time"]); 
		$timestampNow = time();//+1*60*60; 
		$diff = $timestampField - $timestampNow; 
		//echo $diff." * "; 
		if ($diff >0) { 
			$eintrag[3] = $uhrzeit = date("H:i",$diff-1*60*60); 
			if ($diff > $wegezeit*60) { 
				$colour="white"; 
			} 
			else { 
				$colour="yellow"; 
				$eintrag[3]="<font color='#FFFF00'>".$eintrag[3]; 
			} 
		} 
		else { 
			// nicht mehr zu schaffen da zeit abgelaufen 
			$eintrag[3] = "--:--"; 
			if ($wegezeit <>0) 
				$eintrag[3]="<font color='#FF0000'>".$eintrag[3]; 
		} 
		$eintrag[4] = $bahn->timetable[$i]["route_ziel"]; 
		$eintrag[5] = isset($bahn->timetable[$i]["platform"]) ? $bahn->timetable[$i]["platform"] : ''; 
		$eintrag[6] = $bahn->timetable[$i]["ris"]; 
		
		$str .= "<tr>"; 
		
		$count = count( $eintrag );
		for ( $e = 0; $e < $count; $e++ ) {
			if ( $e == 0 ) $class = 'fst'; 
			else if ( $e == $count - 1 ) $class = 'lst'; 
			else $class = 'mid'; 
			$str .= '<td class="'.$class.'">'.$eintrag[$e].'</td>'; 
		}			
		$str .= "</tr>"; 
		
		$pos++; 
		
		if($pos >= $zeilen) 
			break; 
	} 
	$str .= "</table>"; 
	
	return $str; 
} 

// Erzeugt eine Variable unterhalb {id} mit dem Namen {name} vom Typ [type}
// Existiert die Variable schon wird diese zurückgeliefert.
// Types: 0 = Boolean, 1 = Integer, 2 = Float, 3 = String
function CreateVariableByName($id, $name, $type) 
{ 
   $vid = @IPS_GetVariableIDByName($name, $id); 
   if($vid===false) { 
      $vid = IPS_CreateVariable($type); 
      IPS_SetParent($vid, $id); 
      IPS_SetName($vid, $name); 
   }
   return $vid; 
}

// Erzeugt ein Variablenprofil vom Typ {type} mit Name n{name} 
function CreateProfile($name, $type)
{
	if(!IPS_VariableProfileExists($name)) {
		IPS_CreateVariableProfile($name, $type);
	} 
	else {
	  $profile = IPS_GetVariableProfile($name);
	  if($profile['ProfileType'] != $type)
	    throw new Exception("Variable profile type does not match for profile ".$name);
	}
}

// Erzeugt ein Integer-Variablenprofil
function CreateProfileInteger($name, $icon, $prefix, $suffix, $minvalue, $maxvalue, $step, $digits, $asso = NULL)
{
	CreateProfile($name, 1);

	IPS_SetVariableProfileIcon($name, $icon);
	IPS_SetVariableProfileText($name, $prefix, $suffix);
	IPS_SetVariableProfileDigits($name, $digits);
	
	if(sizeof($asso) !== 0){
	  $minvalue = 0;
	  $maxvalue = 0;
	} 
	IPS_SetVariableProfileValues($name, $minvalue, $maxvalue, $step);
	
	if(sizeof($asso) !== 0){
	  foreach($asso as $ass) {
	    IPS_SetVariableProfileAssociation($name, $ass[0], $ass[1], $ass[2], $ass[3]);
	  }
	}         
}

# --------------------------------- KLASSE BAHN --------------------------------
# 
#	Author: Frederik Granna (sysrun) 
#	Version 0.1 
# 
# ------------------------------------------------------------------------------
class Bahn
{ 
    var $_BASEURL="https://reiseauskunft.bahn.de/bin/bhftafel.exe/dn?maxJourneys=20"; 
    var $_PARAMS=array(); 
    var $timetable=array(); 
    var $bahnhof=false; 
    var $_FETCHMETHOD; 

    function Bahn($bahnhof=null,$type="abfahrt"){ 
       $type=strtolower($type); 
       if(!$bahnhof) 
          $bahnhof="008003280"; 
        $this->_init($bahnhof); 
        $this->fetchMethodCURL(true); 
        $this->boardType($type);
    } 

    function TypeBUS($state=true){$this->_PARAMS['GUIREQProduct_5'] = ($state) ? "on" : false;} 
    function TypeICE($state=true){$this->_PARAMS['GUIREQProduct_0'] = ($state) ? "on" : false;} 
    function TypeIC($state=true){$this->_PARAMS['GUIREQProduct_1'] = ($state) ? "on" : false;} 
    function TypeRE ($state=true){$this->_PARAMS['GUIREQProduct_3'] = ($state) ? "on" : false;} // NV genannt 
    function TypeSBAHN ($state=true){$this->_PARAMS['GUIREQProduct_4'] = ($state) ? "on" : false;} 
    function TypeFAEHRE ($state=true){$this->_PARAMS['GUIREQProduct_6'] = ($state) ? "on" : false;}   // UBAHN 
    function TypeTRAM ($state=true){$this->_PARAMS['GUIREQProduct_8'] = ($state) ? "on" : false;}   // STrassenbahn 
    function TypeUBAHN ($state=true){$this->_PARAMS['GUIREQProduct_7'] = ($state) ? "on" : false;}   // UBAHN 

    function boardType($type){ 
        if($type=="ankunft") 
            $this->_PARAMS['boardType']="arr"; 
        else 
            $this->_PARAMS['boardType']="dep";
    } 

    function datum($datum){ 
        $this->_PARAMS['date']=$datum; 
    } 

    function zeit($zeit){ 
        $this->_PARAMS['time']=$zeit; 

    } 

    function fetch($html=null){ 
       if($html){ 
          return $this->_parse($html); 
       }else if($this->_FETCHMETHOD=="CURL"){ 
            return $this->_queryCurl(); 
        } 
    } 

    function _queryCurl(){ 
        $this->buildQueryURL(); 
        $result=$this->_call(); 
        return $this->_parse($result); 
    } 

    function buildQueryURL(){ 
       $fields_string=""; 
        foreach($this->_PARAMS as $key=>$value){ 
           if($value) 
                $fields_string .= $key.'='.urlencode($value).'&'; 
        }; 
        rtrim($fields_string,'&'); 

        $this->_URL=$this->_BASEURL.$fields_string; 
        return $this->_URL; 
    } 

    function _parse($data){ 
        $dom = new DOMDocument(); 
        @$dom->loadHTML($data); 

        $select=$dom->getElementById("rplc0"); 
        if($select->tagName=="select"){ 
            $options=$select->getElementsByTagName("option"); 
            foreach($options AS $op){ 
                echo utf8_decode($op->getAttribute("value")."-".$op->nodeValue)."n"; 
            } 
            return false; 
        }else{ 
           $this->bahnhof=utf8_decode($select->getAttribute("value")); 
            $this->_process_dom($dom); 
            return true; 
        } 
    } 

    function _process_dom($dom){ 
        $test=$dom->getElementById("sqResult")->getElementsByTagName("tr"); 
        $data=array(); 
        foreach($test as $k=>$t){ 
            $tds=$t->getElementsByTagName("td"); 
            foreach($tds AS $td){ 
               $dtype=$td->getAttribute("class"); 
                switch($dtype){ 
                    case 'train':
                        if($a=$td->getElementsByTagName("a")->item(0)){
	                     	$data[$k]['train']=str_replace(" ","",$a->nodeValue);
                            if($img=$a->getElementsByTagName("img")->item(0)){
                                if (preg_match('%/([a-z_]*)_24%', $img->getAttribute("src"), $regs)) {
                                   switch($regs[1]){ 
                                      case 'EC': 
                                         $data[$k]['type']="IC"; 
                                      break; 
                                        default: 
                                            $data[$k]['type']=strtoupper($regs[1]); 
                                        break; 
                                    } 
                                } 
                            } 
                        } 
                    break; 
                    case 'route': 
                       if($span=@$td->getElementsByTagName("span")->item(0)){ 
                          $data[$k]['route_ziel']=$span->nodeValue; 
                        } 
                        preg_match_all('/(.*)s*([0-9:]{5})/', $td->nodeValue, $result, PREG_PATTERN_ORDER); 
                        $tmp=array(); 
                        foreach($result[1] AS $rk=>$rv){ 
                        	$tmp[$result[2][$rk]]=utf8_decode(trim(html_entity_decode(str_replace("n","",$rv)))); 
                        } 
                        $data[$k]['route']=$tmp; 
                    break; 
                    case 'time': 
                    case 'platform': 
                    case 'ris': 
                       $data[$k][$dtype]=$td->nodeValue; 
                    break; 
                } 
            } 
        } 
        foreach($data AS $d){ 
            if(array_key_exists("train",$d)){ 
               foreach($d AS $dk=>$dv) 
                  if(!is_array($dv)) 
                      $d[$dk]=ltrim(str_replace("
","",utf8_decode(trim(html_entity_decode($dv)))),"-"); 
                $d['route_start']=$this->bahnhof; 
                $this->timetable[]=$d; 
         	} 
        } 
    } 

    function fetchMethodCURL($state){ 
        if($state){ 
            $this->_FETCHMETHOD="CURL"; 
        }else{ 
            $this->_FETCHMETHOD="OTHER"; 
        } 
    } 

    function _call(){ 
        $this->_CH = curl_init(); 
        curl_setopt($this->_CH,CURLOPT_RETURNTRANSFER,true); 
        curl_setopt($this->_CH,CURLOPT_URL,$this->_URL); 
        $result = curl_exec($this->_CH); 
        curl_close($this->_CH); 
        return $result; 
    } 

    function _init($bahnhof) { 
        $this->_PARAMS=array( 
            'country'=>'DEU', 
            'rt'=>1, 
            'GUIREQProduct_0'=>'on',	// ICE 
            'GUIREQProduct_1'=>'on',	// Intercity- und Eurocityzüge 
            'GUIREQProduct_2'=>'on',	// Interregio- und Schnellzüge 
            'GUIREQProduct_3'=>'on',	// Nahverkehr, sonstige Züge 
            'GUIREQProduct_4'=>'on',	// S-Bahn 
            'GUIREQProduct_5'=>'on',	// BUS 
            'GUIREQProduct_6'=>'on',	// Schiffe 
            'GUIREQProduct_7'=>'on',	// U-Bahn 
            'GUIREQProduct_8'=>'on',	// Strassenbahn 
            'REQ0JourneyStopsSID'=>'', 
            'REQTrain_name'=>'', 
            'REQTrain_name_filterSelf'=>'1', 
            'advancedProductMode'=>'', 
            'boardType'=>'dep',			// dep oder arr 
            'date'=>date("d.m.Y"), 
            'input'=>$bahnhof, 
            'start'=>'Suchen', 
            'time'=>date("H:i") 
        ); 
    } 
} 
# ------------------------------------------------------------------------------ 
?>

@pitti: vielen Dank für den sehr netten Support! Und für das tolle Skript, das Du zusammengetragen, verbessert un zu einer tollen Funktion gebracht hast.

@all: mein Problem mit dem „+ FEHLER“ lag an Leerzeichen, die sich beim Kopieren in das Skript eingeschlichen hatten, vor dem PHP-Start-Zeichen „<?“ und nach dem Endezeichen „?>“. Pitti ist drauf gekommen, ich hätte endlos gesucht und es wohl nicht gefunden. Wieder was gelernt.

Hi pitti,

falls Du das Farbkonzept perfektionieren magst: Der Tabellenkopf fällt farblich etwas aus dem Rahmen. Mit IPS-Blau wäre es so:

$style = $style.'.th { color: rgb(255, 255, 255); background-color: rgb(0, 0, 178);

Nur eine Anregung, kein Soll. :smiley:

Grüße
galleto