Проблема (по вертикали) Центрирование текста в другом DIV с относительным значением%

Отказ от ответственности: Я не верю, что это дубликат, поскольку я использую относительные размеры для создания полноэкранной сетки без использования px.

Проблема: В этом jsFiddle http://jsfiddle.net/X3ZDy/73/ У меня есть четыре одинаково распределенных поля. Они предназначены для охвата ширины экрана и остаются квадратными. Внутри них находятся некоторые образцы квадратов DIV (40% x 40%). Однако я пытаюсь получить текстовую метку lbl по горизонтали и по вертикали в пределах bbl.

Все примеры, которые я видел (и пытались), не работают, поскольку они требуют, чтобы я знал высоту своего ярлыка, или они использовали трюки table-layout с ограниченным доступом. Мне нужно сделать это со всеми относительными размерами по скрипту.

Может ли кто-нибудь помочь? Мне нужно, чтобы это работало во всех браузерах с помощью чистого CSS (без JS) решения. Я удивлен, что кажется довольно сложным для вертикального выравнивания текста в div. Я не возражаю, если мы используем блок или встроенные элементы в качестве текстовой метки.

Обратите внимание, что я НЕ ищу решение TABLE, это головоломка DIV и CSS, которая требует рабочего jsFiddle.

Больше: Спасибо всем за ваши ответы, но для будущих плакатов обратите внимание, что (ширина == padding-bottom) - это волшебство, которое позволяет моим DIVs квадратным. Это ключ к системе компоновки сетки, поэтому мне нужно это поддерживать.

обновляется Это довольно сложно работать с относительными размерами и фиксированными высотами, но я думаю, что наконец нашел ответ на проблему (ниже).

Ответ 1

Я думаю, что наконец нашел ответ на проблему, которая работает. Проблема в том, что почти все другие решения, которые я видел, не могут справиться, когда размер ребенка изменяется, и ни одна из высот не известна. Я нуждался в этом, чтобы работать на отзывчивый дизайн всех%, где нигде нет фиксированных высот.

Я наткнулся на этот ответ SO Выровнять по вертикали с помощью CSS 3, который был моим вдохновением.

vertically centered text

Во-первых, используя конструкцию all%, вам нужен элемент обертки с нулевой высотой, чтобы выступать в качестве позиционирования в родительском элементе;

<body>
<div class="container">
    <div class="divWrapper">
        <div class="tx">This text will center align no matter how many lines there are</div>
    </div>
</div>
</body>

My Container в этом случае представляет собой простую коробчатую плитку;

.container
{
    margin:2%;
    background-color:#888888;
    width:30%;
    padding-bottom:30%; /* relative size and position on page  */
    float: left;
    position:relative;  /* coord system stop */
    top: 0px; /* IE? */
}

Так что ничего особенного в этом, кроме того, что у него нет высоты, что делает эту общую проблему центрирующих элементов сложной. Он должен быть абсолютно позиционирован таким образом, чтобы мы могли использовать координаты позиционирования в дочерних элементах (я думаю, для этого может потребоваться "верх" в IE).

Далее, обертка, которая абсолютно позиционируется, чтобы точно наложить родительский элемент и полностью заполнить его.

.divWrapper
{
     position:absolute;
     top:0px;
     padding-top:50%; /* center the top of child elements vetically */
     padding-bottom:50%;
     height:0px;
}

Прокладка означает, что любые дочерние элементы будут начинаться точно в середине родительского элемента, но сама оболочка не имеет высоты и не занимает места на странице.

Пока ничего нового.

Наконец, дочерний элемент, который мы хотим центрировать. Хитрость здесь заключалась в том, чтобы дочерний элемент скользил вертикально на основе собственной высоты. Вы не можете использовать 50%, потому что 50% родительского контейнера не являются самим собой. Обманчиво простой ответ заключается в использовании преобразования. Я не могу поверить, что раньше не заметил этого;

.tx
{               
    position: relative;
    background-color: transparent;
    text-align: center; /* horizontal centering */

    -webkit-transform: translateY(-50%); /* child now centers itself relative to the  midline based on own contents */
    -moz-transform: translateY(-50%);
    -ms-transform: translateY(-50%);
    -ms-filter: 'progid:DXImageTransform.Microsoft.Matrix(M11=0.5, M12=0, M21=0, M22=0.5,  SizingMethod="auto expand")'; /*IE8 */
    filter: progid:DXImageTransform.Microsoft.Matrix(M11=0.5, M12=0, M21=0, M22=0.5,  SizingMethod='auto expand'); /*IE6, IE7*/
    transform: translateY(-50%);    
}

Здесь Fiddle

Однако я не тестировал это на IE6 +, поэтому, если кто-то захочет проверить мое преобразование матрицы, я был бы признателен.

