CSS3-Übergangsanimation beim Laden?

195

Ist es möglich, CSS3-Übergangsanimationen beim Laden von Seiten ohne Javascript zu verwenden?

Dies ist eine Art von dem, was ich will, aber beim Laden der Seite:

http://rilwis.googlecode.com/svn/trunk/demo/image-slider.html

Was ich bisher gefunden habe

  • CSS3-Übergangsverzögerung , eine Möglichkeit, Auswirkungen auf Elemente zu verzögern. Funktioniert nur beim Schweben.
  • CSS3 Keyframe , arbeitet unter Last, ist aber extrem langsam. Aus diesem Grund nicht nützlich.
  • Der CSS3-Übergang ist schnell genug, wird jedoch beim Laden der Seite nicht animiert.
Jens Törnell
quelle
2
Keyframes erreichen dies und bieten den besten Fallback, wenn CSS3-Animationen nicht unterstützt werden. Warum denkst du, sind sie zu langsam?
Zachleat
Hallo! Der Link ist jetzt defekt und ich weiß nicht, wohin er gehen soll. Kann jemand ihn bitte reparieren?
Linux4Life531

Antworten:

458

Sie können eine CSS- Animation beim Laden der Seite ausführen, ohne JavaScript zu verwenden. Sie müssen nur CSS3-Keyframes verwenden .

Schauen wir uns ein Beispiel an ...

Hier ist eine Demonstration eines Navigationsmenüs, das nur mit CSS3 eingerichtet wird :

@keyframes slideInFromLeft {
  0% {
    transform: translateX(-100%);
  }
  100% {
    transform: translateX(0);
  }
}

header {  
  /* This section calls the slideInFromLeft animation we defined above */
  animation: 1s ease-out 0s 1 slideInFromLeft;
  
  background: #333;
  padding: 30px;
}

