Jak mogę utworzyć div nie większy niż jego zawartość?

2070

Mam układ podobny do:

<div>
    <table>
    </table>
</div>

Chciałbym, divaby rozszerzyło się tylko na tak szerokie, jak się tablestaje.

Peter Mortensen
źródło
90
efekt nazywa się „kurczeniem” i zgodnie z odpowiedzią istnieje kilka sposobów na zrobienie tego (pływanie, wstawianie, szerokość
min./maks.

Odpowiedzi:

2426

Rozwiązaniem jest ustawienie divna display: inline-block.

użytkownik473598
źródło
239
@ leif81 Możesz użyć a spanlub a divlub ulcokolwiek innego, ważną częścią jest to, że kontener, który ma być minimalnej szerokości, ma właściwość CSSdisplay: inline-block
miahelf,
10
jeśli ktoś się zastanawia: można następnie wyśrodkować element nadrzędny tabeli, ustawiając na nim element „text-align: center” i „text-align: left” (np. <body style = "text-align: center"> < span style = "text-align: left; display: inline-block;"> <table> ... </table> </span> </body>)
Bernstein
12
Nie działa dla mnie na chrom z rozpiętością, ale działa przy użyciu białych znaków: nowrap;
albanx
57
Pamiętaj, że po display: inline-blockustawieniu właściwości margin: 0 auto;nie będzie działać zgodnie z oczekiwaniami. W takim przypadku, jeśli kontener macierzysty ma, text-align: center;wówczas inline-blockelement zostanie wyśrodkowany w poziomie.
Savas Vedova
12
inline-blockNIE działało dla mnie, ale NIE inline-flex.
mareoraft
331

Chcesz elementu blokowego, który ma to, co CSS nazywa kurczącą się, aby dopasować szerokość, a specyfikacja nie zapewnia błogosławionego sposobu na uzyskanie takiej rzeczy. W CSS2 dopasowanie do kurczenia się nie jest celem, ale oznacza radzenie sobie z sytuacją, w której przeglądarka „musi” uzyskać szerokość powietrza. Te sytuacje to:

  • pływak
  • element absolutnie pozycjonowany
  • element blokowy
  • element stołu

gdy nie określono szerokości. Słyszałem, że myślą o dodaniu tego, co chcesz w CSS3. Na razie skorzystaj z jednego z powyższych.

Decyzja, aby nie ujawniać funkcji bezpośrednio, może wydawać się dziwna, ale jest dobry powód. To jest drogie. Zmniejsz dopasuj oznacza formatowanie co najmniej dwa razy: nie możesz rozpocząć formatowania elementu, dopóki nie poznasz jego szerokości i nie możesz obliczyć szerokości bez przejścia przez całą zawartość. Co więcej, nie trzeba elementu kurczliwego dopasowywać tak często, jak mogłoby się wydawać. Dlaczego potrzebujesz dodatkowego diva przy stole? Może podpis tabeli jest wszystkim, czego potrzebujesz.

buti-oxa
źródło
34
Powiedziałbym, że inline-blockjest dokładnie do tego przeznaczony i doskonale rozwiązuje problem.
miahelf,
6
myślę, że dodają css4 i byłoby tocontent-box, max-content, min-content, available, fit-content, auto
Muhammad Umer
4
Nowe fit-contentsłowo kluczowe (nieistniejące, gdy ta odpowiedź została napisana po raz pierwszy i nadal nie jest w pełni obsługiwane ) pozwala jawnie zastosować wymiarowanie „zmniejsz do dopasowania” do elementu, eliminując potrzebę jakiegokolwiek z sugerowanych tu hacków, jeśli jesteś na tyle, że mogę celować tylko w przeglądarki z obsługą. Niemniej jednak +1; te pozostają na razie przydatne!
Mark Amery
floatzrobiłem to, co musiałem zrobić!
nipunasudha
228

Myślę, że za pomocą

display: inline-block;

działałoby, jednak nie jestem pewien kompatybilności przeglądarki.


Innym rozwiązaniem byłoby zawinięcie divw inne div(jeśli chcesz zachować zachowanie bloku):

HTML:

<div>
    <div class="yourdiv">
        content
    </div>
</div>

CSS:

.yourdiv
{
    display: inline;
}
Mbillard
źródło
23
Aby odpowiedzieć na pytanie dotyczące zgodności przeglądarki: nie będzie działać z IE7 / 8 w elementach DIV. Musisz użyć elementów SPAN.
Matt Brock,
@feeela - zawsze umieszczam * przed powiększeniem, np *display: inline; *zoom: 1;. Nie testowałem tej konkretnej sytuacji, ale zawsze w przeszłości zawsze stwierdziłem, że hack hasLayout jest wymagany tylko dla IE7 lub IE8 w trybie IE7 (lub IE8 w dziwactwach!).
robocat
@robocat Tak, to rzeczywiście jest obejście, które inline-block
włączono
@feela - twój komentarz nie ma dla mnie sensu! Sugerowałem także umieszczenie * przed powiększeniem, tj. * powiększenie: 1;
robocat
4
Wyjaśnij, dlaczego działa twoje rozwiązanie wbudowanego bloku.
HelloWorldNoMore
220

display: inline-block dodaje dodatkowy margines do elementu.

Poleciłbym to:

#element {
    display: table; /* IE8+ and all other modern browsers */
}