Обновление

Оказывается, оболочка даже не нужна. Это все, что вам нужно, чтобы правильно вертикально центрировать;

.tx
{       
    width:100%;        // +1 to @RonM
    position: absolute;
    text-align: center;
    padding-top:100%;
    -webkit-transform: translateY(-50%); /* child now centers itself relative to the midline based on own contents */
    -moz-transform: translateY(-50%);
    -ms-transform: translateY(-50%);
    -o-transform: translateY(-50%);
    -ms-filter: 'progid:DXImageTransform.Microsoft.Matrix(Dx=0,Dy=0)'; /*IE8 */
    filter: progid:DXImageTransform.Microsoft.Matrix(Dx=0,Dy=0); /*IE6, IE7*/
    transform: translateY(-50%);    
}

И обновленный Fiddle

Но все еще не работает в IE6 - глядя на эти преобразования, я не думаю, что это можно сделать для этого наследия без JavaScript.

Ответ 2

Не злоупотребляйте собой; пусть IE7 пойдет...:) (Согласно this, это не очень многие люди используют.)

Я сделал это с двумя подходами: один использует display: table, а другой использует line-height. К сожалению, у меня нет доступа к ПК, поэтому они протестированы только в браузерах Chrome 25.0.1365.1, FF 18 и Safari 6.0 на Mac 10.8.1, iOS 6.0.1 Safari и iOS Simulator 5.0 и 5.1 Safari,

В подходе display: table есть проблемы с iOS Simulator 5.0 и 5.1, текст не очень центрирован по вертикали.

Согласно quirksmode, метод display:table должен быть совместим с IE8 и выше. Теоретически, метод line-height может быть совместим с IE 6/7.

Чтобы создать центрированный квадрат в каждом квадрате, я установил .box6 в position: relative и изменил стиль .bc на:

.bc  {
    position:absolute;
    top: 30%;
    bottom: 30%;
    left: 30%;
    right: 30%;
    overflow: hidden;
}

Каждый подход создает очень высокий контейнер со статической высотой внутри элемента .bc. Точное значение для статической высоты произвольно, оно просто должно быть выше, чем содержание, которое будет содержать.

Метод display: table изменяет стили .bbl и .bbl .lbl на:

.bbl {
  display: table;
  height: 500px;
  padding-top: 50%;
  margin-top: -250px;
  background-color: blanchedalmond;
  width: 100%;
}

.bbl .lbl {
  display: table-cell;
  vertical-align: middle;
  text-align:center;
}

Для метода line-height HTML:

<div class="bc">
    <div id="line-h-outter">
        <span id="line-h-inner">a lot more text than in the other blob. The quick brown fox jumped over the lazy dog</span>
    </div>
</div>

CSS

#line-h-outter {
  line-height: 500px;
  vertical-align: middle;
  margin-top: -250px;
  padding-top: 50%;
}

#line-h-inner {
  display: inline-block;
  line-height: normal;
  vertical-align: middle;
  text-align: center;
  width: 100%;
}

http://jsfiddle.net/X3ZDy/93/

Ответ 3

Реальность такова, что единственными тегами в HTML, которые имеют собственное вертикальное выравнивание жидкости, являются ячейки таблицы.

У CSS нет ничего, что могло бы получить то, что вы хотите. Не сегодня.

Если требования: 1. Работает с каждым браузером 2. высота жидкости 3. вертикальное центрирование 4. Отсутствие скриптов 5. Нет ТАБЛИЦ 6. Вы хотите решение сегодня, а не через несколько лет.

Осталось 1 вариант: 1. Снимите ОДИН из ваших требований.

В противном случае эта "головоломка" не может быть завершена. И это единственный полный приемлемый ответ на ваш запрос.

... если бы я мог получить все зарплаты за потраченные часы по этой конкретной проблеме:)

Ответ 4

Название должно быть Центрирование в неизвестном; -)

Я обновил ваш пример, используя таблицы: http://jsfiddle.net/uWtqY/, и текст выравнивается внутри поля, которое вы описали с помощью таблиц, но вы не хочу это.

Добавлена ​​таблица с подобным:

<table width="100%" height="100%"><tr><td>One line</td></tr> </table></div>

внутри <div class="lbl">

Просто для поддержки кросс-браузера.

ИЗМЕНИТЬ

После выполнения некоторых исследований действительно очень сложно v-выровнять элемент внутри процентов. Пробовал много всего, но ваш код я не уверен, соответствует ли он дизайну всех из них. Хорошо, что я имею в виду, другими словами, вам сначала нужно построить вертикальное выравнивание, а затем попытаться сыграть с процентами. Из моего опыта в этой области я узнал, что хороший подход начинается с разработки внутренних элементов, а затем выходит, если сложность возрастает. Таким образом, процентное соотношение во всем может оказаться не лучшей реализацией (а не при приеме на мобильные устройства).

