28172 sujets

CSS et mise en forme, CSS3

Bonjour,

Je développe un formulaire de contact qui est fonctionnel mais quelques petits détails m'embêtent sans être handicapant.

Comme le montre l'image ci-dessous, il y a un "dézoom" du label lorsque le curseur est sur un champs. Le soucis est que pour avoir cet effet, j'ai du ajouter l'attribut "required" à mes input et textarea. Dans le cas contraire, le "dézoom" est permanent, ce dont je ne saisi pas trop (je ne suis plus très a jour au niveau css depuis pas mal d'années).

Ça ne poserait pas de soucis si tous les champs étaient obligatoire mais j'en ai justement un optionnel.

upload/1576576491-78199-champs.jpg

Voici mon code html (je n'en mets qu'une partie car c'est grosso modo une répétition du même code) :

<div class="container">
				<form action="<?php echo $_SERVER['PHP_SELF'];?>" method="post" enctype="multipart/form-data">

				<fieldset><legend>Vos coordonnées</legend><br />
				<div class="group">
					<?php if ($fehler["name"] != "") { echo $fehler["name"]; } ?>
					<input type="text" name="name" value="<?php echo $_POST[name]; ?>" <?php if ($fehler["name"] != "") { echo 'class="errordesignfields"'; } ?> />
					<span class="highlight"></span>
					<span class="bar"></span>
					<label>Nom</label>
				</div>
				</form>
			</div>


Et mon code CSS :

* { box-sizing:border-box; }

/* basic stylings ------------------------------------------ */

.container {
	width:1000px;
	margin:30px auto 0;
	display:block;
	padding:10px 50px 50px;
}

/* form starting stylings ------------------------------- */
.group {
	position:relative;
	margin-bottom:45px;
}

textarea { height :200px; }

input, textarea {
	width :500px;
	font-size:18px;
	padding:10px 10px 10px 5px;
	display:block;
	border:none;
	border-bottom:1px solid #4bb5f2;
	background :transparent;
}
input:focus, textarea:focus { outline:none; }

/* LABEL ======================================= */
label {
	color:#4bb5f2;
	font-size:18px;
	font-weight:normal;
	position:absolute;
	pointer-events:none;
	left:5px;
	top:10px;
	transition:0.2s ease all;
	-moz-transition:0.2s ease all;
	-webkit-transition:0.2s ease all;
}

/* active state */
input:focus ~ label, input:valid ~ label, textarea:focus ~ label, textarea:valid ~label {
	top:-20px;
	font-size:14px;
	color:#5fd072;
}

/* BOTTOM BARS ================================= */
.bar { position:relative; display:block; width:500px; }

.bar:before, .bar:after {
	content:'';
	height:2px;
	width:0;
	bottom:1px; 
	position:absolute;
	background:#5fd072;
	transition:0.2s ease all;
	-moz-transition:0.2s ease all;
	-webkit-transition:0.2s ease all;
}
.bar:before {
	left:50%;
}
.bar:after {
	right:50%;
}

/* active state */
input:focus ~ .bar:before, input:focus ~ .bar:after, textarea:focus ~ .bar:before, textarea:focus ~.bar:after {
	width:50%;
}

/* HIGHLIGHTER ================================== */
.highlight {
	position:absolute;
	height:60%;
	width:100px;
	top:25%; 
	left:0;
	pointer-events:none;
	opacity:0.5;
}

/* active state */
input:focus ~ .highlight, textarea:focus ~ .highlight {
	-webkit-animation:inputHighlighter 0.3s ease;
	-moz-animation:inputHighlighter 0.3s ease;
	animation:inputHighlighter 0.3s ease;
}

/* ANIMATIONS ================ */
@-webkit-keyframes inputHighlighter {
	from { background:#5264AE; }
	to { width:0; background:transparent; }
}
@-moz-keyframes inputHighlighter {
	from { background:#5264AE; }
	to { width:0; background:transparent; }
}
@keyframes inputHighlighter {
	from { background:#5264AE; }
	to { width:0; background:transparent; }
}


De plus, l'info bulle qui apparaît lors d'une saisie invalide, suit le scrolling de la page au lieu d'être "fixé" sous le champs.

Comment puis-je régler ces petits soucis ?

Je vous remercie d'avance.
Modifié par Xhanxhand (17 Dec 2019 - 10:55)
Salut,

la partie du css qui fait remonté le label :
/* active state */
input:focus ~ label, input:valid ~ label, textarea:focus ~ label, textarea:valid ~label {
	top:-20px;
	font-size:14px;
	color:#5fd072;
}


En gros ça dit que pour les inputs et pour les textarea, si il y a le focus ou que le champs est valide, cela remonte le label.
Le truc c'est que t'es champs optionnels sont toujours "valides", du coup ils s'affichent directement avec le label remonté Smiley sweatdrop

J'ai essayé quelques trucs (rajouté un pattern sur le champs non requis, jouer avec input:not(:placeholder-shown), verifier si la value est vide) mais je n'arrive pas à le faire fonctionner en pur css Smiley bawling

A priori cela pourrait fonctionner en faisant une vérification en javascript qui modifie à la volée la value au fur et a mesure que l'utilisateur remplit le champs optionnel

Bon courage
Je comprend mieux le soucis. En effet, ça paraît compliqué de faire ceci en pur CSS.

Mais ce n'est pas grave, j'ai réfléchi et j'ai rendu ce champs de type "tel" et obligatoire. J'ai ensuite utilisé un pattern pour la validité.

Maintenant, j'ai un autre soucis. Certes, pas bien méchant mais un peu embêtant pour le visiteur. Je vais décrire mon soucis même si ce n'est pas vraiment le même. S'il faut que je crée un autre sujet, je le ferais^^

Donc, le petit soucis est qu'il y a un champs de type file pour joindre un fichier. Tout fonctionne sans soucis sauf que si l'extension n'est pas autorisée ou que le fichier est trop volumineux, le formulaire va vérifier tous les champs et ce dernier sera simplement réinitialisé sans aucun message d'avertissement.
Message qui existe dans le code php mais qui semble être court-circuité part le CSS sans que je ne sache exactement pourquoi.

Voici la partie HTML :

				<?php
				if(0<$cfg['NUM_ATTACHMENT_FIELDS']){
					echo '<fieldset><legend>Joindre un fichier</legend><br />';
					for ($i=0; $i < $cfg['NUM_ATTACHMENT_FIELDS']; $i++) {
						echo '
							<div class="group">
								<input type="file" name="f[]" />
								<span class="highlight"></span>
								<span class="bar_textarea"></span>
								<label>Poids maximum du fichier : 2Mo</label>
							</div>';
					}
				echo '</fieldset>';
				}
				?>

Et le code PHP concernant l'ajout de fichier (même si je doute que ça puisse servir car d'origine, donc sans la mise en forme, j'avais bien le message d'avertissement) :

if (!isset($fehler) || count($fehler) == 0) {
		$error             = false;
		$errorMessage      = '';
		$uploadErrors      = array();
		$uploadedFiles     = array();
		$totalUploadSize   = 0;

		if ($cfg['UPLOAD_ACTIVE'] && in_array($_SERVER['REMOTE_ADDR'], $cfg['BLACKLIST_IP']) === true) {
			$error = true;
			$fehler['upload'] = "<span class='errormsg'>Vous n\'êtes pas autorisé à envoyer des fichiers.</span>";
		}

		if (!$error) {
			for ($i=0; $i < $cfg['NUM_ATTACHMENT_FIELDS']; $i++) {
				if ($_FILES['f']['error'][$i] == UPLOAD_ERR_NO_FILE) {
					continue;
				}

				$extension = explode('.', $_FILES['f']['name'][$i]);
				$extension = strtolower($extension[count($extension)-1]);
				$totalUploadSize += $_FILES['f']['size'][$i];

				if ($_FILES['f']['error'][$i] != UPLOAD_ERR_OK) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					switch ($_FILES['f']['error'][$i]) {
						case UPLOAD_ERR_INI_SIZE :
							$uploadErrors[$j]['error'] = 'Le fichier est trop volumineux (PHP-Ini directive).';
						break;
						case UPLOAD_ERR_FORM_SIZE :
							$uploadErrors[$j]['error'] = 'Le fichier est trop volumineux (MAX_FILE_SIZE in HTML-Formular).';
						break;
						case UPLOAD_ERR_PARTIAL :
							if ($cfg['UPLOAD_ACTIVE']) {
								$uploadErrors[$j]['error'] = 'Le fichier a été téléchargé partiellement.';
							} else {
								$uploadErrors[$j]['error'] = 'Le fichier a été envoyé partiellement.';
							}
						break;
						case UPLOAD_ERR_NO_TMP_DIR :
							$uploadErrors[$j]['error'] = 'Aucun dossier temporaire n\'a été trouvé.';
						break;
						case UPLOAD_ERR_CANT_WRITE :
							$uploadErrors[$j]['error'] = 'Erreur lors de l\'enregistrement du fichier.';
						break;
						case UPLOAD_ERR_EXTENSION  :
							$uploadErrors[$j]['error'] = 'Erreur inconnue due à une extension.';
						break;
						default :
							if ($cfg['UPLOAD_ACTIVE']) {
								$uploadErrors[$j]['error'] = 'Erreur inconnue lors du téléchargement.';
							} else {
								$uploadErrors[$j]['error'] = 'erreur inconnue lors de l\'envoi des pièces jointes.';
							}
					}

					$j++;
					$error = true;
				}
				else if ($totalUploadSize > $cfg['MAX_ATTACHMENT_SIZE']*1024) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					$uploadErrors[$j]['error'] = 'Téléchargement maximum atteint ('.$cfg['MAX_ATTACHMENT_SIZE'].' KB).';
					$j++;
					$error = true;
				}
				else if ($_FILES['f']['size'][$i] > $cfg['MAX_FILE_SIZE']*1024) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					$uploadErrors[$j]['error'] = 'Le fichier est trop volumineux (max. '.$cfg['MAX_FILE_SIZE'].' KB).';
					$j++;
					$error = true;
				}
				else if (!empty($cfg['BLACKLIST_EXT']) && strpos($cfg['BLACKLIST_EXT'], $extension) !== false) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					$uploadErrors[$j]['error'] = 'L\'extension de fichier n\'est pas autorisée.';
					$j++;
					$error = true;
				}
				else if (preg_match("=^[\\:*?<>|/]+$=", $_FILES['f']['name'][$i])) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					$uploadErrors[$j]['error'] = 'Symboles non valides dans le nom de fichier (\/:*?<>|).';
					$j++;
					$error = true;
				}
				else if ($cfg['UPLOAD_ACTIVE'] && file_exists($cfg['UPLOAD_FOLDER'].'/'.$_FILES['f']['name'][$i])) {
					$uploadErrors[$j]['name'] = $_FILES['f']['name'][$i];
					$uploadErrors[$j]['error'] = 'Le fichier existe déjà.';
					$j++;
					$error = true;
				}
				else {
					if ($cfg['UPLOAD_ACTIVE']) {
						move_uploaded_file($_FILES['f']['tmp_name'][$i], $cfg['UPLOAD_FOLDER'].'/'.$_FILES['f']['name'][$i]);
					}
					$uploadedFiles[$_FILES['f']['tmp_name'][$i]] = $_FILES['f']['name'][$i];
				}
			}
		}


Le code CSS est le même que dans mon premier message.

De nouveau merci Smiley smile
Modifié par Xhanxhand (17 Dec 2019 - 19:41)