¿Hay alguna manera de hacer que el ancho de un DIV secundario sea más ancho que el DIV primario usando CSS?

229

¿Hay alguna manera de tener un DIV secundario dentro de un DIV contenedor principal que sea más ancho que el primario? El DIV secundario debe tener el mismo ancho de la ventana gráfica del navegador.

Ver ejemplo a continuación: ingrese la descripción de la imagen aquí

El DIV hijo debe permanecer como hijo del padre div. Sé que puedo establecer márgenes negativos arbitrarios en el div hijo para hacerlo más ancho, pero no puedo encontrar la manera de hacerlo esencialmente al 100% del ancho del navegador.

Sé que puedo hacerlo:

.child-div{
    margin-left: -100px;
    margin-right: -100px;
}

Pero necesito que el niño tenga el mismo ancho que el navegador, que es dinámico.

Actualizar

Gracias por sus respuestas, parece que la respuesta más cercana hasta ahora es hacer que la posición DIV secundaria sea absoluta y establecer las propiedades izquierda y derecha en 0.

El siguiente problema que tengo es que el padre tiene position: relative, lo que significa que las propiedades izquierda y derecha siguen siendo relativas al padre div y no al navegador, vea el ejemplo aquí: jsfiddle.net/v2Tja/2

No puedo eliminar la posición relativa del padre sin arruinar todo lo demás.

Camsoft
fuente
Sus requisitos realmente no tienen sentido. El "div hijo" debe permanecer como hijo del div padre, y sin embargo, el div padre tiene position: relative? ¿Para qué necesitas position: relative? Supongo que lo que pregunto es: ¿qué intentas hacer?
thirtydot
@Camsoft ¿Viste mi comentario en mi respuesta? Que funciona para mí, Compruebe también mi página web edocuments.co.uk el que hace lo que usted está tratando de hacer de una manera diferente
Blowsie
1
@Camsoft además, realmente no debería haber necesidad de jquery / js en su solución
Blowsie

Respuestas:

112

Usar posicionamiento absoluto

.child-div {
    position:absolute;
    left:0;
    right:0;
}
Blowsie
fuente
14
Ok, siguiente pregunta, ¿qué pasa
Camsoft
¿qué tal otro div padre siendo posición: estática, y otro div dentro con posición: relativa? jsfiddle.net/blowsie/v2Tja/3
Blowsie
10
¿hay alguna manera de hacer esto, con la altura automática de .child-div y todavía tiene la ubicación correcta a continuación?
Philippe Gilbert el
2
y no establezca el div padre "overflow: hidden" ^^
Chris
@Blowsie, ¿qué tal position:fixed ? ¿Por qué no funciona correctamente?
Mostafa Ghadimi
227

Aquí hay una solución genérica que mantiene el elemento hijo en el flujo de documentos:

.child {
  width: 100vw;
  position: relative;
  left: calc(-50vw + 50%);
}

Establecemos el widthelemento secundario para llenar todo el ancho de la ventana gráfica, luego hacemos que coincida con el borde de la pantalla moviéndolo a leftuna distancia de la mitad de la ventana gráfica, menos el 50% del ancho del elemento principal.

Manifestación:

* {
  box-sizing: border-box;
}

body {
  margin: 0;
  overflow-x: hidden;
}

.parent {
  max-width: 400px;
  margin: 0 auto;
  padding: 1rem;
  position: relative;
  background-color: darkgrey;
}

.child {
  width: 100vw;
  position: relative;
  left: calc(-50vw + 50%);

  height: 100px;
  border: 3px solid red;
  background-color: lightgrey;
}
<div class="parent">
  Pre
  <div class="child">Child</div>
  Post
</div>

El soporte del navegador para vw y para calc () generalmente se puede ver como IE9 y más reciente.

Nota: Esto supone que el modelo de caja está configurado en border-box. Sin esto border-box, también tendrías que restar los rellenos y bordes, haciendo que esta solución sea un desastre.