Bonus: Możesz teraz z łatwością wyśrodkować ten wymyślny nowy #element, dodając go margin: 0 auto.

Salman von Abbas
źródło
14
+1 - To najlepsze i najczystsze rozwiązanie dla nowoczesnych przeglądarek, które pozwala również na wyśrodkowanie elementu. Komentarz warunkowy z position: absolutejest niezbędny dla <IE8.
uınbɐɥs
21
Określenie display: inline-blocknie dodaje żadnych marginesów. Ale CSS obsługuje białe znaki, które mają być wyświetlane między elementami wbudowanymi.
feeela
Wyjaśnij, dlaczego Twoje rozwiązanie display: table działa.
HelloWorldNoMore
2
blok inline uniemożliwia pozycjonowanie elementu w jego obiekcie nadrzędnym (np. jeśli istnieje wyrównanie tekstu: środek nie da się go przykleić do lewej) display: table is perfect :)
FlorianB
1
To jest position: absolute
właściwa
90

Możesz spróbować fit-content(CSS3):

div {
  width: fit-content; 
  /* To adjust the height as well */ 
  height: fit-content;
}
Vitalii Fedorenko
źródło
1
@BartlomiejSkwira Każdy zastępca pracujący w IE lub Eclipse? inne rozwiązanie, ponieważ blok wbudowany nie działa dla mnie .. \
DAVIDBALAS1
8
Ma to zbyt duży sens, oczywiście, że nie ma wsparcia.
Sava B.
86

Dla mnie działa:

display: table;

w div. (Testowany na Firefox i Google Chrome ).

Sony Santos
źródło
4
Tak, szczególnie jeśli potrzebujesz wyśrodkować z marginesem: auto. Ten blok wewnętrzny nie jest rozwiązaniem.
Zsolt Szatmari
1
Pamiętaj również, że jeśli chcesz, aby wypełnienie działało w tym elemencie, musisz ustawić border-collapse: separate;styl. Jest to domyślne w wielu przeglądarkach, ale często frameworki css, takie jak bootstrap, resetują wartość do collapse.
Ruslan Stelmachenko
Testowany na MSIE 6 na telefonie z systemem Windows Mobile 6.5 wyprodukowanym w 2009 roku: z wdziękiem obniża się do pełnej szerokości div (co raczej nie jest problemem na telefonie). Jeśli ktoś używa wersji Internet Explorera mniejszej niż 8 na komputerze, korzysta z nieobsługiwanego systemu operacyjnego (IE6 był dostarczany z XP, IE7 z Vista); Przekierowałbym ich na stronę z informacją, aby zaktualizowali system do GNU / Linux, jeśli chcą kontynuować bezpieczne korzystanie z Internetu na tym komputerze.
Silas S. Brown
85

