Verschiedene Möglichkeiten zum Animieren eines Rahmens in CSS
Rahmen festlegen
Es gibt mehrere Methoden, um einem Element einen Rahmen hinzuzufügen: border
, outline
und box-shadow
. Wie in The 3 CSS Methods for Adding Element Borders von Stephanie Eckles beschrieben, hat jeder Ansatz seine eigenen Vor- und Nachteile, insbesondere wenn es um die Animation der Ränder geht. Der Hauptgrund, warum keine richtige CSS-border
verwendet wird, sind Animationen.
Ein Artikel, der mir vor Kurzem aufgefallen ist, ist Fantastic CSS border animation (Fantastische CSS-Grenzanimation), in dem die Autorin Coco weitere Optionen untersucht hat. Durch das Einfügen von generierten Inhalten mit ::before
und ::after
wird ein künstlicher Rahmen erstellt, der dann animiert wird.
Am meisten gefallen mir die unterstützenden animierten Visualisierungen im Artikel. Sie helfen wirklich zu erklären, was genau getan wird, um den gewünschten Effekt zu erzielen.
Sowohl die weiße Ebene als auch die farbigen Linien sind generierte Inhalte. Durch das Ein- und Ausblenden der weißen Ebene wird deutlich, wie sie übereinander liegen und wie die Animation funktioniert.
Boxmodell beibehalten
Ein Nachteil der Verwendung von generierten Inhalten, um einen Rahmen zu imitieren, ist, dass das Box-Modell nicht mehr funktioniert: Die Inhalte können den gefälschten Rahmen jetzt verdecken, da dieser „Rahmen“ darunter gemalt wird. Um dies zu vermeiden, müssen Sie die gewünschte border-width
als padding
anwenden.
Um einen echten Rahmen zu erhalten und damit die Funktionsweise des Boxmodells beizubehalten, können Sie mehrere Hintergründe verwenden, die Sie dann in den Rahmenbereich ausdehnen.
Grundlagen
Erstellen Sie zuerst einen gepunkteten Rahmen und fügen Sie die verschiedenen Hintergründe hinzu.
/* Size of the border */
--border-size: 0.5rem;
/* Create a dotted border */
border: var(--border-size) dotted lime;
/* Create two background layers:
1. A white semi-transparent
2. A layer with the colored boxes
*/
background-image:
linear-gradient(to right, rgb(255 255 255 / 0.5), rgb(255 255 255 / 0.5)),
conic-gradient(
from 45deg,
#d53e33 0deg 90deg,
#fbb300 90deg 180deg,
#377af5 180deg 270deg,
#399953 270deg 360deg
)
;
Größe der Hintergründe mit background-origin
festlegen
Wie Sie sehen, ist hier etwas Seltsames mit den Hintergründen passiert: Sie sind in den Rahmen gemalt, aber die conic-gradient
scheint völlig falsch zu sein. Das ist ein beabsichtigtes Verhalten: Standardmäßig werden Hintergrundbilder nicht in den Rahmen eingezeichnet, da ihr Ursprung die padding-box
des Elements ist. Um einen Rahmen zu erstellen, werden die festgelegten Hintergrundbilder im Rahmen selbst wiederholt, was zu diesem seltsamen visuellen Effekt führt.
Um dieses Problem zu beheben, müssen Sie den Hintergrund so strecken, dass er auch die Größe des Rahmens einnimmt. Sie können dies manuell tun, indem Sie den Hintergrund strecken und neu positionieren. Am besten verwenden Sie jedoch die Eigenschaft background-origin
, um die Größe des Hintergrunds an das border-box
anzupassen.
/* Manually add or offset the size of the border where needed */ background-position: calc(var(--border-size) * -1) calc(var(--border-size) * -1); background-size: calc(var(--border-size) * 2 + 100%) calc(var(--border-size) * 2 + 100%);
background-origin: border-box;
Durch diese eine Ergänzung sieht alles viel besser aus:
Weiße Hintergrundebene mit background-clip
verkleinern
Da die Hintergründe jetzt den gesamten Platz einnehmen, muss die halbtransparente Ebene wieder verkleinert werden. Anstatt noch einmal mit background-size
herumzuspielen, gibt es eine einfachere Möglichkeit: Verwenden Sie background-clip
und setzen Sie den Wert auf padding-box
. So wird der Hintergrund nicht mehr unter dem Bereich des Rahmens gezeichnet.
background-clip:
padding-box, /* Clip white semi-transparent to the padding-box */
border-box /* Clip colored boxes to the border-box (default) */
;
Legen Sie abschließend einen Rahmen von transparent
fest, um den vollen Effekt zu erzielen.
border: 0.3rem dotted transparent;
Animation
Wenn Sie den Rahmen wieder animieren möchten, können Sie den Startwinkel von conic-gradient
anpassen.
--angle: 0deg;
conic-gradient(
from var(--angle),
#d53e33 0deg 90deg,
#fbb300 90deg 180deg,
#377af5 180deg 270deg,
#399953 270deg 360deg
);
Dank @property ist das in Browsern, die diese Funktion unterstützen, ein Kinderspiel:
@property --angle {
syntax: "<angle>";
initial-value: 0deg;
inherits: false;
}
@keyframes rotate {
to {
--angle: 360deg;
}
}
Zusammen ergibt sich daraus folgender Code:
Bonusinhalte: border-image
Wie bereits erwähnt, können Sie mit CSS border-image
einen Farbverlauf für den Rahmen zeichnen.
Sie ermöglicht einen vereinfachten Code, da sich die Hintergründe nicht überschneiden. Die Animation kann wie bisher angewendet werden.
/* Create a border */
border: 0.5rem solid transparent;
/* Paint an image in the border */
border-image:
conic-gradient(
from var(--angle),
#d53e33 0deg 90deg,
#fbb300 90deg 180deg,
#377af5 180deg 270deg,
#399953 270deg 360deg
) 1
;
Allerdings gibt es einige Dinge, die mit diesem Ansatz nicht mehr funktionieren:
- Die
border-image
folgt nicht derborder-radius
, sondern bleibt immer rechteckig. - Wenn
border-image-slice
zum Füllen festgelegt wird, wirdborder-image
nicht unter der Gruppebackground
, sondern oben angezeigt. Dies kann problematisch sein, wenn der Hintergrund halbtransparent sein soll.
Bei Abschluss
Es gibt viele Möglichkeiten, Ränder in CSS zu animieren. Je nach Anwendungsfall kann es sinnvoll sein, die eine oder die andere Methode zu verwenden.