/* Added for aesthetics */ body {margin: 0;font-family: "Segoe UI", Arial, Helvetica, Sans Serif;} a {text-decoration: none; display: inline-block; margin-right: 10px; color:#fff;}
<header>
  <a href="#">Home</a>
  <a href="#">About</a>
  <a href="#">Products</a>
  <a href="#">Contact</a>
</header>

Mach es kaputt ...

Die wichtigen Teile hier sind die Keyframe-Animation, die wir slideInFromLeft...

@keyframes slideInFromLeft {
    0% {
        transform: translateX(-100%);
    }
    100% {
        transform: translateX(0);
    }
}

... was im Grunde sagt "am Anfang wird der Header um seine volle Breite vom linken Bildschirmrand entfernt sein und am Ende wird er an Ort und Stelle sein".

Der zweite Teil nennt diese slideInFromLeftAnimation:

animation: 1s ease-out 0s 1 slideInFromLeft;

Oben ist die Kurzversion, aber hier ist die ausführliche Version zur Klarheit:

animation-duration: 1s; /* the duration of the animation */
animation-timing-function: ease-out; /* how the animation will behave */
animation-delay: 0s; /* how long to delay the animation from starting */
animation-iteration-count: 1; /* how many times the animation will play */
animation-name: slideInFromLeft; /* the name of the animation we defined above */

Sie können alle möglichen interessanten Dinge tun, z. B. Inhalte verschieben oder auf Bereiche aufmerksam machen.

Hier ist, was W3C zu sagen hat.

Chris Spittles
quelle
20
Was bewirkt, dass dies beim Laden der Seite ausgeführt wird und nicht früher?
Rolf
2
Um die obige Frage zu beantworten, wird die Animation standardmäßig ohne Verzögerung mit 0s nach dem Anwenden gestartet. Es gibt eine zusätzliche Eigenschaft, die Animationsverzögerung, die eingestellt werden kann, um dies zu steuern. Siehe: w3.org/TR/css3-animations/#animation-delay-property
Michael Davis
2
Um sicherzustellen, dass die Animation nach dem Laden des Dokuments beginnt, platzieren Sie den Animationscode in einem Stylesheet unter dem Body-Element oder dem Style-Tag am unteren Rand des Body-Elements.
TaylorMac
@SuzanneEdelmanCreoconcept Meines Wissens unterstützt IE9 die Übergangseigenschaft nicht. Ihre Optionen wären JS oder anmutige Verschlechterung.
Chris Spittles
1
Hervorragende Antwort, hat mir 2019 geholfen!
Gosi
28

Es ist sehr wenig Javascript erforderlich:

window.onload = function() {
    document.body.className += " loaded";
}

Nun das CSS:

.fadein {
    opacity: 0;
    -moz-transition: opacity 1.5s;
    -webkit-transition: opacity 1.5s;
    -o-transition: opacity 1.5s;
    transition: opacity 1.5s;
}

body.loaded .fadein {
    opacity: 1;
}

Ich weiß, dass die Frage "ohne Javascript" lautete, aber ich denke, es ist erwähnenswert, dass es eine einfache Lösung gibt, die eine Zeile Javascript umfasst.

Es könnte sogar Inline-Javascript sein, so etwas:

<body onload="document.body.className += ' loaded';" class="fadein">

Das ist alles JavaScript, das benötigt wird.

Rolf
quelle
2
Ein kleiner Fix: <body onload = "document.body.setAttribute ('class', 'geladen')">
Ivan
1
Wenn Sie das Ereignis page onLoad nicht abwarten müssen, fügen Sie diesen Code vor dem </ body> -Tag ein: <script type = "text / javascript"> document.body.setAttribute ('class', 'geladen'); </ script>
Ivan
7
Um das Überschreiben bestehender bodyKlassen zu vermeiden, verwenden Sie:document.body.classList.add('loaded)
Vyacheslav Cotruta
1
Ich fand document.body.className += " loaded";es etwas weniger ausführlich , die loadedKlasse zu vorhandenen Klassen hinzuzufügen .
Pim Schaaf
1
@PimSchaaf Danke für deinen Vorschlag, es macht total Sinn. Ich werde es jetzt bearbeiten. Heutzutage können Sie auch classList verwenden, die etwas eleganter (aber weniger kompatibel) ist.
Rolf
20

Ich glaube, ich habe eine Art Problemumgehung für die OP-Frage gefunden - anstelle eines Übergangs, der mit 'on.load' der Seite beginnt - habe ich festgestellt, dass die Verwendung einer Animation für das Einblenden der Deckkraft den gleichen Effekt hat (nach dem ich gesucht habe) das gleiche wie OP).

Daher wollte ich, dass der Textkörper beim Laden der Seite von Weiß (wie der Hintergrund der Website) in die Farbe Schwarzes Schwarz eingeblendet wird - und ich habe erst seit Montag codiert, also suchte ich nach einem Code im Stil "on.load". Aber ich kenne JS noch nicht - hier ist mein Code, der für mich gut funktioniert hat.

#main p {
  animation: fadein 2s;
}
@keyframes fadein {
  from { opacity: 0}
  to   { opacity: 1}
}

Und aus irgendeinem Grund funktioniert dies nicht .classnur für #id(zumindest nicht für meine)

Hoffe das hilft - wie ich weiß, hilft mir diese Seite sehr!

Lee John
quelle
6

Nun, das ist eine schwierige Frage.

Die Antwort lautet "nicht wirklich".

CSS ist keine funktionale Ebene. Es ist nicht bekannt, was wann passiert. Es wird einfach verwendet, um eine Präsentation hinzuzufügen verschiedenen "Flags" (Klassen, IDs, Status) .

Standardmäßig bietet CSS / DOM keinen "On Load" -Status für CSS. Wenn Sie JavaScript verwenden möchten / könnten, würden Sie eine Klasse bodyoder etwas zuweisen , um CSS zu aktivieren.

Davon abgesehen können Sie einen Hack dafür erstellen. Ich werde hier ein Beispiel geben, aber es kann auf Ihre Situation zutreffen oder nicht.

Wir gehen davon aus, dass "Schließen" "gut genug" ist:

<html>
<head>
<!-- Reference your CSS here... -->
</head>
<body>
    <!-- A whole bunch of HTML here... -->
    <div class="onLoad">OMG, I've loaded !</div>
</body>
</html>

Hier ist ein Auszug aus unserem CSS-Stylesheet:

.onLoad
{
    -webkit-animation:bounceIn 2s;
}