Istnieją dwa lepsze rozwiązania

  1. display: inline-block;

    LUB

  2. display: table;

Z tych dwóch display:table;jest lepiej, ponieważ display: inline-block;dodaje dodatkowy margines.

Dla display:inline-block;można użyć metody ujemny margines, aby ustalić dodatkową przestrzeń

Shuvo Habib
źródło
2
Czy masz coś przeciwko wyjaśnieniu, dlaczego display:tablejest lepiej?
Nathaniel Ford
1
W przypadku wyświetlania: blok wbudowany, należy zastosować metodę ujemnego marginesu, aby naprawić dodatkowe odstępy.
Shuvo Habib,
8
@NathanielFord, display:tablepozostawia element w kontekście formatowania bloku, dzięki czemu można kontrolować jego pozycję z marginesami itp. Jak zwykle. display:-inline-*, z drugiej strony, umieszcza element w kontekście formatowania Inline, powodując, że przeglądarka tworzy wokół niego anonimowe opakowanie bloków, zawierające pole linii z odziedziczonymi ustawieniami czcionki / wysokości linii, i wstawia blok do tego pola linii (wyrównując domyślnie pionowo w stosunku do linii bazowej). Wymaga to więcej „magii”, a zatem potencjalnych niespodzianek.
Ilya Streltsyn,
43

Nie wiedząc w jakim kontekście to pojawi się, ale wierzę, że właściwość CSS stylu floatalbo leftczy rightbędzie miał ten efekt. Z drugiej strony będzie miał również inne skutki uboczne, takie jak narzucanie tekstu.

Jeśli jednak się mylę, popraw mnie, nie jestem w 100% pewien i obecnie nie mogę tego samodzielnie przetestować.

falstro
źródło
1
Tak, w CSS 2.1. (CSS2.0 sprawi, że liczba zmiennoprzecinkowa będzie pełna, ale tak naprawdę robi to tylko IE5 / Mac). Tabele i zmiennoprzecinkowe są jedynymi typami wyświetlania, które mogą się kurczyć, aby dopasować ich zawartość.
Bobin
41

Odpowiedź na twoje pytanie leży w przyszłości, mój przyjacielu ...

mianowicie „intrinsic” nadchodzi z najnowszą aktualizacją CSS3

width: intrinsic;

niestety IE jest opóźniony, więc jeszcze go nie obsługuje

Więcej informacji na ten temat: CSS Intrinsic & Extrinsic Sizing Module Level 3 and Can I Use? : Wymiarowanie wewnętrzne i zewnętrzne .

Na razie musisz być zadowolony <span>lub <div>ustawiony na

display: inline-block;
trojański
źródło
12
intrinsicponieważ wartość jest niestandardowa. Tak naprawdę jest width: max-content. Zobacz stronę MDN na tym lub już połączonym projekcie.
maryisdead
34

Rozwiązaniem kompatybilnym z CSS2 jest użycie:

.my-div
{
    min-width: 100px;
}

Możesz również unosić swój div, który zmusi go do jak najmniejszego, ale musisz użyć poprawki, jeśli coś w twoim div się unosi:

.my-div
{
    float: left;
}
Soviut
źródło
3
Powinno. Z jakiego typu dokumentów korzystasz?
Soviut
34
width:1px;
white-space: nowrap;

działa dobrze dla mnie :)

Daft Wullie
źródło
Ale znowu moja sprawa była tekstem w div, a nie tabelą taką jak OP.
Rui Marques,
dla suwaka interfejsu użytkownika jquery jest to
mile widziane,
26

OK, w wielu przypadkach nawet nie musisz nic robić, jak domyślnie div ma heighti widthjako auto, ale jeśli to nie twoja sprawa, zastosowanie inline-blockwyświetlania będzie dla ciebie działać ... spójrz na kod, który dla ciebie stworzyłem i robi to czego szukasz:

