Add a div below inline-block wrapped row

2019-02-17 13:41发布

问题:

I have a list of inline-block elements that wrap to form several rows. I'd like to display a div element between on of the rows, depending on where a specific element is located. For example, the first few rows are numbered:

numbered inline-block elements http://i43.tinypic.com/2zxw9jt.jpg

If I wanted to target the third element and display a full length element (100% of the div containing the blocks), then it would look like this:

between first and second rows http://i39.tinypic.com/qsr51h.jpg

The position of the full-length div would be the same for any of the blocks 1-5. Or, if another block was targeted, like 7 or 8, it would look like:

between second and third rows http://i43.tinypic.com/j14lua.jpg

Notice how the rows are "shifted down". I understand how to do this with block-level elements, but not in between rows of wrapped inline-block elements. The rows that each of the numbered blocks would be on would change as the browser window width changes, and the full-length div would "know" which row to be positioned beneath.

How would someone go about placing the div below that particular row of elements? Is it possible with some kind of relative or absolute position with CSS? Could the row position change dynamically as the blocks are reordered with window width changes?

UPDATE: Here is a codepen that has the blocks and the inserted div. The div is styled to be absolutely positioned, and can be moved to the appropriate position by inserting it after the desired block element tag, but I still can't get the row beneath it to make room and slide down.

回答1:

Here's a different alternative:

http://jsfiddle.net/SYJaj/7/

There is no need to have the "banner" be absolutely positioned. Just give it display:inline-block; like everything else, and calculate which block it needs to follow with the offset method in jQuery.

The key is in this code:

function placeAfter($block) {
    $block.after($('#content'));
}

$('.wrapblock').click(function() {
    $('#content').css('display','inline-block');
    var top = $(this).offset().top;
    var $blocks = $(this).nextAll('.wrapblock');
    if ($blocks.length == 0) {
        placeAfter($(this));
        return false;
    }
    $blocks.each(function(i, j) {
        if($(this).offset().top != top) {
            placeAfter($(this).prev('.wrapblock'));
            return false;
        } else if ((i + 1) == $blocks.length) {
            placeAfter($(this));
            return false;
        }
    });
});

EDIT: Changed the stylesheet to look like yours.



回答2:

Challenge accepted. A CSS only solution:

http://codepen.io/mlhaufe/pen/aONRGP

HTML:

<div class="container">
    <label class="item">
        <input type="radio" name="rdo-visible">
        <span class="box">1</span>
        <span class="block">1. Lipsum Lipsum</span>
    </label>
    ...
</div>

CSS:

* {
    box-sizing: border-box;
}
.container {
    position: relative;
    outline: 1px solid green;
    width: 60%;
    margin:auto;
    font: 16pt sans-serif;
}
.item {
    position: static;
    display: inline-block;
    vertical-align: top;
    margin: 10px;
    width: 50px;
    overflow: visible;
}
[name=rdo-visible] {
    opacity: 0;
    position: absolute;
    top: 0;
    left: 0;
}
[name=rdo-visible]:checked ~ .box {
    margin-bottom: 2em;
}
[name=rdo-visible]:checked ~ .block {
    display: block;
    margin-top: -1.6em;
}
.box {
    display: block;
    cursor: pointer;
    width: 50px;
    height: 50px;
    background-color: red;
    color: white;
    line-height: 50px;
    text-align: center;
}
.block {
    display: none;
    position: absolute;
    left: 10px;
    right: 10px;
    height: 2em;
    line-height: 2em;
    background-color: blue;
    color: white;
}