Welcome! Please hold on...

0 %
Kashif Sohail
Sr. Frontend Developer
  • Residence:
    Pakistan
  • City:
    Karachi
  • Age:
    26
Magento 1x 2x
Wordpress
Laravel
Angular
React
English
Urdu
  • Bootstrap, Tailwind
  • Sass, Less, Css
  • Webpack
  • GIT knowledge
0

No products in the cart.

Fluid Everything Else | CSS-Tricks

December 7, 2024

[ad_1]

Wir alle wissen, wie man Responsive Design macht, oder? Wir verwenden Medienanfragen. Nun nein, wir verwenden Containerabfragen Nun, nicht wahr? Manchmal werden wir erfinderisch Flexbox oder Automatisch fließende Gitter. Wenn wir uns wirklich abenteuerlustig fühlen, können wir danach greifen flüssige Typografie.

Es ist mir etwas unangenehm, dass Responsive Design oft in diskrete Abschnitte aufgeteilt wird, wie zum Beispiel „Layout A bis zu dieser Größe, dann Layout B, bis genug Platz für Layout C ist.“ Es ist in Ordnung, es funktioniert und passt in einen Workflow, in dem Bildschirme als statische Layouts in PhotoFigVa entworfen werden (Vorbehalt, das habe ich mir ausgedacht). Aber der Prozess fühlt sich für mich wie ein Kompromiss an. Ich bin seit langem davon überzeugt, dass responsives Design für den Benutzer nahezu unsichtbar sein sollte. Wenn sie meine Website auf einem mobilen Gerät besuchen, während sie in der Schlange auf K-Pop-Tickets warten, sollten sie nicht bemerken, dass es anders ist als noch vor einer Stunde, als sie an dem riesigen gebogenen Gaming-Monitor saßen, von dem sie ihrem Chef überzeugt hatten, dass er ihn brauchte.

Betrachten Sie dieses einfache Heldenbanner und sein mobiles Äquivalent. Entschuldigung für das schlichte Design. Das Bild ist KI-generiert, aber es ist das Einzige an diesem Artikel.

Das Erdmännchen und der Text sind alle unterschiedlich positioniert und unterschiedlich groß. Der traditionelle Weg, dies zu erreichen, besteht darin, zwei Layouts zu haben, die von a ausgewählt werden MedienEntschuldigung, Containerabfrage. In jedem Layout könnte es eine gewisse Flexibilität geben, vielleicht die Zentrierung des Inhalts und eine etwas flüssige Typografie auf dem font-sizeaber wir werden einen Punkt wählen, an dem wir das Layout in die gestapelte Version hinein- und wieder herausdrehen. Daher ist es wahrscheinlich, dass es in der Nähe des Haltepunkts Breiten gibt, bei denen das Layout entweder etwas leer oder etwas überfüllt aussieht.

Gibt es einen anderen Weg?

Es stellt sich dort heraus Ist. Wir können das Konzept der flüssigen Typografie auf fast alles anwenden. Auf diese Weise können wir ein Layout erstellen, das sich fließend mit der Größe des übergeordneten Containers ändert. Nur wenige Benutzer werden den Übergang jemals sehen, aber sie alle werden die Ergebnisse zu schätzen wissen. Ehrlich gesagt, das werden sie.

Lassen Sie uns das aufpeppen

Lassen Sie uns im ersten Schritt die Layouts individuell gestalten, ähnlich wie wir es bei der Verwendung von Breitenabfragen und einem Haltepunkt tun würden. Lassen Sie uns tatsächlich eine Containerabfrage und einen Haltepunkt zusammen verwenden, damit wir leicht erkennen können, welche Eigenschaften geändert werden müssen.

Dies ist der Markup für unseren Helden, und er wird sich nicht ändern:

LookOut

Eagle Defense System

Dies ist das relevante CSS für die breite Version:

#hero {
  container-type: inline-size;
  max-width: 1200px;
  min-width: 360px;

  .details {
    position: absolute;
    z-index: 2;

    top: 220px;
    left: 565px;

    h1 { font-size: 5rem; }

    p { font-size: 2.5rem; }
  }

  &::before {
    content: '';
    position: absolute;
    z-index: 1;

    top: 0; left: 0; right: 0; bottom: 0;

    background-image: url(../meerkat.jpg);
    background-origin: content-box;
    background-repeat: no-repeat;

    background-position-x: 0;
    background-position-y: 0;
    background-size: auto 589px;
  }
}

Ich habe das Hintergrundbild an a angehängt ::before Pseudoelement, damit ich Containerabfragen darauf verwenden kann (da Container sich nicht selbst abfragen können). Wir werden dies später aufbewahren, damit wir es verwenden können Inline-Containerabfrage (cqi) Einheiten. Hier ist zunächst die Containerabfrage, die nur die Werte anzeigt, die wir fließend machen werden:

