所属分类:web前端开发
网页设计领域讨论最多的概念之一是响应式网页设计。关于响应式网页设计的文章已有数千篇,因此我不会在本文中讨论它。然而,响应式网页设计有一个重要的限制,响应式网页设计大部分是基于浏览器视口的大小。
虽然这种方法非常适合提供正确尺寸和分辨率的图像,但它并不适合所有情况,视频内容就是一个例子。在这些情况下,我们真正需要的是有关设备网络连接的更多信息。
假设您正在智能手机或平板电脑上访问 YouTube。您在家并通过 Wi-Fi 连接。在这种情况下,您并不关心正在下载的字节数,您只对高质量视频内容感兴趣。如果您通过慢速移动连接进行连接,则情况并非如此。在这种情况下,您想看视频,质量是次要的。
我应该明确的是,每个希望网站真正优秀的开发者仍然必须优化其所提供的资源,以允许页面尽可能快地加载。不过,在上面的示例中,提供高分辨率视频并不是浪费用户的带宽,而是改善了用户体验。
网络信息 API 正是我们需要了解有关设备网络连接的更多信息的地方。
网络信息 API 提供对系统用于与网络、蜂窝网络、Wi-Fi、蓝牙等进行通信的连接类型的访问。它还提供了一种在连接类型发生变化时通知脚本的方法。这是为了允许开发人员对 DOM 进行动态更改和/或通知用户网络连接类型已更改。
网络信息 API 规范于 2011 年首次发布,但此后该 API 已发生多次更改。作为证明,当前版本只是编辑草稿,这意味着将来肯定会发生变化。
尽管发生了这些变化,但该 API 的用例非常有趣,确实值得探索。在本文中,我们将讨论该规范的最新版本,但我们还将查看一些已弃用的属性和事件,原因我将在稍后解释。
当前版本的网络信息 API 公开了属于 window.navigator
对象的 connection
对象。 connection
对象包含一个属性,type
,该属性返回用户代理的连接类型。 type
属性可以具有以下值之一:
蓝牙
cellular
以太网
none
wifi
其他
未知
其中一些值是不言自明的,例如 bluetooth
和 wifi
,而其他值则需要更多解释。 cellular
类型是指移动连接,例如 EDGE、3G、4G 等。 other
类型表示当前连接类型不是 unknown
,但它也不是任何其他类型。 unknown
类型表示用户代理已建立网络连接,但无法确定连接类型是什么。
除了 type
之外,网络信息 API 还公开 ontypechange
事件。每次网络连接类型发生变化时都会触发它。
开发者可以使用网络信息 API 根据当前的连接类型更改某些功能。例如,如果我们检测到设备正在使用移动连接,我们可以减慢占用大量带宽的进程。 API 还允许我们将特定的类分配给 html
元素,例如 high-bandwidth
,与 Modernizr 的方式相同。我们可以利用 CSS 更改元素的一个或多个属性,例如背景图像。
既然我们知道了 Network Information API 的作用以及我们可以从中受益,那么让我们看看哪些浏览器支持该 API。
在撰写本文时,网络信息 API 仅受使用其供应商前缀的 Firefox 和 Chrome Canary 支持。在 Chrome Canary 中,我们必须启用实验性网络平台功能标志才能使用 API。您可以在 Paul Irish 的这篇文章中找到更多信息。
好像对网络信息 API 的支持还不够差,最新版本 30 版的 Firefox 支持旧的 API 规范。因此,如果您现在想使用 Network Information API,请务必查看以前的 API 规范公开的属性和事件。
旧规范公开了两个属性:bandwidth
和 metered
。 bandwidth
属性是一个双精度值,表示当前带宽的估计值(以兆字节每秒 (MB/s) 为单位)。 metered
属性是一个布尔值,指定设备的网络连接是否受到任何限制。之前的规范还定义了 onchange
事件,以通知任何侦听器上述属性的更改。
为了让您了解规范的新版本和旧版本,在下一节中我们将构建一个使用这两个版本的演示。
到目前为止,我们已经介绍了 API 公开的属性和事件以及 API 的用例。在本部分中,我们将创建一个简单的网页来查看 API 的运行情况。
该演示由一个 HTML5 页面组成,该页面包含一个包含三个列表项的无序列表。每个项目都包含一个文本片段,用于验证网络信息 API 的旧规范和新规范公开的属性值。列表项默认隐藏,仅在支持相应属性时才显示。
该演示还检测浏览器是否实现旧的 API 规范(针对 Firefox)以及浏览器是否支持网络信息 API。在第一种情况下,您将看到支持旧 API 版本消息,在第二种情况下,将显示不支持 API 消息。
网络信息 API 支持的测试非常简单,如下所示:
// Deal with vendor prefixes var connection = window.navigator.connection || window.navigator.mozConnection || null; if (connection === null) { // API not supported :( } else { // API supported! Let's start the fun :) }
要检测实现的版本是否是旧规范,我们可以测试 metered
属性是否存在,如下所示:
if ('metered' in connection) { // Old version } else { // New version }
一旦我们测试了对网络信息 API 的支持,并确定了浏览器支持的规范版本,我们就可以将处理程序附加到正确的事件。在处理程序内,我们更新相应列表项的文本,例如新 API 规范的 type
。
您可以在下面找到演示的完整代码,如果您愿意,也可以使用它。
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"/> <meta name="author" content="Aurelio De Rosa"> <title>Network Information API Demo by Aurelio De Rosa</title> <style> * { -webkit-box-sizing: border-box; -moz-box-sizing: border-box; box-sizing: border-box; } body { max-width: 500px; margin: 2em auto; padding: 0 0.5em; font-size: 20px; } h1 { text-align: center; } .api-support { display: block; } .hidden { display: none; } .value { font-weight: bold; } .author { display: block; margin-top: 1em; } </style> </head> <body> <h1>Network Information API</h1> <span id="ni-unsupported" class="api-support hidden">API not supported</span> <span id="nio-supported" class="api-support hidden">Old API version supported</span> <ul> <li class="new-api hidden"> The connection type is <span id="t-value" class="value">undefined</span>. </li> <li class="old-api hidden"> The connection bandwidth is <span id="b-value" class="value">undefined</span>. </li> <li class="old-api hidden"> The connection is <span id="m-value" class="value">undefined</span>. </li> </ul> <small class="author"> Demo created by <a href="http://www.audero.it">Aurelio De Rosa</a> (<a href="https://twitter.com/AurelioDeRosa">@AurelioDeRosa</a>).<br /> This demo is part of the <a href="https://github.com/AurelioDeRosa/HTML5-API-demos">HTML5 API demos repository</a>. </small> <script> var connection = window.navigator.connection || window.navigator.mozConnection || null; if (connection === null) { document.getElementById('ni-unsupported').classList.remove('hidden'); } else if ('metered' in connection) { document.getElementById('nio-supported').classList.remove('hidden'); [].slice.call(document.getElementsByClassName('old-api')).forEach(function(element) { element.classList.remove('hidden'); }); var bandwidthValue = document.getElementById('b-value'); var meteredValue = document.getElementById('m-value'); connection.addEventListener('change', function (event) { bandwidthValue.innerHTML = connection.bandwidth; meteredValue.innerHTML = (connection.metered ? '' : 'not ') + 'metered'; }); connection.dispatchEvent(new Event('change')); } else { var typeValue = document.getElementById('t-value'); [].slice.call(document.getElementsByClassName('new-api')).forEach(function(element) { element.classList.remove('hidden'); }); connection.addEventListener('typechange', function (event) { typeValue.innerHTML = connection.type; }); connection.dispatchEvent(new Event('typechange')); } </script> </body> </html>
在本文中,我向您介绍了网络信息 API。在本文的第一部分中,我们讨论了 API 是什么以及它可以为我们做什么。我们还了解了 Network Information API 公开了哪些属性和事件。正如我在浏览器支持中提到的,该 API 目前支持不佳,部分原因是 API 规范发生了一些变化。
网络信息 API 使用起来非常简单,一旦更多浏览器支持它,就没有理由不利用它提供的信息。您觉得这个 API 怎么样?当更多浏览器支持时您会使用它吗?