div {
  display: inline-block;
}
<div>
  <table>
    <tr>
      <td>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi ultrices feugiat massa sed laoreet. Maecenas et magna egestas, facilisis purus quis, vestibulum nibh.</td>
      <td>Nunc auctor aliquam est ac viverra. Sed enim nisi, feugiat sed accumsan eu, convallis eget felis. Pellentesque consequat eu leo nec pharetra. Aenean interdum enim dapibus diam.</td>
      <td>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi ultrices feugiat massa sed laoreet. Maecenas et magna egestas, facilisis purus quis, vestibulum nibh.</td>
    </tr>
  </table>
</div>

Alireza
źródło
22

Zostało to wspomniane w komentarzach i trudno znaleźć w jednej z odpowiedzi, więc:

Jeśli używasz display: flexz jakiegokolwiek powodu, możesz zamiast tego użyć:

div {
    display: inline-flex;
}

Jest to również szeroko obsługiwane w różnych przeglądarkach.

youngrrrr
źródło
Właśnie tego potrzebowałem, gdy już display: flex;
używałem
19

Możesz to zrobić po prostu za pomocą display: inline;(lub white-space: nowrap;).

Mam nadzieję, że uznasz to za przydatne.

miksiii
źródło
18

Możesz używać inline-blockjako @ user473598, ale uważaj na starsze przeglądarki ..

/* Your're working with */
display: inline-block;

/* For IE 7 */
zoom: 1;
*display: inline;

/* For Mozilla Firefox < 3.0 */
display:-moz-inline-stack;

Mozilla w ogóle nie obsługuje wbudowanego bloku, ale ma -moz-inline-stackto mniej więcej to samo

Niektóre inline-blockatrybuty wyświetlania w różnych przeglądarkach : https://css-tricks.com/snippets/css/cross-browser-inline-block/

Niektóre testy z tym atrybutem można zobaczyć w: https://robertnyman.com/2010/02/24/css-display-inline-block-why-it-rocks-and-why-it-sucks/

RPichioli
źródło
1
O czym mówisz? Mozilla Firefox obsługuje inline-blockod 3.0 (2008). Źródło: developer.mozilla.org/en-US/docs/Web/CSS/…
Chazy Chaz
18

Po prostu umieść styl w swoim pliku CSS

div { 
    width: fit-content; 
}
Hamza
źródło
1
Nie sądzę, że jest to opcja obsługiwana przez różne przeglądarki.
David Rector,
2
Obecnie nie działa w Edge: caniuse.com/#search=fit-content
molsson
Możesz użyć -moz-fit-contentdla FF, prawdopodobnie inne prefiksy dostawców pozwolą na ich własne ...
Benj
1
Jest to to samo, co odpowiedź
Witalija
18
<table cellpadding="0" cellspacing="0" border="0">
    <tr>
        <td>
            <div id="content_lalala">
                this content inside the div being inside a table, needs no inline properties and the table is the one expanding to the content of this div =)
            </div>
        </td>
    </tr>
</table>

Wiem, że ludzie czasem nie lubią stołów, ale muszę wam powiedzieć, że próbowałem hacków inline css, a oni trochę działali w niektórych divach, ale w innych nie, więc naprawdę łatwiej było dołączyć rozszerzającą się div w tabela ... i ... może mieć właściwość inline lub nie, a mimo to tabela może pomieścić całkowitą szerokość zawartości. =)

Edward
źródło
2
To nie jest „właściwy” sposób, ale IE6 / 7/8 często po prostu nie działają dobrze, gdy sprawy stają się nieco skomplikowane, więc całkowicie rozumiem, dlaczego zrobiłbyś to w ten sposób. Masz mój głos.
Craigo
Zrobiłbym to, ale muszę otaczać każde pole wejściowe, więc to dużo dodatkowego HTML.
NickSoft,
15

Działające demo jest tutaj

.floating-box {
    display:-moz-inline-stack;
    display: inline-block;

    width: fit-content; 
    height: fit-content;

    width: 150px;
    height: 75px;
    margin: 10px;
    border: 3px solid #73AD21;  
}
<h2>The Way is using inline-block</h2>

Supporting elements are also added in CSS.