@container (max-width: 800px) {
  #hero {
    .details {
      top: 50px;
      left: 20px;

      h1 { font-size: 3.5rem; }

      p { font-size: 2rem; }
    }

    &::before {
      background-position-x: -310px;
      background-position-y: -25px;
      background-size: auto 710px;
    }
  }
}

Sie können sehen, wie der Code in a ausgeführt wird Live-Demo – Es ist völlig statisch, die Grenzen eines typischen Ansatzes aufzuzeigen.

Lassen Sie uns flüssig werden

Jetzt können wir diese Start- und Endpunkte für die Größe und Position von Text und Hintergrund verwenden und sie fließend gestalten. Die Textgröße verwendet flüssige Typografie auf eine Weise, die Sie bereits kennen. Hier ist das Ergebnis – ich erkläre die Ausdrücke, sobald Sie sich den Code angesehen haben.

Zuerst die Änderungen an der Position und Größe des Textes:

/* Line changes
 * -12,27 +12,32
 */
  
.details {
  /* ... lines 14-16 unchanged */
  /* Evaluates to 50px for a 360px wide container, and 220px for 1200px */
  top: clamp(50px, 20.238cqi - 22.857px, 220px);

  /* Evaluates to 20px for a 360px wide container, and 565px for 1200px */
  left: clamp(20px, 64.881cqi - 213.571px, 565px);
  
  /* ... lines 20-25 unchanged */
  h1 {
    /* Evaluates to 3.5rem for a 360px wide container, and 5rem for 1200px */
    font-size: clamp(3.5rem, 2.857rem + 2.857cqi, 5rem);
    /* ... font-weight unchanged */

  }

  p {
    /* Evaluates to 2rem for a 360px wide container, and 2.5rem for 1200px */
    font-size: clamp(2rem, 1.786rem + 0.952cqi, 2.5rem);
  }
}

Und hier ist die Hintergrundposition und -größe für das Erdmännchenbild:

/* Line changes
 * -50,3 +55,8
 */

/* Evaluates to -310px for a 360px wide container, and 0px for 1200px */
background-position-x: clamp(-310px, 36.905cqi - 442.857px, 0px);
/* Evaluates to -25px for a 360px wide container, and 0px for 1200px */
background-position-y: clamp(-25px, 2.976cqi);
/* Evaluates to 710px for a 360px wide container, and 589px for 1200px */
background-size: auto clamp(589px, 761.857px - 14.405cqi, 710px);

Jetzt können wir die Containerabfrage vollständig fallen lassen.

Lassen Sie uns diese erklären clamp() Ausdrücke. Wir beginnen mit dem Ausdruck für top Eigentum.

/* Evaluates to 50px for a 360px wide container, and 220px for 1200px */
top: clamp(50px, 20.238cqi - 22.857px, 220px);

Sie werden bemerkt haben, dass es dort einen Kommentar gibt. Diese Ausdrücke sind ein gutes Beispiel dafür Magische Zahlen sind eine schlechte Sache. Aber wir können sie hier nicht vermeiden, da sie das Ergebnis der Lösung einiger gleichzeitiger Gleichungen sind – was CSS nicht kann!

Die oberen und unteren Grenzen werden übergeben clamp() sind klar genug, aber der Ausdruck in der Mitte stammt aus diesen simultanen Gleichungen:

f + 12v = 220
f + 3.6v = 50

…Wo f ist die Anzahl der Längeneinheiten fester Größe (d. h. px) Und v ist die Einheit variabler Größe (cqi). In der ersten Gleichung sagen wir, dass der Ausdruck ausgewertet werden soll 220px Wann 1cqi ist gleich 12px. In der zweiten Gleichung sagen wir, wir wollen 50px Wann 1cqi Ist 3.6pxwas zu Folgendem führt:

f = -22.857
v = 20.238

…und das schafft Ordnung 20.238cqi – 22.857px in einem calc()-freundlicher Ausdruck.

Wenn die feste Einheit unterschiedlich ist, müssen wir die Größe der variablen Einheiten entsprechend ändern. Also für die

Elemente font-size wir haben;

/* Evaluates to 2rem for a 360px wide container, and 2.5rem for 1200px */
font-size: clamp(2rem, 1.786rem + 0.952cqi, 2.5rem);

Dies löst diese Gleichungen, da bei einer Containerbreite von 1200px, 1cqi ist das gleiche wie 0.75rem (meine Rems sind relativ zum Standard-UA-Stylesheet, 16px) und bei 360px breit, 1cqi Ist 0.225rem.

f + 0.75v = 2.5
f + 0.225v = 2

Dies ist wichtig zu beachten: Die Gleichungen unterscheiden sich je nachdem, auf welche Einheit Sie abzielen.