Wir gehen auch davon aus, dass moderne Browser progressiv gerendert werden, sodass unser letztes Element zuletzt gerendert wird und dieses CSS zuletzt aktiviert wird.

foxy
quelle
1

Ähnlich wie bei @ Rolf, aber überspringen Sie den Verweis auf externe Funktionen oder spielen Sie mit der Klasse. Wenn die Deckkraft nach dem Laden auf 1 festgelegt werden soll, verwenden Sie einfach das Inline-Skript, um die Deckkraft direkt über den Stil zu ändern. Beispielsweise

<body class="fadein" onload="this.style.opacity=1">

Dabei wird das CSS-System "Fadein" pro @ Rolf definiert, wobei der Übergang definiert und die Deckkraft auf den Anfangszustand gesetzt wird (dh 0).

Der einzige Haken ist, dass dies nicht mit SPAN- oder DIV-Elementen funktioniert, da sie kein funktionierendes Onload-Ereignis haben

user3907296
quelle
1

Starten Sie es mit einem Schwebeflug des Körpers als Es wird gestartet, wenn sich die Maus zum ersten Mal auf dem Bildschirm bewegt, was meist innerhalb einer Sekunde nach der Ankunft der Fall ist. Das Problem hierbei ist, dass es sich umkehrt, wenn es sich außerhalb des Bildschirms befindet.

html:hover #animateelementid, body:hover #animateelementid {rotate ....}

Das ist das Beste, was ich mir vorstellen kann: http://jsfiddle.net/faVLX/

Vollbild: http://jsfiddle.net/faVLX/embedded/result/

Bearbeiten siehe Kommentare unten:
Dies funktioniert auf keinem Touchscreen-Gerät, da kein Hover vorhanden ist, sodass der Benutzer den Inhalt nur sehen kann, wenn er darauf tippt. - Rich Bradshaw

Bartcode
quelle
Ja, das habe ich selbst herausgefunden. Es ist eine gute Problemumgehung, wenn nichts anderes funktioniert. Eine Stimme dafür.
Jens Törnell
13
Dies ist eine schreckliche Idee - auf jedem Touchscreen-Gerät gibt es keinen Schwebeflug, sodass der Benutzer den Inhalt nur sehen kann, wenn er darauf tippt.
Rich Bradshaw
1

CSS nur mit einer Verzögerung von 3s

Ein paar Punkte, die Sie hier beachten sollten:

  • mehrere Animationen in einem Anruf
  • Wir erstellen eine Warteanimation , die nur die eigentliche verzögert (in unserem Fall die zweite).

Code:

header {
    animation: 3s ease-out 0s 1 wait, 0.21s ease-out 3s 1 slideInFromBottom;
}

@keyframes wait {
    from { transform: translateY(20px); }
    to { transform: translateY(20px); }
}

@keyframes slideInFromBottom {
  from { transform: translateY(20px); opacity: 0; }
  to { transform: translateY(0); opacity: 1; }
}
Claudiu
quelle
0

Ok, ich habe es geschafft, eine Animation zu erzielen, wenn die Seite nur mit CSS-Übergängen geladen wird (irgendwie!):

Ich habe 2 CSS-Stylesheets erstellt: Das erste ist, wie das HTML vor der Animation gestaltet werden soll ... und das zweite ist, wie die Seite aussehen soll, nachdem die Animation ausgeführt wurde.

Ich verstehe nicht ganz, wie ich das erreicht habe, aber es funktioniert nur, wenn die beiden CSS-Dateien (beide im Kopf meines Dokuments) wie folgt durch Javascript getrennt sind.

Ich habe dies mit Firefox, Safari und Oper getestet. Manchmal funktioniert die Animation, manchmal springt sie direkt zur zweiten CSS-Datei und manchmal scheint die Seite geladen zu werden, aber es wird nichts angezeigt (vielleicht bin es nur ich?)

<link media="screen,projection" type="text/css" href="first-css-file.css"  rel="stylesheet" />

<script language="javascript" type="text/javascript" src="../js/jQuery JavaScript Library v1.3.2.js"></script>