РЕДАКТИРОВАТЬ 2

После консолидации с несколькими моими партнерами по работе и действительно выродками в области HTML ответ был ясен. Либо вы поддерживаете < IE7, и вы делаете это с помощью табличных или призрачных элементов или интервалов, либо вы используете все текуники, которые описаны в нескольких сообщениях, и вы можете иметь поддержку для >= IE7. Другой вариант - использовать определенную структуру для каждого браузера.

Ссылка, которая, я думаю, объясняет это как есть и имеет хороший заголовок (в основном то, что вам нужно):

- > Центрирование в неизвестном

Надеюсь, что самое лучшее.

PS. Ссылки для справки:

Сообщите мне, если это поможет

Ответ 5

Я обновил css, чтобы использовать класс "spacer". Он помещается перед вашим "bc" div и внутри цветных ящиков. Это дало мне эффект, который, я думаю, вы просили.

html:
<div class="rgCol boxCol box6" style="background-color:lightgray">
        <div class="spacer"></div>
        <div class="bc">


css
.spacer {width:100%;padding-bottom:30%;display:block; }

Я набрал прокладку на 30%, а затем переместил абсолютную левую позицию вашего "bbl" div до 30% (от 2%). Бландесделемоны сохраняют форму и размер.

http://jsfiddle.net/X3ZDy/37/

Ответ 6

Хорошо, я отредактировал ваш код, пожалуйста, посетите обновленную ссылку

Я уверен, что это то, что вы ищете

Ответ 7

Сегодня я столкнулся с подобной проблемой - как с вертикальным, так и с горизонтальным центром дочернего элемента квадратных divs, которые имеют предварительно установленную ширину (они сделаны sqare с использованием техники прокладки). Я должен был использовать его для изображений, сохраняя пропорции, но изменение дочернего элемента в любой целевой элемент было бы простым.

В этой ситуации не подходит линия-высота, поле margin/padding или display: table-cell. Но есть решение с использованием margin: auto.

HTML:

<div class="squareContainer>
    <div class="contentWrapper">
        <img class="imagePreview" alt="Image preview" src="//URL.jpg">
    </div>
</div>

CSS

div.squareContainer {
    position: relative;
    box-sizing: border-box;
    height: 0;
    padding-bottom: 25%;
    width: 25%;
}
div.contentWrapper {
    position: absolute;
    bottom: 0;
    left: 0;
    right: 0;
    top: 0;
}
img.imagePreview {
    display: block;
    position: absolute;
    bottom: 0;
    left: 0;
    right: 0;
    top: 0;
    margin: auto;  /* This is the important line */
    max-height: 90%;
    max-width: 90%;
}

Полезные ресурсы:

http://jsfiddle.net/mBBJM/1/

http://codepen.io/HugoGiraudel/pen/ucKEC

Надеюсь, что это поможет!

Ответ 8

Вы можете решить это тривиально, без всякой странности (возможно, когда-нибудь они исправит модель блока CSS, но до тех пор):

<table>
<tr>
<td width="50" height="50" align="center" valign="middle">text</td>
</tr>
</table>

Вот и все. Выберите ширину и высоту, опустите его в div и назовите это хорошо.

Идея о том, чтобы никогда не использовать таблицы, является очень плохим ориентиром, чтобы быть самоуничительным.

Ответ 9

Вы имеете в виду это?

IMAGE

<div class="mycontainer">
  <div class="rgRow">
    <div class="rgCol" style="background-color:pink">
      <div class="boxCol">BOX1</div>
    </div>
    <div class="rgCol" style="background-color:lightgray">
      <div class="boxCol">
        <div class="boxLabel">a lot more text than in the other blob. The quick brown fox jumped over the lazy dog</div>
      </div>
    </div>
    <div class="rgCol" style="background-color:maroon">
      <div class="boxCol">
        <div class="boxLabel">One liner</div>
      </div>
    </div>
    <div class="rgCol" style="background-color:yellow">
      <div class="boxCol">BOX4</div>
    </div>
  </div>
</div>


.mycontainer
{
    background-color: #000000;
    display: inline-table;
}

.rgRow
{
    width: 100%;
    display: table-row;
}

.rgCol
{
    width: 25%;
    height: 100%;
    text-align: center;
    vertical-align: middle;
    display: table-cell;
}

.boxCol
{
    display: inline-block;
    width: 100%;
    text-align: center;
    vertical-align: middle;
}

.boxLabel
{
    text-align: center;
    vertical-align: middle;
    background-color: blanchedalmond;
    overflow: hidden;
    margin: 2%;
    width: 96%;
    height: 96%;
}