Ehrlich gesagt ist das jedes Mal langweilige Mathematik Ich habe einen Taschenrechner erstellt, den Sie verwenden können. Es löst nicht nur die Gleichungen für Sie (bis auf drei Dezimalstellen, um Ihr CSS sauber zu halten), sondern bietet auch einen hilfreichen Kommentar, den Sie neben dem Ausdruck verwenden können, damit Sie sehen können, woher sie kommen, und magische Zahlen vermeiden können. Fühlen Sie sich frei, es zu verwenden. Ja, es gibt viele ähnliche Taschenrechner, aber sie konzentrieren sich auf Typografie und sind daher (zu Recht) darauf fixiert rem Einheiten. Sie könnten das JavaScript wahrscheinlich portieren, wenn Sie einen CSS-Präprozessor verwenden.

Der clamp() Die Funktion ist an dieser Stelle nicht unbedingt erforderlich. In jedem Fall sind die Grenzen von clamp() werden auf die Werte gesetzt, wenn der Container entweder ist 360px oder 1200px breit. Da der Container selbst durch die Einstellung auf diese Grenzen beschränkt ist min-width Und max-width Werte – die clamp() Der Ausdruck sollte niemals eine der beiden Bindungen aufrufen. Allerdings behalte ich es lieber clamp() für den Fall, dass wir jemals unsere Meinung ändern (was wir gleich tun werden), denn implizite Grenzen wie diese sind schwer zu erkennen und aufrechtzuerhalten.

Verletzungen vermeiden

Wir könnten unsere Arbeit als erledigt betrachten, aber das sind wir noch nicht. Das Layout funktioniert immer noch nicht ganz. Der Text verläuft direkt über dem Kopf des Erdmännchens. Obwohl man mir versichert hat, dass dies dem Erdmännchen keinen Schaden zufügt, gefällt mir das Aussehen nicht. Nehmen wir also einige Änderungen vor, damit der Text nicht auf das Erdmännchen trifft.

Das erste ist einfach. Wir bewegen das Erdmännchen schneller nach links, damit es ihm aus dem Weg geht. Dies lässt sich am einfachsten erreichen, indem man das untere Ende der Interpolation auf einen breiteren Container umstellt. Wir stellen es so ein, dass das Erdmännchen vollständig zurückbleibt 450px statt auf 360px. Es gibt keinen Grund, warum die Start- und Endpunkte für alle unsere flüssigen Ausdrücke auf die gleiche Breite ausgerichtet sein müssen, damit wir die anderen Ausdrücke auf flüssig beschränken können 360px.

Mit meinem zuverlässigen Taschenrechner müssen wir nur das ändern clamp() Ausdrücke für die background-position Eigenschaften:

/* Line changes
 * -55,5 +55,5
 */

/* Evaluates to -310px for a 450px wide container, and 0px for 1200px */
background-position-x: clamp(-310px, 41.333cqi - 496px, 0px);

/* Evaluates to -25px for a 450px wide container, and 0px for 1200px */
background-position-y: clamp(-25px, 3.333cqi - 40px, 0px);

Das verbessert die Dinge, aber nicht vollständig. Ich möchte es nicht noch schneller verschieben, also schauen wir uns als Nächstes den Weg an, den der Text nimmt. Im Moment bewegt es sich geradlinig, etwa so:

Zeigt den Weg an, den die Überschrift zurücklegt, während das Hero-Banner von der Desktop-Größe über die Tablet-Größe bis hin zur mobilen Größe wechselt.

Aber können wir es biegen? Ja, das können wir.

Eine Kurve im Weg

Eine Möglichkeit, dies zu erreichen, besteht darin, zwei verschiedene Interpolationen für zu definieren top Koordinate, die die Linie in verschiedenen Winkeln platziert, und dann den kleinsten Winkel auswählen. Auf diese Weise kann die steilere Linie bei größeren Behälterbreiten „gewinnen“, und die flachere Linie wird zum Wert, der gewinnt, wenn der Behälter schmaler als etwa ist 780px. Das Ergebnis ist eine Linie mit einer Krümmung, die das Erdmännchen verfehlt.

Alles, was wir ändern, ist der Spitzenwert, aber wir müssen zuerst zwei Zwischenwerte berechnen:

/* Line changes
 * -18,2 +18,9 @@
 */

/* Evaluates to 220px for a 1200px wide container, and -50px for 360px */
--top-a: calc(32.143cqi - 165.714px);

/* Evaluates to 120px for a 1200px wide container, and 50px for 360px */
--top-b: calc(20px + 8.333cqi);

/* By taking the max, --topA is used at lower widths, with --topB taking over when wider.
We only need to apply clamp when the value is actually used */
top: clamp(50px, max(var(--top-a), var(--top-b)), 220px);