Nota: Se recomienda ocultar el desbordamiento horizontal de su contenedor de desplazamiento, ya que ciertos navegadores pueden optar por mostrar una barra de desplazamiento horizontal a pesar de que no haya desbordamiento.

Nils Kaspersson
fuente
44
¿Qué sabes? De hecho, funciona en IE9. +1 Niza
CatShoes
13
Esto era exactamente lo que estaba buscando, muchas gracias. OMI, esta es una mejor respuesta que la aceptada, ya que esta no interrumpe el flujo de documentos
Rémi
18
vw no es bueno. Si tiene una barra de desplazamiento vertical, 100vw le dará una barra de desplazamiento horizontal.
Soleado
2
Parece que esto solo funciona un nivel más abajo. ¿Hay alguna manera de que funcione independientemente de cuántos elementos primarios tenga un elemento secundario?
mythofechelon
3
¡Esta es la respuesta correcta para envolver un elemento hijo más amplio en un position: relativepadre!
Hanfei Sun
14

He buscado por todas partes una solución a este problema durante mucho tiempo. Idealmente, queremos que el hijo sea más grande que el padre, pero sin conocer de antemano las limitaciones del padre.

Y finalmente encontré una brillante respuesta genérica aquí . Copiándolo literalmente:

La idea aquí es: empujar el contenedor hasta el centro exacto de la ventana del navegador con la izquierda: 50% ;, luego jalarlo hacia el borde izquierdo con un margen negativo de -50vw.

.child-div {
  width: 100vw;
  position: relative;
  left: 50%;
  right: 50%;
  margin-left: -50vw;
  margin-right: -50vw;
}
dangom
fuente
1
Descubrí que si quiero que sea, digamos, el 90% del ancho de la ventana gráfica, puedo usar lo anterior pero establecer el ancho en 90vw. Además, parece que margin-rightno tiene ningún efecto en ningún caso.
Jason Dufair
Tuve que cambiar los valores de margen izquierdo y derecho porque mi contenedor es el 80% del ancho de la ventana gráfica. Entonces, en mi caso, tenía que ser margin-left: -10vw y margin-right: -10vw y ¡funcionó perfectamente! ¡Gracias!
Timotheus Triebl
1
Esta fue una respuesta brillante! Gracias.
cullanrocks
7

Basado en su sugerencia original (configuración de márgenes negativos), he intentado encontrar un método similar usando unidades de porcentaje para el ancho dinámico del navegador:

HTML

<div class="grandparent">
    <div class="parent">
        <div class="child">
            <p>Lorem ipsum dolor sit amet, consectetur adipisicing elit. Dolore neque repellat ipsum natus magni soluta explicabo architecto, molestias laboriosam rerum. Tempore eos labore temporibus alias necessitatibus illum enim, est harum perspiciatis, sit, totam earum corrupti placeat architecto aut minus dignissimos mollitia asperiores sint ea. Libero hic laudantium, ipsam nostrum earum distinctio. Cum expedita, ratione, accusamus dicta similique distinctio est dolore assumenda soluta dolorem quisquam ex possimus aliquid provident quo? Enim tempora quo cupiditate eveniet aperiam.</p>
        </div>
    </div>
</div>

CSS:

.child-div{
   margin: 0 -100%;
   padding: 0 -100%;
}

.parent {
    width: 60%;
    background-color: red;
    margin: 0 auto;
    padding: 50px;
    position:relative;
}

.grandparent {
        overflow-x:hidden;
        background-color: blue;
        width: 100%;
        position:relative;
    }

Los márgenes negativos permitirán que el contenido fluya fuera de la DIV principal. Por lo tanto, configuré padding: 0 100%;para que el contenido vuelva a los límites originales del Chlid DIV.

Los márgenes negativos también harán que el ancho total de .child-div se expanda fuera de la ventana del navegador, lo que resulta en un desplazamiento horizontal. Por lo tanto, debemos recortar el ancho de extrusión aplicando un overflow-x: hiddena un DIV de abuelo (que es el padre de la División de padres):