<div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
   <div class="floating-box">Floating box</div>
</div>

Abrar Jahin
źródło
13

Moje rozwiązanie flexbox CSS3 w dwóch wariantach: jeden na górze zachowuje się jak rozpiętość, a ten na dole zachowuje się jak div, biorąc całą szerokość za pomocą opakowania. Ich klasy to odpowiednio „góra”, „dół” i „bottomwrapper”.

body {
    font-family: sans-serif;
}
.top {
    display: -webkit-inline-flex;
    display: inline-flex;
}
.top, .bottom {
    background-color: #3F3;
    border: 2px solid #FA6;
}
/* bottomwrapper will take the rest of the width */
.bottomwrapper {
    display: -webkit-flex;
    display: flex;
}
table {
    border-collapse: collapse;
}
table, th, td {
    width: 280px;
    border: 1px solid #666;
}
th {
    background-color: #282;
    color: #FFF;
}
td {
    color: #444;
}
th, td {
    padding: 0 4px 0 4px;
}
Is this
<div class="top">
	<table>
        <tr>
            <th>OS</th>
            <th>Version</th> 
        </tr>
        <tr>
            <td>OpenBSD</td>
            <td>5.7</td> 
        </tr>
        <tr>
            <td>Windows</td>
            <td>Please upgrade to 10!</td> 
        </tr>
    </table>
</div>
what you are looking for?
<br>
Or may be...
<div class="bottomwrapper">
    <div class="bottom">
    	<table>
            <tr>
                <th>OS</th>
                <th>Version</th> 
            </tr>
            <tr>
                <td>OpenBSD</td>
                <td>5.7</td> 
            </tr>
            <tr>
                <td>Windows</td>
                <td>Please upgrade to 10!</td> 
            </tr>
        </table>
    </div>
</div>
this is what you are looking for.

Lloyd Dominic
źródło
hołd dla display: inline-flex;. BTW działa to bez prefiksu dla Chrome 62, Firefox 57 i Safari 11
Horacio
12
<div class="parentDiv" style="display:inline-block">
    // HTML elements
</div>

Spowoduje to, że nadrzędna szerokość div będzie taka sama jak największa szerokość elementu.

Jaimin Dave
źródło
Czy istnieje sposób, aby zastosować to tylko do rozmiaru pionowego, aby zminimalizować i utrzymać poziomą dużą wielkość?
Gobliiny
12

Spróbować display: inline-block;. Aby był kompatybilny z wieloma przeglądarkami, użyj poniższego kodu css.

div {
  display: inline-block;
  display:-moz-inline-stack;
  zoom:1;
  *display:inline;
  border-style: solid;
  border-color: #0000ff;
}
<div>
  <table>
    <tr>
      <td>Column1</td>
      <td>Column2</td>
      <td>Column3</td>
    </tr>
  </table>
</div>

James
źródło
11

Manipulując przy Firebug, znalazłem wartość właściwości, -moz-fit-contentktóra dokładnie robi to, czego chciał OP, i może być używana następująco:

width: -moz-fit-content;

Chociaż działa tylko w przeglądarce Firefox, nie mogłem znaleźć odpowiednika dla innych przeglądarek, takich jak Chrome.

Hamed Momeni
źródło
Od stycznia 2017 r. IE (wszystkie wersje, Edge i mobile w zestawie) i Opera Mini nie obsługują fit-content. Firefox obsługuje tylko szerokość. Inne przeglądarki dobrze to obsługują.
Gavin
11

Możesz wypróbować ten kod. Postępuj zgodnie z kodem w sekcji CSS.

div {
  display: inline-block;
  padding: 2vw;
  background-color: green;
}

table {
  width: 70vw;
  background-color: white;
}
<div>
    <table border="colapsed">
      <tr>
        <td>Apple</td>
        <td>Banana</td>
        <td>Strawberry</td>
      </tr>
      <tr>
        <td>Apple</td>
        <td>Banana</td>
        <td>Strawberry</td>
      </tr>
      <tr>
        <td>Apple</td>
        <td>Banana</td>
        <td>Strawberry</td>
      </tr>

    </table>
