Estou tentando centralizar os elementos internos de uma <button>
-tag com o do flexbox justify-content: center
. Mas o Safari não os centraliza. Posso aplicar o mesmo estilo a qualquer outra tag e funciona como planejado (consulte a <p>
-tag). Apenas o botão é alinhado à esquerda.
Experimente o Firefox ou o Chrome e você verá a diferença.
Há algum estilo de agente de usuário que devo substituir? Ou alguma outra solução para este problema?
div {
display: flex;
flex-direction: column;
width: 100%;
}
button, p {
display: flex;
flex-direction: row;
justify-content: center;
}
<div>
<button>
<span>Test</span>
<span>Test</span>
</button>
<p>
<span>Test</span>
<span>Test</span>
</p>
</div>
E um jsfiddle: http://jsfiddle.net/z3sfwtn2/2/
Respostas:
O problema
Em alguns navegadores, o
<button>
elemento não aceita alterações em seudisplay
valor, além de alternar entreblock
einline-block
. Isso significa que um<button>
elemento não pode ser um flex ou um contêiner de grade, ou<table>
também.Além dos
<button>
elementos, você pode descobrir que essa restrição se aplica a elementos<fieldset>
e<legend>
também.Veja os relatórios de bug abaixo para mais detalhes.
Nota: Embora eles não possam ser flex containers, os
<button>
elementos podem ser flex items.A solução
Existe uma solução alternativa simples e fácil em vários navegadores para esse problema:
Envolva o conteúdo de
button
em aspan
e façaspan
o flex container.HTML ajustado (
button
conteúdo empacotado em aspan
)<div> <button> <span><!-- using a div also works but is not valid HTML --> <span>Test</span> <span>Test</span> </span> </button> <p> <span>Test</span> <span>Test</span> </p> </div>
CSS ajustado (direcionado
span
)button > span, p { display: flex; flex-direction: row; justify-content: center; }
Demonstração Revisada
Referências / relatórios de bug
Flexbox em um
<button>
bloqueia o conteúdo, mas não estabelece um contexto de formatação flexívelAdicionar suporte para exibição: flex / grade e layout de conjunto de colunas dentro dos
<button>
elementosVeja também:
fonte
<button>
s, mas por que diabos não funciona para<fieldset>
também? Esse elemento não deveria ser considerado um elemento de nível de bloco regular válido para um flex container?div
não pode ser filho de abutton
porque, se você pensar nisso no HTML da velha escola, um elemento de nível de bloco não pode ser filho de um elemento de nível embutido. Mas hoje, com HTML5, a resposta tecnicamente correta é que umbutton
elemento só pode aceitar conteúdo de frase . Aspan
representa o conteúdo da frase , mas adiv
não. Adiv
representa o conteúdo do fluxo . Mais detalhesAqui está meu hack mais simples.
button::before, button::after { content: ''; flex: 1 0 auto; }
fonte
Iniciando o Chrome 83,
button
agora funciona comoinline-grid/grid/inline-flex/flex
, você pode ver mais sobre esse novo recurso aquiAqui está um snippet (para aqueles que usam o Chrome 83 e superior)
button { display: inline-flex; height: 2rem; align-items: flex-end; width: 4rem; -webkit-appearance: none; justify-content: flex-end; }
<!-- The align-items keyword should fail in Chrome 81 or earlier, but work in Chrome 83 or later. To see the error, the button needs styles that make it more of an extrinsic container. In other words, it needs a height or width set. --> <button>Hi</button> <input type="button" value="Hi">
fonte