Aquí está el JSfiddle

Había intentado con Nils Kaspersson left: calc(-50vw + 50%); funcionó perfectamente bien en Chrome y FF (aún no estoy seguro sobre IE) hasta que descubrí que los navegadores Safari no lo hacen correctamente. Espero que hayan solucionado esto pronto, ya que en realidad me gusta este método simple.

Esto también puede resolver su problema donde el elemento DIV principal debe ser position:relative

Los 2 inconvenientes de este método de solución alternativa son:

  • Requerir marcado adicional (es decir, un elemento abuelo (al igual que el método de alineación vertical de la buena tabla no es así ...)
  • El borde izquierdo y derecho del Child DIV nunca se mostrará, simplemente porque están fuera de la ventana del navegador.

Avíseme si hay algún problema con este método;). Espero eso ayude.

Austeroide
fuente
4

Flexbox se puede usar para hacer que un niño sea más ancho que su padre con tres líneas de CSS.

Solo el niño display, margin-lefty widthnecesita ser configurado. margin-leftDepende del niño width. La formula es:

margin-left: calc(-.5 * var(--child-width) + 50%);

Las variables CSS se pueden usar para evitar calcular manualmente el margen izquierdo.

Demo # 1: Cálculo manual

.parent {
  background-color: aqua;
  height: 50vh;
  margin-left: auto;
  margin-right: auto;
  width: 50vw;
}

.child {
  background-color: pink;
  display: flex;
}

.wide {
  margin-left: calc(-37.5vw + 50%);
  width: 75vw;
}

.full {
  margin-left: calc(-50vw + 50%);
  width: 100vw;
}
<div class="parent">
  <div>
    parent
  </div>
  <div class="child wide">
    75vw
  </div>
  <div class="child full">
    100vw
  </div>
</div>

Demostración n. ° 2: uso de variables CSS

.parent {
  background-color: aqua;
  height: 50vh;
  margin-left: auto;
  margin-right: auto;
  width: 50vw;
}

.child {
  background-color: pink;
  display: flex;
  margin-left: calc(-.5 * var(--child-width) + 50%);
  width: var(--child-width);
}

.wide {
  --child-width: 75vw;
}

.full {
  --child-width: 100vw;
}
<div class="parent">
  <div>
    parent
  </div>
  <div class="child wide">
    75vw
  </div>
  <div class="child full">
    100vw
  </div>
</div>

Markus
fuente
3

Usé esto:

HTML

<div class="container">
 <div class="parent">
  <div class="child">
   <div class="inner-container"></div>
  </div>
 </div>
</div>

CSS

.container {
  overflow-x: hidden;
}

.child {
  position: relative;
  width: 200%;
  left: -50%;
}

.inner-container{
  max-width: 1179px;
  margin:0 auto;
}
hsuastegui
fuente
1

Puedes probar posición: absoluta. y dar ancho y alto, arriba: 'eje y desde arriba' e izquierda: 'eje x'

Khurram Ijaz
fuente
1

Tuve un problema similar Se suponía que el contenido del elemento secundario debía permanecer en el elemento primario mientras que el fondo tenía que extender el ancho completo de la ventana gráfica.

Resolví este problema creando el elemento hijo position: relativey agregando un pseudo elemento ( :before) con él position: absolute; top: 0; bottom: 0; width: 4000px; left: -1000px;. El pseudo elemento permanece detrás del elemento secundario real como un pseudo elemento de fondo. Esto funciona en todos los navegadores (incluso IE8 + y Safari 6+, no tienen la posibilidad de probar versiones anteriores).

Pequeño ejemplo de violín: http://jsfiddle.net/vccv39j9/

Seika85
fuente
Esto parece funcionar, pero hace que el navegador muestre una barra de desplazamiento horizontal ya que el ancho es de 4000 px. ¿Cuál es la solución para mantener el pseudo elemento dentro del ancho de la ventana gráfica?
Aaron Hudon
Por supuesto, debe configurar el cuerpo o el div de ajuste de página overflow-x: hidden.
Seika85
1

