wie man das absolute Div-Stacking-Layout von pinterest.com repliziert [geschlossen]

104

Ich möchte das div-Layout von Pinterest.com replizieren, insbesondere, wie sich die Anzahl der Spalten an die Größe des Browsers anpasst und die vertikale Stapelung nicht von den benachbarten Spaltenhöhen abhängt. Der Quellcode zeigt, dass jedes Div eine absolute Position ist. Ein Mitbegründer hat auf einen Quora-Beitrag geantwortet, der besagt, dass dies mit benutzerdefiniertem jQuery und CSS erfolgt. Ich möchte, dass die Ergebnisse von links nach rechts sortiert werden. Jede Richtung, die Sie geben könnten, um es selbst zu machen, wäre sehr dankbar.

chrickso
quelle
Ich habe meine eigenen mit einfachem Jquery und CSS codiert. Wenn Sie möchten, dass sich dies beim Ändern der Größe ändert, schließen Sie es einfach in eine Funktion ein und beobachten Sie das Ändern der
Andrew WC Brown

Antworten:

79

Sie können auch das jQuery Plug-in Masonry auf diese Art von Funktionalität überprüfen .

Bob.
quelle
3
Wirklich erstaunliche Bibliothek. Jetzt benutze ich es ohne Probleme.
AhmetB - Google
183

Ich habe das Pinterest-Skript geschrieben. Die IDs haben nichts mit dem Layout zu tun und werden für andere interaktionsbezogene JS verwendet. Hier ist die Basis, wie es funktioniert:

Vorweg:

  • Positionieren Sie die Stiftbehälter unbedingt
  • Spaltenbreite bestimmen
  • Bestimmen Sie den Abstand zwischen den Säulen (der Rinne).

Richten Sie ein Array ein:

  • Ermitteln Sie die Breite des übergeordneten Containers. Berechnen Sie die Anzahl der Spalten, die passen
  • Erstellen Sie ein leeres Array mit einer Länge, die der Anzahl der Spalten entspricht. Verwenden Sie dieses Array, um die Höhe jeder Spalte beim Erstellen des Layouts zu speichern, z. B. wird die Höhe von Spalte 1 als Array [0] gespeichert.

Schleife durch jeden Stift:

  • Setzen Sie jeden Stift zum Zeitpunkt des Hinzufügens in die kürzeste Spalte
  • "left:" === die Spaltennummer (Indexarray) mal die Spaltenbreite + Rand
  • "top:" === Der Wert im Array (Höhe) für die kürzeste Spalte zu diesem Zeitpunkt
  • Fügen Sie abschließend die Höhe des Stifts zur Spaltenhöhe hinzu (Array-Wert).

Das Ergebnis ist leicht. In Chrome dauert das Auslegen einer vollständigen Seite mit mehr als 50 Pins <10 ms.

Evan Sharp
quelle
4
Wie meinst du die Höhe der Säule berechnen? Woher wissen Sie, wie hoch es sein sollte, wenn Sie die Anzahl und Höhe der darin enthaltenen Elemente nicht kennen? Gibt es eine Chance, einen Pseudocode zu erstellen, um dies zu demonstrieren?
Michael Giovanni Pumo
22
Hier ist ein solides Tutorial - benholland.me/javascript/…
hollandben
1
Feedback eines Anonymus-Benutzers (in der Bearbeitungswarteschlange): Seltsamerweise habe ich in jQuery genau das gleiche Skript erstellt, mit dem kleinen Unterschied, dass tatsächlich eine Tabelle mit 1 Zeile und N Spalten erstellt und nur von links nach rechts an die kürzeste Spalte angehängt wurde Priorität. Obwohl ich auch eine Konstante "Minimaler Höhenunterschied" hinzugefügt habe, die erforderlich ist, um eine Spalte beim Positionieren von links nach rechts tatsächlich zu überspringen, erhält das Layout eine chronologisch intuitive Anzeige, ohne dass die Höhen so gleichmäßig wie möglich sind
oers
1
@MichaelGiovanniPumo Ich denke, die Höhe sollte vor dem Layout bekannt sein (im Fall von Pinterest), sie haben keinen "Anfangszustand", in dem sich Divs überlappen. Dies ist nicht möglich, wenn die Höhe nicht bekannt ist.
Ptgamr
1
@ hollandbens Link ist tot, neuer Link: benholland.me/javascript/2012/02/20/…
Lukmo
57

