html - CSS: Format Based on Number of Children Elements (bonus: eliminate extra white space) -
this question has answer here:
for project i'm working on, had wrap head around way format children of element based on how many exist within given element. example:
<nav> <ul> <!-- items here may vary //--> <li>option</li> <li>option</li> <li>option</li> </ul> </nav>
based on script i'm running, ul tag can have anywhere between 3 , 5 li elements within of varying size. however, in layout, these need have same width, , fit within block has fixed width. running issues in formatting rendered white space between li tags, if gave them proper width.
amount-based formatting
the solution came may not advanced other methods i've seen, including perform arithmetic calculations during render (to end, since there aren't calculations, may render marginally faster, that's beside point). however, strikes me more read, , purposes superior.
i reasoned combination of complex selectors employed specify elements wanted format. choices nth-child, nth-last-child, first-child, , last-child. initially, did nav>ul>li:nth-child(n):last-child selector, ran issues when trying select sibling elements. instead, decided select based on last child element.
nav>ul>li{ width: 100%; display: inline-block; /* if border, padding, or margin desirable aesthetically, separate element should put inside li element , formatted include */ margin: 0; padding: 0; border: 0; } nav>ul>li:nth-last-child(2):first-child, nav>ul>li:nth-last-child(2):first-child ~ li { width: 50%; } nav>ul>li:nth-last-child(3):first-child, nav>ul>li:nth-last-child(3):first-child ~ li { width: 33%; } nav>ul>li:nth-last-child(4):first-child, nav>ul>li:nth-last-child(4):first-child ~ li { width: 25%; } nav>ul>li:nth-last-child(5):first-child, nav>ul>li:nth-last-child(5):first-child ~ li { width: 20%; } /* repeat ad nauseum */
in method, first child of n siblings selected, , of siblings selected.
non-uniform formatting
with methodology, clever , change rules depending on how many siblings there are. example sets first , last li elements @ 20% width, , middle 1 @ 60% width (could layout purposes, , it's calculations hard-pressed accomplish in cases):
nav>ul>li:nth-last-child(3):first-child, nav>ul>li:nth-last-child(3):first-child ~ li:last-child { width: 20%; } nav>ul>li:nth-last-child(3):first-child ~ li:nth-child(2) { width: 60%; }
fixing white space problem
i'll have digging, because found solution here, , want give credits it's due, i'm having hard time tracking down (if moderator knew wanted edit in, i'd appreciative). basically, gist of problem inline-block elements rendered text, , elements have @ least 1 non-breaking space between them.
there 3 solutions i've seen, , each has advantages , disadvantages.
removing space
as described here, method removes space between elements. preferred method semantically, because relies least on formatting tomfoolery. drawback of method more complex elements in question, more obfuscated can become. in essence, code in question becomes this:
<nav> <ul> <!-- items here may vary //--> <li>option</li><li>option</li><li>option</li> </ul> </nav>
floating elements
as described here, method adds 2 simple css attributes li elements. first floats of elements left, setting them display in order, before rendered text, , sets them not try clear 1 another. major drawback 1 other floating elements may interact these elements, , floated elements tend misbehave more others (some browsers seem unsure of how handle floating elements, in legacy). rule be:
nav>ul>li { float: left; clear: none; }
hiding text
this answer i'm having hard time finding - needless say, not idea. is, however, solution employed situation. assuming don't want obfuscate code or float elements, css, still have control on how text renders (and must remember non-breaking space still text). in essence, we're shrinking text font-size 0. drawback here need make sure li elements (and children) have proper font size. means need 2 rules:
nav>ul { font-size: 0; } nav>ul>li { /* note, can change needed, don't delete it. */ font-size: initial; }
you may need write rule, depending on how control have on li element's contents:
nav>ul>li * { /* note, can change needed, don't delete it. */ font-size: initial; }
hope has been helpful! :d
Comments
Post a Comment