造型HTML< li>元素:避免无效的父< div> [英] Styling HTML <li> elements: avoiding an invalid parent <div>

查看:136
本文介绍了造型HTML< li>元素:避免无效的父< div>的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个网站,其中有多个页面的问题列表。



每个问题都由一个标签和一个输入组成。问题divs在一个额外的div内,提供分组和边界样式等。

问题:

我想对我的问题编号,但希望避免硬编码编号。但是,将< li> 放置在div或标签内是无效的。

另外, $ b

strong>有些问题div有条件隐藏,并根据用户输入显示。因此,divs提供了关键的功能,并且这些数字必须与这些div一起隐藏并显示出来(因此,在div之外定位每个< li> 会是有问题的。 p>

代码:



下面是我的表单的简化结构示例,显示两个问题块:

 < form id =myformmethod =postaction =/ destinaion / page.php> 
< div class =formfield>
< div class =page1>
< div class =lowerborder>
< div class =question>
< label for =q2>问题1< / label>
< input type =numberid =q1name =q1/>
< / div>

< div class =question>
< label for =q1>问题2< ; / label>
<输入type =numberid =q2name =q2/>
< / div>
< / div>
< / div>
< / div>
< / form>

div类表单域包含表单页面和page1页面的各种样式细节。 p>

我想从我的问题中列出一个有序列表,可能类似于

尝试实现goal:

 < form id =myformmethod =postaction =/ destination / page .PHP> 
< div class =formfield>
< ol>
< div class =page1>
< div class =lowerborder>
< div class =question>
< label for =q2>< li>问题1< / li>< / label>
< input type =numberid =q1name =q1/>
< / div>

< div class =question>
< label for =q1>< li>问题2< / li>< / label>
< input type =numberid =q2name =q2/>
< / div>
< / div>
< / div>
< / ol>
< / div>
< / form>

但是,您可以看到我将< li> < code>< label> 其中a)无效的html,以及b)在所有浏览器中播放不佳。
$ b

当我的列表项被多个嵌套div分隔时,如何避免将< li> 元素放入无效父项内?



jsFiddle: 我上面的尝试的一个小提琴。包括我试图实现的一些样式和功能(通过嵌套div创建样式,隐藏问题等等)

解决方案

请参阅<一个href =http://jsfiddle.net/xH95y/2/ =nofollow noreferrer>这个小提琴展示了如何在不插入任何其他元素的情况下做你想做的一切。我发现任何地方都不需要任何单独的div。



注意:我最初使用 float:left 使答案正确排列。但是,这导致IE只显示答案左侧的数字,而不是左侧的问题。我切换到使用 display:inline-block ,现在所有东西都可以在IE中使用。



评论: p>


  • 我清理了样式表,这些样式表有些部分重复且相互冲突。我删除了不必要的规则。

  • 我使用一个类创建了分隔问题组的线条,并且我还将它应用于问题的顶部边框,而不是底部,这样即使有隐藏的问题结束了一个组,也可以使用它,因为隐藏的问题可能永远不会开始组。在我看来,Reveal复选框的标签应该是它旁边的文本,所以您可以点击该文字来检查并取消选中该框。因此,我在问题中添加了一个问题类,而不是使用标签。您必须对问题应用样式问题以使其样式正确。您可以将其应用于标签元素(这是否适用于其他内容),也可以使用跨度或其他元素在不是标签的情况下包含文本。

  • 即使问题的样式为 vertical-align:top ,IE 7也会愚蠢地将数字放在行底。我现在不知道如何解决这个问题,但对于那些比我更擅长CSS专家的人来说,这可能是另一个问题。

  • 非常好地处理隐藏方法,占用额外的空间,然后在揭示不显示子元素时,所以我使用了绝对定位(通过将其从文档流中取出,具有相同的效果)。看看CSS是如何工作的。 我修改了应用揭示脚本的方式。而不是手动接线每个单独的项目,而是将数据值放在复选框本身上,然后在准备好的事件中使用它来适当地连接页面。现在,您可以使用复选框来显示更多问题,只需在显示的问题中添加一个id(或者如果您需要一次显示多个问题,则使用class)以及数据expando属性,如 data-togglehidden =l4指定要在复选框元素中右移的id。不需要改变脚本。 看起来有点像你可能会有div-itis,这是在所有地方都会增加div的倾向。不需要感到尴尬,当我刚接触html开发时,我也有过分歧。由于这样的经历,你会发展壮大。一般来说,您应该使用普通的非div页面元素并直接对其进行样式设置,而不是将事物封装在div中并对其进行样式设置。当您需要设置一组相关功能或提供不同元素的框时,Div可用。暗示你可能不适当地使用div,当他们只有一个单独的项目(尤其是另一个div)时。有时候这是必要的,但问问自己:我可以将样式移动到父元素还是子元素? 我需要更多地了解页面你提到的那些工作是你原来的html标记。这里 只有在打印html时,才会在html中显示页面。所以我不太清楚这意味着什么或如何为你设计网页风格。


