Ajax, PHP, Javascript: Wertübergabe zwischen JS und PHP

Holgip

Lt. Commander
Registriert
Dez. 2012
Beiträge
1.779
Hallo liebe Programmierer,

ich habe ein kleines RaspberryPi-Projekt, mit dem ich meine Steckdosenleiste für meinen kleinen "Server" (Zotac ID14 mit 3xUSB-Festplatten, insgesamt 4 Steckdosen) steuern kann. Für die Steuerung habe ich folgende Dateien erstellt:

Eine HTML-Datei, die die Oberfläche zur Verfügung stellt und auch die PHP-Routinen zum Aufruf der einzelnen php-Dateien beinhaltet. Sie läuft als php-Datei, damit alles funktioniert und der Apache-Server auf dem Pi ist dementsprechend konfiguriert.

Für jede Festplatten-Steckdose zwei php-Dateien, die die Python-Dateien aufrufen, die wiederum die GPIOs steuern (ja ich weiß, von hinten durch die Brust ins Auge, aber bei meinen beschränkten Programmierkenntnissen war das jetzt der einfachste Weg).

Für den "Server" eine php-Datei zum Einschalten und eine zum Ausschalten, die gleich alles ausschaltet.

Das Ganze funktioniert auch einwandfrei.

Jetzt bin ich auf die verrückte Idee gekommen, beim Abschalten von allen Steckdosen eine Abfrage, ob auch wirklich ausgeschaltet werden soll, zu implementieren. Zum Testen und der Übersicht halber habe ich die Original-html-Datei "verschlankt", d.h. nur noch die Steuerung vom "Server" und einer Festplatte drin gelassen, und unter einem anderen Namen (komisch.php) abgespeichert.

Vornweg: ich weiß, dass Javascript auf dem Client und php auf dem Server (bei mir der Pi) läuft, aber leider kann man mit php keine Abfragebox erstellen und so musste ich auf JS zurück greifen. Da ich wenig Ahnung von JS und Ajax habe und das mit meinem doch schon älteren Hirn nicht so kapiere, versuchte ich mich an den Beispielen, die man im Internet findet.

Das Problem ist die Übergabe des angeklickten Buttons (Ja oder Abbruch) von JS an php. Ich bekomme den Wert partout nicht in php, solange die JS-Box in einer php-If-Routine läuft (es geht um die Zeilen 44 bis 68).
Erst probierte ich es mit "document.write", dann mit jQuery, leider ohne Erfolg.
Die Box wird zwar angezeigt, aber der Wert wird nicht übergeben.
echo = "mist" wird noch angezeigt, aber die Variable $ja ist leer, also wird auch Script "austest.php" nicht ausgeführt, das die Abschaltung übernimmt.

Wie bekomme ich den angeklickten Button nach php, wo ich ihn dann auswerten kann? Leider finde ich im Internet keine entsprechenden Beispiele.

Bitte in einfachen Worten erklären.

Hier die HTML-Datei:
Code:
<!DOCTYPE HTML>
<html>
<head>
<script src="https://code.jquery.com/jquery-1.10.2.js"></script>
</head>

<body style="background-image:url(hintergrund.jpg)">
<font face="Arial">
<center>
<br>
<br>
<table>

<tr>
<th>
<!-- ***************************************Server schalten******************************************** -->
<font face="Arial">Server</font>
<form name="form1" method="POST" action="komisch.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Server" name="serverein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Server" name="serveraus">
</form>


<?php

if(shell_exec('gpio -g read 17')==0){
	if(isset($_POST['serverein_x'])&& isset($_POST['serverein_y'])){
	include("servertest.php");
	}
	$server = "Server.png";
}

if(shell_exec('gpio -g read 17')==1){
	if(isset($_POST['serveraus_x'])&& isset($_POST['serveraus_y'])){

        $ja=0;

		echo '<script type="text/javascript">
		<!--
		if(window.confirm("Wirklich abschalten?") == true)
        {
            data = 1;
            var request = new XMLHttpRequest();
            request.open("POST", "komisch.php", false);
            request.setRequestHeader("Content-Type", "application/x-www-formurlencoded");
            request.send("a="+data);
         }
 		// -->
		</script>';
  	echo "mist";
		}
		$ja = $_POST['a'];
    echo $ja;
	if($ja==1)
    {
        include ("austest.php");
    }


	$server = "Server_on.jpg";
}
?>
</th>

<th>
<img src="<?php echo $server; ?>">
</th>

<th>
ACHTUNG!<br>Vergewissern, dass niemand<br>mehr auf den Server zugreift!<br>Hiermit wird alles ausgeschaltet!</th>
<th></th>
<!*****************************************************************************************************-->
<th><img src="leer.png"></th>
<th>
<!-- ***************************************Backup schalten******************************************* -->
Backup Festplatte
<form name="form4" method="POST" action="komisch.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Backup" name="backupein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Backup" name="backupaus">
</form>

<?php

