将div放入锚点是否正确?


529

我听说将block元素放入内联元素是HTML的罪过:

<a href="http://www.mydomain.com"><div>
What we have here is a problem. 
You see, an anchor element is an inline element,
and the div element is a block level element.
</div></a>

但是,如果您像display:block样式表那样设置外部锚点,该怎么办?还是错吗?关于块级和内联元素的HTML 4.01规范似乎是这样认为的:

样式表提供了指定任意元素呈现的方法,包括将元素呈现为块还是内联。在某些情况下,例如列表元素的内联样式,这可能是适当的,但总的来说,不鼓励作者以这种方式覆盖HTML元素的常规解释。

有人对此问题有其他建议吗?



@DisgruntledGoat-感谢您的链接-希望我能早点看到:-)
汤姆(Tom)2009年

锚和/或链接元素是浏览器自动化控件。因此,它具有浏览器预定义的呈现和行为。要包装真正的普通html元素:但是,在span内插入div是一种罪过。A标签不添加任何级别行为这一事实背后的原因是,在不干扰文档流的情况下标记文本的一部分是必需的,这不是因为它们是内联元素。从那个pov,A,是什么都不做的标签。它的存在超出了问题的范围,而不是犯罪,但可能会导致代码丑陋和/或模棱两可。
Bekim Bacaj

以后在这里检查的所有其他用户,请注意,虽然锚标记能够包含块级元素,但它们在HTML5中并不代表它们,但它们不能包含包含其他锚标记的块级元素!因为基本上,定位标记不能在其中包含其他定位标记。:你可以阅读更多的在这里stackoverflow.com/questions/13052598/...
aderchox

Answers:


746

根据您要满足的HTML版本:

  • HTML 5声明<a>元素“只要其中没有交互内容(例如按钮或其他链接),就可以包裹整个段落,列表,表格等,甚至整个节”。

  • HTML 4.01指定<a>元素只能包含内联元素。A<div>是一个块元素,因此它可能不会出现在内<a>

    当然,您可以随意设置内联元素的样式,使其看起来像是一个块,或者也可以对一个块进行样式化,以使其内联。在HTML中使用术语inlineblock是指元素与文档的语义结构之间的关系,而在CSS中,相同的术语更多地与元素的视觉样式相关。如果使内联元素以块状显示,那很好。

    但是,当没有CSS时(例如,通过屏幕阅读器等辅助技术进行访问时,或者由强大的Googlebot进行检查时),您应该确保文档的结构仍然有意义。


4
w3.org/TR/REC-html40/sgml/dtd.html上有一个4.01的DTD 。A可以包含%inline%;%inline%是一堆不同的东西(您可以点击链接),但DIV不在其中。因此,内部带有DIV的A不能通过XML验证。我认为DTD很好地表达了委员会的意图,所以我想说:不
卡尔·斯莫特里奇

2
@Ewan:我的答案中的第一个链接是HTML 4.01的相关部分。
NickFitz

62
在我读完有关HTML5的最后一行之前,我打算放弃在项目中执行此操作的可能性,这很高兴知道,谢谢。
伊莱恩·马利

16
Mozilla开发人员网络(developer.mozilla.org/en-US/docs/Web/HTML/Element/a)反映了以下事实:HTML5 <a>元素现在支持流内容元素,例如<div>,<ul>或<table> 。
AxeEffect 2013年

12
在HTML5下,a元素被分类为transparent,这意味着仅当a元素的父元素可以包含flow元素时,它才能包含flow元素(读取为default = block)。否则,仅允许使用短语元素(阅读default = inline)。因此,如果一个是在形式DIV,它可以包含一个DIV,但一个内部p,它不能。参见w3.org/TR/html-markup/terminology.html
Patanjali,

81

不,它不会验证,但是是的,它通常可以在现代浏览器中运行。话虽如此,请在锚点内部使用一个跨度,并display: block在其上进行设置,这肯定会在任何地方都有效,并且它将验证!


7
如果设置display: block,从技术上讲,它不是成为一个块元素吗?
WhyNotHugo 2012年

20
@hugo从技术上讲重要吗?
安迪·蔡斯

5
好吧,HTML 4.01指定a元素只能包含内联元素。如果将span元素设为块元素,从技术上讲,它不应位于锚点内部。
WhyNotHugo 2012年

