[tuto jquery] drag ‘n drop avec sauvegarde automatique en base de données (2/2)
Posté par Guiral antoine le mars 9, 2008
Ce tutoriel est disponible sur mon nouveau blog (lien direct). Afin d’eviter le duplicate content je vais tronquer une partie de l’article…
Ça y est, la suite est enfin là! Dans la première partie de ce tutoriel nous avions vu comment faire un drag’n drop avec jQuery. Maintenant nous allons voir comment effectuer notre sauvegarde automatique grâce à l’AJAX. Il y a deux modifications majeures à apporter à notre code. La première est la partie base de données : création des tables, des requêtes,etc… La seconde est l’ajout d’un traitement lors d’un drop d’ingrédient dans une recette. Autrement dit, effectuer les requêtes au bon moment.
- La BDD
Notre base sera composée de 3 tables :
- la table recette sera composé d’un identifiant (id_recette) et d’un nom de recette (recette).
- la table ingrédient avec un identifiant (id_ingredient) et du nom de l’ingrédient (ingredient).
- la table recette_ingredient qui contiendra les compositions de nos recettes sous la forme de couple id_recette,id_ingredient.
Cette organisation vient de nos cardinalités : un ingrédient peut être dans plusieurs recettes et une recette peut contenir plusieurs ingrédients.
Voici le code SQL pour créer les tables :
CREATE DATABASE `tuto_drag` ;
CREATE TABLE `recettes` (
`recette` VARCHAR( 50 ) NOT NULL
) ENGINE = innodb;
CREATE TABLE `ingredients` (
`ingredient` VARCHAR( 50 ) NOT NULL
) ENGINE = innodb;
CREATE TABLE `recette_ingredient` (
`refid_recette` INT NOT NULL
) ENGINE = INNODB CHARACTER SET latin1 COLLATE latin1_swedish_ci
ALTER TABLE `recette_ingredient` ADD PRIMARY KEY ( `id_ingredient` , `id_recette` )
INSERT INTO `ingredients` ( `id_ingredient` , `ingredient` )
VALUES (NULL,’oeuf’),(NULL,’sucre’),(NULL,’farine’),(NULL,’sel’),(NULL,’lait’);
INSERT INTO `recettes` ( `id_recette` , `recette` )
VALUES (NULL,’Pâte à crêpe’),(NULL,’Pâte brisée’);
- Les traitements coté serveur
Maintenant que nous avons une base de données il faut créer les scripts qui vont nous permettre d’interagir avec elle. Nous devons pouvoir ajouter une recette, un ingrédient et faire nos sauvegarde de composition de recette. Appelons notre fichier “traitement.php”.
La suite du tutoriel est disponible sur mon nouveau blog (lien direct). Désolé pour la gêne occasionnée ^_^’
bruno bichet a dit
Bon, là, maintenant, il faut que je me bouge un peu pour tester et comprendre tout ça
Merci.
Guiral antoine a dit
De rien!
Si tu as besoin de précision n’hésite pas
(twit moi ou gtalk) j’ai commenté un peu rapidement certaine partie (notamment le SQL)…
bon courage! Mais avec tes talent de designer tu va pouvoir faire des truc de ouf! :-p
killartem a dit
J’ai une question toute à fait stupide : à quoi servent les “$” dans le code javascript ?
Il est difficile de faire une recherche la-dessus …
Cependant, j’ai trouvé ça dans la doc officielle :
You use variables as symbolic names for values in your application. The names of variables, called identifiers, conform to certain rules.
A JavaScript identifier must start with a letter, underscore (_), or dollar sign ($); subsequent characters can also be digits (0-9). Because JavaScript is case sensitive, letters include the characters “A” through “Z” (uppercase) and the characters “a” through “z” (lowercase).
C’est pas très clair…
Merci par avance, Yves.
Guiral antoine a dit
Ici nous utilisons un framework javascript qui s’appelle jQuery. Tous les objets jQuery sont identifiés grâce à la variable “$”. Par exemple $(“p”) va retourner un objet jQuery contenant tous les paragraphes (balises p) du document.
Je répond à ta question?
A bientôt! (et aucun question n’est stupide!)
David Linotte a dit
Hello,
Très joli tuto que celui-là. Cela fait pas mal de temps que je cherche un tutoriel de ce genre et je suis donc très content de trouver celui-ci.
J’aurais néanmoins une petite requête. Ce que je veux faire est un peu différent. J’ai une liste d’objets “dragables” dont je veux pouvoir changer la position en glissant un objet à une autre place dans la liste et en enregistrant la modification dans une base de donnée. En gros, si je prends le 5ième élément et que je le glisse en 2ième, celui-ci reçoit la position 2, le 2 glisse en 3, le 3 en 4 et le 4 en 5. J’espère que je suis assez clair…
Existerait-il quelque part un tuto pour faire ce genre de chose ou quelqu’un aurait-il une idée sur la façon de procéder ? Je suis en effet incapable de développer ça tout seul… (snif)
Merci d’avance !
Guiral antoine a dit
Salut david,
oui je vois ce que tu veux faire. Tu parle de liste, tu as une liste au sens html? c’est à dire balise ul/li ou ol/li?
Merci pour les compliments sur le tuto
A bientôt
David Linotte a dit
En fait là je les ai mis dans un div mais à la base c’est une liste.
<img src="../images/gestion/icone_page.png" alt="" width="80" height="80" /><a href="contenu.php?id= ">C’est un while qui parcourt la base de données et sort toutes les pages. Ces pages ont un champs position sur lequel je veux faire des modifications.
Merci pour l’aide (et rapide en plus).
Guiral antoine a dit
Tu aurais une page d’exemple? Si c’est une liste il existe des truc tout fais pour ça tu n’aurais plus qu’à t’occuper de la partie sauvegarde en bdd. Dès que j’ai un exemple de ce que tu veux faire je t’envoie les liens (pour être sûr que c’est ce que tu veux
).
David Linotte a dit
Je te mets plus de code et je le mets en liste pour que tu voie ce que c’est et un lien vers une image de la page (c’est sécurisé je saurais pas te la montrer).
<img src="../images/gestion/icone_page.png" alt="" width="80" height="80" /><a href="contenu.php?id= ">
L’image
Ce sont les blocs entourés en pointillés.
Guiral antoine a dit
Oui c’est galère de mettre du code dans les commentaires,
je pense que tu trouvera ton bonheur ici : http://interface.eyecon.ro/demos avec les sortables lists ou sortables floats . Ensuite il faut que tu adapte le code pour faire la sauvegarde en bdd. Une fois que tu auras coder le “sortable” contact moi par mail je pourrais te filer un coup de main.
Au passage : le design de ta page est super.
David Linotte a dit
OK je regarde ça demain et je te tiens au courant.
Encore merci !
Guiral antoine a dit
ok ca marche! Avec plaisir!
A bientôt!
David Linotte a dit
Hello,
J’essaye d’implémenter le script interface pour rendre mes blocs tribales mais je n’y arrive pas.
Je ne vois pas ce qui ne fonctionne pas j’ai pourtant suivi cet exemple.
Je suppose que j’ai dû faire une erreur mais je ne vois pas où… Une idée ?
David Linotte a dit
Bon décidément ça ne passe pas pour le code.
J’ai mis la page dans un dossier test de manière à ce que tu puisse regarder le code.
Guiral antoine a dit
Je viens de regarder ton code tu as des erreurs de compil. Corrige déjà ca on verra pour la suite
J’ai aussi vu que tu avais du html dans un fichier js :s pas tres coherent.. Je te passe mon gmail : guiral[.]antoine[at]gmail[.]com
Courage
Callec Emmanuel a dit
Bonjour,
Bon script, probablement le plus clair parmi tous les tuto fr que j’ai trouvé.
Cependant j’ai deux petites questions :
A quoi ça sert de mettre “substr” ici $id_recette=substr($_GET[’id_recette’],1,1); cat si ton id_recette fait “25″ il ne va te sortir que “2″ !?
Et aussi : $sql=’insert into recette_ingredient values(\”.$id_recette.’\’,\”.$id_ingredient.’\’)’; si tu ne précises pas les champs à remplir comment peut-il enregistrer ?
@+
Manu
Guiral antoine a dit
Bonjour emmanuel,
)!
tout d’abord merci pour le compliment (en plus cela correspond assez bien à ton site
Ensuite pour les deux points que tu abordes : en e qui concerne le substr en effet il ne ressortira que le 2. A vrai dire je ne m’ettais même pas posé la quetion la “difficulté” du tuto n’étant pas là. Mais si j’ai le temps un de ces 4 je ferais la modif (ca y est c’est sur mon todo).
Par contre pour la requête cela fonctionne. Ma table contient deux champs, si je lui envoi le bon nombre d’info dans le bon ordre c’est ok. Sinon il faut en effet préciser le noms des champs dans lesquels on veut faire l’insert.
A bientôt!
(
Callec Emmanuel a dit
Bonjour Antoine,
En effet, j’avais oublié qu’il était possible d’écrire un insert into de cette manière, en ce qui me concerne, je ne le fais jamais car j’ai toujours peur qu’en cas de surcharge du serveur ce dernier s’emmêle les pinceaux dans l’interprétation de la requête alors je reste très précis dans ces dernières.
Sinon pour en revenir au script, étant nul en ajax je me creuse la tête depuis plusieurs heures pour ajouter une amélioration, à savoir, lorsque, pour reprendre l’exemple, l’on ajoute un ingrédient pour la recette j’aimerai que cet ingrédient devienne rouge dans la liste des ingrédients (ou n’importe quelle autre couleur), afin de montrer qu’il a déjà été utilisé et de même, retirer la couleur si l’on retire l’aliment de la recette. J’aimerai utilisé ton script de la sorte pour remplir une liste d’objets afin de mieux voir ceux qui ont déjà été ajouté à la liste.
Bref si tu pouvais m’aider sur ce coup ça serai super !
Manu
Guiral antoine a dit
Salut manu,
alors j’ai un peu réfléchit à ce que tu veux faire…la première chose à faire c’est créer les classes CSS que tu appliquera à tes éléments. Ensuite je pense que tu peux procéder de deux manières : la première serait de modifier le script en profondeur et d’associer à chaque zone droppable un array et ensuite de comparer les arrays afin d’appliquer le style aux doublons. La seconde consisterais à appliquer le style au moment ou tu clones ton élément dans ta liste d’objets et à l’enlever au moment ou tu tue ton drag.
Mais dans les deux cas cela sous entend que tu ne gère qu’une recette parce que comment faire comprendre qu’un ingrédient à été utilisé dans une recette parmi celles affichés?
Bon courage et tiens nous au courant de tes avancées
Callec Emmanuel a dit
Salut Antoine,
Bon, hier j’ai passé toute mon après midi à réfléchir à ce script, comme toi je me suis dit que c’était au moment de cloner les éléments que tout devrait se passer.
Bon je rappel que je suis nul en ajax et que syntaxiquement parlant je penses que l’on peut améliorer encore le truc.
Pour commencer j’ai créer un style .drag2{height:20px;width:60px; background-color:#FF0000;} ce qui sous-entend qu’une fois ce style appliqué ton élément n’est plus dropable mais dans mon cas c’est pas un problème, sinon il suffit d’ajouter background-color:#FF0000; directement dans ton div
Au niveau de la boucle située dans j’ai rajouté ce petit bout de code php
while($data=mysql_fetch_assoc($req_ingredients))
{
//On regarde si cet ingredient est déjà dans la table recette
$sql_ingredient="select * from recette_ingredient where refid_ingredient=".$data['id_ingredient']."";
$req_recettes_2=mysql_query($sql_ingredient);
$nombre_ingredient = mysql_num_rows($req_recettes_2);
if($nombre_ingredient != "0")
{
echo''.$data['ingredient'].'
';
}
else
{
echo''.$data['ingredient'].'
';
}
}
Pour le moment il m’affiche en rouge les ingrédients uniquement si je recharge la page dans son intégralité, c’est pas top.
Alors je me suis dit “il faut pouvoir charger les nouvelles données dans “, on peu peut-être lui faire faire un “refresh” mais j’ai pas vérifié si c’était possible.
Donc tout d’abord je crée une page scriptboucle.php dans laquelle je remet la boucle qui sera rechargée
Dans le script Ajax je rajoute $(“.ingredient”).load(“scriptboucle.php”); juste en dessous des deux appels $.get(“traitement.php”… comme ça, ça recharge quand on ajoute et quand on enlève un ingrédient.
Un problème se pose lorsque l’on recharge, la connexion à la base de donnée et script.js sautent. je rajoute donc dans ma page scriptboucle.php
// on se connecte à MySQL
$mysql_link=mysql_connect(”localhost”, “root”, “”);
//on selectionne notre base de donnée
mysql_select_db(”tuto_drag”, $mysql_link);
//requete pour les ingredients
$sql='select * from ingredients order by ingredient';
$req_ingredients=mysql_query($sql);
echo '';
Et voilà, le script est opérationnel.
Bon je le répète on peut CERTAINEMENT améliorer encore tout ça.
Manu
Callec Emmanuel a dit
Arf il m’a ignoré certaine balise :
Alors je me suis dit “il faut pouvoir charger les nouvelles données dans div class=”recette_ingredient” “
Guiral antoine a dit
salut,
bon c’est bien si tu as avancé!
Tu pourrais nous mettre un lien vers ce que tu as fais pour qu’on puisse voir? :-p
Ensuite si tu veux me contacter par mail pas de prob, ça sera plu simple pour envoyer du code la ca merde un peu -_-
Bye
stay a dit
Salut,
Est-il possible de mettre dans un dossier le fichier traitement.php ?
Merci
Guiral antoine a dit
Salut stay,
Par contre prend bien soin de mettre à jour tes urls vers les fichiers : “traitement.php” deviendra “tonDossier/traitement.php”.
oui c’est possible
Bon courage et à bientôt!
PS : reviens vite ou abonnes toi au flux si tu veux suivre le prochain tuto sur la navigation ajax non intrusive.
clonike a dit
Le site pour télécharger le fichier interface est down depuis ce matin
(enfin j’essaye d’y accéder depuis ce matin).
Y’a t-il moyen de se procurer les fichiers ailleurs ? ou qu’on me les transmettent ?
Merci
Guiral antoine a dit
Pas de problème, c’est déjà parti! Bon courage!