$backup = "Backup.png";
if(shell_exec('gpio -g read 17')==1){
	if(shell_exec('gpio -g read 23')==0){
		if(isset($_POST['backupein_x'])&& isset($_POST['backupein_y'])){
		include("backuptest.php");
		}
		$backup = "Backup.png";
	}

	if(shell_exec('gpio -g read 23')==1){
		if(isset($_POST['backupaus_x'])&& isset($_POST['backupaus_y'])){
		include("backup_austest.php");
		}
		$backup = "Backup_on.jpg";
	}
}
?>
</th>
<th>
<img src="<?php echo $backup; ?>">
</th>
</tr>
<!*****************************************************************************************************-->
</table>
</center>
</body>
</html>
 
Überleg mal:
Code:
//Zeile 44-68:
$ja=0;
echo 'whatever';
echo 'mist';
$ja=$_POST["a"];
Wie soll $_POST["a"] mit Werten gefüllt sein. ​​​

Das XHR erzeugt vielleicht ein !neuen! HTML Seitenaufruf und startet das Script erneut (an Zeile 1). Du musst bei deiner Seite auf $_POST["a"] prüfen. Das machst du bspw. am Anfang​. Dann kannst du darauf reagieren.

Denk daran:
PHP arbeitet genau eine Abfrage ab, diese ändert sich während der Laufzeit des Scripts auch nicht.
PHP kann kein JS.
HTML ist stateless, das heißt, jede Abfrage steht für sich.
JS ist asynchron, das kann quasi sofort, später oder nie ausgeführt werden.
 
Hallo Hancock,