22
@Hugo:HTML4中的限制似乎是语义的,而不是表述的。在语义上,即使文档随附的CSS另有规定,a <div>还是块级的,而a <span>是内联的。
罗伊·廷克

添加了样式=“ display:block;” 在span标签中,它就像一个魅力。刚玩填充可以得到我想要的结果
Harif87

31

W3C文档没有使用错误犯罪之类的概念,但是确实使用了提供手段之类的概念可能是适当的不鼓励使用

实际上,在第4节的第二段中,4.01规范的措辞如下:

本文档中的关键字“必须”,“不得”,“必须”,“应”,“应禁止”,“应”,“不应”,“建议”,“可以”和“可选”是如[RFC2119]中所述进行解释。但是,为了便于阅读,在本规范中,这些单词并非全部以大写字母出现。

考虑到这一点,我相信最终声明是在7.5.3块级和内联元素中

通常,内联元素可以仅包含数据和其他内联元素。

条件“通常”似乎引入了足够的歧义,可以说HTML 4.01确实允许内联元素包含块元素。

当然,CSS2具有显示属性值inline-block,似乎适合您描述的目的。我不确定它是否曾经得到广泛支持,但是似乎有人预料到需要这种行为。

DTD在这里似乎不太宽容,但DTD文本符合规范:

HTML 4.01规范包括不能在DTD中表达的其他语法约束。

在另一个注释中,建议您通过将其包装在锚点中来使其处于活动状态。我不认为HTML禁止这样做,而CSS显然允许这样做。因此,回答有关是否正确的标题问题,我说是。按照标准,有时是正确的。


2
在提到文档类型之前,您一直拥有我。
罗伯特·哈维,

不是doctype,doctype.com
Ewan Todd

您可能是对的-我应该使用doctype.com。抱歉-我会在下次记得。PHP-> SO,HTML-> doctype.com
汤姆

2
我的看法是,没有“关闭doctype.com上的投票权”选项(也不应该有)。
罗伯特·哈维

7
我同意Rob-堆栈溢出用于编程。在我看来,HTML / CSS当然是编程。
DisgruntledGoat

13

使用HTML5规范...现在可以将块级元素放入内联元素中。因此,现在非常适合将'div'或'h1'放入'a'元素内。


1
仅内部元素(默认= )或具有允许元素的父元素的透明元素(如a)。例如,p不允许元素(如DIV),但只有措辞元素(缺省值= 直列),所以一个一个一个内部p不能包含DIV。然而,一个一个内部的div可以包含p S,DIV S或任何其他元件。
Patanjali

4

你不能把<div>里面<a>-它不是有效的(X)HTML。

即使您使用display:块设置跨度样式,也仍然不能在其中放置块级元素:(X)HTML仍然必须遵守(X)HTML DTD(无论使用哪种样式),无论CSS如何改变事物。

浏览器可能会根据需要显示它,但这并不正确。


4

http://www.w3.org/TR/REC-html40/sgml/dtd.html上有HTML 4的DTD 。此DTD是规范的机器可处理形式,其局限性在于DTD支配XML和HTML 4,尤其是“瞬态”风格,允许很多不是“合法” XML的事物。尽管如此,我认为这已经接近整理说明者的意图。

<!ELEMENT A - - (%inline;)* -(A)       -- anchor -->

<!ENTITY % inline "#PCDATA | %fontstyle; | %phrase; | %special; | %formctrl;">

<!ENTITY % fontstyle "TT | I | B | BIG | SMALL">

<!ENTITY % phrase "EM | STRONG | DFN | CODE | SAMP | KBD | VAR | CITE | ABBR | ACRONYM" >

<!ENTITY % special "A | IMG | OBJECT | BR | SCRIPT | MAP | Q | SUB | SUP | SPAN | BDO">

<!ENTITY % formctrl "INPUT | SELECT | TEXTAREA | LABEL | BUTTON">

我会将在此层次结构中列出的标签解释为允许的标签总数。

尽管规范可能会说“内联元素”,但我很确定这并不是要通过声明块元素的显示类型为内联来绕开意图。内联标签具有不同的语义,无论您如何滥用它们。

另一方面,我发现引人入胜的是special似乎允许嵌套A元素。规范中可能有一些措辞强硬的措辞,即使它在XML语法上是正确的,也不允许这样做,但由于它不是问题的主题,因此我将不做进一步介绍。