<script type='text/javascript'>
$(document).ready(function(){

// iOS Hover Event Class Fix
if((navigator.userAgent.match(/iPhone/i)) || (navigator.userAgent.match(/iPod/i)) ||
(navigator.userAgent.match(/iPad/i))) {
$(".container .menu-text").click(function(){  // Update class to point at the head of the list
});
}
});
</script>

<link media="screen,projection" type="text/css" href="second-css-file.css"  rel="stylesheet" />

Hier ist ein Link zu meiner Work-in-Progress-Website: http://www.hankins-design.co.uk/beta2/test/index.html

Vielleicht irre ich mich, aber ich dachte, Browser, die keine CSS-Übergänge unterstützen, sollten keine Probleme haben, da sie ohne Verzögerung oder Dauer direkt zur zweiten CSS-Datei springen sollten.

Ich bin daran interessiert zu sehen, wie suchmaschinenfreundlich diese Methode ist. Mit meinem schwarzen Hut könnte ich vermutlich eine Seite mit Schlüsselwörtern füllen und die Deckkraft um 9999 Sekunden verzögern.

Mich würde interessieren, wie Suchmaschinen mit dem Attribut "Übergangsverzögerung" umgehen und ob sie mit der oben beschriebenen Methode überhaupt die Links und Informationen auf der Seite sehen würden.

Noch wichtiger ist, ich würde wirklich gerne wissen, warum dies nicht jedes Mal konsistent ist, wenn die Seite geladen wird, und wie ich dies korrigieren kann!

Ich hoffe, dass dies einige Ansichten und Meinungen erzeugen kann, wenn nichts anderes!

Michael Walkling
quelle
0

Wenn jemand andere Probleme hatte, zwei Übergänge gleichzeitig durchzuführen, habe ich Folgendes getan. Ich brauchte Text, um beim Laden der Seite von oben nach unten zu kommen.

HTML

<body class="existing-class-name" onload="document.body.classList.add('loaded')">

HTML

<div class="image-wrapper">
    <img src="db-image.jpg" alt="db-image-name">
    <span class="text-over-image">DB text</span>
</div>

CSS

.text-over-image {
    position: absolute;
    background-color: rgba(110, 186, 115, 0.8);
    color: #eee;
    left: 0;
    width: 100%;
    padding: 10px;
    opacity: 0;
    bottom: 100%;
    -webkit-transition: opacity 2s, bottom 2s;
    -moz-transition: opacity 2s, bottom 2s;
    -o-transition: opacity 2s, bottom 2s;
    transition: opacity 2s, bottom 2s;
}

body.loaded .text-over-image {
    bottom: 0;
    opacity: 1;
}

Ich weiß nicht, warum ich immer wieder versucht habe, 2 Übergangsdeklarationen in einem Selektor zu verwenden, und (nicht wirklich) dachte, dass beide verwendet werden würden.

s3c
quelle
0

Noch einfachere Lösung (immer noch mit [einzeiliger Inline] Javascript):

Verwenden Sie dies als der Body - Tag: Beachten Sie, dass body.oder this.nicht für mich arbeiten. Nur die langen; querySelectorerlauben die Verwendung von classList.remove(Linux Chromium)

<body class="onload" onload="document.querySelector('body').classList.remove('onload')">

und fügen Sie diese Zeile zusätzlich zu Ihren anderen CSS-Regeln hinzu.

body.onload *{ transform: none !important; }

Beachten Sie, dass dies für die Deckkraft gelten kann (wie von OP [anderen Postern] gefordert), indem Sie stattdessen die Deckkraft als Übergangsauslöser verwenden. (Funktioniert möglicherweise sogar mit anderen CSS-Regeln auf dieselbe Weise, und Sie können mehrere Klassen für die explizite Verzögerung zwischen dem Auslösen verwenden.)