Danke für deine Antwort. Das $ja=0; soll sicherstellen, dass die Variable einen definierten Wert hat, das Weglöschen bringt nichts.
echo "mist" soll eigentlich nur zeigen, dass die If-Bedingung ausgeführt wird.
So wie ich die Beispiele verstanden habe, wird die Vaiable a über das XHR (request.send ("a="+data) gesetzt und somit müsste sich bei meinem Verständnist auch ein Wert im $_POST["a"] befinden.
Du musst bei deiner Seite auf $_POST["a"] prüfen. Das machst du bspw. am Anfang​. Dann kannst du darauf reagieren.

Du meinst, ich sollte im Header eine PHP-Function erstellen, wo ich die Abfrage von $_POST["a"] und die weitere Verarbeitung erledige?
 
Ja.

PHP wartet nicht, bis das JS ausgeführt wird. PHP weiß nicht mal, dass es ausgeführt wird (für PHP ist das eine Zeichenfolge).
Dass das JS ausgeführt wird, erfährt PHP erst, wenn AJAX-Request auf dem Server verarbeitet wird. Und diese Verarbeitung startet wieder ganz am Anfang, mit einem neuen PHP Script, einem neuen Prozess, neuen Variablen, ...
 
Du machst dir das Leben recht schwer, schau dir das mal an:

Code:
<script type="text/javascript">
function testSubmit(e) {
 if(window.confirm("Wirklich abschalten?") == true){ 
 var oConfirm = document.createElement('input');
 oConfirm.type='hidden';
 oConfirm.name=e;
 oConfirm.value="true";
 document.getElementById(e).parentNode.appendChild(oConfirm);
 document.getElementById(e).parentNode.submit();
 }
}
</script>

<html>
<form name="form1" method="POST" action="komisch.php">
<input type="button" id="serveraus_1" value="Server ausschalten" onclick="testSubmit('serveraus_1');" />
</form>
</html>

Runtergebrochen: du löst mit deinem Aus- Button kein Submit des Forms aus sondern nur das Javascript, das dann nachfragt ob wirklich ausgeschaltet weden soll. Wenn ja wird ein Input angelegt, der kriegt als Namen die ID des aufrufenden Buttons, wird an das Form angehangen und dann das Form mit submit() weggeposted. Im PHP kannst du dann gucken ob $_POST['serveraus_1'] gesetzt ist.

EDIT: nicht ausprobiert, sollte aber gehen.
EDIT2: gerade gesehen du benutzt jQuery, das hat wahrscheinlich solche Funktionen schon fertig an Bord, damit kenn ich mich aber nicht besonders aus.
 
Zuletzt bearbeitet von einem Moderator:
Okay, ich habe jetzt im Header folgende Funktion angesiedelt:
PHP:
<?php
function aus()
{
    $ja = $_POST["a"];

	if($ja==1)
    {
        include("austest.php");
    }
 }
 ?>

Der Funktionsaufruf passiert gleich nach dem JS:

PHP:
<?php

if(shell_exec('gpio -g read 17')==0){
	if(isset($_POST['serverein_x'])&& isset($_POST['serverein_y'])){
	include("servertest.php");
	}
	$server = "Server.png";
}

if(shell_exec('gpio -g read 17')==1){
	if(isset($_POST['serveraus_x'])&& isset($_POST['serveraus_y'])){

		echo '<script type="text/javascript">
		<!--
		if(window.confirm("Wirklich abschalten?") == true)
        {
            data = 1;
            var request = new XMLHttpRequest();
            request.open("POST", "komisch.php", true);
            request.setRequestHeader("Content-Type", "application/x-www-formurlencoded");
            request.send("a="+data);
         }
 		// -->
		</script>';
        aus();
		}
	$server = "Server_on.jpg";
}
?>

Leider gibt es immer noch keine Übergabe zwischen dem "request.send" und der Funktion. Variable a ist immer noch leer.
Muss das JS-Teil auch mit in die Funktion?

@mambokurt: In einer neuen Datei funktioniert dein Script. Wenn ich es allerdings im Header meiner komisch.php platziere, passiert beim Klick auf die Schaltfläche gar nichts. Außerdem habe ich schon Buttons und wollte keine Form benutzen.
 
Danke für den Link, aber da ich ja schon alles komplett habe, bis auf diese dämliche Abfrage, stricke ich das nicht mehr um. Wenn sich keine Lösung zeigt, lasse ich die Abfrage ganz weg. Ist zwar nicht so gut, falls man mal aus Versehen auf Aus klickt, aber damit kann ich auch leben.
Blablub, du hast Recht. Dieser Mischmasch ist nicht besonders gut. Schön wäre, wenn wie in VB alles in einer Sprache wäre (Messageboxen, if-, while-Abfragen, etc.) und es vielleicht noch das HTML gäbe als Textkörpersprache. Dann müsste man sich nicht mit sowas herumschlagen.
 
Hallo Hancock,
danke für den Link, aber beim ersten Beispiel wüsste ich nicht, wie es in eine Funktion zu packen wäre und die anderen werden anscheinend mit der jQuery Library gemacht. Ich habe mir das mal angesehen und für mich ist es ein Buch mit sieben Siegel. Ich wüsste nicht, wie ich die Library einbinden soll. Ausserdem ist das für meine Zwecke zu elaboriert und mit Kanonen auf Spatzen geschossen.
Ich würde eine ganz einfache Lösung vorziehen, die ich auch verstehen kann.
Kannst du mir erklären, warum das Beispiel in #6 nicht klappt, oder was ich da falsch gemacht habe?
Vielleicht fällt ja dann der Groschen.
 
Holgip schrieb:
@mambokurt: In einer neuen Datei funktioniert dein Script. Wenn ich es allerdings im Header meiner komisch.php platziere, passiert beim Klick auf die Schaltfläche gar nichts. Außerdem habe ich schon Buttons und wollte keine Form benutzen.


Code:
<form name="form1" method="POST" action="komisch.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Server" name="serverein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Server" name="serveraus">
</form>

Du hast doch schon lange ein Form und funktionierenden Code, der darauf aufbaut, und du baust jetzt lieber eine extra PHP Weiche + Ajax statt _einen_ Button zu überarbeiten und 10 Zeilen Javascript einzubinden?

Ich will dir das jetzt nicht ausreden, wenn man damit keine Zeit rumbringen würde wärs ja kein Hobby... :D So ich bin raus :D
 
@mambokurt:
Wenn man die Form in einer php-Funktion unterbringen könnte, würde ich es ja machen, aber leider kommt da auch nichts bei rum. Die Positionen der Buttons werden in einem solchen Fall nicht übergeben, also kann man auch nichts abfragen.
Habe ich gerade mit den vorhandenen Buttons probiert, egal, wie's aussieht. Die Buttons werden angezeigt, aber beim Draufklicken wird nur die Seite neu geladen.
Eine andere Möglichkeit, html in php einzubinden, als mit "echo" habe ich noch nicht herausgefunden.

PHP:
<?php
function aus()
{
echo '<form name="form0" method="POST" action="komisch.php">
<input type="image" src="ein.png" height="40px" width="40px" alt="Server" name="aus">
<input type="image" src="aus.png" height="40px" width="40px" alt="Server" name="nix">
</form>';

	if(isset($_POST['aus_x'])&& isset($_POST['aus_y'])){
            include("austest.php");
        }
}
     ?>
 
Ich glaube du bist generell etwas verwirrt ob deines Spaghetticodes und der vielen möglichen Lösungen für dein Problem, kann das sein?

Du hattest doch eine funktionierende PHP, die erstmal das gemacht hat, was du wolltest, also mit verschiedenen Steckdosen usw. Poste die doch mal komplett und wir haben erstmal was womit wir anfangen können zu arbeiten.

Wie gesagt, du kannst das alles auch mit Ajax usw machen, aber das ist halt von hinten durch die Brust ins Auge und eigentlich viel komplizierter als du bräuchtest.

Ich bin mir sicher deinen funktionierenden Code mit etwas Javascript zu dekorieren um da ein Ja/Nein Fenster anzuzeigen ist nur 1/8 so kompliziert, als du dir gerade vorstellst. Im Prinzip nehmen wir nur die Buttons, die jetzt ausschalten und hängen da das Javascript für sicher/ja/nein dran, und wenn da halt auf ja geklickt wird schicken wir alles so ans PHP, als wäre der Button in deinem Originalcode geklickt worden.

Wenn du es gerne etwas in schön haben willst, wäre die zweite Variante IMHO erstmal den Code auf eine Template Engine umzustellen und PHP und HTML auseinanderzudröseln, das liest sich nicht nur besser sondern als Anfänger wird einem dann auch ein bisschen klarer, was da überhaupt wann passiert.
 
Hallo Mambokurt,

erstmal sorry, dass ich mich erst jetzt melde. Ich war den ganzen Tag unterwegs und habe gerade jetzt deine Antwort gesehen.
Du hast recht, dass ich verwirrt bin. Ich habe mich vor ca. 10 Jahren mal mit HTML beschäftigt und meine Basic-Zeiten sind schon 25 Jahre vorbei. Dementsprechend bin ich nicht mehr so firm in den neueren HTML- und wie sie alle heißen -Codes. Schon das Erstellen eines CSS würde mich überfordern. Trotzdem habe ich mich ein wenig in PHP eingelesen, um zumindest den Pi für mein Projekt zu steuern. Das erschien mir einfacher, als irgendein Basic-Programm zu schreiben.
Die komplette PHP, die auch funktioniert lade ich hoch, sie unterscheidet sich nicht so sehr von der Testdatei in #1. Die PHP-Dateien, die die Python-Scripte aufrufen sind alle ähnlich aufgebaut, deshalb poste ich nur das für den Server.
Die Python-Scripte steuern dann die GPIOs. Ich weiß, Spaghetticode und umständlich, aber es ist für meine Zwecke und Kenntnisse ausreichend.

Index.php:

PHP:
<!DOCTYPE HTML>
<html>
<head>
<script type="text/javascript">
function neuladen() {
location.reload();
}
window.setTimeout("neuladen()",60000);
</script>
</head>

<body style="background-image:url(hintergrund.jpg)">
<font face="Arial">
<!--<body>-->
<center>
<br>
<br>
<table>

<tr>
<th>
<!-- ***************************************Server schalten******************************************** -->
<font face="Arial">Server</font>
<form name="form1" method="POST" action="index.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Server" name="serverein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Server" name="serveraus">
</form>


<?php

if(shell_exec('gpio -g read 17')==0){
	if(isset($_POST['serverein_x'])&& isset($_POST['serverein_y'])){
	include("server.php");
	}
	$server = "Server.png";
}

if(shell_exec('gpio -g read 17')==1){
	if(isset($_POST['serveraus_x'])&& isset($_POST['serveraus_y'])){
		include("aus.php");
	}
	$server = "Server_on.jpg";
}
?>
</th>

<th>
<img src="<?php echo $server; ?>">
</th>

<th>
ACHTUNG!<br>Vergewissern, dass niemand<br>mehr auf den Server zugreift!<br>Hiermit wird alles ausgeschaltet!</th>
<th></th>
<!*****************************************************************************************************-->
<th><img src="leer.png"></th>
<th>
<!-- ************************************Filme schalten*********************************************** -->
Filme Festplatte
<form name="form2" method="POST" action="index.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Filme" name="filmeein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Filme" name="filmeaus">
</form>

<?php

$filme = "Filme.png";
# if(shell_exec('gpio -g read 17')==1){
	if(shell_exec('gpio -g read 18')==0){
		if(isset($_POST['filmeein_x'])&& isset($_POST['filmeein_y'])){
		include("filme_ein.php");
		}
		$filme = "Filme.png";
	}
	if(shell_exec('gpio -g read 18')==1){
		if(isset($_POST['filmeaus_x'])&& isset($_POST['filmeaus_y'])){
		include("filme_aus.php");
		}
		$filme = "Filme_on.jpg";
	}
# }
?>
</th>

<th>
<img src="<?php echo $filme; ?>">
</th>
<th>ACHTUNG!<br>Vergewissern, dass niemand<br>mehr auf die Filme zugreift!</th>
</tr>
<!*****************************************************************************************************-->

<tr><th><img src="leer.png"></th></tr>
<th><img src="leer.png"></th>
<tr>
<th>
<!-- ***********************************Filme 1 und 2 schalten**************************************** -->
Filme 1 und 2
<form name="form3" method="POST" action="index.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="filme12" name="filme12ein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="filme12" name="filme12aus">
</form>

<?php

$filme12 = "Filme12.png";
# if(shell_exec('gpio -g read 17')==1){
	if(shell_exec('gpio -g read 22')==0){
		if(isset($_POST['filme12ein_x'])&& isset($_POST['filme12ein_y'])){
		include("filme12_ein.php");
		}
		$filme12 = "Filme12.png";
	}

	if(shell_exec('gpio -g read 22')==1){
		if(isset($_POST['filme12aus_x'])&& isset($_POST['filme12aus_y'])){
		include("filme12_aus.php");
		}
		$filme12 = "Filme12_on.jpg";
	}
# }
?>
</th>

<th>
<img src="<?php echo $filme12; ?>">
</th>
<th>ACHTUNG!<br>Vergewissern, dass niemand<br>mehr auf die Filme zugreift!</th>
<th></th>
<!*****************************************************************************************************-->
<th><img src="leer.png"></th>
<th>
<!-- ***************************************Backup schalten******************************************* -->
Backup Festplatte
<form name="form4" method="POST" action="index.php">
<br>
<input type="image" src="ein.png" height="40px" width="40px" alt="Backup" name="backupein">
<br>
<input type="image" src="aus.png" height="40px" width="40px" alt="Backup" name="backupaus">
</form>

<?php

$backup = "Backup.png";
# if(shell_exec('gpio -g read 17')==1){
	if(shell_exec('gpio -g read 23')==0){
		if(isset($_POST['backupein_x'])&& isset($_POST['backupein_y'])){
		include("backup.php");
		}
		$backup = "Backup.png";
	}

	if(shell_exec('gpio -g read 23')==1){
		if(isset($_POST['backupaus_x'])&& isset($_POST['backupaus_y'])){
		include("backup_aus.php");
		}
		$backup = "Backup_on.jpg";
	}
# }
?>
</th>
<th>
<img src="<?php echo $backup; ?>">
</th>
</tr>
<!*****************************************************************************************************-->
</table>
</center>
</body>
</html>


Server.php:

PHP:
<?php
shell_exec('sudo python /home/pi/Server.py');
header ("Location:index.php");
?>

Für mich geht's dann morgen weiter, denn ich bin müde und geh jetzt in die Heia.

Danke dir, dass du es doch nicht aufgegeben hast.

Gruß

Holgip
 
So habs mal umgebastelt. Zwar keine Template Engine/Framework oder CSS Framework drin, da ich nicht weiss ob du sowas benutzen moechtest. Nur jQuery war schon im Beispiel vorhanden.

  • Array als Konfiguration hinzugefuegt, so kannst einfach andere Rechner hinzufuegen ohne am Code zu basteln
  • Bilder aus dem Stammverzeichnis verschoben nach img/<bla>.png.
  • server.php usw. fallen weg, da die Zeile Code auch so ausgefuehrt werden kann.
  • JavaScript nach js/main.js verschoben
  • CSS nach css/main.css verschoben


PHP:
<!doctype html>
<html class="no-js" lang="">
    <head>
        <meta charset="utf-8">
        <meta http-equiv="x-ua-compatible" content="ie=edge">
        <title></title>
        <meta name="description" content="">
        <meta name="viewport" content="width=device-width, initial-scale=1">

        <link rel="stylesheet" href="css/main.css">
    </head>
    <body>
        <?php include 'config.php'; ?>

        <div class="container">
            <?php
                // Nur wenn Form abgeschickt wurde
                if(isset($_POST['computer']) && isset($_POST['action']))
                {
                    // Wenn Computer existiert
                    if(isset($config['computer'][$_POST['computer']]))
                    {
                        // Python Script ausfuehren
                        $computer = $config['computer'][$_POST['computer']];
                        if($_POST['action'] == 1)
                        {
                            shell_exec('sudo python ' . $computer['pythonOnScript']);
                        }
                        else
                        {
                            shell_exec('sudo python ' . $computer['pythonOffScript']);
                        }
                    }
                }
            ?>

            <!-- Computer anzeigen -->
            <?php foreach($config['computer'] as $computerKey => $computer): ?>
                <div class="computer">
                    <div class="left">
                        <h1><?php echo $computer['name']; ?></h1>
                        <form name="<?php echo $computerKey ?>" method="post" action="index.php" class="switches">
                            <input type="hidden" name="computer" value="<?php echo $computerKey ?>">
                            <input type="image" src="img/ein.png" alt="An" name="action" value="1">
                            <input type="image" src="img/aus.png" alt="Aus" name="action" value="0">
                        </form>
                    </div>
                    <div class="right">

                        <!-- Statusbild anzeigen -->
                        <?php if((shell_exec('gpio -g read ' . $computer['gpioPort']) == 1)): ?>
                            <img src="<?php echo $computer['imageOn']; ?>">
                        <?php else: ?>
                            <img src="<?php echo $computer['imageOff']; ?>">
                        <?php endif; ?>

                        <span class="warning">ACHTUNG! <?php echo $computer['message']; ?></span>
                    </div>
                </div>
            <?php endforeach; ?>
        </div>

        <script src="https://code.jquery.com/jquery-1.10.2.js"></script>
        <script src="js/main.js"></script>
    </body>
</html>

PHP:
<?php
$config = array();
$config['computer'] = array(
    'server' => array(
        'name' => 'Server',
        'imageOn' => 'img/server.png',
        'imageOff' => 'img/server_off.png',
        'gpioPort' => '17',
        'pythonOnScript' => '/home/pi/ServerOn.py',
        'pythonOffScript' => '/home/pi/ServerOff.py',
        'message' => 'Vergewissern, dass niemand mehr auf den Server zugreift! Hiermit wird alles ausgeschaltet!',
    ),
    'filme' => array(
        'name' => 'Filme Festplatte',
        'imageOn' => 'img/filme.png',
        'imageOff' => 'img/filme_off.png',
        'gpioPort' => '18',
        'pythonOnScript' => '/home/pi/FilmeOn.py',
        'pythonOffScript' => '/home/pi/FilmeOff.py',
        'message' => 'Vergewissern, dass niemand mehr auf die Filme zugreift!',
    ),
    'filme12' => array(
        'name' => 'Filme 1 und 2',
        'imageOn' => 'img/filme12.png',
        'imageOff' => 'img/filme12_off.png',
        'gpioPort' => '22',
        'pythonOnScript' => '/home/pi/Filme12On.py',
        'pythonOffScript' => '/home/pi/Filme12Off.py',
        'message' => 'Vergewissern, dass niemand mehr auf die Filme zugreift!',
    ),
    'backup' => array(
        'name' => 'Backup Festplatte',
        'imageOn' => 'img/backup.png',
        'imageOff' => 'img/backup_off.png',
        'gpioPort' => '23',
        'pythonOnScript' => '/home/pi/BackupOn.py',
        'pythonOffScript' => '/home/pi/BackupOff.py',
        'message' => 'Vergewissern, dass niemand mehr auf die Filme zugreift!',
    ),
);

Code:
// Reload ein wenig geaendert
window.setTimeout(function() {
    location.reload();
}, 60000);

// Reagiere wenn im Form auf einen An/Aus Knopf geklickt wurde
$('form').on('click', 'input[name=action]', function(event)
{
    // Button der geklickt wurde
    var $this = $(this);

    // Name des Computers aus der Ueberschrift (h1) holen.
    var computer = $this.parent().siblings('h1').text();

    // Wert des Buttons
    var onoff = $this.val() == 0;

    // Meldung anzeigen
    if( ! window.confirm(computer + ' wirklich ' + (onoff ? 'auschalten' : 'anschalten') + '?'))
    {
        // Wenn auf Abbrechen geklickt wird, wird das Form nicht abgeschickt
        event.preventDefault();
    }
});

CSS:
body {
    background-image:url(img/hintergrund.jpg);
    font-family: Arial;
    font-size: 0.6em;
}

/* Umschliesst alles */
.container {
    width: 60%;
    margin: 0 auto;
}

/* Einzelene Computer */
.computer {
    width: 50%;
    float: left;
}

/* Breite des Forms festlegen */
.switches {
    width: 40px;
}

/* Breite der Buttons festlegen*/
.switches input[type=image] {
    width: 40px;
    height: 40px;
}

/* Linke Seite eines Computer Elements (Buttons und Name) */
.left {
    float: left;
    padding: 10px;
    width: 15%;
}
/* Rechte Seite eines Computer Elements (Statusbild und Warnung) */
.right {
    float: left;
    padding: 10px;
    width: 75%;
}

/* Warnung */
.warning {
    font-size: 1.5em;
    font-weight: bold;
}

Lizenz: http://unlicense.org/UNLICENSE
 
Zuletzt bearbeitet: (Code Update)
Hallo r15ch13,

Wow! Da hast du dir wirklich viel Mühe gemacht. Viiieelen dank dafür.

Vor allem die Idee mit der config.php gefällt mir.

Ich habe es gleich ausprobiert, aber leider funktioniert es noch nicht. Die Abfragen funktionieren, aber die Python-Scripts werden nicht ausgeführt.

In Zeile 18 ist eine If-Abfrage nach den Variablen 'computer' und 'action'. Dort hängt es anscheinend, denn wenn ich kurz vorher ein "echo $_POST ['computer'];" einsetze, wird mir das jeweilige Gerät angezeigt. Ändere ich die Zeile zu "echo $_POST ['action'];", bekomme ich nichts auf den Bildschirm. 'action' ist anscheinend leer und deshalb die If-Bedingung nicht erfüllt. Ich habe auch nirgends die Definition von 'action' gefunden, oder ist das eine von php oder js vorgegebene Variable?
Füge ich ein "echo Hallo" nach der If-Bedingung ein, wird es mir auch nicht angezeigt.

Gruß

Holgip

Edit: habe die Def. von 'action' in main.js gefunden und schaue mal, warum sie leer bleibt.
Kann es evtl. damit zu tun haben, dass ich Firefox benutze?

Nochmal Edit: Habe aus der If-Abfrage das 'action' herausgenommen und das Einschalten funktioniert!
Nur das Abschalten geht nicht, weil ich eigene Python-Scripte fürs Abschalten geschrieben habe, und hier immer nur die Einschaltscripte aufgerufen werden. Ich muss also in der config.php noch etwas ergänzen und in der index.php auch. Mal sehen, ob ich das hinbekomme.

Ein anderes Problem: Beim automatischen Reload der Seite bekomme ich die Meldung, dass die Daten erneut gesendet werden müssen. Ich muss dann auf einen Button klicken, was natürlich nervig ist. Was kann man dagegen tun?
 
Zuletzt bearbeitet:
Die Bedingung wird auch nur ausgeloest wenn man auf einen Button drueckt.
$_POST['action'] ist der Name der Input Buttons und hat den Wert 0 oder 1.
Mit var_dump() kannst du besser herausfinden was in einer Variable steht als mit echo. z.B. var_dump($_POST);

Update:config.php
PHP:
'pythonOnScript' => '/home/pi/ServerOn.py',
'pythonOffScript' => '/home/pi/ServerOff.py',

usw.

Oh ich sehe gerade das Firefox den Input type="image" anders verarbeitet als Chrome.
Der sendet den Wert nicht, sondern nur die X/Y Koordinaten die auf dem Bild angeklickt wurden.

Edit: Firefoxfix
Update: main.js
Behebt Reloadmeldung
Code:
// Reload ein wenig geaendert
window.setTimeout(function() {
    window.location = window.location;
}, 60000);

Update: index.php
PHP:
            <?php
                // Nur wenn Form abgeschickt wurde
                if(isset($_POST['computer']))
                {
                    // Wenn Computer existiert
                    if(isset($config['computer'][$_POST['computer']]))
                    {
                        // Python Script ausfuehren
                        $computer = $config['computer'][$_POST['computer']];
                        if(isset($_POST['action_on_x']))
                        {
                            shell_exec('sudo python ' . $computer['pythonOnScript']);
                        }
                        else if(isset($_POST['action_off_x']))
                        {
                            shell_exec('sudo python ' . $computer['pythonOffScript']);
                        }
                    }
                }
            ?>

und im Form:


                            <input type="image" src="img/ein.png" alt="An" name="action_on">
                            <input type="image" src="img/aus.png" alt="Aus" name="action_off">
 
Zuletzt bearbeitet: (Update fuer Firefox)
Ich habe die Änderungen eingefügt. Der Reload klappt jetzt ohne Meldung. Super, danke!

Jetzt ist es so, dass keine Abfrage mehr stattfindet, da sich der Name für 'action' ja geändert hat. Darauf habe ich im main.js den input-Namen erstmal in 'action_off' geändert, weil ich ja eigentlich nur beim Ausschalten die Meldung brauche. In der config.php habe ich für jedes Gerät noch ein 'pythonScriptAus' ==> '/home/pi/"Ausschaltscript".py' (Name geändert, auch in der index.php) hinzugefügt, wie du geschrieben hast.

Leider ist es so, dass das Ausschalten nicht funktioniert. Das Programm läuft zwar in die If-Bedingung, was ich an einem hinzugefügten
"var_dump($_POST['computer']);" sehe (bei der Backup-Festplatte wird z.B. nach der Abfrage "string(6) "backup" angezeigt), das Script wird jedoch nicht ausgeführt.
Die Namen in der config.php und index.php stimmen überein, die Namen der Python-Scripte sind ebenfalls richtig.

Edit: Die CSS-Datei wird verarbeitet, Hintergrundbild geht (Pfadangabe hat nicht gestimmt. Da der Pfad von der CSS-Datei ausgeht, muss man schreiben: url(../img/hintergrund.jpg).
Bleibt also noch die Anordnung der Bilder und Texte.

Das Einschalten funktioniert einwandfrei.

Was geht da noch schief?
Es scheint, dass der Umweg über die Abfrage der Grund ist, aber warum?

Ich poste nochmal die relevanten Codes.

index.php:

PHP:
                    // Nur wenn Form abgeschickt wurde
                         if(isset($_POST) && isset($_POST['computer']))
                    {

                        // Wenn Computer existiert
                        if(isset($config['computer'][$_POST['computer']]))
                        {
                            // Python Script ausfuehren
                        // Python Script ausfuehren
                        $computer = $config['computer'][$_POST['computer']];
                        if(isset($_POST['action_on_x']))
                        {
                            shell_exec('sudo python ' . $computer['pythonScriptEin']);
                        }
                        else if(isset($_POST['action_off_x']))
                        {
                            shell_exec('sudo python ' . $computer['pythonScriptAus']);
                        }
                        }
                    }
                ?>

config.php:

PHP:
    <?php
    $config = array();
    $config['computer'] = array(
        'server' => array(
            'name' => 'Server',
            'imageOn' => 'img/Server_on.jpg',
            'imageOff' => 'img/Server.png',
            'gpioPort' => '17',
            'pythonScriptEin' => '/home/pi/Server.py',
            'pythonScriptAus' => 'home/pi/AlleAus.py',
            'message' => 'ACHTUNG! Vergewissern, dass niemand mehr auf den Server zugreift! Hiermit wird alles ausgeschaltet!',
        ),
        'filme' => array(
            'name' => 'Filme Festplatte',
            'imageOn' => 'img/Filme.jpg',
            'imageOff' => 'img/Filme.png',
            'gpioPort' => '18',
            'pythonScriptEin' => '/home/pi/Filme.py',
            'pythonScriptAus' => 'home/pi/FilmeAus.py',
            'message' => 'ACHTUNG! Vergewissern, dass niemand mehr auf die Filme zugreift!',
        ),
        'filme12' => array(
            'name' => 'Filme 1 und 2',
            'imageOn' => 'img/Filme12_on.jpg',
            'imageOff' => 'img/Filme12.png',
            'gpioPort' => '22',
            'pythonScriptEin' => '/home/pi/12FilmeEin.py',
            'pythonScriptAus' => 'home/pi/12FilmeAus.py',
            'message' => 'ACHTUNG! Vergewissern, dass niemand mehr auf die Filme zugreift!',
        ),
        'backup' => array(
            'name' => 'Backup Festplatte',
            'imageOn' => 'img/Backup_on.jpg',
            'imageOff' => 'img/Backup.png',
            'gpioPort' => '23',
            'pythonScriptEin' => '/home/pi/Backup.py',
            'pythonScriptAus' => 'home/pi/BackupAus.py',
        ),
    );
    ?>

main.js:

HTML:
    // Reload ein wenig geaendert
    window.setTimeout(function() {
    window.location = window.location;
    }, 60000);

    // Reagiere wenn im Form auf einen An/Aus Knopf geklickt wurde
    $('form').on('click', 'input[name=action_off]', function(event)
    {
        // Button der geklickt wurde
        var $this = $(this);

        // Name des Computers aus der Ueberschrift (h1) holen.
        var computer = $this.parent().siblings('h1').text();

        // Wert des Buttons
        var onoff = $this.val() == 0;

        // Meldung anzeigen
        if( ! window.confirm(computer + ' wirklich ' + (onoff ? 'auschalten' : 'anschalten') + '?'))
        {
            // Wenn auf Abbrechen geklickt wird, wird das Form nicht abgeschickt
            event.preventDefault();
        }
    });


Edit: Gerade gesehen: die Pfadangaben für die Ausschaltscripts sind falsch. Es fehlt noch ein "/"
Jetzt funktioniert es! :D

Das Einzige, mit dem ich jetzt noch hadere ist die Formatierung. Dafür benutze ich aber eine neue Antwort.
Ergänzung ()

So, nachdem die programmiertechnischen Hürden dank eurer Hilfe (speziellen Dank an r15ch13!) kommt jetzt die Kosmetik.

Im Moment sieht das Ganze auf meinem 23" 16:9 Monitor so aus:

ist.JPG

Komischer weise wird der Hintergrund nicht angezeigt (evtl. ein Firefox Problem?) und es ist alles ein wenig durcheinander.

Meine ursprüngliche index.php sah auf dem Bildschirm so aus (mit HTML-Tabelle realisiert):

soll.JPG

Wie bekomme ich es so hin, dass der Hintergrund angezeigt wird, die Warnhinweise neben den Bildern steht und das Ganze etwas mehr geordnet ist?
In der main.css kann ich die Werte ändern wie ich will, es zeigt sich keine Änderung am Bild, so, als ob sie gar nicht aufgerufen werden würde.

EDIT: CSS-Datei wird verarbeitet, Hintergrundbild wird angezeigt. Grund: Pfadangabe. Die Angabe geht von der CSS-Datei aus, also muss der Pfad lauten: url(../img/hintergrund.jpg).

Bleibt nur noch die Anordnung der Bilder und Texte.
Ergänzung ()

So, jetzt habe ich es hinbekommen, dass die Elemente einigermaßen ordentlich angeordnet werden. Es lag an dem zu langen Warntext des Servers.
Was ich nicht geregelt kriege sind die Warntexte selbst, die ich eigentlich rechts neben den Bildern haben will.
Selbst ein neuer Container in der main.css in den ich die Texte einfüge hat nicht geholfen. Vielleicht kann mir nochmal jemand helfen?

Die index.php habe ich so geändert:

HTML:
                <!-- Computer anzeigen -->
                <?php foreach($config['computer'] as $computerKey => $computer): ?>
                    <div class="computer">
                        <div class="left">
                            <h1><?php echo $computer['name']; ?></h1>
                            <form name="<?php echo $computerKey ?>" method="post" action="index.php" class="switches">
                                <input type="hidden" name="computer" value="<?php echo $computerKey ?>">
                                <input type="image" src="img/ein.png" alt="An" name="action_on">
                                <input type="image" src="img/aus.png" alt="Aus" name="action_off">
                            </form>
                        </div>
                        <div class="right">

                            <!-- Statusbild anzeigen -->
                            <?php if((shell_exec('gpio -g read ' . $computer['gpioPort']) == 1)): ?>
                                <img src="<?php echo $computer['imageOn']; ?>">
                            <?php else: ?>
                                <img src="<?php echo $computer['imageOff']; ?>">
                            <?php endif; ?>

                        </div>
                        <div class="mess">
                            <div class="warning"><?php echo $computer['message']; ?></div>
                        </div>
                    </div>

Und die CSS-Datei so:

Code:
    body {
        background-image: url(../img/hintergrund.jpg);
        font-family: Arial;
        font-size: 0.6em;
    }

    /* Umschliesst alles */
    .container {
        width: 70%;
        margin: 5% auto;
    }

    /* Einzelene Computer */
    .computer {
        width: 50%;
        margin: inherit;
        float: left;
    }

    /* Breite des Forms festlegen */
    .switches {
        width: 40px;
    }

    /* Breite der Buttons festlegen*/
    .switches input[type=image] {
        width: 40px;
        height: 40px;
    }

    /* Linke Seite eines Computer Elements (Buttons und Name) */
    .left {
        float: left;
        padding: 0px;
        width: 22%;
        height: 50%;
    }
    /* Rechte Seite neben Bild (Warnung) */
    .mess {
        float: left;
        padding: 10px;
        width: 60%;
        height: 50%;
    }
    /* Warnung */
    .warning {
/*        float: left; */
        font-size: 1.5em;
        font-weight: bold;
    }

Heraus kommt das:

sollist.JPG
 
Zuletzt bearbeitet:
PHP:
                    <div class="right">
                        <!-- Statusbild anzeigen -->
                        <?php if((shell_exec('gpio -g read ' . $computer['gpioPort']) == 1)): ?>
                            <img src="<?php echo $computer['imageOn']; ?>">
                        <?php else: ?>
                            <img src="<?php echo $computer['imageOff']; ?>">
                        <?php endif; ?>

                        <div class="warning">ACHTUNG! <?php echo $computer['message']; ?></div>
                    </div>
CSS:
/* Rechte Seite eines Computer Elements (Statusbild und Warnung) */
.right {
    float: left;
    padding: 10px;
    width: 75%;
}

/* Bild */
.right img {
    width: 128px; /* kannst anpassen an deine Bildgroesse */
    float: left;
}

/* Warnung */
.warning {
    margin-top: 10%;
    font-size: 1.5em;
    font-weight: bold;
}
 
Super r15ch13, das war's! Vielen Dank!

Nochmal an alle ein herzliches Dankeschön, dass ihr mir geholfen habt. Inzwischen habe ich auch die Funktionsweise der Scripte verstanden. Ich wäre aber im Leben nicht drauf gekommen, es so zu verwirklichen. :)

Gruß

Holgip
 
Zurück
Oben