CSS to line break ก่อน / หลังไอเท็ม `inline-block`


202

สมมติว่าฉันมี HTML นี้:

<h3>Features</h3>
<ul>
    <li><img src="alphaball.png">Smells Good</li>
    <li><img src="alphaball.png">Tastes Great</li>
    <li><img src="alphaball.png">Delicious</li>
    <li><img src="alphaball.png">Wholesome</li>
    <li><img src="alphaball.png">Eats Children</li>
    <li><img src="alphaball.png">Yo' Mama</li>
</ul>

และ CSS นี้:

li { text-align:center; display:inline-block; padding:0.1em 1em }
img { width:64px; display:block; margin:0 auto }

สามารถดูผลลัพธ์ได้ที่นี่: http://jsfiddle.net/YMN7U/1/

ทีนี้ลองนึกดูว่าฉันต้องการแยกสิ่งนี้ออกเป็นสามคอลัมน์ซึ่งเท่ากับการฉีด a <br>หลังจากสาม<li>อัน (จริง ๆ แล้วการทำเช่นนั้นจะไม่ถูกต้องทางความหมายและ syntactically)

ฉันรู้วิธีเลือกตัวที่สาม<li>ใน CSS แต่ฉันจะบังคับให้ตัวแบ่งบรรทัดหลังจากนั้นได้อย่างไร สิ่งนี้ไม่ทำงาน:

li:nth-child(4):after { content:"xxx"; display:block }

ผมยังไม่ทราบว่ากรณีนี้โดยเฉพาะอย่างยิ่งเป็นไปได้โดยใช้floatแทนแต่ผมไม่ได้สนใจในการแก้ปัญหาโดยใช้inline-block floatฉันรู้ว่าด้วยบล็อกความกว้างคงที่นี้เป็นไปได้โดยการตั้งค่าความกว้างบนพาเรนต์เป็นulประมาณ 3x ฉันไม่สนใจวิธีนี้ ฉันก็รู้ว่าฉันสามารถใช้display:table-cellถ้าฉันต้องการคอลัมน์จริง; ฉันไม่สนใจวิธีนี้ ฉันสนใจในความเป็นไปได้ของการบังคับให้แบ่งเนื้อหาอินไลน์

แก้ไข : เพื่อความชัดเจนฉันสนใจ 'ทฤษฎี' ไม่ใช่วิธีแก้ปัญหาเฉพาะ CSS สามารถฉีดเส้นแบ่งตรงกลางdisplay:inline(-block)?องค์ประกอบหรือเป็นไปไม่ได้ หากคุณมั่นใจว่าเป็นไปไม่ได้นั่นเป็นคำตอบที่ยอมรับได้


2
ใส่อันดับที่ 1 และ 3 ในรายการที่แตกต่างกันสองรายการ ฉันสมมติว่าคุณไม่ต้องการทำเช่นนี้ แต่ฉันคิดว่าฉัน "โยนมันออกไปที่นั่น
JakeParis

ดูเหมือนคุณจะต้องบอกเราว่าคุณพยายามทำอะไรให้สำเร็จเพื่อให้ใครบางคนสามารถแนะนำวิธีที่ดีที่สุด ตัวเลือกทั้งหมดที่คุณยกเว้นมีอยู่เพื่อแก้ไขปัญหาที่คุณมีทำไมต้องมีวิธีแก้ไขปัญหาอื่น
Jake

4
@ เจคในความเป็นจริงฉันทำสิ่งที่ฉันระบุ: ใช้รายการความหมายขององค์ประกอบและต้องการห่อหลังจากที่เฉพาะเจาะจง ในทางปฏิบัติฉันตั้งค่าความกว้างของคอนเทนเนอร์ แต่สิ่งนี้ใช้ได้เฉพาะในกรณีของฉันเท่านั้นเนื่องจากรายการที่เกิดขึ้นมีความกว้างเท่ากันและฉันต้องการให้พวกเขาห่อที่ขอบที่สอดคล้องกัน นี่อาจไม่เป็นเช่นนั้นเสมอไป สิ่งที่ฉัน"พยายามบรรลุจริงๆ"คือเรียนรู้ว่า CSS สามารถบังคับให้ตัวแบ่งบรรทัดในระหว่างการไหลแบบอินไลน์หรือไม่ คำตอบที่มั่นใจ"ไม่สามารถทำได้อย่างแน่นอน"เป็นที่ยอมรับ (ถ้าถูกต้อง)
Phrogz

คำตอบ:


302

ฉันสามารถทำให้มันทำงานบนองค์ประกอบ LI แบบอินไลน์ได้ น่าเสียดายที่มันไม่ทำงานหากองค์ประกอบ LI เป็นบล็อกอินไลน์:

การสาธิตสด: http://jsfiddle.net/dWkdp/

หรือรุ่นบันทึกหน้าผา:

li { 
     display: inline; 
}
li:nth-child(3):after { 
     content: "\A";
     white-space: pre; 
}

2
ทำไม, "\ A" ถึงไม่พิมพ์ออกมา? ทุกสิ่งที่ฉันได้ลองด้วยการ:afterพิมพ์เป็นข้อความแบบตรงเสมอ
JakeParis