这里是清洁的

 < form id =myformmethod = postaction =/ destination / page.php> 
< ol class =formfield>
< li>
< label class =questionfor =q1>您的名字是什么?< / label>
< input type =textid =q1name =q1/>
< / li>
< li>
< label class =questionfor =q2>一个很长的问题2,肯定会运行到第二行,只是为了证明这样的事情能够正常工作而不会弄乱布局,用你自己的话描述?< / label>
< input type =textid =q2name =q2/>
< / li>
< li class =begingroup>
< span class =question>你喜欢不必要地回答额外问题吗?< / span>
< input type =checkboxid =q3name =q3data-togglehidden =l4/>
< label for =q3>是,是的,就是我!!!< / label>
< / li>
< li id =l4class =hidden>
< label class =questionfor =q4>为什么你喜欢做额外的不必要的工作?< / label>
< input type =textid =q4name =q4/>
< / li>
< li class =begingroup>
< label class =questionfor =q5>您的第一只宠物的名字是什么?< / label>
< input type =textid =q5name =q5/>
< / li>
< / ol>
< / form>

下面是它在Firefox 16.0.2中的样子:



而在IE 7.0.5730.13CO中:



CSS:

  ol.formfield {
width:500px;
保证金:10px auto;
padding:16px 16px 16px 0;
border:5px groove#005E9B;
list-style:小数外部;
颜色:黑色;
背景颜色:#6Fc2F7;
font-family:'Oxygen',sans-serif;
font-size:15px;
}

ol.formfield li {
clear:both;
padding:2px;
margin-left:1.7em;
}

ol.formfield li.begingroup {
margin-top:8px;
padding-top:8px;
border-top:1px solid#005E9B;
}

.question {
display:inline-block;
width:300px;
vertical-align:top;
}

.hidden {
position:absolute;
height:0;
width:0;
overflow:hidden;
}

ol.formfield input {
border-radius:5px; / * css 3 * /
-moz-border-radius:5px; / * mozilla * /
-webkit-border-radius:5px; / * webkit * /
}

以及基于隐藏/显示的脚本 $ $('ol.formfield input :checkbox')
.each(function(){
var d = $(this).data('togglehidden');
if(d){
$(this ).on('change',function(){
if($(this).attr('checked')){
$('#'+ d)
.removeClass( 'hidden')
.find(':input')
.focus();
} else {
$('#'+ d).addClass('hidden' );
}
});
}
});


The situation:

I have a site with a long list of questions across multiple pages.

Each question is within a made up of a label and an input. Groups of question divs are within an additional div to provide grouping and bordering styles, etc.

The problem:

I want to number my questions, but want to avoid hard coding the numbering. However, it is invalid html to place the <li> inside the divs or labels.

In addition some question divs are conditionally hidden and revealed depending on user input. The divs therefore provide key functionality, and the number must be hidden and revealed along with these divs, (so positioning each <li> outside a divs would be problematic.

Code:

Here is an example of a pared down structure of my form, showing two question "blocks":

<form id="myform" method="post" action="/destinaion/page.php">
    <div class="formfield">
        <div class="page1">
            <div class="lowerborder">
                <div class="question">                      
                    <label for="q2">Question 1</label> 
                    <input type="number" id="q1" name="q1"/>
                </div>

                <div class="question">                      
                    <label for="q1">Question 2</label> 
                    <input type="number" id="q2" name="q2"/>
                </div>
            </div>
        </div>
    </div>
</form>

The div class form field contains the form page, and page1 various styling particulars for page 1.

I'd like to make an ordered list from my questions, perhaps something like

Attempt at achieving goal:

<form id="myform" method="post" action="/destination/page.php">
    <div class="formfield">
    <ol>
        <div class="page1">
            <div class="lowerborder">
                <div class="question">                      
                    <label for="q2"><li>Question 1</li></label> 
                    <input type="number" id="q1" name="q1"/>
                </div>

                <div class="question">                      
                    <label for="q1"><li>Question 2</li></label> 
                    <input type="number" id="q2" name="q2"/>
                </div>
            </div>
        </div>
    </ol>
    </div>
</form>

But as you can see I am putting the <li> inside the <label> which a) is not valid html, and b) doesn't play well with all browsers.

How can I avoid putting <li> elements inside invalid parents, when my list items are separated by many nested divs?

jsFiddle:

See a fiddle of my above attempt. Including some styling and functionality I am trying to achieve (styling via nested divs, hidden questions that reveal etc)

解决方案

Please see this fiddle demonstrating how to do everything you want without interposing any other elements. I found no need for even a single div anywhere.

Note: I initially used float:left for the question to make the answers line up properly. However, this caused IE to render the numbers just left of the answers instead of left of the questions. I switched to using display:inline-block and now everything works in IE as well.