</div>

Showrin Barua
źródło
7

Rozwiązałem podobny problem (gdzie nie chciałem używać, display: inline-blockponieważ element był wyśrodkowany), dodając spanznacznik wewnątrz divznacznika i przenosząc formatowanie CSS z zewnętrznego divznacznika na nowy spanznacznik wewnętrzny . Po prostu rzucenie tego jako kolejny alternatywny pomysł, jeśli display: inline blocknie jest dla ciebie odpowiednią odpowiedzią.

Jessica Brown
źródło
7

Możemy użyć jednego z dwóch sposobów na divelemencie:

display: table;

lub,

display: inline-block; 

Wolę używać display: table;, ponieważ sam obsługuje wszystkie dodatkowe miejsca. Podczas gdy display: inline-blockwymaga dodatkowego mocowania przestrzeni.

Nowicjusz
źródło
6
div{
  width:auto;
  height:auto;
}
Ajchandu
źródło
To nie zadziała, jeśli div zawiera elementy inline (lub inline-block) i mają one inny rozmiar czcionki i wysokość linii niż sam div.
cytuje Br
5

Jeśli masz linie podziału kontenerów, po godzinach szukając dobrego rozwiązania CSS i nie znajdując żadnego, używam teraz jQuery:

$('button').click(function(){

  $('nav ul').each(function(){
    
    $parent = $(this).parent();
    
    $parent.width( $(this).width() );
    
  });
});
nav {
  display: inline-block;
  text-align: left; /* doesn't do anything, unlike some might guess */
}
ul {
  display: inline;
}

/* needed style */
ul {
  padding: 0;
}
body {
  width: 420px;
}

/* just style */
body {
  background: #ddd;
  margin: 1em auto;
}
button {
  display: block;
}
nav {
  background: #bbb;
  margin: 1rem auto;
  padding: 0.5rem;
}
li {
  display: inline-block;
  width: 40px;
  height: 20px;
  border: solid thin #777;
  margin: 4px;
  background: #999;
  text-align: center;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>

<button>fix</button>

<nav>
  <ul>
    <li>3</li>
    <li>.</li>
    <li>1</li>
    <li>4</li>
  </ul>
</nav>

<nav>
  <ul>
    <li>3</li>
    <li>.</li>
    <li>1</li>
    <li>4</li>
    <li>1</li>
    <li>5</li>
    <li>9</li>
    <li>2</li>
    <li>6</li>
    <li>5</li>
    <li>3</li>
    <li>5</li>
  </ul>
</nav>

Cregox
źródło
Jest to widocznie zepsute we fragmencie dla mnie w Chrome; ponowne kliknięcie przycisku naprawy powoduje uzyskanie innych wyników niż kliknięcie go po raz pierwszy.
Mark Amery
@ MarkAmery na moim komputerze Mac Właśnie wypróbowałem to na Chrome, Safari i Firefox i wszystko jest w porządku: brak widocznych błędów, nic na konsoli, spójne zachowanie. może to coś z oknami ...
cregox
5

Zmieniono (działa, jeśli masz wiele dzieci): Możesz użyć jQuery (spójrz na link JSFiddle)

var d= $('div');
var w;


d.children().each(function(){
 w = w + $(this).outerWidth();
 d.css('width', w + 'px')
});

Nie zapomnij dołączyć jQuery ...

Zobacz JSfiddle tutaj

Kowal
źródło
Jest to zepsute, jeśli twój div ma wiele dzieci; po prostu ustawia szerokość div na szerokość pierwszego dziecka.
Mark Amery
@ MarkAmery Przede wszystkim, zanim oddasz głos negatywny, przeczytaj uważnie pytanie, poprosili o jedno dziecko. Jeśli naprawdę jesteś ciekawy, jak to zrobić z wieloma dziećmi, zobacz poprawioną odpowiedź.
Bondsmith
4

Próbowałem div.classname{display:table-cell;}i zadziałało!

UnLoCo
źródło