Agregando a la solución de Nils Kaspersson, también estoy resolviendo el ancho de la barra de desplazamiento vertical. Estoy usando 16pxcomo ejemplo, que se resta del ancho del puerto de vista. Esto evitará que aparezca la barra de desplazamiento horizontal.

width: calc(100vw - 16px);
left: calc(-1 * (((100vw - 16px) - 100%) / 2));
Zona A
fuente
1
Creo 16pxque lo que necesita restar porque está causando que la barra de desplazamiento horizontal sea el margen / relleno predeterminado del navegador, en lugar de restarlo, solo use esto, por html, body{ margin:0; padding:0 }lo que no necesitará hacer cálculos adicionales para el16px
Mi-Creativity
Esto es cuando el contenido de la página es más largo y va debajo del doblez y la barra de desplazamiento aparece automáticamente. Por supuesto, cuando el contenido está dentro del pliegue, esto no es necesario. Agrego el 16px a la fórmula solo cuando sé que el contenido de la página será largo y la barra de desplazamiento aparecerá.
Zona A
Creo que no funcionará en dispositivos móviles. El móvil no tiene barra de desplazamiento.
hjchin
1

Suponiendo que el padre tiene un ancho fijo, por ejemplo, #page { width: 1000px; }y está centrado #page { margin: auto; }, desea que el niño se ajuste al ancho de la ventana del navegador que simplemente puede hacer:

#page {
    margin: auto;
    width: 1000px;
}

.fullwidth {
    margin-left: calc(500px - 50vw); /* 500px is half of the parent's 1000px */
    width: 100vw;
}
Nabil Kadimi
fuente
1

Para que el elemento secundario sea tan ancho como el contenido, intente esto:

.child{
    position:absolute;
    left:0;
    overflow:visible;
    white-space:nowrap;
}
Toki
fuente
0
.parent {
    margin:0 auto;
    width:700px;
    border:2px solid red;
}
.child {
    position:absolute;
    width:100%;
    border:2px solid blue;
    left:0;
    top:200px;
}
Sam
fuente
Inteligente, pero no parece funcionar (con tramos incrustados dentro de li, al menos).
ruffin
0

Sé que esto es viejo, pero para cualquiera que venga a esto por una respuesta, lo haría así:

Desbordamiento oculto en un elemento que contiene el elemento padre, como el cuerpo.

Dele a su elemento hijo un ancho mucho más ancho que su página y colóquelo a la izquierda absoluta en -100%.

Aquí hay un ejemplo:

body {
  overflow:hidden;
}

.parent{
  width: 960px;
  background-color: red;
  margin: 0 auto;
  position: relative;    
}

.child {
  height: 200px;
  position: absolute;
  left: -100%;
  width:9999999px;
}

También aquí hay un JS Fiddle: http://jsfiddle.net/v2Tja/288/

Tom Chinery
fuente
0

Entonces la solución será la siguiente.

HTML

<div class="parent">
    <div class="child"></div>
</div>

CSS

.parent{
        width: 960px;
        margin: auto;
        height: 100vh
    }
    .child{
        position: absolute;
        width: 100vw
    }
Himavan
fuente
Si bien este código puede responder la pregunta, proporcionar un contexto adicional con respecto a cómo y / o por qué resuelve el problema mejoraría el valor a largo plazo de la respuesta.
R Balasubramanian
0

Probé algunas de tus soluciones. Éste :

margin: 0px -100%;
padding: 0 100%;

es, con mucho, el mejor, ya que no necesitamos CSS adicional para pantallas más pequeñas. Hice un codePen para mostrar los resultados: utilicé un div padre con una imagen de fondo y un divon div con contenido interno.

https://codepen.io/yuyazz/pen/BaoqBBq

blogob
fuente