Comments:

  • I cleaned up the style sheet, which had some sections repeated and conflicting style rules. I removed unnecessary rules.

  • I created the lines separating groups of questions using a class, and I also made it apply to the top border of a question rather than the bottom, so that you can use it even if there are hidden questions ending a group, since a hidden question would probably never begin a group. There was no need for additional elements to have borders.

  • In my opinion the label for the "Reveal" checkbox should be the text next to it, so that you can click that text to check and uncheck the box. Thus, I added a "question" class to the items that are the question, rather than using a label. You must apply the style "question" to the questions to make them style properly. You can apply that to a label element (which is for something else or not), or you can use a span or other element to contain the text when it is not a label.

  • IE 7 stupidly puts the numbers at the bottom of the line, even though the questions are styled with vertical-align:top. I don't know how to fix that at this time, but it could be another question to those more expert than I in CSS quirks.

  • IE was not handling the "hidden" method very well, taking up extra space and then when revealing not showing the child elements, so I used absolute positioning instead (which, by taking it out of the document flow, has the same effect). See the CSS for how it works.

  • I modified the way you were applying the reveal script. Instead of manually wiring up each individual item, instead I put a data value on the checkbox itself, then at the ready event I use that to wire up the page appropriately. Now you can have checkboxes that reveal more questions just by adding an id to the revealed question (or use class instead if you need to reveal more than one at a time) and a data expando attribute like data-togglehidden="l4" to specify the id to toggle right in the checkbox element. No script changes required.

  • It looks a little like you may have "div-itis" which is the tendency to multiply divs all over the place. No need to be embarrassed, I have had div-itis too, when I was new to html development. You'll grow out of it due to experiences like this. In general, you should use normal non-div page elements and style them directly, rather than wrap things in divs and styling those. Divs are useful when you need to style a group of related functionality or provide a box for different elements. One hint that you may be using divs improperly is when they only have a single item in them (especially another div). Sometimes that is necessary, but ask yourself: can I move the style to the parent or child element instead?

  • I need to know more about how the "pages" work that you mentioned and that were in your original html markup. There are no pages in html, only when html is printed. So I'm not quite sure what that means or how to style your pages for you.

Here is the cleaned-up html, without the need of additional elements between ol and li:

<form id="myform" method="post" action="/destination/page.php">
    <ol class="formfield">
        <li>
            <label class="question" for="q1">What is your first name?</label>
            <input type="text" id="q1" name="q1"/>
        </li>
        <li>
            <label class="question" for="q2">A very long question 2 that is sure to run to a second line just to prove that such a thing will work properly and not mess up the layout, described in your own words?</label>
            <input type="text" id="q2" name="q2"/>
        </li>
        <li class="begingroup">
            <span class="question">Are you the type of person who likes to needlessly answer extra questions?</span>
            <input type="checkbox" id="q3" name="q3" data-togglehidden="l4"/>
            <label for="q3">Yes, yes, that's me!!!</label>
        </li>
        <li id="l4" class="hidden">
            <label class="question" for="q4">Why do you like to do extra needless work?</label>
            <input type="text" id="q4" name="q4"/>
        </li>
        <li class="begingroup">
            <label class="question" for="q5">What was your first pet's name?</label>
            <input type="text" id="q5" name="q5"/>
        </li>
    </ol>
</form>

Here's what it looks like in Firefox 16.0.2:

And in IE 7.0.5730.13CO:

The CSS:

ol.formfield {
    width: 500px;
    margin: 10px auto;
    padding: 16px 16px 16px 0;
    border: 5px groove #005E9B;
    list-style: decimal outside;
    color: black;
    background-color: #6Fc2F7;    
    font-family: 'Oxygen', sans-serif;
    font-size:15px;
}

ol.formfield li {
    clear: both;
    padding: 2px;
    margin-left: 1.7em;
}

ol.formfield li.begingroup {
    margin-top: 8px;
    padding-top: 8px;
    border-top: 1px solid #005E9B;
}

.question {
    display:inline-block;
    width:300px;
    vertical-align:top;      
}

.hidden {
    position: absolute;
    height: 0;
    width: 0;
    overflow: hidden;
}

ol.formfield input {
    border-radius:5px; /* css 3 */
    -moz-border-radius:5px; /* mozilla */
    -webkit-border-radius:5px; /* webkit */
}

And the script to wire up your hide/reveal based on data values on elements:

$('ol.formfield input:checkbox')
    .each(function() {
        var d = $(this).data('togglehidden');
        if(d) {
            $(this).on('change', function() {
                if ($(this).attr('checked')) {     
                    $('#' + d)
                        .removeClass('hidden')
                        .find(':input')
                        .focus();
                } else {
                    $('#' + d).addClass('hidden');
                }
            });
        }
    });

这篇关于造型HTML&lt; li&gt;元素:避免无效的父&lt; div&gt;的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