12
@JMCCreative นั่นคือ ASCII 0x0A, AKA a ตัวอักษร LF (ตัวดึงข้อมูลบรรทัด) ดูw3.org/TR/CSS2/syndata.html#strings
Phrogz

5
@JMC \Aเป็นตัวละครตัวดึงข้อมูลบรรทัด ... มันเป็นการหลบหนี
Šime Vidas

3
@JMC ข้อมูลจำเพาะอย่างเป็นทางการ: w3.org/TR/CSS21/syndata.html#strings Sitepoint: reference.sitepoint.com/css/content
Šime Vidas

18
แสดงความคิดเห็นที่นี่ในขณะที่ฉันกลับมาที่คำถามนี้ทุกสองสามเดือน ... มันจะไม่ทำงานในบล็อกแบบอินไลน์เพราะคุณกำลังเพิ่มตัวแบ่งบรรทัดภายในสิ่งที่มันทำหน้าที่เหมือนภาชนะบล็อกภายในบริบทแบบอินไลน์ หากคุณสามารถแยกออกจากบริบทโดยการแทรกตัวแบ่งบรรทัดระหว่าง <li> มันจะทำงาน ความอัปยศจริงๆเพราะเป็นประโยชน์สำหรับจุดพักการออกแบบที่ตอบสนอง ฉันเดาว่าเวลาส่วนใหญ่ "inline" นั้นมีประโยชน์พอ ๆ กับ inline-block สำหรับรายการ
user1010892

21

คุณไม่สนใจ "วิธีแก้ไขปัญหา" มากมายสำหรับปัญหาของคุณ ฉันไม่คิดว่าจะมีวิธีที่ดีในการทำสิ่งที่คุณต้องการจะทำ ทุกสิ่งที่คุณแทรกโดยใช้:afterและcontentมีความถูกต้องทางไวยากรณ์และความหมายแบบเดียวกับที่มันจะทำถ้าคุณเพิ่งเขียนไว้ในนั้นเอง

เครื่องมือ CSS ให้การทำงาน คุณควรลอยlis แล้วclear: leftเมื่อคุณต้องการเริ่มบรรทัดใหม่ตามที่คุณพูดถึง:

ดูตัวอย่าง: http://jsfiddle.net/marcuswhybrow/YMN7U/5/


18
OP ไม่สนใจโซลูชันของคุณ :)
Šime Vidas

2
ไม่มีอะไรที่คุณสามารถทำได้โดยการใช้:afterจะถูกต้อง syntactically หรือความคิดที่ดีเนื่องจากมีเครื่องมือในการทำเช่นนี้ ดังนั้นคำตอบ
Marcus Whybrow

32
float: centerเหตุผลหนึ่งที่จะไม่ใช้ลอยเป็นว่าไม่มีสิ่งดังกล่าวเป็น
เปลือกตา

7
plus inline-block ช่วยให้การจัดเรียงแนวตั้งทุกประเภทที่ไม่สามารถลอยได้
user1010892

20
"สิ่งที่คุณใส่โดยใช้: หลังจากและเนื้อหามีความถูกต้องทางไวยากรณ์และความหมายเหมือนกันทุกประการ" - มาช้าไปงานปาร์ตี้ แต่ฉันไม่เห็นด้วยกับสิ่งนี้ - จุดใช้งานทั้งหมด: ก่อนและ: หลังจากนั้นจะสามารถใส่สไตล์ที่ ไม่รบกวนความหมายเชิงความหมายของ Html
รูเพิร์

4

เมื่ออนุญาตให้เขียน html ใหม่ได้คุณสามารถซ้อน<ul>s ไว้ใน<ul>และปล่อยให้การ<li>แสดงผลด้านในเป็นแบบอินไลน์บล็อก สิ่งนี้จะทำให้เกิดความหมายแบบ IMHO ในเชิงความหมายเนื่องจากการจัดกลุ่มยังสะท้อนอยู่ใน html ด้วย


<ul>
    <li>
        <ul>
            <li>Item 1</li>
            <li>Item 2</li>
            <li>Item 3</li>
        </ul>
    </li>
    <li>
        <ul>
            <li>Item 4</li>
            <li>Item 5</li>
            <li>Item 6</li>
        </ul>
    </li>
</ul>

li li { display:inline-block; }

การสาธิต