Die Logik ist dieselbe. Keine Transformation erzwingen (mit :none !importantallen untergeordneten Elementen von body.onloadund nach dem Laden des Dokuments entfernen Sie die Klasse, um alle Übergänge für alle Elemente auszulösen, wie in Ihrem CSS angegeben.

ERSTE ANTWORT UNTEN (SIEHE BEARBEITEN OBEN FÜR KURZE ANTWORT)

Hier ist eine umgekehrte Lösung:

  1. Erstellen Sie Ihr HTML-Layout und stellen Sie das CSS entsprechend Ihrem Endergebnis ein (mit allen gewünschten Transformationen).
  2. Stellen Sie die Übergangseigenschaft nach Ihren Wünschen ein
  3. Fügen Sie den Elementen, die Sie NACH dem Laden transformieren möchten, eine Klasse (z. B. waitload) hinzu. Das CSS-Schlüsselwort ! Wichtig ist hier das Schlüsselwort.
  4. Verwenden Sie nach dem Laden des Dokuments JS, um die Klasse aus den Elementen zu entfernen und die Transformation zu starten (und entfernen Sie den Übergang: Keine überschreiben).

Funktioniert mit mehreren Übergängen für mehrere Elemente. Ich habe keine Cross-Browser-Kompatibilität versucht.

#rotated{
    transform : rotate(90deg) /* any other transformation */;
    transition  3s;
}
#translated{
    transform : translate(90px) /* any other transformation */;
    transition  3s;
}
.waitload{
    transform: none !important;
}
<div id='rotated' class='waitload'>
    rotate after load
</div>
<div id='translated' class='waitload'>
    trasnlate after load
</div>
<script type="text/javascript">
     // or body onload ?
    [...document.querySelectorAll('.waitload')]
        .map(e => e.classList.remove('waitload'));

</script>
Louis Loudog Trottier
quelle
-2

Nicht wirklich, da CSS so schnell wie möglich angewendet wird, aber die Elemente möglicherweise noch nicht gezeichnet wurden. Sie könnten eine Verzögerung von 1 oder 2 Sekunden erraten, aber dies sieht für die meisten Menschen nicht richtig aus, abhängig von der Geschwindigkeit ihres Internets.

Wenn Sie beispielsweise etwas einblenden möchten, ist CSS erforderlich, das den zu liefernden Inhalt verbirgt. Wenn der Benutzer keine CSS3-Übergänge hat, wird er diese nie sehen.

Ich würde empfehlen, jQuery (aus Gründen der Benutzerfreundlichkeit + Sie möchten möglicherweise Animationen für andere UAs hinzufügen) und einige JS wie diese zu verwenden:

$(document).ready(function() {
    $('#id_to_fade_in')
        .css({"opacity":0})   // Set to 0 as soon as possible – may result in flicker, but it's not hidden for users with no JS (Googlebot for instance!)
        .delay(200)           // Wait for a bit so the user notices it fade in
        .css({"opacity":1});  // Fade it back in. Swap css for animate in legacy browsers if required.
});

Zusammen mit den im CSS hinzugefügten Übergängen. Dies hat den Vorteil, dass bei Bedarf problemlos die Verwendung von Animationen anstelle des zweiten CSS in älteren Browsern möglich ist.

Rich Bradshaw
quelle
17
Warum wurde diese Antwort akzeptiert? Es macht eigentlich nichts, wonach die Frage gestellt hat. Es startet einfach (und sehr schnell, manchmal unbemerkt) das Element unsichtbar, wartet den Bruchteil einer Sekunde (200 ms) und macht es dann sofort wieder sichtbar. Das ist keine Überblendung, zuletzt habe ich nachgesehen.
VoidKing
Sie würden einen CSS-Übergang in die Liste aufnehmen #id_to_fade in, obwohl ich damit einverstanden bin, was aus der Antwort nicht so klar hervorgeht.
Rich Bradshaw
wie in, fügen Sie dem jQuery-Aufruf eine weitere .css ({Übergang: 'Deckkraft 2s'}) hinzu? Oder nur in deiner CSS? Ich habe das Gefühl, dass ich das Gefühl haben werde, dass dies eine dumme Frage ist ...
VoidKing
3
Es ist in Ordnung - ich hätte wirklich eine Demo erstellen sollen. In CSS #id_to_fade_in { -webkit-transition:opacity 0.5s ease-in-out; }+ -o-auch -moz-Präfixe.
Rich Bradshaw
2
Dies sollte nicht die akzeptierte Antwort sein, da die Verwendung von Keyframes der richtige Weg ist.
Eduardo Naveda