Wir haben ein jQuery-Plugin veröffentlicht, weil wir für Wookmark mehrmals dieselbe Frage haben . Es erstellt genau diese Art von Layout. Hier ansehen - Wookmark jQuery Plugin

GBKS
quelle
4
Diese Lösung scheint schneller zu laden als Mauerwerk
Michael L Watson
was findest du besser das Wookmark oder das Mauerwerk?
Ramje
Ich bevorzuge dies gegenüber Mauerwerk, scheint schneller zu sein, wie Michael sagte.
Nerdburn
2

Nachdem ich mir alle Optionen angesehen hatte, implementierte ich das Layout ähnlich wie bei Pinterest folgendermaßen:

Alle DIVs sind:

div.tile {
    display: inline-block;
    vertical-align: top;
}

Dadurch positionieren sie sich besser in Reihen als beim Schweben.

Wenn die Seite geladen wird, iteriere ich alle DIVs in JavaScript, um Lücken zwischen ihnen zu entfernen. Es funktioniert akzeptabel gut, wenn:

  1. DIVs sind nicht sehr unterschiedlich hoch.
  2. Es macht Ihnen nichts aus, wenn geringfügige Verstöße gegen die Reihenfolge vorliegen (einige Elemente, die sich unten befanden, können oben angezeigt werden).
  3. Es macht Ihnen nichts aus, wenn das Endergebnis unterschiedlich hoch ist.

Der Vorteil dieses Ansatzes: Ihr HTML ist für Suchmaschinen sinnvoll, kann mit JavaScript arbeiten, das von der Firewall deaktiviert / blockiert wird. Die Reihenfolge der Elemente in HTML entspricht der logischen Reihenfolge (die neueren Elemente vor den älteren).

insb
quelle
Hey, kannst du mir sagen, wie du den Offset berechnet hast, den du subtrahieren musstest? Und wie haben Sie das Problem gelöst, dass sich das letzte Element auf der rechten Seite befindet, weil es ein Element gibt, das etwas größer ist und es dorthin schiebt?
Lukas Oppermann
@LukasOppermann 1) Der Versatz für die Kachel ist die Summe aus dem Versatz für die Kachel in derselben Spalte in der vorherigen Zeile und der Differenz zwischen der Höhe der höchsten Kachel in der vorherigen Zeile und der Höhe der Kachel in derselben Spalte in der vorherigen Zeile. Werfen Sie einen Blick auf dev.sheeporpig.com/news (müssen Sie zunächst auf den Link klicken dev.sheeporpig.com/sheep/3210 Zugriff auf die Entwicklung vor Ort zu bekommen - so dass Sie unkomprimierte & kommentierte Skripte in separaten Dateien sehen), Skriptdatei stock_news.js, Funktion compressTiles.
Esp
@LukasOppermann 2) Wenn Sie CSS als Antwort verwenden (insbesondere Anzeige: Inline-Block), passiert dies nicht. Es passiert nur, wenn Sie schweben: verlassen Sie Ihre divs. Ich benutze kein Float.
Esp
0

Sie teilen Entitäten nach Spalten mit IDs auf (schlechte Lösung ... verwenden Sie besser Klassennamen) und berechnen dann Positionen nach Spaltengruppen

ant_Ti
quelle
2
+1 Zum Durchschauen des Quellcodes.
Bojangles
Es war interessant für mich, aber ich denke, es gibt eine bessere Lösung mit weniger js Berechnungen
ant_Ti
Sie könnten verwenden, display: inline-blocknehme ich an, aber Gegenstände mit unterschiedlicher vertikaler Höhe würden nicht zusammenpassen.
Bojangles
1
Verwenden Sie besser float:left;overflow: hidden;
Spaltencontainer
4
Guter Punkt. Wenn Sie wirklich den JavaScript-Weg gehen wollten, könnten Sie jQuery Masonry verwenden?
Bojangles
0

Sie könnten Floats verwenden und Ihre Div-Breiten mithilfe von Prozentsätzen zusammen mit der Min-Breite dimensionieren, um zu erzwingen, dass Divs automatisch fallen, sobald die Mindestbreite erreicht ist. So haben wir es auf http://www.goldtree.co.za/work zum Laufen gebracht

Ich bin Goldtree
quelle