在本文中,我们将探讨这些用例,并了解如何改善(而不是阻碍)用户体验。用户选择属性还有其他值,这些值可用于更改文本选择的行为而不是完全禁用它,以及另一个甚至强制文本选择的值,这也是毫无价值的,所以我们也将看看这些值。user-select: none
none
user-select
让我们通过运行不同的值及其作用来开始事情。user-select
应用于元素意味着其文本内容和嵌套文本内容在功能上不可选择或视觉上可选(即不起作用)。如果要进行包含一些不可选择内容的选择,则不可选择的内容将从选择中省略,因此它得到了很好的实现。而且支持很棒。user-select: none;
::selection
user-select: contain
是一个有趣的。应用它意味着如果选择在元素内开始,那么它也必须在元素中结束,包含它。然而,奇怪的是,当选择在元素之前开始时,这并不适用,这可能就是为什么目前没有浏览器支持它的原因。(Internet Explorer和早期版本的Microsoft Edge以前以它的幌子支持它。user-select: element
选择元素的一部分内容会导致自动选择所有元素内容。要么全有,要么全无,这非常不妥协,但在用户更有可能将内容复制到剪贴板(例如共享和嵌入链接、代码片段等)的情况下很有用。用户无需双击,只需单击一次即可自动选择内容。user-select: all
但是要小心,因为这并不总是您认为的功能。如果用户只想选择部分内容(例如,仅选择 Google 字体代码段的字体名称部分或代码段的一部分),该怎么办?
更好的应用是确保报价被完全准确地复制。user-select: all
当您从网页复制内容时,它可能来自文章或其他类型的长篇内容,对吧?您可能不希望您的选择包含图像、表情符号(有时可以复制为文本,例如“:thinkingface:”),以及您可能期望包含在 anelement 中的其他内容(例如,文章内号召性用语、广告或其他不属于主要内容的内容)。
若要防止某些内容包含在选择中,请确保将其包装在 HTML 元素中,然后应用于它:user-select: none
- <p>lorem <span style="user-select: none">🤔span> ipsump>
-
- <aside style="user-select: none">
- <h1>Headingh1>
- <p>Paragraphp>
- <a>Call to actiona>
- aside>
在这种情况下,我们不会禁用选择,而是对其进行优化。还值得一提的是,选择并不一定意味着复制——许多读者(包括我自己)喜欢在阅读内容时选择内容,以便他们能够记住它们的位置(如书签),这是优化而不是完全禁用的另一个原因。
应用于看起来像按钮的链接(例如)。user-select: none
Click Me!
无法选择主动脉的文本内容因为,好吧,你为什么要选择?但是,此行为不适用于链接,因为传统上它们构成应可选择的段落的一部分。
很公平。
我当然容易意外选择东西,因为我在床上使用笔记本电脑比我愿意承认的要多。此外,还有几种医疗条件会影响控制和协调,将预期的点击变成意外的拖动/选择,因此也可以解决可访问性问题。user-select
当然,需要(有意)拖动的交互也确实存在(例如在浏览器游戏中),但这些并不常见。不过,它只是表明它实际上确实有很多用例。user-select
付费内容会受到很多仇恨,但如果你觉得你需要保护你的内容,那就是你的内容——没有人有权窃取它,因为他们不相信他们应该为此付费。
如果您确实想走这条路,有很多方法可以使用户更难绕过付费墙(或类似地,复制受版权保护的内容,例如其他人的已发布作品)。
使用 CSS 模糊内容:
article { filter: blur(); }
禁用开发工具的键盘快捷方式:
- document.addEventListener("keydown", function (e) {
- if (e.keyCode == 123) e.preventDefault();
- else if ((e.ctrlKey || e.metaKey) && e.altKey && e.keyCode == 73) e.preventDefault();
- else if ((e.ctrlKey || e.metaKey) && e.altKey && e.keyCode == 74) e.preventDefault();
- else if ((e.ctrlKey || e.metaKey) && e.altKey && e.keyCode == 85) e.preventDefault();
- });
通过禁用上下文菜单本身来禁用对 DevTools 的访问:
document.addEventListener("contextmenu", e => e.preventDefault())
当然,为了防止用户在源头不被允许阅读内容时复制内容,请应用:user-select: none
<article style="user-select: none">