$(function() { $('img').attr('src', 'http://phrogz.net/tmp/alphaball.png'); });
h3 {
  border-bottom: 1px solid #ccc;
  font-family: sans-serif;
  font-weight: bold;
}
ul {
  margin: 0.5em auto;
  list-style-type: none;
}
li li {
  text-align: center;
  display: inline-block;
  padding: 0.1em 1em;
}
img {
  width: 64px;
  display: block;
  margin: 0 auto;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<h3>Features</h3>
<ul>
  <li>
    <ul>
      <li><img />Smells Good</li>
      <li><img />Tastes Great</li>
      <li><img />Delicious</li>
    </ul>
  </li>
  <li>
    <ul>
      <li><img />Wholesome</li>
      <li><img />Eats Children</li>
      <li><img />Yo' Mama</li>
    </ul>
  </li>
</ul>


3

วิธีง่าย ๆ ในการแยกรายการออกเป็นแถวคือการลอยแต่ละรายการจากนั้นรายการที่คุณต้องการไปที่บรรทัดถัดไปคุณสามารถล้างการลอย

ตัวอย่างเช่น

<li style="float: left; display: inline-block"></li>
<li style="float: left; display: inline-block"></li>
<li style="float: left; display: inline-block"></li>

<li style="float: left; display: inline-block; clear: both"></li> --- this will start on a new line
<li style="float: left; display: inline-block"></li>
<li style="float: left; display: inline-block"></li>

17
คุณควรสังเกตว่าการfloatตั้งค่าจะแทนที่การinline-blockตั้งค่า พวกเขาไม่ได้อยู่ด้วยกันจริงๆ
Itay

4
ถ้าคุณใช้การทำข้อความ: ศูนย์ มันจะไม่ทำงาน (หยุดพักแบบลอยตัว)
ПавелИванов

3

ฉันรู้ว่าคุณไม่ต้องการใช้ทุ่นและคำถามนี้เป็นเพียงทฤษฎี แต่ในกรณีที่ใครก็ตามเห็นว่าสิ่งนี้มีประโยชน์นี่เป็นวิธีแก้ปัญหาโดยใช้ทุ่น

เพิ่มคลาสซ้ายไปยังliองค์ประกอบที่คุณต้องการลอยตัว:

<li class="left"><img src="http://phrogz.net/tmp/alphaball.png">Smells Good</li>

และแก้ไข CSS ของคุณดังนี้:

li { text-align:center; float: left; clear: left; padding:0.1em 1em }
.left {float: left; clear: none;}

http://jsfiddle.net/chut319/xJ3pe/

คุณไม่จำเป็นต้องระบุความกว้างหรืออินไลน์บล็อคและทำงานได้ไกลเท่า IE6


1

ฉันทำสิ่งนี้ได้สำเร็จโดยการสร้าง :: ก่อนตัวเลือกสำหรับองค์ประกอบอินไลน์แรกในแถวและทำให้ตัวเลือกนั้นเป็นบล็อกที่มีระยะขอบด้านบนหรือล่างเพื่อแยกแถวออกเล็กน้อย

.1st_item::before
{
  content:"";
  display:block;
  margin-top: 5px;
}

.1st_item
{
  color:orange;
  font-weight: bold;
  margin-right: 1em;
}

.2nd_item
{
  color: blue;
}

-1

โปรดทราบว่านี่จะใช้งานได้ขึ้นอยู่กับว่าคุณแสดงหน้าเว็บอย่างไร แต่วิธีการเกี่ยวกับการเริ่มต้นรายการที่ไม่มีการเรียงลำดับใหม่ได้อย่างไร

กล่าวคือ

<ul>
<li>
<li>
<li>
</ul>
<!-- start a new ul to line break it -->
<ul>


-2

ทางออกที่ดีกว่าคือการใช้ -webkit-columns: 2;

http://jsfiddle.net/YMN7U/889/

 ul { margin:0.5em auto;
-webkit-columns:2;
}

สำหรับบางกรณีการใช้งานอาจเป็นวิธีแก้ปัญหาที่สมเหตุสมผล มันไม่ได้เป็นทางออกที่ดีในกรณีนี้เพราะมันสั่งซื้อเนื้อหาทั้งหมดให้ข้ามไปแล้วแทนที่จะข้ามไปแล้ว
Phrogz

5
ใครบ้างที่ต้องการสร้างเว็บแอปพลิเคชั่นที่ใช้งานได้ในเบราว์เซอร์บางตัวเท่านั้น
2867288

-3

อาจเป็นไปได้อย่างสมบูรณ์กับ CSS เท่านั้น แต่ฉันชอบที่จะหลีกเลี่ยง "float" มากที่สุดเท่าที่จะทำได้เพราะมันรบกวนความสูงของผู้ปกครอง

หากคุณใช้ jQuery คุณสามารถสร้างปลั๊กอิน `wrapN` แบบง่าย ๆ ที่คล้ายกับ` wrapAll 'ยกเว้นว่าจะล้อมองค์ประกอบ "N" เท่านั้นจากนั้นจะแบ่งและตัดองค์ประกอบ "N" ถัดไปโดยใช้ลูป จากนั้นตั้งค่าคลาส wrappers ของคุณเป็น `display: block;`

(function ($) {
    $.fn.wrapN = function (wrapper, n, start) {
        if (wrapper === undefined || n === undefined) return false;
        if (start === undefined) start = 0;
        for (var i = start; i < $(this).size(); i += n)
           $(this).slice(i, i + n).wrapAll(wrapper);
        return this;
    };
}(jQuery));

$(document).ready(function () {
    $("li").wrapN("<span class='break' />", 3);
});

นี่คือ JSFiddle ของผลิตภัณฑ์สำเร็จรูป:

http://jsfiddle.net/dustinpoissant/L79ahLoz/

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.