Am fost abordat de unul din cititorii mei cu urmatoarea situatie (am sa reproduc felul in care a pus el problema):
Avem de-a face cu o pagina simpla (un HTML, sa zicem) care contine un formular; o vom numi pagina A. Pagina A face submit catre un script PHP, pe care-l vom numi B si care dupa ce termina ce are de facut redirecteaza utilizatorul catre pagina C (un landing page).
Deci care e problema? Pai, problema e ca scriptul B ruleaza cam mult (trimite o serie de email-uri) si utilizatorul sta si asteapta ca browser-ul sa incarce “ceva”.
Gabriel a venit cu o solutie interesanta la aceasta problema. A cautat un preloader care sa ruleze in timp ce se incarca scriptul B. Nu-i rau, dar eu cred ca aici se preteaza bine un AJAX. In general pentru astfel de situatii executarea asincrona este cea mai buna solutie.
Vezi Demo
Avand in vedere noile informatii, abordarea va fi in felul urmator: Pagina A face un request AJAX catre scriptul B si asteapta un raspuns. Intre timp afisaza o imagine de loading… (sau orice altceva). Cand termina ce are de facut, scriptul B il anunta pe A ca este momentul sa faca un redirect; catre landing page-ul C.
Bun, acum ca am vauzut despre ce-i vorba, sa descuram putin itele problemei. Vom incepe prin a da nume descriptive fisierelor, ca sa nu ne mai incurcam in litere.
Fisierul care contine formularul se numeste index.php
si contine urmatorul cod:
<!DOCTYPE html> <html lang="en"> <head> <title>AJAX Submitter</title> <link rel="stylesheet" href="style.css" type="text/css" /> </head> <body> <div id="wrapper"> <form method="POST" action="submit.php"> <p> <label for="name">Name</label> <input type="text" name="name" id="name" /> </p> <p> <label for="email">Email</label> <input type="text" name="email" id="email" /> </p> <p> <label for="message">Message</label><br /> <textarea name="message" cols="50" rows="7"></textarea> </p> <p> <input type="submit" value="Send" id="submit" /> <img id="spinner" src="loading.gif" style="display:none; float: right;" /> </p> </form> </div> </body> </html>
Codul este cat se poate de simplu, ca sa nu pierdem din vedere scopul principal. Dupa cum vedeti, formularul face submit catre un fisier PHP numit sugestiv submit.php
.
<?php session_start(); $name = "No name sumbitted"; if(isset($_POST["name"])) $name = $_POST["name"]; $email = "No email sumbitted"; if(isset($_POST["email"])) $email = $_POST["email"]; $message = "No message sumbitted"; if(isset($_POST["message"])) $message = $_POST["message"]; $_SESSION["name"] = $name; sleep(3); $_SESSION["email"] = $email; sleep(3); $_SESSION["message"] = $message; sleep(3); header("Location: landing.php"); ?>
Codul este irelevant. L-am pus acolo doar ca sa execute ceva in spate. Mai mult, observati folosirea functiei sleep()
de cateva ori. Asta ca sa simuleze faptul ca scriptul dureaza ceva mai mult decat in mod normal.
Dupa ce se executa codul, trimitem utilizatorul la un landing.php
ca sa-l anuntam ca totul s-a intamplat cu succes. Codul arata asa:
<?php session_start(); ?> <!DOCTYPE html> <html lang="en"> <head> <title>AJAX Landing</title> <link rel="stylesheet" href="style.css" type="text/css" /> </head> <body> <div id="wrapper"> <h3>The following data has been sumbitted</h3> <p>Name: <?php echo $_SESSION["name"] ?></p> <p>Email: <?php echo $_SESSION["email"] ?></p> <p>Message: <?php echo $_SESSION["message"] ?></p> </div> </body> </html>
In momentul de fata avem exact situatia despre care vorbeam mai sus. La click, user-ul este trimis la submit.php
unde nu vede decat o fereastra goala pana se executa codul. Abia la final este trimis catre landing.php
.
Ca sa rezolvam problema, vom executa scriptul submit.php
asincron. Ca sa ne fie mai usor, vom apela la jQuery pentru partea de AJAX.
Mai intai includem libraria jQuery:
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js"></script>
Apoi, tot ce trebuie sa facem este sa adaugam cateva linii de cod. Explicatiile le gasiti in comentarii la fiecare linie de cod unde acest lucru este necesar. P.S. Daca vi se pare greu de citit, il aveti mai jos fara comentarii (plus arhiva de la final):
$(document).ready(function() { $("#submit").click(function(event) { // Declansam la click pe Submit event.preventDefault(); // Avem grija sa nu mai faca submit clasic $.ajax({ url: "submit.php", // Unde facem requestul AJAX beforeSend: function() { // Inainte de request executam: $("#submit").css("display", "none"); // Ascundem butonul de submit $("#spinner").css("display", "block"); // Incarcam un loader (un gif) }, type: "POST", data: ({ name: $("#name").val(), // Luam valoarea lui 'name' pentru submit email: $("#email").val(), // Luam valoarea lui 'email' pentru submit message: $("#message").val() // Luam valoarea lui 'message' pentru submit }), success: function(msg) { window.location.replace("landing.php"); // La final, redirectam utilizatorul la landing.php } }); }); });
La final, ar trebui sa obtinem un fisier index.php
care arata asa:
<!DOCTYPE html> <html lang="en"> <head> <title>AJAX Submitter</title> <link rel="stylesheet" href="style.css" type="text/css" /> <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js"></script> <script type="text/javascript"> $(document).ready(function() { $("#submit").click(function(event) { event.preventDefault(); $.ajax({ url: "submit.php", beforeSend: function() { $("#submit").css("display", "none"); $("#spinner").css("display", "block"); }, type: "POST", data: ({ name: $("#name").val(), email: $("#email").val(), message: $("#message").val() }), success: function(msg) { window.location.replace("landing.php"); } }); }); }); </script> </head> <body> <div id="wrapper"> <form method="POST" action="submit.php"> <p> <label for="name">Name</label> <input type="text" name="name" id="name" /> </p> <p> <label for="email">Email</label> <input type="text" name="email" id="email" /> </p> <p> <label for="message">Message</label><br /> <textarea name="message" cols="50" rows="7"></textarea> </p> <p> <input type="submit" value="Send" id="submit" /> <img id="spinner" src="loading.gif" style="display:none; float: right;" /> </p> </form> </div> </body> </html>
Dupa cum vedeti, n-am schimbat nimic in fisierele submit.php
si landing.php
. Am schimbat numai modul in care apelam aceste fisiere.
Acestea sunt elementele de baza pe care trebuie sa le stim pentru a oferi utilizatorului o experienta mai eleganta cu ajutorul AJAX.