Anstatt diese Werte formal anhand eines sorgfältig gewählten Mittelpunkts zu berechnen, experimentierte ich mit den Endpunkten, bis ich das gewünschte Ergebnis erhielt. Experimente sind genauso sinnvoll wie Berechnungen, um das gewünschte Ergebnis zu erzielen. In diesem Fall habe ich mit Duplikaten der Interpolation in benutzerdefinierten Variablen begonnen. Ich hätte den Pfad mithilfe einer Containerabfrage in explizite Abschnitte aufteilen können, aber das verringert nicht den mathematischen Aufwand und die Verwendung von min() Die Funktion ist für mein Auge sauberer. Außerdem geht es in diesem Artikel nicht ausschließlich um Containerabfragen, oder?

Nun bewegt sich der Text entlang dieses Pfades. Öffne das Live-Demo um es in Aktion zu sehen.

Zeigt den Weg an, den die Überschrift zurücklegt, während das Hero-Banner von einer Desktop-Größe über eine Tablet-Größe bis hin zu einer mobilen Größe wechselt. Der Weg bildet einen spitzen Winkel, während er über das Erdmännchen verläuft.

CSS kann nicht alles

Als letzte Anmerkung zu den Berechnungen sei darauf hingewiesen, dass es Einschränkungen hinsichtlich dessen gibt, was wir tun können und was nicht. Das erste, das wir bereits ein wenig abgeschwächt haben, ist, dass diese Interpolationen linear sind. Das bedeutet, dass ein nachlassendes Ein- oder Aussteigen oder ein anderes komplexes Verhalten nicht möglich ist.

Eine weitere große Einschränkung besteht darin, dass CSS auf diese Weise nur Längenwerte generieren kann. Daher gibt es in reinem CSS keine Möglichkeit, beispielsweise Deckkraft oder einen Drehwinkel anzuwenden, der basierend auf der Container- oder Ansichtsfenstergröße fließend ist. Auch Präprozessoren können uns hier nicht weiterhelfen, da die Einschränkung auf dem Weg ist calc() Funktioniert im Browser.

Beide Einschränkungen können aufgehoben werden, wenn Sie bereit sind, sich auf ein wenig JavaScript zu verlassen. Es sind lediglich ein paar Zeilen erforderlich, um die Breite des Containers zu beobachten und eine benutzerdefinierte CSS-Eigenschaft ohne Einheiten festzulegen. Ich werde das verwenden, um den Text einer quadratischen Bezier-Kurve folgen zu lassen, etwa so:

Zeigt den Weg an, den die Überschrift zurücklegt, während das Hero-Banner von einer Desktop-Größe über eine Tablet-Größe bis hin zu einer mobilen Größe wechselt. Der Weg macht eine sanfte Kurve, während er über das Erdmännchen verläuft.

Es gibt zu viel Code, um ihn hier aufzulisten, und zu viel Mathematik, um die Bezier-Kurve zu erklären, aber schauen Sie sich das in Aktion an diese Live-Demo.

Wir bräuchten nicht einmal JavaScript, wenn Ausdrücke wie calc(1vw / 1px) ist in CSS nicht fehlgeschlagen. Es gibt keinen Grund, sie zu versagen, da sie ein Verhältnis zwischen zwei Längen darstellen. So wie es sie gibt 2.54cm In 1ines gibt 8px In 1vw wenn das Ansichtsfenster ist 800px breit, also calc(1vw / 1px) sollte zu einer Einheit ohne Einheit ausgewertet werden 8 Wert.

Sie scheitern jedoch, also können wir nur unseren Standpunkt darlegen und weitermachen.

Flüssiges Alles löst nicht alle Layouts

Natürlich wird es immer einige Layouts geben, die Größenabfragen erfordern; Einige Designs müssen Änderungen einfach an festen Haltepunkten einrasten lassen. Es gibt keinen Grund, das zu vermeiden, wenn es richtig ist. Es gibt auch keinen Grund, eine Vermischung der beiden zu vermeiden, indem man beispielsweise die Größe und Positionierung des Hintergrunds fließend verändert und gleichzeitig eine Abfrage verwendet, um zwischen Rasterdefinitionen für die Textplatzierung zu wechseln. Mein Erdmännchen-Beispiel ist aus Demonstrationsgründen bewusst einfach gehalten.

Eine Sache, die ich hinzufügen möchte, ist, dass ich von der Möglichkeit, das Neue zu nutzen, ziemlich begeistert bin Ankerpositionierungs-API für flüssige Positionierung. Es besteht die Möglichkeit, die Ankerpositionierung zu verwenden, um zu definieren, wie zwei Elemente zusammen über den Bildschirm fließen könnten, aber das steht auf einem anderen Blatt.

[ad_2]

Source link

Posted in TechnologyTags:
Write a comment