你知道什么- - 意思吗 我试图找到一种解释,但找不到。
伊万·托德

4

诸如HTML之类的块级元素<div>可以由<a>标签包装。尽管根据MDN, a <div>被认为是流内容容器/包装,<a>s被认为是流内容。从语义上讲,创建充当块级元素的内联元素可能更好。


1
作为一个元件是透明的,只有当的父元素一个允许(默认为)的元件。
Patanjali

2

如果要避免将div放置在锚标记中的语义麻烦,只需将锚标记放置在与div相同的水平上,然后将它们全部包装在具有位置:相对的容器中,将锚标记的位置设置为绝对:并将其扩展为装满容器。另外,如果不在内容流的末尾,请确保将z-index放在其中,以将其放置在内容上方。

根据建议,我添加了一个标记代码:

<div class="div__container>
  <div class="div__one>
  </div>
  <div class="div__two">
  </div>
  <a href="#"></a>
</div>

和CSS:

.div__container {
  position: relative; 
}
.div__container a {
  position: absolute;
  top: 0;
  bottom: 0;      
  left: 0;
  right: 0;
  z-index: 999;
}

1
虽然您的答案可能是正确的,但如果您用标记说明它会有所帮助。
datashaman

1

如果您要努力制作<a>块,为什么不放到<a>div内,作为块元素,它会给您同样的效果。


36
因为我可能希望锚点包含多个div。
汤姆”,

1

如果将其更改为块样式元素,则不会,它不再“错误”,但可能无法验证。但是做自己在做的事情没有多大意义。您应该只将anchor标签作为没有内部div的块级元素保留,或者将div放在外面。


1

这是错的。使用跨度


4
rofl多数民众赞成在同一件事上使用div。我认为我已经在blip.tv上看到完成了此操作(使用div),但是正如其他人提到的那样,如果使用div或span或其他相同的功能,根据spec block = block会出错!
James Mitch

0

我认为大多数情况下,当人们问这个问题时,他们只建立了一个div网站,现在,其中一个div需要成为链接。

我看到有人在锚标记内使用透明的空白图像PNG,只是为了在div内建立链接,并且图像的大小与div相同。

实际上非常难过...但是它可以工作...


0

您可以通过添加“ :: before”伪元素来实现

纯CSS技巧;)

a:before{
  position: absolute;
  top: 0;
  right: 0;
  bottom: 0;
  left: 0;
  z-index: 1;
  pointer-events: auto;
  content: "";
  background-color: rgba(0,0,0,0);
}
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.0/css/bootstrap.min.css" rel="stylesheet"/>
<div class="card" style="width: 18rem;">
  <img src="https://via.placeholder.com/250" class="card-img-top" alt="...">
  <div class="card-body">
    <h5 class="card-title">Card with stretched link</h5>
    <p class="card-text">Some quick example text to build on the card title and make up the bulk of the card's content.</p>
    <a href="#" class="btn btn-primary stretched-link">Go somewhere</a>
  </div>
</div>


-8

就像供参考。

如果您的目标是使div可点击,则可以使用jQuery / Java Script。

像这样定义div:

<div class="clickableDiv" style="cursor:pointer">
  This is my div. Try clicking it!
</div>

然后,您的jQuery将像这样实现:

 <script type="text/javascript">

    $(document).ready(function () {

        $("div.clickableDiv").click(function () {
            alert("Peekaboo"); 
        });
    });
</script>

这也适用于多个div-根据此线程中Tom的评论


17
这太可怕了,不能与键盘一起使用,您也无法看到悬停的链接。它几乎像一个链接一样工作,但不是真正的链接。您也不能单击鼠标中键,也不能右键单击它作为链接。
WhyNotHugo 2012年

1
它肯定有其用途。您可以在div内放置一个锚点,并使div单击重定向到子锚点的位置。通过将div上的光标设置为指针,您将具有锚点的外观和感觉,以及一个有效的回退解决方案(如果不允许javascript或出于可访问性原因,仅在div内具有锚点)。您可以从语义和语法上获得正确的html,而不必摆弄可疑的显示样式更改。
Pedery

如果您的div包含链接,则可以使单击处理程序捕获事件,请找到锚点(确保只有一个),然后使用该锚点。可通过常规锚标签访问。例如,这将允许具有图像和标题以及“阅读更多”链接的一堆人物。有什么想法吗?
Julix
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.