简体   繁体   中英

Fill remaining width inside parent that is also filling remaining width

I have a fixed-size navbar (using Bootstrap ) that contains four divs. These divs contain a logo, some links/dropdowns and a search box:

┌────────────────────────────navbar (fixed-size)──────────────────────────────┐
│┌───logo───┐┌───dropdown───┐┌───────────links──────────┐┌────search box─────┐│
││fixed-size││  fixed-size  ││      variable width      ││  fill remaining   ││
│└──────────┘└──────────────┘└──────────────────────────┘└───────────────────┘│
└─────────────────────────────────────────────────────────────────────────────┘

I want the search box (the box on the far right) to fill the remaining space in the container. The search box comprises an input and a button:

┌─────────────────────────────────┐
│┌─────────────────────┐┌────────┐│
││        <input>      ││<button>││
│└─────────────────────┘└────────┘│
└─────────────────────────────────┘

The button has a fixed size but I want the input to scale horizontally, stretching the search box to fill its parent (the nav-bar).

Edit: To clarify, I want the search box to take up the (horizontal) space left over from when it's siblings (logo, dropdown and links) have taken up their space. Since the search box is made out of an input and a button and the button will have a fixed width, I want the input to expand and push the search box's boundaries until the search box fills the space it's siblings left in the navbar

This is how I would do it: http://jsfiddle.net/vU52q/

You have your wrapper and child elements:

<div class="search">
    <input type="text" />
    <button type="submit">Go</button>
</div>

And you set the container to position: relative; and your submit button to position: absolute; and give the container enough padding for the button.

.search {
    box-sizing: border-box;
    background: #0f0;
    padding: 5px 100px 5px 5px;
    position: relative;
    width: 300px;
}
.search input {
    width: 100%;
}
.search button {
    position: absolute;
    top: 5px;
    right: 5px;
    width: 85px;
}

That way, the input is always the width of the parent element minus the width of the fixed width button.

You could also play with inline alignment and css calc , but this is my preferred way.

If you want to play with calc, you can check this out, and it might provide more of an option to add additional fixed size elements: http://jsfiddle.net/ug7a9/

This takes into account each section and explicitly adds it to the width calculation.

<div class="search">
    <button type="submit">Go</button><!--
    --><button type="submit">Go</button><!--
    --><input type="text" /><!--
    --><button type="submit">Go</button>
</div>

The comments are in there to prevent space in between elements (you can also do a font-size: 0) on the .search element.

* {
    box-sizing: border-box;
}
.search {
    background: #0f0;
    position: relative;
    width: 300px;
}
.search input {
    display: inline-block;
    width: calc(100% - 50px - 50px - 50px);
}
.search button {
    display: inline-block;
    width: 50px;
}

You'd want to be a bit more explicit with your selectors (ie don't do * ), but for quick demo purposes I put this in.

you can use the calc function but not is cross-browser

calc(100% - element size);

http://jsfiddle.net/8CQHP/

You can see the support in caniuse.com

I ended up changing my code and using the idea from the solution Chad provided in the comment to his answer. I also used his absolute-positioned button trick. This is what I did:

I used a span for the search box and moved the button out of the search box straight into the nav:

<nav>
    ...

    <span>
        <input type="text" placeholder="Search...">
    </span>
    <button class="searchBtn" type="button"></button>
</nav>

Using this css:

span {
    display: block;         /*This is the trick from*/
    overflow: hidden;       /*the solution Chad provided*/
}

input {
    width: 100%;
    padding-right: 65px;    /*This is to make room*/
}                           /*for the button*/

button {
    position: absolute;
    right: 0px;
    top: 0px;
}

overflow: hidden on the span makes it all possible. Read about it here: http://colinaarts.com/articles/the-magic-of-overflow-hidden/#making-room-for-floats

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM