WebXR 设备 接口参考 - Web API 接口参考

WebXR 设备 接口参考
=============

**WebXR** 是一组支持将渲染 3D 场景用来呈现虚拟世界（虚拟现实，也称作 VR）或将图形图像添加到现实世界（增强现实，也称作 AR）的标准。 **WebXR 设备 API** 实现了 WebXR 功能集的核心，管理输出设备的选择，以适当的帧速率将 3D 场景呈现给所选设备，并管理使用输入控制器创建的运动矢量。

WebXR-兼容性设备包括沉浸式 3D 运动和定位跟踪耳机，通过框架覆盖在真实世界场景之上的眼镜，以及手持移动电话，它们通过用摄像机捕捉世界来增强现实，并通过计算机生成的图像增强场景。

为了完成这些事情，WebXR 设备 API 提供了以下关键功能：

* 查找兼容的 VR 或 AR 输出设备
* 以适当的帧率将 3D 场景渲染到设备
* （可选）将输出镜像到 2D 显示器
* 创建代表输入控件运动的向量

在最基本的层面上，通过计算应用于场景的透视图，以从每个用户的视角呈现场景，从而在 3D 中呈现场景，考虑到眼睛之间的常规距离，然后渲染场景两次，每只眼睛一次。然后将生成的图像 (场景在一个帧上呈现两次，每只眼睛一半) 显示给用户。

由于 WebGL 用于将 3D 世界渲染到 WebXR 会话中，因此你首先应该熟悉 WebGL 的一般用法以及 3D 图形的基本知识。你很可能不会直接使用 WebGL API，而是利用在 WebGL 之上构建的框架或库之一来使其使用更加方便。其中最流行的是three.js。

使用库而不是直接使用 WebGL API 的一个特殊好处是，库取向于实现虚拟相机函数性的接口。OpenGL（WebGL 的扩展）不直接提供照相机视图，使用库模拟一个的话可以使你的工作变得非常非常容易，特别是在构建允许在虚拟世界中自由移动的代码时。

重要的健康和安全提示
----------

因为本质上来说，创建虚拟 3D 世界的整个过程是一个技巧，它利用了我们对眼睛如何收集光以及大脑如何解释所收集的数据的理解，因此务必要牢记，软件设计师开发人员有责任比平时更加 小心，以确保结果正确。

缺陷，未对准或变形会混淆眼睛和大脑，导致眼睛疼痛或头痛乃至眩晕，头晕或潜在的严重恶心。考虑到 VR 护目镜的全部特性，需要特别注意，开发者对可能引起癫痫发作的任何事物都要保持警惕；如果它引起困扰，则用户可能无法快速将视线从你呈现的图像上移开。

如果你有任何可能对任何用户构成风险的内容，则应提供警告消息。有备无患！

WebXR 设备 API 的概念和用法
-------------------

### WebXR: AR and VR

举例 WebXR 硬件装备

![Sketch of a person in a chair with wearing goggles labelled "Head mounted display (HMD)" facing a monitor with a webcam labeled "Position sensor"](/zh-CN/docs/Web/API/WebXR_Device_API/hw-setup.png)

较早的 WebVR API 仅设计为支持虚拟现实（VR），而 WebXR 在 Web 上同时支持 VR 和增强现实（AR）。WebXR 增强现实模块增加了对 AR 功能的支持。

典型的 XR 设备可以具有 3 或 6 个自由度，并且有没有外部位置传感器都可以。

该设备还可以包括加速度计，气压计或其他传感器，用于感测用户何时在空间中移动，旋转其头部等。

### WebXR 应用程序生命周期

使用 WebXR 的大多数应用程序将遵循类似的总体设计模式：

1. 检查用户的设备和浏览器是否都能够呈现你想要提供的 XR 体验。
    1. 确保 WebXR API 可用；如果 `navigator.xr` (en-US) 未定义，则可以判断用户的浏览器和/或设备不支持 WebXR。如果不支持，请禁用用于激活 XR 功能的任何用户界面，并中止任何进入 XR 模式的尝试。
    2. 调用 `navigator.xr.isSessionSupported()` (en-US), 指定要提供的 WebXR 体验模式：`inline`, `immersive-vr`, 或 `immersive-ar`, 以确定你希望提供的会话类型是否可用。
    3. 如果要使用的会话类型可用，请向用户提供适当的界面以允许他们激活它。
2. 当用户通过上述的界面开启了 WebXR 功能后，通过调用 `navigator.xr.requestSession()` (en-US)，也是指定使用的模式为以下三种之一： `inline`, `immersive-vr`, 或 `immersive-ar`后，可以将一个 `XRSession` (en-US) 设定在期望的模式下。
3. 当 `requestSession()` 返回的 promise 被 resolve 后，使用新的 `XRSession` (en-US) 在整个 WebXR 体验期间运行帧循环。
    1. 调用 `XRSession` (en-US) 的 `requestAnimationFrame()` (en-US) 方法，以调度 XR 设备的首帧渲染。
    2. 每一个 `requestAnimationFrame()` 的回调都需要使用 WebGL 渲染已提供信息的 3D 世界中的物体。
    3. 持续在回调中调用 `requestAnimationFrame()` (en-US) 保证每一帧都成功地按顺序渲染。
4. 当需要结束 XR 会话的时候；或者用户主动退出 XR 模式。
    1. 通过调用 `XRSession.end()` (en-US) 可手动结束 XR 会话。
    2. 无论通过何种方式（开发者、用户或者浏览器）终止会话，`XRSession` (en-US) 的 `end` (en-US) 事件都会接收到通知。
### 获取许可与安全性

WebXR Device API 受到一系列许可与安全性的控制。这些控制不涉及法律责任，但也需要引起重视。其控制场景主要在于身临其境的 `immersive-vr` 会话模式和 AR 会话下。

#### VR 的沉浸式（immersive）

首先，如果域名不支持请求有权限打开沉浸模式，那么 `immersive-vr` 模式就会被拒绝。这个权限管理来自`xr-spatial-tracking` 特征策略。

一旦有权限了，申请开启 `immersive-vr` 模式的请求还需要再检查以下三点，全部满足才能开启：

* 在用户事件句柄总或者在用户启动 web 应用中执行的 `requestSession()` 调用；
* 文档是可信赖的，其中的内容是可靠的、及时更新的以及有着重点；
* 用户有明确的使用沉浸式 VR 模式的意图，后文中，用户意图一节将有详细描述。

如果上述三点均满足， `requestSession()` 返回的 Promise 将被 resolve，新的 `XRSession` (en-US) 对象被传入完成时的处理函数中。如果有不满足的情况，将会根据具体场景抛出异常，比如当没有权限进入沉浸式模式情况下， `SecurityError` 将被抛出。

#### 内联（inline）

当你在 `inline` 模式下发出 `XRSession` (en-US) 请求想要请求其他的特性时，浏览器仅允许那些明显由**用户意图**发起才会执行的代码所调用到的 `requestSession()` (en-US)。

特别注意：

* 如果 `requestSession()` 调用的发起既不来自用户事件中，也不是在 Web 应用启动时，那该请求将会被驳回，Promise 放返回 `false`;
* 如果发起请求的文档不属于对应的脚本，该请求将被驳回；
* 如果发起请求的文档不可信任，该请求会被驳回且 Promise 返回 `false`。一个可信任文档指的是该文档是活跃的、负责任的且有重点的；
* 如果设备无法明确用户开启内联模式的意图，该请求将会被驳回。对用户的目的的理解可以是隐性或者显性的。

**备注：** 当调用 `requestSession()` 时，根据选择对象需要指定的特性不同，将会执行额外的请求。

#### 用户意图

**用户意图**指的是用户自身是否想执行某个动作的时候可以通过代码控制实际的执行情况。有两种用户意图类型：**显性**和**隐性**。

直接询问用户是否同意执行某个操作，即**显性的用户意图** (用户显示的同意操作) 。

当以下情况发生时，我们可以认为出现了**隐性的用户意图** (用户暗示同意)：

* The user has interacted with the document in some way which has in turn caused your request to occur. For example, if you have an "Enter XR mode" button, and the user clicks it, calling `requestSession()` from the button's `click` event handler will permitted.
* If your code is executing during the launch of a web application, the runtime may consider the act of launching your web application to qualify as user intent.
### WebXR 的可用性

As a new and still in development API, WebXR support is limited to specific devices and browsers; and even on those, it may not be enabled by default. There may be options available to allow you to experiment with WebXR even if you don't have a compatible system, however.

#### WebXR polyfill

The team designing the WebXR specification has published a WebXR polyfill which you can use to simulate WebXR on browsers which don't have support for the WebXR APIs. If the browser supports the older WebVR API, that is used. Otherwise, the polyfill falls back to an implementation which uses Google's Cardboard VR API.

The polyfill is maintained alongside the specification, and is kept up to date with the specification. Additionally, it is updated to maintain compatiblity with browsers as their support for WebXR and other technologies related to it and to the implementation of the polyfill change over time.

Be sure to read the readme carefully; the polyfill comes in several versions depending on what degree of compatibility with newer JavaScript features your target browsers include.

#### WebXR API Emulator extension

The Mozilla WebXR team has created a WebXR API Emulator browser extension, compatible with both Firefox and Chrome, which emulates the WebXR API, simulating a variety of compatible devices such as the HTC Vive, the Oculus Go and Oculus Quest, Samsung Gear, and Google Cardboard. With the extension in place, you can open up a developer tools panel that lets you control the position and orientation of the headset and any hand controllers, as well as button presses on the controllers.

While somewhat awkward compared to using an actual headset, this makes it possible to experiment with and developer WebXR code on a desktop computer, where WebXR isn't normally available. It also lets you perform some basic testing before taking your code to a real device. Be aware, however, that the emulator does not yet completely emulate all of the WebXR API, so you may run into problems you're not expecting. Again, carefully read the readme file and make sure you're aware of the limitations before you begin.

**备注：** **Important:** You should *always* test your code on actual AR and/or VR hardware before releasing or shipping a product! Emulated, simulated, or polyfilled environments are *not* an adequate substitute for actual testing on physical devices.

Download the WebXR API Emulator for your supported browser below:

* Google Chrome
* Mozilla Firefox

The source code for the extension is also available on GitHub.

调用 WebXR API
------------

To gain access to the WebXR API within the context of a given window, use the `navigator.xr` (en-US) property.

`navigator.xr` (en-US) 只读

This property, added to the `Navigator` interface, returns the `XR` (en-US) object through which the WebXR API is exposed. If this property is missing or `null`, WebXR is not available.

WebXR 接口
--------

`XR` (en-US)

The `navigator.xr` (en-US) property returns the window's instance of `XR` (en-US), which is the mechanism by which your code accesses the WebXR API. Using the `XR` interface, you can create `XRSession` (en-US)s to represent actual AR and/or VR sessions.

`XRFrame` (en-US)

While presenting an XR session, the state of all tracked objects which make up the session are represented by an `XRFrame`. To get an `XRFrame`, call the session's `requestAnimationFrame()` (en-US) method, providing a callback which will be called with the `XRFrame` once available. Events which communicate tracking states will also use `XRFrame` to contain that information.

`XRRenderState` (en-US)

Provides a set of configurable properties which change how the imagery output by an `XRSession` is composited. These properties include the range of distances from the viewer within which content should be rendered, the vertical field of view (for inline presentations), and a reference to the `XRWebGLLayer` (en-US) being used as the target for rendering the scene prior to it being presented on the XR device's display or displays.

`XRSession` (en-US)

Provides the interface for interacting with XR hardware. Once an `XRSession` is obtained from `XR.requestSession()` (en-US), the session can be used to check the position and orientation of the viewer, query the device for environment information, and present the virtual or augmented world to the user.

`XRSpace` (en-US)

`XRSpace` is an opaque base class on which all virtual coordinate system interfaces are based. Positions in WebXR are always expressed in relation to a particular `XRSpace` at the time at which a particular `XFrame` takes place. The space's coordinate system has its origin at the a given physical position.

`XRReferenceSpace` (en-US)

A subclass of `XRSpace` (en-US) which is used to identify a spatial relationship in relation to the user's physical emvironment. The `XRReferenceSpace` coordinate system is expected to remain unchanged through the lifespan of the `XRSession` (en-US).The world has no boundaries and extends infinitely in every direction.

`XRBoundedReferenceSpace` (en-US)

`XRBoundedReferenceSpace` extends the `XRReferenceSpace` (en-US) coordinate system to further include support for a finite world with set boundaries. Unlike `XRReferenceSpace`, the origin must be located on the floor (that is, *y* = 0 at the floor). The x and z components of the origin are typically presumed to be located at or near the center of the room or surface.

`XRView` (en-US)

Represents a single view into the XR scene for a particular frame. Each `XRView` corresponds to the video display surface used to present the scene to the user. For example, a given XR device might have two views: one for the left eye and one for the right. Each view has an offset used to shift the position of the view relative to the camera, in order to allow for creating stereographic effects.

`XRViewport` (en-US)

Describes a viewport. A viewport is a rectangular portion of a graphic surface.

`XRRigidTransform` (en-US)

A transform defined using a position and orientation in the virtual space's coordinate system as described by the `XRSpace` (en-US).

`XRPose` (en-US)

Describes a position and orientation in space relative to an `XRSpace` (en-US).

`XRViewerPose` (en-US)

Based on `XRPose` (en-US), `XRViewerPose` specifies the state of a viewer of the WebXR scene as indicated by the XR device. Included is an array of `XRView` (en-US) objects, each representing one perspective on the scene. For example, it takes two views to create the stereoscopic view as perceived by human vision—one for the left eye and a second for the right eye. One view is offset to the left slightly from the viewer's position, and the other view is offset to the right by the same distance. The view list can also be used to represent the perspectives of each of the spectators of a scene, in a multi-user environment.

`XRInputSource` (en-US)

Represents any input device the user can use to perform targeted actions within the same virtual space as the viewer. Input sources may include devices such as hand controllers, optical tracking systems, and other devices which are explicitly associated with the XR device. Other input devices such as keyboards, mice, and gamepads are not presented as `XRInputSource` instances.

`XRWebGLLayer` (en-US)

A layer which serves as a WebGL frame buffer into which a scene's view is rendered. Using WebGL to render the scene gains substantial performance benefits due to graphics acceleration.

### 事件接口

The following interfaces are used to represent the events used by the WebXR API.

`XRInputSourceEvent` (en-US)

Sent when the state of an `XRInputSource` (en-US) changes. This can happen, for example, when the position and/or orientation of the device changes, or when buttons are pressed or released.

`XRInputSourcesChangeEvent` (en-US)

Sent to indicate that the set of available input sources has changed for the `XRSession` (en-US).

`XRReferenceSpaceEvent` (en-US)

Sent when the state of an `XRReferenceSpace` (en-US) changes.

`XRSessionEvent` (en-US)

Sent to indicate that the state of an `XRSession` (en-US) has changed. For example, if the position and/or orient

WebGL API 的扩展
-------------

The WebGL API is extended by the WebXR specification to augment the WebGL context to allow it to be used to render views for display by a WebXR device.

`WebGLRenderingContextBase.makeXRCompatibile()`

Configures the WebGL context to be compatible with WebXR. If the context was not initially created with the `xrCompatible` property set to `true`, you must call `makeXRCompatible()` prior to attempting to use the WebGL context for WebXR rendering. Returns a `promise` which resolves once the context has been prepared, or is rejected if the context cannot be configured for use by WebXR.

指南与教程
-----

The following guides and tutorials are a great resource to learn how to comprehend WebXR and the underlying 3D and VR/AR graphics concepts.

Fundamentals of WebXR (en-US)

Before diving into the details of how to create content using WebXR, it may be helpful to read this overview of the technology, which includes introductions to terminology that may be unfamiliar to you, or which may be used in a new way.

Matrix math for the web

A guide covering how matrices can be used on the web, including both for CSS transforms and for WebGL purposes, as well as to handle the positioning and orientation of objects in WebXR contexts.

Geometry and reference spaces in WebXR (en-US)

In this guide, the required concepts of 3D geometry are briefly reviewed, and the fundamentals of how that geometry is represented in WebXR are detailed. Learn how reference spaces are used to position objects—and the viewer—and the differences among the available types of reference space, as well as their use cases.

Spatial tracking in WebXR (en-US)

This guide describes how objects—including the user's body and its parts—are located in space, and how their movement and orientation relative to one another is monitored and managed over time. This article explains the relationship between spaces, poses, views (and viewers), and poses.

Rendering and the WebXR frame loop

Starting with how you schedule frames to be rendered, this guide then continues to cover how to determine the placement of objects in the view and how to then render them into the WebGL buffer used for each of the two eyes' views of the scene.

Movement, orientation, and motion: A WebXR example

In this example and tutorial, we use information learned throughout the WebXR documentation to create a scene containing a rotating cube which the user can move around using both VR headset and keyboard and mouse.

Inputs and input sources (en-US)

A guide to input sources and how to efficiently manage the input devices being used to control the WebXR session, and how to receive and process user inputs from those devices.

Supporting gamepads in WebXR applications

WebXR implements the Gamepad API to allow gamepads connected to the XR device to be used as input controls. This guide describes how this works.

规范
--

| 规范 |
| --- |
| **WebXR Device API**（Source、Issues、Explainer） |
| **WebXR Anchors Module**（Source、Issues、Explainer） |
| **WebXR Augmented Reality Module**（Source、Issues、Explainer） |
| **WebXR Depth Sensing Module**（Source、Issues、Explainer） |
| **WebXR DOM Overlays Module**（Source、Issues、Explainer） |
| **WebXR Gamepads Module**（Source、Issues、Explainer） |
| **WebXR Hand Input Module**（Source、Issues、Explainer） |
| **WebXR Hit Test Module**（Source、Issues、Explainer） |
| **WebXR Layers API**（Source、Issues、Explainer） |
| **WebXR Lighting Estimation API**（Source、Issues、Explainer） |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* Web 上的图形
* 绘制图形
* WebGL API：加速 Web 上的 2D 和 3D 图形
* Canvas API：Web 2D 绘图
* Canvas 教程


ImageBitmapRenderingContext - Web API 接口参考

ImageBitmapRenderingContext
===========================

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

**`ImageBitmapRenderingContext`** 接口是 canvas 的渲染上下文，它只提供了使用给定 `ImageBitmap` 替换 canvas 的功能。它的上下文 ID (`HTMLCanvasElement.getContext()` 或 `OffscreenCanvas.getContext()` (en-US) 的第一个参数) 是 `"bitmaprenderer"`。

这个接口可用于 window context 和 worker context.

方法
--

`ImageBitmapRenderingContext.transferFromImageBitmap()` (en-US)

在与此渲染上下文相关的 canvas 中显示给定的 `ImageBitmap` 。 `ImageBitmap` 的所有权被转移到画布上。这个函数以前命名为`transferImageBitmap()`，但在规范中修改了原名字。为了避免影响之前的代码，旧名称作为别名被保留下来。

规范
--

Currently drafted as a proposal in the OffscreenCanvas specification.

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

相关链接
----

* `OffScreenCanvas`


Window - Web API 接口参考

Window
======

`window` 对象表示一个包含 DOM 文档的窗口，其 `document` 属性指向窗口中载入的 DOM 文档 。

使用 `document.defaultView` 属性可以获取指定文档所在窗口。

代表了脚本正在运行的窗口的 `window` 全局变量，被暴露给 Javascript 代码。

`Window` 接口是各种函数、命名空间、对象和构造函数的家，它们不一定与用户界面窗口的概念直接相关。然而，`Window` 接口是一个可以包含这些需要全局可用的项目的合适的地方。其中很多内容都在 JavaScript 参考和 DOM 参考中有所记载。

在标签式浏览器中，每个标签都由自己的 `Window` 对象表示；在特定标签中运行的 JavaScript 代码所看到的全局 `window` 总是代表代码所运行的标签。也就是说，即使在标签浏览器中，一些属性和方法仍然适用于包含标签的整个窗口，如 `resizeTo()` 和 `innerHeight`。一般来说，任何不能合理地与标签有关的东西都与窗口有关。

EventTarget

Window实例属性
----

*本接口从 `EventTarget` 接口继承属性。*

注意，对象类型的属性（例如：覆盖内建元素的原型）被列于下面单独的小节之中。

`Window.caches` 只读

返回与当前环境相关的 `CacheStorage` 对象。这个对象可以实现一些功能，如存储供离线使用的资源，以及对请求生成自定义响应。

`Window.clientInformation` 只读

`Window.navigator` 对象的别名。

`Window.closed` 只读

此属性表示当前窗口是否关闭。

`Window.console` 只读

返回对 console 对象的引用，该对象提供对浏览器调试控制台的访问。

`Window.credentialless` (en-US) 只读
实验性

非标准

返回一个布尔值，表示当前文档是否在无凭据（credentialless）的 `<iframe>` 中加载。参见 IFrame credentialless (en-US) 以了解更多细节。

`Window.crypto` 只读

返回浏览器的 crypto 对象。

`Window.customElements` 只读

返回对 `CustomElementRegistry` 对象的引用，该对象可用于注册新的自定义元素并获取之前注册的自定义元素的信息。

`Window.devicePixelRatio` 只读

返回当前显示器中物理像素和设备独立像素之间的比率。

`Window.document` 只读

返回对 window 所包含的文档的引用。

`Window.frameElement` 只读

返回窗口被嵌入的元素，如果窗口没有被嵌入，则返回空。

`Window.frames` 只读

返回当前窗口中的子框架（subframe）形成的数组。

`Window.fullScreen`
非标准

此属性指示窗口是否以全屏显示。

`Window.history` 只读

返回对 history 对象的引用。

`Window.indexedDB` 只读

为应用程序提供异步访问索引数据库的能力；返回一个 `IDBFactory` 对象。

`Window.innerHeight` 只读

获取浏览器窗口的内容区域的高度，包括（已渲染的）水平滚动条。

`Window.innerWidth` 只读

获取浏览器窗口的内容区域的宽度，包括（已渲染的）竖直滚动条。

`Window.isSecureContext` 只读

返回一个布尔值，表示当前上下文安全（`true`）或不安全（`false`）。

`Window.launchQueue` (en-US) 只读
实验性

当一个渐进式 web 应用（PWA）以 `focus-existing`、`navigate-new` 或 `navigate-existing` 的 `launch_handler` (en-US) `client_mode` 值启动时，`launchQueue` 提供对 `LaunchQueue` (en-US) 类的访问，这允许为 PWA 实现自定义的启动导航处理。

`Window.length` 只读

返回窗口中的帧数。参见 `window.frames`。

`Window.location`

获取/设置 window 对象的位置，或当前的 URL。

`Window.locationbar` 只读

返回 locationbar 对象。

`Window.localStorage` 只读

返回一个对用于存储数据的本地存储对象的引用，该对象只能由创建它的源访问。

`Window.menubar` 只读

返回 menubar 对象。

`Window.mozInnerScreenX` 只读
非标准

返回窗口视口左上角的水平（X）坐标，以屏幕坐标表示。这个值是以 CSS 像素为单位报告的。请参阅 `nsIDOMWindowUtils` 中的 `mozScreenPixelsPerCSSPixel`，以获得转换系数，以便在需要时适应屏幕像素。

`Window.mozInnerScreenY` 只读
非标准

返回窗口视口左上角的垂直（Y）坐标，以屏幕坐标表示。这个值是以 CSS 像素为单位报告的。请参阅 `mozScreenPixelsPerCSSPixel`，如果需要的话，可以用一个转换系数来适应屏幕像素。

`Window.name`

获取/设置 window 对象的名称。

`Window.navigation` (en-US) 只读
实验性

返回当前 `window` 的相关 `Navigation` (en-US) 对象。是 `Navigation API` (en-US) 的入口点。

`Window.navigator` 只读

返回对 navigator 对象的引用。

`Window.opener`

返回对打开当前窗口的 window 的引用。

`Window.origin` 只读

返回全局对象的源，序列化为一个字符串。

`Window.outerHeight` 只读

获取浏览器窗口外侧的高度。

`Window.outerWidth` 只读

获取浏览器窗口外侧的宽度。

`Window.pageXOffset` 只读

`window.scrollX` 的别名。

`Window.pageYOffset` 只读

`window.scrollY` 的别名。

`Window.parent` 只读

返回对当前窗口或子框架的被继承对象的引用。

`Window.performance` 只读

返回一个 `Performance` 对象，其中包括 `timing` 和 `navigation` 属性，每个属性都是提供性能相关数据的对象。有关其他信息和例子，请参见使用导航计时。

`Window.personalbar` (en-US) 只读

返回 personalbar 对象。

`Window.scheduler` (en-US) 只读

返回与当前上下文相关的 `Scheduler` (en-US) 对象。这是使用优先级任务调度 API (en-US) 的入口。

`Window.screen` 只读

返回与该窗口相关的 screen 对象的引用。

`Window.screenX` 和 `Window.screenLeft` 只读

这两个属性都返回从用户浏览器视口的左边界到屏幕左侧的水平距离。

`Window.screenY` 和 `Window.screenTop` 只读

这两个属性都会返回从用户浏览器视口的上边界到屏幕上侧的垂直距离。

`Window.scrollbars` 只读

返回 scrollbars 对象。

`Window.scrollMaxX`
非标准
 只读

窗口在水平方向上可以滚动的最大偏移量，即文档宽度减去视口宽度。

`Window.scrollMaxY`
非标准
 只读

窗口在竖直方向上可以滚动的最大偏移量，即文档高度减去视口高度。

`Window.scrollX` 只读

返回文档已经被水平滚动的像素数。

`Window.scrollY` 只读

返回文档已经被竖直滚动的像素数。

`Window.self` 只读

返回对 window 对象本身的引用。

`Window.sessionStorage`

返回对用于存储数据的会话存储对象的引用，这些数据只能由创建它的源访问。

`Window.speechSynthesis` (en-US) 只读

返回 `SpeechSynthesis` 对象，这是使用 Web Speech API 语音合成功能的入门点。

`Window.statusbar` (en-US) 只读

返回 statusbar 对象。

`Window.toolbar` (en-US) 只读

返回 toolbar 对象。

`Window.top` 只读

返回对窗口层次结构中最顶层窗口的引用。这个属性是只读的。

`Window.visualViewport` 只读

返回 `VisualViewport` 对象，代表一个给定窗口的视觉视口。

`Window.window` 只读

返回对当前 window 的引用。

`window[0]`、`window[1]` 等

以逐帧形式返回对 `window` 对象的引用，要了解更多细节，参见 `Window.frames`。

### 已废弃属性

`Window.event`
已弃用
 只读

返回**当前事件**，即当前由 JavaScript 代码的上下文处理的事件，如果当前没有事件被处理，则返回 `undefined`。应尽可能使用直接传递给事件处理程序的 `Event` 对象来代替。

`Window.external`
已弃用
 只读

返回一个带有向浏览器添加外部搜索提供者的功能的对象。

`Window.orientation` (en-US)
已弃用
 只读

返回视口相对于设备自然方向的度数（以 90 度为增量）。

`Window.sidebar` (en-US)
已弃用

非标准
 只读

返回对侧边栏的 window 对象的一个引用。

`Window.status` (en-US)
已弃用

获取/设置浏览器底部状态栏中的文本。

实例方法
----

*本接口从 `EventTarget` 接口继承方法。*

`Window.addEventListener()`

为 window 上的特定事件类型注册一个事件处理器。

`Window.atob()`

解码一个使用 base-64 编码的数据字符串。

`Window.alert()`

显示一个警告对话框。

`Window.blur()`

将焦点从窗口上移开。

`Window.btoa()`

从一串二进制数据中创建一个 base-64 编码的 ASCII 字符串。

`Window.cancelAnimationFrame()`

取消之前使用 `Window.requestAnimationFrame` 安排的回调。

`Window.cancelIdleCallback()`

取消之前使用 `Window.requestIdleCallback` 安排的回调。

`Window.clearImmediate()`

取消使用 `setImmediate()` 设置的重复执行任务。

`Window.clearInterval()`

取消使用 `setInterval()` 设置的重复执行任务。

`Window.clearTimeout()`

取消使用 `setTimeout()` 设置的延时执行任务。

`Window.close()`

关闭当前窗口。

`Window.confirm()`

显示一个带有用户需要回应的信息对话框。

`Window.createImageBitmap()`

接受各种不同的图像源，并返回一个 `Promise`，经兑现可得到 `ImageBitmap`。可以选择将图片源裁剪成以 *(sx, sy)* 为起点的像素矩形，宽度为 sw，高度为 sh。

`Window.dispatchEvent()`

用于触发事件。

`Window.dump()`
非标准

向控制台中写一条消息。

`Window.fetch()`

开始从网络获取资源的过程。

`Window.find()`
非标准

在窗口中搜索给定的字符串。

`Window.focus()`

在当前窗口上设置焦点。

`Window.getComputedStyle()`

获取指定元素的计算样式。计算的样式表示该元素的所有 CSS 属性的计算值。

`Window.getDefaultComputedStyle()`
非标准

获取指定元素的默认计算样式，忽略作者样式表。

`Window.getSelection()`

返回代表所选项目的 selection 对象。

`Window.matchMedia()`

返回代表指定媒体查询字符串的 `MediaQueryList` 对象。

`Window.moveBy()`

将当前窗口移动一个指定的偏量值。

`Window.moveTo()`

将窗口移动到指定的坐标。

`Window.open()`

打开一个新窗口。

`Window.postMessage()`

为一个窗口向另一个窗口发送一串数据提供了安全的手段，该窗口不需要与第一个窗口在同一域内。

`Window.print()`

打开“打印”对话框，打印当前文档。

`Window.prompt()`

返回用户在提示对话框中输入的文本。

`Window.queryLocalFonts()`
实验性

返回 `Promise`，经兑现可得到包含一个代表本地可用字体的 `FontData` 对象数组。

`Window.removeEventListener()`

从 window 上移除一个事件监听器。

`Window.reportError()` (en-US)

报告一个脚本中的错误，模拟一个未处理的异常。

`Window.requestAnimationFrame()`

告诉浏览器一个动画正在进行中，要求浏览器为下一个动画帧安排窗口的重绘。

`Window.requestIdleCallback()`

启用浏览器空闲期间的任务调度。

`Window.resizeBy()`

按一定的变化量调整当前窗口的大小。

`Window.resizeTo()`

动态地调整窗口的大小。

`Window.scroll()`

将窗口滚动到文档中的一个特定位置。

`Window.scrollBy()`

将窗口中的文档按给定值滚动。

`Window.scrollByLines()`
非标准

按给定的行数滚动文档。

`Window.scrollByPages()`
非标准

按给定的页数滚动文档。

`Window.scrollTo()`

将文档滚动至特定坐标。

`Window.setImmediate()`

在浏览器完成其他繁重的任务后执行一个函数。

`Window.setInterval()`

安排一个函数，在给定的毫秒数过去后执行。

`Window.setResizable()` (en-US)
非标准

切换用户调整窗口大小的能力。

`Window.setTimeout()`

安排函数在给定的时间内执行。

`Window.sizeToContent()`
非标准

根据窗口的内容确定其大小。

`Window.showOpenFilePicker()`
实验性

显示一个文件选择器，允许用户选择一个文件或多个文件。

`Window.showSaveFilePicker()`
实验性

显示一个文件选择器，允许用户保存一个文件。

`Window.showDirectoryPicker()`
实验性

显示一个目录选择器，允许用户选择一个目录。

`Window.stop()`

该方法停止了窗口的加载。

`Window.updateCommands()`
非标准

更新当前 chrome 窗口（用户界面）的命令状态。

### 已废弃方法

`Window.back()`
非标准

已弃用

在窗口历史中后退一步。该方法已被废弃，应该使用 `history.back()` 代替。

`Window.captureEvents()` (en-US)
已弃用

注册窗口以捕获所有指定类型的事件。

`Window.forward()` (en-US)
非标准

已弃用

在窗口历史中前进一步。该方法已被废弃，应该使用 `history.forward()` 代替。

`Window.releaseEvents()` (en-US)
已弃用

解除窗口对特定类型事件的捕获。

`Window.showModalDialog()`
非标准

已弃用

显示一个对话框。

事件
--

通过使用 `addEventListener()` 或给这个接口的 `oneventname` 属性指定一个事件监听器来监听这些事件。

`error`

当一个资源加载失败，或不能使用时触发该事件。例如，如果脚本有一个执行错误，或者图像找不到或无效。

`languagechange` (en-US)

当用户的首选语言发生变化时，在全局范围对象中触发该事件。

`devicemotion`

以固定的时间间隔触发该事件，显示设备所接受的物理加速力的大小和旋转速率（如果有）。

`deviceorientation`

当磁力计方向传感器提供了关于设备当前方向与地球坐标框架的新数据时，触发该事件。

`resize`

窗口大小发生变化时触发。

`storage`

当一个存储区域（`localStorage` 或 `sessionStorage`）在另一个文档的上下文中被修改时，触发该事件。

### 动画事件

`animationcancel` (en-US)

当一个动画意外地中止时，触发该事件。

`animationend` (en-US)

当一个动画正常完成时，触发该事件。

`animationiteration` (en-US)

当一个动画迭代完成时，触发该事件。

`animationstart` (en-US)

当一个动画开始时，触发该事件。

### 剪切板事件

`copy`

当用户通过浏览器的用户界面启动一个复制动作时，触发该事件。也可通过 `oncopy` 属性设置。

`cut`

当用户通过浏览器的用户界面启动一个剪切动作时，触发该事件。也可通过 `oncut` 属性设置。

`paste`

当用户通过浏览器的用户界面启动一个粘贴动作时，触发该事件。也可通过 `paste` 属性设置。

### 连接事件

`offline`

当浏览器失去了对网络的访问，并且 `navigator.onLine` 的值转换为 `false` 时，触发该事件。

`online`

当浏览器获得了对网络的访问，并且 `navigator.onLine` 的值转换为 `true` 时，触发该事件。

### 聚焦事件

`blur`

当一个元素失去焦点时，触发该事件。

`focus`

当一个元素获得焦点时，触发该事件。

### Gamepad 事件

`gamepadconnected`

当浏览器检测到游戏板已被连接或首次使用游戏板的按钮/轴时启动。

`gamepaddisconnected` (en-US)

当浏览器检测到游戏板被断开连接时启动。

### 历史记录事件

`hashchange`

当 URL 的片段标识符（URL 中以 `#` 符号开头及其后面的部分）发生变化时，触发该事件。

`pagehide`

当浏览器隐藏了当前的文档，而在切换到显示会话历史中的另一个文档时触发该事件。例如，当用户点击“后退”按钮或点击“前进”按钮在会话历史中移动时，就会发生这种情况。

`pageshow`

当浏览器因导航任务而使文件可见时触发该事件，不仅包括页面首次加载时，还包括用户在同一标签内导航到另一个页面后再返回该页面等情况。

`popstate`

当活动的历史条目改变时，触发该事件。

### 加载和卸载事件

`beforeunload`

当窗口、文档及其资源即将被卸载时，触发该事件。

`load`

当整个页面加载完毕时触发该事件，包括所有依赖资源，如样式表图片。

`unload`

当文档或子资源正在被卸载时触发，触发该事件。

### 清单事件

`appinstalled`

当浏览器成功地将一个页面安装为一个应用程序时，触发该事件。

`beforeinstallprompt`

当用户即将被提示安装一个 web 应用程序时，触发该事件。

### 消息事件

`message`

窗口收到消息时触发该事件，例如从另一个浏览上下文中调用 `Window.postMessage()`。

`messageerror`

当 `Window` 对象收到无法反序列化的消息时，触发该事件。

### 打印事件

`afterprint`

在相关文档开始打印或打印预览关闭后，触发该事件。

`beforeprint`

当相关文件即将被打印或预览打印时，触发该事件。

### Promise 拒绝事件

`rejectionhandled`

每当一个 JavaScript `Promise` 被拒绝时，不管是否有处理程序来捕捉拒绝，都会触发该事件。

`unhandledrejection`

当 JavaScript `Promise` 被拒绝，但没有处理程序来捕获拒绝时，触发该事件。

### 渐变事件

`transitioncancel` (en-US)

当 CSS 渐变被取消时，触发该事件。

`transitionend` (en-US)

当 CSS 渐变完成时，触发该事件。

`transitionrun` (en-US)

当 CSS 渐变首次创建时，触发该事件。

`transitionstart` (en-US)

当 CSS 渐变真正开始时，触发该事件。

### 已废弃事件

`orientationchange`
已弃用

当设备的方向改变时，触发该事件。

`vrdisplayactivate` (en-US)
已弃用

非标准

当显示器可供呈现时，触发该事件。

`vrdisplayconnect` (en-US)
已弃用

非标准

当兼容的 VR 设备被连接到电脑上时，触发该事件。

`vrdisplaydisconnect` (en-US)
已弃用

非标准

当兼容的 VR 设备从电脑上断开时，触发该事件。

`vrdisplaydeactivate` (en-US)
已弃用

非标准

当显示器不再可供呈现时，触发该事件。

`vrdisplaypresentchange` (en-US)
已弃用

非标准

当 VR 设备的呈现状态发生变化时触发该事件，即从呈现状态变成不呈现状态，或者反之亦然。

接口
--

参见 DOM 参考文档。

规范
--

| Specification |
| --- |
| HTML Standard # the-window-object |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


DedicatedWorkerGlobalScope - Web API 接口参考

DedicatedWorkerGlobalScope
==========================

**`DedicatedWorkerGlobalScope`** 对象（也就是 `Worker` 全局作用域）可以通过 `self` 关键字来访问。一些在 worker 全局作用域下不可用的全局函数、命名空间对象以及构造器，也可以通过此对象使用。在 JavaScript 参考的 Web Workers 可以使用的函数和类 (en-US)页面中，有列举这些特性。

属性
--

*该接口从 `WorkerGlobalScope` (en-US) 接口以及它的父接口 `EventTarget` 继承属性，因此，此接口也实现了来自 `WindowTimers`、`WindowBase64` 的属性。*

`DedicatedWorkerGlobalScope.name` (en-US) 只读

通过 `Worker()` 构造器创建 `Worker` 时，可以选择为其设置一个名称，即此属性的值。这主要用于调试。

### 从 WorkerGlobalScope 继承的属性

`WorkerGlobalScope.self`

返回一个指向 `DedicatedWorkerGlobalScope` 本身的对象引用。

`WorkerGlobalScope.console` (en-US) 只读

返回与当前 worker 相关联的 `Console`。

`WorkerGlobalScope.location` (en-US) 只读

返回与当前 worker 相关联的 `WorkerLocation` (en-US)。`WorkerLocation` 是一个 worker 专有的 location 对象，基本上是浏览器作用域下 `Location` 的子集，但被被适配给了 worker。

`WorkerGlobalScope.navigator` (en-US) 只读

返回与当前 worker 相关联的 `WorkerNavigator` (en-US)。`WorkerNavigator` 是一个 worker 专有的 navigator 对象，基本上是浏览器作用域下 `Navigator` 的子集，但被被适配给了 worker。

`WorkerGlobalScope.performance` (en-US) 只读
非标准

返回与当前 worker 相关联的 `Performance`，是一个正常的 performance 对象，但只有一部分属性和方法可用。

### 事件处理器

*该接口从 `WorkerGlobalScope` (en-US) 接口以及它的父接口 `EventTarget` 继承事件处理器，因此，此接口也实现了来自 `WindowTimers`、`WindowBase64` 的事件处理器。*

`DedicatedWorkerGlobalScope.onmessage` (en-US)

Is an event handler representing the code to be called when the `message` event is raised. These events are of type `MessageEvent` and will be called when the worker receives a message from the document that started it (i.e. from the `Worker.postMessage` method.)

`DedicatedWorkerGlobalScope.onmessageerror` (en-US)

Is an event handler representing the code to be called when the `messageerror` (en-US) event is raised.

方法
--

*该接口从 `WorkerGlobalScope` (en-US) 接口以及它的父接口 `EventTarget` 继承方法，因此，此接口也实现了来自 `WindowTimers`、`WindowBase64` 的方法。*

`WorkerGlobalScope.close()` (en-US)

抛弃当前 `WorkerGlobalScope` 的 event loop 中所有正在排队的任务，关闭当前作用域。

`DedicatedWorkerGlobalScope.postMessage` (en-US)

向该 worker 的父文档发送消息——消息可以是任何 Javascript 对象。

### 从 WorkerGlobalScope 继承的方法

`WorkerGlobalScope.dump()` (en-US)
非标准

向控制台写入一条消息。

`WorkerGlobalScope.importScripts()`

向当前 worker 的作用域导入一或更多条脚本。可按需导入任意数量的脚本，使用逗号分割参数。比如： `importScripts('foo.js', 'bar.js');`

### 从其他来源实现的方法

`WindowBase64.atob()`

解码使用 base-64 编码的字符串数据。

`WindowBase64.btoa()`

从字符串生成使用 base-64 编码的 ASCII 字符串。

`WindowTimers.clearInterval()` (en-US)

取消使用 `WindowTimers.setInterval()` (en-US) 创建的定时操作。

`WindowTimers.clearTimeout()`

取消使用 `WindowTimers.setTimeout()` (en-US) 创建的定时操作。

`WindowTimers.setInterval()` (en-US)

每隔一定时间执行一次给定函数。

`WindowTimers.setTimeout()` (en-US)

延迟一定时间执行给定函数。

事件
--

`message` (en-US)

 Fired when the worker receives a message from its parent.
 Also available via the `onmessage` (en-US) property.

`messageerror` (en-US)

 Fired when a worker receives a message that can't be deserialized.
 Also available via the `onmessageerror` (en-US) property.

规范
--

| Specification |
| --- |
| HTML Standard # dedicated-workers-and-the-dedicatedworkerglobalscope-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `Worker`
* `WorkerGlobalScope` (en-US)
* 使用 web worker
* worker 可以使用的函数


HashChangeEvent - Web API 接口参考

HashChangeEvent
===============

**`HashChangeEvent`** 接口表示一个变化事件，当 URL 中的片段标识符发生改变时，会触发此事件。

片段标识符指 URL 中 `#` 号和它以后的部分。

Event

HashChangeEvent属性
--

*这个接口也从 `Event` 中继承属性。*

`HashChangeEvent.newURL` 只读

window 即将导航到达的新 URL。

`HashChangeEvent.oldURL` 只读

window 此前导航到达过的 URL。

方法
--

*这个接口没有自己的方法，但从 `Event` 中继承方法。*

示例
--

### 基本示例

```js
function locationHashChanged() {
  if (location.hash === "#somecoolfeature") {
    somecoolfeature();
  }
}

window.addEventListener("hashchange", locationHashChanged);
```

回落方法（Polyfill）
--------------

在 Modernizr GitHub page 中列出了几种回落（fallback）脚本。基本上，这些脚本每隔一段时间检查以此 `location.hash`。这里是其中一个版本，其仅允许一个处理程序（handler）绑定在 `onhashchange` 属性上：

```js
(function (window) {
  // 如果浏览器已经实现了此事件，则退出函数
  if ("onhashchange" in window.document.body) return;

  var location = window.location,
    oldURL = location.href,
    oldHash = location.hash;

  // 每隔 100 毫秒，检查一次片段标识符
  setInterval(function () {
    var newURL = location.href,
      newHash = location.hash;

    // 如果片段标识符有变化，且处理程序存在
    if (newHash != oldHash && typeof window.onhashchange === "function") {
      // 执行处理程序
      window.onhashchange({
        type: "hashchange",
        oldURL: oldURL,
        newURL: newURL,
      });

      oldURL = newURL;
      oldHash = newHash;
    }
  }, 100);
})(window);
```

规范
--

| Specification |
| --- |
| HTML Standard # the-hashchangeevent-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

相关事件
----

* `hashchange`
* `popstate`


Clipboard API - Web API 接口参考

Clipboard API
=============

Limited availability
--------------------

This feature is not Baseline because it does not work in some of the most widely-used browsers.

* Learn more
* See full compatibility
* Report feedback
剪贴板 **Clipboard** **API** 提供了响应剪贴板命令（剪切、复制和粘贴）与异步读写系统剪贴板的能力。从权限 Permissions API (en-US) 获取权限之后，才能访问剪贴板内容；如果用户没有授予权限，则不允许读取或更改剪贴板内容。

该 API 被设计用来取代使用 `document.execCommand()` 的剪贴板访问方式。

访问剪贴板
-----

除了在实例化中创建一个 `Clipboard` 对象，你还可以使用全局的 `Navigator.clipboard` 来访问系统剪贴板。

```js
navigator.clipboard
  .readText()
  .then(
    (clipText) => (document.querySelector(".editor").innerText += clipText),
  );
```

上述代码提取了剪贴板的文本并将其附在 class 为 `editor` 的第一个元素后面。因为当剪贴板中不是文本时， `readText()` (and `read()` (en-US), for that matter) 会返回一个空字符串，所以这段代码是安全的。

接口
--

`Clipboard` 安全上下文

提供了一个用于读写系统剪贴板上的文本和数据的接口。规范中被称为异步剪贴板 API（Async Clipboard API）。

`ClipboardEvent` 安全上下文

表示提供了有关剪贴板修改的信息的事件，也就是 `cut`、`copy`，和 `paste`。规范中被称为剪贴板事件 API（Clipboard Event API）。

规范
--

| Specification |
| --- |
| Clipboard API and events # clipboard-interface |
| Clipboard API and events # clipboard-event-interfaces |
| Clipboard API and events # clipboarditem |

浏览器兼容性
------

### api.Clipboard

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

### api.ClipboardEvent

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

### api.ClipboardItem

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* 权限 API：Permissions API (en-US)
* 使用权限 API


HTMLTemplateElement - Web API 接口参考

HTMLTemplateElement
===================

可以使用 **`HTMLTemplateElement`** 接口来访问 HTML `<template>` 元素的内容。

属性
--

*这个接口继承了 `HTMLElement` 的属性。*

`HTMLTemplateElement.content`只读

`DocumentFragment` 对象，包裹了模板元素 `<template>` 的内容。这个属性是只读的 DOM 树。

方法
--

*这个接口继承了 `HTMLElement` 的方法。*

规范
--

| Specification |
| --- |
| HTML Standard # htmltemplateelement |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


clearTimeout() - Web API 接口参考

clearTimeout()
==============

`WindowOrWorkerGlobalScope` 内置的 **`clearTimeout()`** 方法取消了先前通过调用`setTimeout()`建立的定时器。

语法
--
```

scope.clearTimeout(timeoutID)
```

### Parameters

`timeoutID`

你要取消定时器的标识符。该 ID 由相应的`setTimeout()`调用返回。

值得注意的是，`setTimeout()` 和 `setInterval()` 使用共享的 ID 池，意味着在技术上可以混用 `clearTimeout()` 和 `clearInterval()`。但是，为了清楚起见，你应该避免这样做。

示例
--

在一个网页中运行如下脚本，并且点击一次页面。一秒钟后你会看见弹出一条信息。如果你在一秒内不停点击页面，弹出框将不再出现。

```js
var alarm = {
  remind: function (aMessage) {
    alert(aMessage);
    delete this.timeoutID;
  },

  setup: function () {
    this.cancel();
    var self = this;
    this.timeoutID = window.setTimeout(
      function (msg) {
        self.remind(msg);
      },
      1000,
      "Wake up!",
    );
  },

  cancel: function () {
    if (typeof this.timeoutID == "number") {
      window.clearTimeout(this.timeoutID);
      delete this.timeoutID;
    }
  },
};
window.onclick = function () {
  alarm.setup();
};
```

注意
--

传入一个错误的 ID 给 `clearTimeout()`不会有任何影响；也不会抛出异常。

规范
--

| Specification |
| --- |
| HTML Standard # dom-cleartimeout-dev |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

更多
--

* `WindowTimers.setTimeout()` (en-US)
* `WindowTimers.setInterval()` (en-US)
* `WindowTimers.clearInterval()` (en-US)
* `Window.requestAnimationFrame()`
* *Daemons* management


Permissions - Web API 接口参考

Permissions
===========

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

Permissions API的 Permissions 接口提供核心 PermissionAPI 功能，例如查询和撤消权限的方法。

方法
--

`Permissions.query()` (en-US)

返回给定 API 的用户权限状态。

`Permissions.request()`

请求使用给定 API 的权限，目前此功能尚未在任何浏览器中被支持。

`Permissions.requestAll()`

请求使用一组给定 API 的权限。目前此功能尚未在任何浏览器中被支持。

`Permissions.revoke()` (en-US)

返回撤消当前在给定 API 上设置的权限。

Example
-------

```js
navigator.permissions.query({ name: "geolocation" }).then(function (result) {
  if (result.state === "granted") {
    showLocalNewsWithGeolocation();
  } else if (result.state === "prompt") {
    showButtonToEnableLocalNews();
  }
  // 如果没有此权限则不什么也做
});
```

Specification
-------------

| Specification |
| --- |
| Permissions # permissions-interface |

Browser Support
---------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


HTMLOptionElement - Web API 接口参考

HTMLOptionElement
=================

**`HTMLOptionElement`** 接口表示了 `<option>` 元素并继承`HTMLElement`接口所有的类和方法。

属性
--

*继承自其父类属性，`HTMLElement`.*

| 名称 | 类型 | 描述 |
| --- | --- | --- |
| `defaultSelected` | `Boolean` (en-US) | 包含了`selected` HTML 特性的初始值，指示默认情况下是否选择该选项。 |
| `disabled` | `Boolean` (en-US) | 反映了`disabled` HTML 特性 的值 , 这意味着选项（option）是不可选的。如果一个选项是关闭的`<optgroup>`元素的子元素，那么它也可被关闭。 |
| `form`只读  | `HTMLFormElement` | 如果该选项是`<select>` 元素的后代，则该属性与相应`HTMLSelectElement` (en-US) 对象的`form`属性具有相同的值; 否则为`null`。 |
| `index`只读  | `long` | 该选项在其所属的选项列表中的位置，以树形顺序排列。如果该选项不是选项列表的一部分，例如为 `<datalist>` 元素的一部分时，该值为`0`。 |
| `label` | `DOMString` | 反映`label` HTML 特性的值，该属性为选项提供了一个标签。如果没有特别设置此属性，读取它返回元素的文本内容。 |
| `selected` | `Boolean` (en-US) | 表示当前该 option 是否被选择。 |
| `text` | `DOMString` | 包含元素的文本内容。 |
| `value` | `DOMString` | 反映`value` HTML 特性的值（如果存在）；否则反映`Node.textContent` 特性的值。 |

方法
--

*方法继承自其父类，`HTMLElement`.*

`HTMLOptionElement.Option()`是一个创建`HTMLOptionElement`对象的构造函数。它有四个值：要显示的文本，`文本`，关联的值，`值`，defaultSelected 的值以及`所选`的值。最后三个值是可选的。

规范
--

| Specification |
| --- |
| HTML Standard # htmloptionelement |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* 实现此接口的 HTML 元素 : `<option>`。


MutationRecord - Web API 接口参考

MutationRecord
==============

每个 **`MutationRecord`** 都代表一个独立的 DOM 变化，在每次随 DOM 变化调用 `MutationObserver` 的回调函数时，一个相应的 `MutationRecord` 会被作为参数，传递给回调函数。

属性
--

|  |  |  |
| --- | --- | --- |
| 属性 | 类型 | 描述 |
| `MutationRecord.type` (en-US) | `String` |
 如果是属性变化，则返回 `"attributes"`；如果是
 `characterData` 节点变化，则返回
 `"characterData"`；如果是子节点树
 `childList` 变化，则返回 `"childList"`。
  |
| `MutationRecord.target` (en-US) | `Node` |
 根据
 `MutationRecord.type` (en-US)，返回变化所影响的节点。对于属性
 `attributes` 变化，返回属性变化的节点。对于
 `characterData` 变化，返回
 `characterData` 节点。对于子节点树
 `childList` 变化，返回子节点变化的节点。
  |
| `MutationRecord.addedNodes` (en-US) | `NodeList` |
 返回被添加的节点。如果没有节点被添加，则该属性将是一个空的
 `NodeList`。
  |
| `MutationRecord.removedNodes` (en-US) | `NodeList` |
 返回被移除的节点。如果没有节点被移除，则该属性将是一个空的
 `NodeList`。
  |
| `MutationRecord.previousSibling` (en-US) | `Node` | 返回被添加或移除的节点之前的兄弟节点，或者 `null`。 |
| `MutationRecord.nextSibling` (en-US) | `Node` | 返回被添加或移除的节点之后的兄弟节点，或者 `null`。 |
| `MutationRecord.attributeName` (en-US) | `String` | 返回被修改的属性的属性名，或者 `null`。 |
| `MutationRecord.attributeNamespace` (en-US) | `String` | 返回被修改属性的命名空间，或者 `null`。 |
| `MutationRecord.oldValue` (en-US) | `String` |
 返回值取决于 `MutationRecord.type` (en-US)。对于属性
 `attributes` 变化，返回变化之前的属性值。对于
 `characterData`
 变化，返回变化之前的数据。对于子节点树
 `childList` 变化，返回 `null`。

 注意，如果要让这个属性起作用，在相应的
 MutationObserverInit
 参数的 `MutationObserver`
observe
 方法中，`attributeOldValue` 或者
 `characterDataOldValue` 必须设置为 `true`。

 |

规范
--

| Specification |
| --- |
| DOM Standard # interface-mutationrecord |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


CSSStyleRule - Web API 接口参考

CSSStyleRule
============

**`CSSStyleRule`** 表示一条 CSS 样式规则。它实现了 `CSSRule` 接口，类型的值为 `1`（`CSSRule.STYLE_RULE`）。

属性
--

`CSSStyleRule.selectorText`

返回这条规则的、文本格式的选择器，例如 `"h1,h2"`。

`CSSStyleRule.style` 只读

返回这条规则的 `CSSStyleDeclaration` 对象。

`CSSStyleRule.styleMap` (en-US) 只读

返回一个 `StylePropertyMap` 对象，which provides access to the rule's property-value pairs.

规范
--

| Specification |
| --- |
| CSS Object Model (CSSOM) # the-cssstylerule-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


CSS - Web API 接口参考

CSS
===

`CSS` 接口涵盖 CSS 相关的实用方法。尚且不存在实现这个接口的对象：它仅仅包含静态的方法，因此也是一个实用性的接口。

属性
--

CSS 接口是一个工具接口，无法创建该类型的对象：其内部只定义了静态属性。

### 静态属性

`CSS.paintWorklet` (en-US)
实验性
安全上下文

针对所有与绘制相关的类，提供对负责它们的工作集的访问。

方法
--

CSS 接口是一个工具接口，无法创建该类型的对象：其内部只定义了静态方法。

### 静态方法

没有继承的静态方法。

`CSS.registerProperty()` (en-US)

注册 `custom properties`，启用属性类型检查、默认值，以及继承了或者没有继承它们值的属性。

`CSS.supports()`

返回一个 `Boolean` 来表明键值对、条件，或者传入参数是否受支持。

`CSS.escape()`

可以用来转义一个大多用来当作 CSS 选择器一部分的字符串。

`CSS factory functions`

可以用来返回一个 `CSSUnitValue` (en-US)。它的值由传入的数值以及调用的 factory 方法名称组成。
```

CSS.em(3) // CSSUnitValue {value: 3, unit: "em"}
```

规范
--

| Specification |
| --- |
| CSS Object Model (CSSOM) # namespacedef-css |
| CSS Properties and Values API Level 1  |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* Components.utils.importGlobalProperties


Storage API - Web API 接口参考

Storage API
===========

**安全上下文:** 此项功能仅在一些支持的浏览器的安全上下文（HTTPS）中可用。

Web 存储标准，the Storage Standard，定义了一个通用的、共享的存储系统，供所有 API 和技术使用，以存储各个网站的内容可访问数据。Storage API 允许网站的代码、Web 应用程序知道它们可以使用、已经使用多少存储空间。空间不足时，用户代理会自动清理站点数据，以便为其他用途腾出空间。而 Storage API 甚至可以控制：在执行清理之前，是否需要提醒代码或 Web 应用程序，以便作出反应。

**备注：** 此特性在 Web Worker 中可用

站点存储——由存储标准管理的网站数据——包括以下几种：

* IndexedDB 数据库
* Cache API data
* Service Worker registrations
* Web Storage API data managed using `window.localStorage`
* 使用 `History.pushState()` 保存的历史状态信息
* Application caches
* Notification data
* 可维护的、其他类型的、站点可访问的，站点特定数据
站点存储单元
------

由存储标准描述并使用存储 API 进行交互的站点存储系统，由每个 origin 的单个**站点存储单元**（**site storage unit**）组成。实际上，每个 Web 站点或 Web 应用程序都有自己的存储单元，用于存储数据。下图显示了一个站点存储池，其中包含三个存储单元，显示了存储单元如何可以在其中存储不同的数据类型，并且可能具有不同的配额（最大存储限制）。

![A diagram showing how the site storage pool consists of multiple storage units that contain data from various APIs as well as possible unused space left before the quota is reached.](/zh-CN/docs/Web/API/Storage_API/storageunits.png)

* 来源 1 有一些 Web Storage 数据和一些 IndexedDB 数据，还有一些空闲空间。目前它的使用量没有达到配额限制。
* 来源 2 中没有存储任何数据；它只是一个空盒子在等待内容。然而，这个来源地的配额比其他两个低。它可能是访问较少的站点，或者已知具有较低数据存储要求的站点
* 来源 3 的存储单元已被完全填满；它达到了它的配额限制，并且无法在不删除某些现有数据的情况下存储更多数据。

User agent 可能使用各种技术来确定各种来源的配额。规范特别鼓励的、最有可能的方法之一，实际上是考虑各个站点的流行程度 和/或使用水平，以确定它们的配额应该是什么。还可以想象，浏览器可能会提供一个用户界面来定制这些配额。

存储模式
----

每个站点存储单元中的实际数据存储，被称为它的**框** / **盒**（**box**）。每个站点存储单元只有一个盒，盒中包含其所有数据，且有一个**盒存储模式** / **存储模式**（**box mode**），用于描述其数据保留策略。目前有两种模式：

`"best-effort"`

用户代理将会将尽可能久地保留 box 中包含的数据，但若因存储空间不足儿必须清空 box 以释放存储压力时，用户代理**不会警告用户**。

`"persistent"`

用户代理将会将尽可能久地保留此模式的数据，只有在所有被标记为 `"best-effort"` 的 box 都已被清理后，才会清理被标记为 `"persistent"` 的 box。如果需要考虑清除持久性框（persistent boxes），用户代理将通知用户，并根据需要提供清除一个或多个持久性框（persistent boxes）的方法。

修改某个来源的 box mode 需要取得使用 `"persistent-storage"` 特性的权限。

数据持久性与清理
--------

如果站点或应用程序具有“**永久存储（`persistent-storage`）**”功能权限，则可以使用 `StorageManager.persist()` 方法来请求将其 box 设为持久的。由于使用特性或其他度量，用户代理还可以决定使站点的存储单元持久化。“持久存储”功能的与权限相关的标志、算法和类型都设置为权限的标准默认值，只是整个源位置的权限状态必须相同，并且如果未“授予”权限状态（无论出于何种原因，访问持久性存储功能被拒绝），源站点存储单元的 box 模式总是“尽力”。

**备注：** 请参考 使用 Permissions API 以了解更多关于申请与管理权限的信息。

当清除站点存储单元时，源站的框被视为单个实体；如果用户代理需要清除它并且用户批准，则清除整个数据存储，而不是提供某种仅从单个 api 清除数据的方法。

如果一个框被标记为“持久（`persistent`）” ，那么如果没有数据的源代码本身或用户明确地这样做，用户代理将不会清除内容。这包括用户选择“清除缓存”或“清除最近的历史记录”选项等场景。将特别要求用户具有删除永久性站点存储单元的权限。

配额与使用量的估算
---------

The user agent determines, using whatever mechanism it chooses, the maximum amount of storage a given site can use. This maximum is the origin's **quota**. The amount of this space which is in use by the site is called its **usage**. Both of these values are estimates; there are several reasons why they're not precise:

* User agents are encouraged to obscure the exact size of the data used by a given origin, to prevent these values from being used for fingerprinting purposes.
* De-duplication, compression, and other methods to reduce the physical size of the stored data may be used.
* Quotas are conservative estimates of the space available for the origin's use, and should be less than the available space on the device to help prevent overruns.

User agents may use any method they choose to determine the size of origins' quotas, and are encouraged by the specification to provide popular or frequently-used sites with extra space.

To determine the estimated quota and usage values for a given origin, use the `navigator.storage.estimate()` method, which returns a promise that, when resolved, receives a `StorageEstimate` that contains these figures. For example:

```js
navigator.storage.estimate().then((estimate) => {
  // estimate.quota 是估得的配额
  // estimate.usage 是估得的使用量，单位为 byte 比特
});
```

规范
--

| Specification |
| --- |
| Storage Standard # storagemanager |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `navigator.storage` (en-US)
* `StorageManager` (the object returned by `navigator.storage`)
* 使用 Permissions API


FocusEvent - Web API 接口参考

FocusEvent
==========

**`FocusEvent`** 接口表示和焦点相关的事件比如 `focus`, `blur`, `focusin` (en-US), 和 `focusout`。

Event

UIEvent

FocusEvent构造器
---

`FocusEvent()` (en-US)

使用给定的参数创建 `FocusEvent` 事件。

属性
--

*此接口从它的父级继承了属性 `UIEvent`, 间接来自于 `Event`*.

`FocusEvent.relatedTarget` (en-US) 只读

`EventTarget` 这个代表此次事件的次要目标。在一些案例中，例如切换浏览器 tab 标签时，为了安全的原因，这个属性可能会被设置为 `null` 。

方法
--

*此接口没有特殊的方法。它从父级 `UIEvent` 继承方法*, 并间接从 `Event` 继承方法。

规范
--

| Specification |
| --- |
| UI Events # interface-focusevent |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `Event` 基接口


PerformancePaintTiming - Web API 接口参考

PerformancePaintTiming
======================

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

Paint Timing API (en-US) 提供的 **`PerformancePaintTiming`** 是一个提供页面在构建过程中的“绘制”（也称“渲染”）时间点信息的接口。“绘制”是指将渲染树转换为页面上像素的过程。

应用可以为名为“`paint`”的`performance entry 类型` 注册一个`PerformanceObserver`，然后观察者可以获取绘制相关的事件发生的时间。以此来帮你找出那些花费太多时间去绘制的区域，而后提升用户体验。

PerformanceEntry

PerformancePaintTiming属性
--

这个接口没有属性，但是（为了"`paint`" `performance entry 类型`）通过一些限制和约束 扩展了以下`PerformanceEntry`属性

`PerformanceEntry.entryType`

返回 "`paint`".

`PerformanceEntry.name`

返回 `"first-paint"` 或`"first-contentful-paint"`.

`PerformanceEntry.startTime` (en-US)

当开始“绘制“时返回 `timestamp`.

`PerformanceEntry.duration` (en-US)

返回 0.

方法
--

这个接口没有方法

例子
--

```js
function showPaintTimings() {
  if (window.performance) {
    let performance = window.performance;
    let performanceEntries = performance.getEntriesByType("paint");
    performanceEntries.forEach((performanceEntry, i, entries) => {
      console.log(
        "The time to " +
          performanceEntry.name +
          " was " +
          performanceEntry.startTime +
          " milliseconds.",
      );
    });
  } else {
    console.log("Performance timing isn't supported.");
  }
}
```

上面例子输出如下
```

The time to first-paint was 2785.915 milliseconds.
The time to first-contentful-paint was 2787.460 milliseconds.
```

规范
--

| Specification |
| --- |
| Paint Timing # sec-PerformancePaintTiming |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


DOMTokenList - Web API 接口参考

DOMTokenList
============

**`DOMTokenList`** 接口表示一组空格分隔的标记（tokens）。如由 `Element.classList`、`HTMLLinkElement.relList` (en-US)、`HTMLAnchorElement.relList` (en-US) 或 `HTMLAreaElement.relList` (en-US) 返回的一组值。它和 JavaScript `Array` 对象一样，索引从 0 开始。`DOMTokenList` 总是区分大小写（case-sensitive）。

属性
--

`DOMTokenList.length` 只读

一个整数，表示存储在该对象里值的个数。

`DOMTokenList.value` (en-US)

该属性以 `DOMString` 的形式返回 **`DOMTokenList`** 列表的值。

方法
--

`DOMTokenList.item(index)`

根据传入的索引值返回一个值，如果索引值大于等于符号列表的长度（`length`），则返回 `undefined` 或 `null`，在 Gecko 7.0 之前的版本中返回 `null`。

`DOMTokenList.contains(token)`

如果 DOMTokenList 列表中包括相应的字符串 `token`，则返回 `true`，否则返回 `false`。

`DOMTokenList.add(token1[, token2[, ...tokenN]])`

添加一个或多个标记（`token`）到 `DOMTokenList` 列表中。

`DOMTokenList.remove(token1[, token2[, ...tokenN]])`

从 `DOMTokenList` 列表中移除一个或多个标记（`token`）。

`DOMTokenList.replace(oldToken, newToken)`

使用 `newToken` 替换 `token`\_ 。\_

`DOMTokenList.supports(token)`

如果传入的 `token` 是相关属性（attribute）支持的标记，则返回 `true` 。

`DOMTokenList.toggle(token [, force])`

从 DOMTokenList 字符串中移除标记字串（`token`），并返回 `false`。如果传入的字串（`token`）不存在，则将其添加进去，并返回 `true` 。`force` 是一个可选的布尔值，如果传入 `true` ，且传入的 *`token`* 不存在，则将其添加进去并返回 `true` ，若传入的 *`token`* 存在，则直接返回 `true` ；反之，如果传入 `false` ，则移除存在的 `token`，并返回 `false` ，如 `token` 不存在则直接返回 `false` 。

`DOMTokenList.entries()` (en-US)

返回一个迭代器（`iterator`），以遍历这个对象中的所有键值对。

`DOMTokenList.forEach(callback [, thisArg])` (en-US)

为每个 `DOMTokenList` 中的元素都调用一次传入的 `callback` 函数。

`DOMTokenList.keys()`

返回一个迭代器（`iterator`）以遍历这个对象中所有键值对的键。

`DOMTokenList.values()` (en-US)

返回一个迭代器（`iterator`）以遍历这个对象中所有键值对的值。

示例
--

在下面这个简单的例子中，我们使用 `Element.classList` 获取了 `<p>` 元素的 class 列表，也就是一个`DOMTokenList` ，再使用 `DOMTokenList.add()` 添加了一个 class，然后更新 `<p>` 元素的`Node.textContent`以显示这个新的 `DOMTokenList`。

### HTML

```html
<p class="a b c"></p>
```

### JavaScript

```js
let para = document.querySelector("p");
let classes = para.classList;
para.classList.add("d");
para.textContent = `paragraph classList is "${classes}"`;
```

输出类似这样：

去除空格和重复项目
---------

修改 `DOMTokenList` 的方法（例如 `DOMTokenList.add()`）会自动去除多余的空格（Whitespace）和列表中的重复项目。例如：

```html
<span class=" d d e f"></span>
```

```js
let span = document.querySelector("span");
let classes = span.classList;
span.classList.add("x");
span.textContent = `span classList is "${classes}"`;
```

输出类似这样：

规范
--

| Specification |
| --- |
| DOM Standard # interface-domtokenlist |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `DOMSettableTokenList` (object that extends DOMTokenList with settable *.value* property)
* Firefox bug 501257 - Implement HTML 5's HTMLElement.classList property


SpeechSynthesis - Web API 接口参考

SpeechSynthesis
===============

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

网页语音 API 的\*\*`SpeechSynthesis`\*\* 接口是语音服务的控制接口；它可以用于获取设备上关于可用的合成声音的信息，开始、暂停语音，或除此之外的其他命令。

属性
--

*`SpeechSynthesis` 也从它的父接口继承属性，`EventTarget`.*

`SpeechSynthesis.paused` 只读

当`SpeechSynthesis` 处于暂停状态时， `Boolean` (en-US) 值返回 `true` 。

`SpeechSynthesis.pending` (en-US) 只读

当语音播放队列到目前为止保持没有说完的语音时， `Boolean` (en-US) 值返回 `true` 。

`SpeechSynthesis.speaking` (en-US) 只读

当语音谈话正在进行的时候，即使`SpeechSynthesis`处于暂停状态， `Boolean` (en-US) 返回 `true` 。

### 事件操作

`SpeechSynthesis.onvoiceschanged` (en-US)

当由`SpeechSynthesis.getVoices()`方法返回的`SpeechSynthesisVoice` (en-US)列表改变时触发。

方法
--

*`SpeechSynthesis` 也从它的父接口继承方法， `EventTarget`.*

`SpeechSynthesis.cancel()` (en-US)

移除所有语音谈话队列中的谈话。

`SpeechSynthesis.getVoices()`

返回当前设备所有可用声音的 `SpeechSynthesisVoice` (en-US)列表。

`SpeechSynthesis.pause()` (en-US)

把 `SpeechSynthesis` 对象置为暂停状态。

`SpeechSynthesis.resume()` (en-US)

把 `SpeechSynthesis` 对象置为一个非暂停状态：如果已经暂停了则继续。

`SpeechSynthesis.speak()` (en-US)

添加一个 `utterance` (en-US) 到语音谈话队列；它将会在其他语音谈话播放完之后播放。

示例
--

在我们基础的 Speech synthesiser 演示中，我们第一次用 `window.speechSynthesis`抓取了关于语音播放控制器的参考。在定义了一些必要的变量后，我们用 `SpeechSynthesis.getVoices()`获取了一列可用的声音并且用它们生成一列可选表单，这样用户能够选择他们想要的声音。

`inputForm.onsubmit` 的内部操作中，我们用preventDefault()阻止了表单的提交，创建了一个从`<input>`文本框获取文本的新`SpeechSynthesisUtterance` (en-US)实例，在`<select>`元素可选的声音设置成语音谈话的 voice 属性，然后通过`SpeechSynthesis.speak()` (en-US)方法开始语音播放。

```js
var synth = window.speechSynthesis;

var inputForm = document.querySelector("form");
var inputTxt = document.querySelector(".txt");
var voiceSelect = document.querySelector("select");

var pitch = document.querySelector("#pitch");
var pitchValue = document.querySelector(".pitch-value");
var rate = document.querySelector("#rate");
var rateValue = document.querySelector(".rate-value");

var voices = [];

function populateVoiceList() {
  voices = synth.getVoices();

  for (i = 0; i < voices.length; i++) {
    var option = document.createElement("option");
    option.textContent = voices[i].name + " (" + voices[i].lang + ")";

    if (voices[i].default) {
      option.textContent += " -- DEFAULT";
    }

    option.setAttribute("data-lang", voices[i].lang);
    option.setAttribute("data-name", voices[i].name);
    voiceSelect.appendChild(option);
  }
}

populateVoiceList();
if (speechSynthesis.onvoiceschanged !== undefined) {
  speechSynthesis.onvoiceschanged = populateVoiceList;
}

inputForm.onsubmit = function (event) {
  event.preventDefault();

  var utterThis = new SpeechSynthesisUtterance(inputTxt.value);
  var selectedOption = voiceSelect.selectedOptions[0].getAttribute("data-name");
  for (i = 0; i < voices.length; i++) {
    if (voices[i].name === selectedOption) {
      utterThis.voice = voices[i];
    }
  }
  utterThis.pitch = pitch.value;
  utterThis.rate = rate.value;
  synth.speak(utterThis);

  inputTxt.blur();
};
```

规范
--

| Specification |
| --- |
| Web Speech API # tts-section |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* Web Speech API


CanvasCaptureMediaStream - Web API 接口参考

CanvasCaptureMediaStream
========================

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

**`CanvasCaptureMediaStream`** 接口表示 `MediaStream` 对 `HTMLCanvasElement` 元素进行实时画面捕捉的内容。

属性
--

*此接口继承了其父类 `MediaStream` 与 `EventTarget` 的属性。*

`CanvasCaptureMediaStream.canvas` (en-US) 只读

可返回当前媒体流所对应的 `HTMLCanvasElement` 元素对象。

方法
--

*此接口继承了其父类 `MediaStream` 与 `EventTarget` 的方法。*

`CanvasCaptureMediaStream.requestFrame()` (en-US)

手动获取媒体流的一帧。可以捕捉部分渲染帧画面。

说明
--

| Specification |
| --- |
| Media Capture from DOM Elements # the-canvascapturemediastreamtrack |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

其他参考资料
------

* `HTMLCanvasElement.captureStream()`


WebGLVertexArrayObject - Web API 接口参考

WebGLVertexArrayObject
======================

\*\*`WebGLVertexArrayObject`\*\*接口是WebGL 2 API的一部分，顶点数组对象 (VAOs) 指向顶点数组数据，并提供不同顶点数据集合的名称。

当使用`WebGLVertexArrayObject`对象时，这些方法会很有用：

* `WebGL2RenderingContext.createVertexArray()`
* `WebGL2RenderingContext.deleteVertexArray()` (en-US)
* `WebGL2RenderingContext.isVertexArray()` (en-US)
* `WebGL2RenderingContext.bindVertexArray()` (en-US)

**备注：** **WebGL 1:** `OES_vertex_array_object` 扩展允许你在 WebGL 1 上下文环境中使用顶点数组对象。

示例
--

```js
var vao = gl.createVertexArray();
gl.bindVertexArray(vao);

// ...
// calls to bindBuffer or vertexAttribPointer
// which will be "recorded" in the VAO
// ...
```

规范
--

| Specification |
| --- |
| WebGL 2.0 Specification # 3.6 |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

相关链接
----

* `OES_vertex_array_object`


XMLHttpRequestEventTarget - Web API 接口参考

XMLHttpRequestEventTarget
=========================

`XMLHttpRequestEventTarget` 是一个描述事件处理程序的接口，你可以在一个用于处理 `XMLHttpRequest` 事件的对象中使用到该事件处理程序。

EventTarget

XMLHttpRequestEventTarget属性
--

`XMLHttpRequestEventTarget.onabort`

当请求失败时调用该方法，接受 `abort` 对象作为参数。

`XMLHttpRequestEventTarget.onerror`

当请求发生错误时调用该方法，接受 `error` 对象作为参数。

`XMLHttpRequestEventTarget.onload`

当一个 HTTP 请求正确加载出内容后返回时调用，接受 `load` 对象作为参数。

`XMLHttpRequestEventTarget.onloadstart`

当一个 HTTP 请求开始加载数据时调用，接受 `loadstart` 对象作为参数。

`XMLHttpRequestEventTarget.onprogress`

间歇调用该方法用来获取请求过程中的信息，接受 `progress` 对象作为参数。

`XMLHttpRequestEventTarget.ontimeout`

当超时时调用，接受 `timeout` 对象作为参数；只有设置了 `XMLHttpRequest` 对象的 `timeout` 属性时，才可能发生超时事件。

`XMLHttpRequestEventTarget.onloadend`

当内容加载完成，不管失败与否，都会调用该方法，接受 `loadend` 对象作为参数。

规范
--

| Specification |
| --- |
| XMLHttpRequest Standard # xmlhttprequesteventtarget |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `XMLHttpRequest`
* 使用 XMLHttpRequest


Selection - Web API 接口参考

Selection
=========

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

`Selection` 对象表示用户选择的文本范围或插入符号的当前位置。它代表页面中的文本选区，可能横跨多个元素。文本选区由用户拖拽鼠标经过文字而产生。要获取用于检查或修改的 Selection 对象，请调用 `window.getSelection()`。

一般来说，插入光标的位置可通过 Selection 获取，这时它被标记为 `Collapsed`，这表示选区被压缩至一点，即光标位置。但要注意它与 `focus` 事件或 `Document.activeElement` 等的值没有必然联系。

用户可能从左到右（与文档方向相同）选择文本或从右到左（与文档方向相反）选择文本。`anchor` 指向用户开始选择的地方，而 `focus` 指向用户结束选择的地方。如果你使用鼠标选择文本的话，anchor 就指向你按下鼠标键的地方，而 focus 就指向你松开鼠标键的地方。anchor 和 focus 的概念不能与选区的起始位置和终止位置混淆，因为 anchor 指向的位置可能在 focus 指向的位置的前面，也可能在 focus 指向位置的后面，这取决于你选择文本时鼠标移动的方向（也就是按下鼠标键和松开鼠标键的位置）。

Selection 对象所对应的是用户所选择的 `ranges`（区域），俗称拖蓝。默认情况下，该函数只针对一个区域，我们可以这样使用这个函数：

```js
var selObj = window.getSelection();
var range = selObj.getRangeAt(0);
```

* `selObj` 被赋予一个 Selection 对象
* `range` 被赋予一个 Range 对象

调用 `Selection.toString()` 方法会返回被选中区域中的**纯文本**。要求变量为字符串的函数会自动对对象进行该处理，例如：

```js
var selObj = window.getSelection();
window.alert(selObj);
```

术语表
---

本页面使用的其他关键词汇：

锚点 (anchor)

锚指的是一个选区的起始点（不同于 HTML 中的锚点链接，译者注）。当我们使用鼠标框选一个区域的时候，锚点就是我们鼠标按下瞬间的那个点。在用户拖动鼠标时，锚点是不会变的。

焦点 (focus)

选区的焦点是该选区的终点，当你用鼠标框选一个选区的时候，焦点是你的鼠标松开瞬间所记录的那个点。随着用户拖动鼠标，焦点的位置会随着改变。

范围 (range)

范围指的是文档中连续的一部分。一个范围包括整个节点，也可以包含节点的一部分，例如文本节点的一部分。用户通常下只能选择一个范围，但是有的时候用户也有可能选择多个范围（例如当用户按下 Control 按键并框选多个区域时，Chrome 中禁止了这个操作，译者注）。“范围”会被作为 `Range` 对象返回。Range 对象也能通过 DOM 创建、增加、删减。

可编辑元素 (editing host)

一个用户可编辑的元素（例如一个使用 `contenteditable` 的 HTML 元素，或是在启用了 `designMode` 的 `Document` 的子元素）。详见 开发者笔记。

属性
--

`anchorNode`只读

返回该选区起点所在的节点（`Node`）。

`anchorOffset`只读

返回一个数字，其表示的是选区起点在 `anchorNode` 中的位置偏移量。

1. 如果 `anchorNode` 是文本节点，那么返回的就是从该文字节点的第一个字开始，直到被选中的第一个字之间的字数（如果第一个字就被选中，那么偏移量为零）。
2. 如果 `anchorNode` 是一个元素，那么返回的就是在选区第一个节点之前的同级节点总数。(这些节点都是 `anchorNode` 的子节点)

`focusNode`只读

返回该选区终点所在的节点。

`focusOffset`只读

返回一个数字，其表示的是选区终点在 `focusNode` 中的位置偏移量。

1. 如果 `focusNode` 是文本节点，那么选区末尾未被选中的第一个字，在该文字节点中是第几个字（从 0 开始计），就返回它。
2. 如果 `focusNode` 是一个元素，那么返回的就是在选区末尾之后第一个节点之前的同级节点总数。

`isCollapsed`只读

返回一个布尔值，用于判断选区的起始点和终点是否在同一个位置。

`rangeCount`只读

返回该选区所包含的连续范围的数量。

方法
--

`getRangeAt`

返回选区包含的指定区域（`Range`）的**引用**。

`collapse`

将当前的选区折叠为一个点。

`extend`

将选区的焦点移动到一个特定的位置。

`modify`

修改当前的选区。

`collapseToStart`

将当前的选区折叠到起始点。

`collapseToEnd`

将当前的选区折叠到最末尾的一个点。

`selectAllChildren`

将某一指定节点的子节点框入选区。

`addRange`

一个区域（`Range`）对象将被加入选区。

`removeRange`

从选区中移除一个区域。

`removeAllRanges`

将所有的区域都从选区中移除。

`deleteFromDocument` (en-US)

从页面中删除选区中的内容。

`selectionLanguageChange`

当键盘的朝向发生改变后修改指针的 Bidi 优先级。

`toString`

返回当前选区的纯文本内容。

`containsNode`

判断某一个 `Node` 是否为当前选区的一部分。

开发者笔记
-----

### 选区的字符串表示

调用 `Selection.toString()` 方法返回包含在选区内的文本，例如：

```js
var selObj = window.getSelection();
window.alert(selObj);
```

注意，使用选择对象作为 `window.alert` 的参数将调用对象的 `toString` 方法。

### 选区中的多个区域

一个 `Selection` 对象表示用户选择的 `Range` 的集合。通常，它只包含一个区域，访问方式如下：

```js
var selObj = window.getSelection();
var range = selObj.getRangeAt(0);
```

* `selObj` 是一个 `Selection` 对象
* `range` 是一个 `Range` 对象

`getRangeAt` 方法返回对象的**引用**，并且对该函数返回的 `Range` 对象所运行的函数，会直接作用到选区上，并可能影响用户焦点的情况。

正如 Selection API 规范 所指出的，Selection API 最初由 Netscape 创建，并允许多个区域（例如，允许用户从 `<table>` 中选择列）。但是，Gecko 以外的浏览器没有实现多个区域，而且规范还要求选择的内容始终（仅）具有一个范围（允许多个区域可能引起不必要的兼容性问题，例如同时从多处输入，译者注）。

### Selection 及输入焦点

选择和输入焦点（由 `Document.activeElement` 表示）有一个复杂的关系，该关系因浏览器而异。在跨浏览器兼容的代码中，最好分别处理它们。

Safari 和 Chrome（与 Firefox 不同）目前在以编程方式修改 `Selection` 时会将包含选区的元素作为焦点；这可能在将来会发生变化（请参见 W3C Bug 14383 和 WebKit bug 3869）。

### Selection API 在可编辑元素焦点更改方面的行为

Selection API 有一个共同的行为（即在浏览器之间共通），该行为控制在调用某些方法后*可编辑元素*（Editing Host，可编辑宿主）的焦点行为如何更改。

其行为如下：

1. 如果先前的选区不在可编辑元素内，则可编辑元素将获得焦点。
2. 调用一个 Selection API 方法，从而在可编辑元素内产生一个新选区，来创造一个新的 `Selection` 区域（`Range`）。
3. 然后焦点（此处应指显示的，译者注）移到可编辑元素。

**备注：** Selection API 方法只能将焦点移动到可编辑元素，而不能移动到其他可焦点元素（例如 `<a>`）。

上述行为适用于使用以下方法产生的选区：

* `Selection.collapse()`
* `Selection.collapseToStart()`
* `Selection.collapseToEnd()`
* `Selection.extend()`
* `Selection.selectAllChildren()`
* `Selection.addRange()`
* `Selection.setBaseAndExtent()`

以及在 `Range` 使用以下方法修改时：

* `Range.setStart()`
* `Range.setEnd()`
* `Range.setStartBefore()`
* `Range.setStartAfter()` (en-US)
* `Range.setEndBefore()` (en-US)
* `Range.setEndAfter()` (en-US)
* `Range.collapse()`
* `Range.selectNode()`
* `Range.selectNodeContents()`
规范
--

| Specification |
| --- |
| Selection API # selection-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `window.getSelection`，`document.getSelection` (en-US)及`Range`
* HTML5 DOM Range Interface Selection
* IDL definition in Mozilla cross-reference
* 目前 CSS 实现竖排文本较为通用的方式是什么？（页内搜索"Bidi"可了解 Bidi 优先顺序）


Path2D - Web API 接口参考

Path2D
======

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

Canvas 2D API 的接口 **`Path2D`** 用来声明路径，此路径稍后会被`CanvasRenderingContext2D` 对象使用。`CanvasRenderingContext2D` 接口的 路径方法 也存在于 Path2D 这个接口中，允许你在 canvas 中根据需要创建可以保留并重用的路径。

构造函数
----

`Path2D()`

`Path2D` 构造函数。创建一个新的 `Path2D` 对象。

方法
--

`Path2D.addPath()`

添加一条新路径到对当前路径。

`Path2D.closePath()`

使笔点返回到当前子路径的起始点。它尝试从当前点到起始点绘制一条直线。如果图形已经是封闭的或者只有一个点，那么此函数不会做任何操作。

`Path2D.moveTo()`

将一个新的子路径的起始点移动到 (x，y) 坐标。

`Path2D.lineTo()`

使用直线连接子路径的终点到 `x, y` 坐标。

`Path2D.bezierCurveTo()`

添加一条三次贝赛尔曲线到当前路径。该方法需要三个点。第一、第二个点是控制点，第三个点是结束点。起始点是当前路径的最后一个点，绘制贝赛尔曲线前，可以通过调用 `moveTo()` 进行修改。

`Path2D.quadraticCurveTo()`

添加一条二次贝赛尔曲线到当前路径。

`Path2D.arc()`

添加一条圆弧路径。圆弧路径的圆心在 *(x, y)* 位置，半径为 *r*，根据*anticlockwise* （默认为顺时针）指定的方向从 *startAngle* 开始绘制，到 *endAngle* 结束。

`Path2D.arcTo()`

根据控制点和半径添加一条圆弧路径，使用直线连接前一个点。

`Path2D.ellipse()`

添加一条椭圆路径。椭圆的圆心在（x,y）位置，半径分别是*radiusX* 和 *radiusY*，按照*anticlockwise* （默认顺时针）指定的方向，从 *startAngle* 开始绘制，到 *endAngle* 结束。

`Path2D.rect()`

创建一条矩形路径，矩形的起点位置是 *(x, y)*，尺寸为 *width* 和 *height*。

规范
--

| Specification |
| --- |
| HTML Standard # path2d-objects |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `CanvasRenderingContext2D`


交叉观察器 API - Web API 接口参考

交叉观察器 API
=========

交叉观察器 API（Intersection Observer API）提供了一种异步检测目标元素与祖先元素或顶级文档的视口相交情况变化的方法。

过去，要检测一个元素是否可见或者两个元素是否相交并不容易，很多解决办法不可靠或性能很差。然而，随着互联网的发展，这种需求却与日俱增，比如，下面这些情况都需要用到相交检测：

* 在页面滚动时“懒加载”图像或其他内容。
* 实现“无限滚动”网站，在滚动过程中加载和显示越来越多的内容，这样用户就不必翻页了。
* 报告广告的可见度，以便计算广告收入。
* 根据用户是否能看到结果来决定是否执行任务或动画进程。

过去实施相交检测时，需要调用事件处理程序和循环方法，如 `Element.getBoundingClientRect()` 来为每个受影响的元素建立所需的信息。由于所有这些代码都在主线程上运行，因此即使是其中的一行代码也会导致性能问题。当网站加载这些测试时，情况会变得非常糟糕。

考虑一个使用无限滚动的网页。它使用一个供应商提供的库来管理整个页面中周期性放置的广告，页面到处都是动画图形，并使用一个自定义库来绘制通知框和其他相似的东西。每个库都有自己的相交检测例程，全部在主线程上运行。网站的作者可能根本没有意识到这一点，因为他们可能对所使用的两个库的内部运作知之甚少。当用户滚动页面时，这些相交检测例程会在滚动处理代码中不断触发，导致用户对浏览器、网站和他们的电脑感到失望。

交叉观察器 API 可令代码注册一个回调函数，当特定元素进入或退出与另一元素（或视口）的交集时，或者当两个元素之间的交集发生指定变化时，该函数就会被执行。这样，网站就不再需要在主线程上做任何事情来监视这种元素交集，浏览器也可以根据自己的需要优化交集管理。

交叉观察器 API 无法提供重叠像素的确切数量或具体是哪些像素重叠；不过，它涵盖了“如果它们相交*N*%左右，我需要做什么”这种更常见的用例。

交叉观察器的概念和用法
-----------

交叉观察器 API 允许你配置一个回调函数，当以下情况发生时会被调用：

* **目标**元素与设备视口或指定元素相交。在交叉观察器 API 中，指定元素被称为**根元素**或**根**。
* 观察器（Observer）第一次监听观察目标元素。

通常情况下，需要观察目标元素最近的可滚动祖先的交集变化，如果目标元素不是可滚动元素的后代，则需要观察设备视口的交集变化。要观察相对于设备视口的交集，请为 `root` 选项指定 `null`。请继续阅读有关交叉观察器选项的更详细说明。

无论你是使用视口还是其他元素作为根元素，API 的工作方式都是一样的，只要目标元素的可见性发生变化，与根元素的交集达到所需的程度，就会执行你提供的回调函数。

目标元素与其根元素的交集程度就是**交叉比**。它表示目标元素可见的百分比，数值介于 0.0 和 1.0 之间。

### 创建一个交叉观察器

通过调用 IntersectionObserver 构造函数，创建交叉观测器，并将回调函数传给它，当一个方向或另一个方向越过阈值时，就运行该函数：

```js
let options = {
  root: document.querySelector("#scrollArea"),
  rootMargin: "0px",
  threshold: 1.0,
};

let observer = new IntersectionObserver(callback, options);
```

阈值为 1.0 意味着目标元素完全出现在 `root` 选项指定的元素中 100% 可见时，回调函数将会被执行。

#### IntersectionObserver 选项

传递到 `IntersectionObserver()` 构造函数的 `options` 对象，可以控制在什么情况下调用观察器的回调。它有以下字段：

`root`

用作视口的元素，用于检查目标的可见性。必须是目标的祖先。如果未指定或为 `null`，则默认为浏览器视口。

`rootMargin`

根周围的边距。其值可以类似于 CSS `margin` 属性，例如 `"10px 20px 30px 40px"`（上、右、下、左）。这些值可以是百分比。在计算交叉点之前，这组值用于增大或缩小根元素边框的每一侧。默认值为全零。

`threshold`

一个数字或一个数字数组，表示目标可见度达到多少百分比时，观察器的回调就应该执行。如果只想在能见度超过 50% 时检测，可以使用 0.5 的值。如果希望每次能见度超过 25% 时都执行回调，则需要指定数组 [0, 0.25, 0.5, 0.75, 1]。默认值为 0（这意味着只要有一个像素可见，回调就会运行）。值为 1.0 意味着在每个像素都可见之前，阈值不会被认为已通过。

#### 定位要观察的元素

创建一个观察器后，需要给定一个目标元素进行观察。

```js
let target = document.querySelector("#listItem");
observer.observe(target);

// 我们为观察器设置的回调将在第一次执行，
// 它将等待我们为观察器分配目标（即使目标当前不可见）
```

每当目标满足该 `IntersectionObserver` 指定的阈值（threshold），回调被调用。回调接收 `IntersectionObserverEntry` 对象和观察器的列表：

```js
let callback = (entries, observer) => {
  entries.forEach((entry) => {
    // 每个条目描述一个目标元素观测点的交叉变化：
    // entry.boundingClientRect
    // entry.intersectionRatio
    // entry.intersectionRect
    // entry.isIntersecting
    // entry.rootBounds
    // entry.target
    // entry.time
  });
};
```

回调接收到的条目列表包括每个报告了相交状态变化的目标的一个条目。检查 `isIntersecting` (en-US) 属性的值，查看条目是否代表当前与根相交的元素。

请留意，你注册的回调函数将会在主线程中被执行。所以该函数执行速度要尽可能的快。如果需要执行任何耗时的操作，请使用 `Window.requestIdleCallback()`。

此外，请注意，如果指定了 `root` 选项，目标必须是根元素的后代。

### 交集的计算

交叉观察器 API 所考虑的所有区域都是矩形；形状不规则的元素被视为占据了包围元素所有部分的最小矩形。同样，如果元素的可见部分不是矩形，那么该元素的交点矩形将被视为包含该元素所有可见部分的最小矩形。

了解一下 `IntersectionObserverEntry` 提供的各种属性是如何描述交集的是很有帮助的。

#### 交集根与根边距

在跟踪元素与容器的交集之前，我们需要知道容器是什么。这个容器就是**交集根**，或**根元素**。它可以是文档中作为要观察元素的祖先的特定元素，也可以是 `null`，即使用文档的视口作为容器。

***根交集矩形***是用于检查目标或多个目标的矩形。这个矩形是这样确定的：

* 如果交集根是隐式根（即顶级 `Document`），根交叉点矩形就是视口的矩形。
* 如果交集根存在溢出剪切，根交集矩形就是根元素的内容区域。
* 否则，根交集矩形就是交集根的客户端边界矩形（通过调用 `getBoundingClientRect()` 返回）。

在创建 `IntersectionObserver` 时，可以通过设置**根边距**（rootMargin）来进一步调整交叉点根矩形。`rootMargin` 中的值定义了添加到交叉点根边界框每一侧的偏移量，以创建最终的交叉点根边界（执行回调时将在 `IntersectionObserverEntry.rootBounds` (en-US) 中显示）。

#### 阈值

交叉观察器 API 使用**阈值**，而不是报告目标元素可见度的每一个微小变化。创建观察器时，可以提供一个或多个数值，代表目标元素可见度的百分比。然后，API 只报告超过这些阈值的可见性变化。

例如，如果希望每次目标元素的可见度向后或向前越过每个 25% 的标记时都能得到通知，可以在创建观察器时指定数组 [0, 0.25, 0.5, 0.75, 1] 作为阈值列表。

调用回调时，系统会接收一个 `IntersectionObserverEntry` 对象列表，每个观察到的目标都会有一个对象，这些目标与根相交的程度发生了变化，使得暴露量在任一方向上都超过了某个阈值。

通过查看条目的 `isIntersecting` (en-US) 属性，可以了解目标*当前*是否与根相交；如果其值为 `true`，则表示目标至少与根元素或文档部分相交。这样就可以确定该条目是代表元素从相交到不再相交的过渡，还是代表从不相交到相交的过渡。

请注意，可能存在零相交矩形，如果交集正好沿着两者之间的边界，或者 `boundingClientRect` (en-US) 的面积为零。这种目标和根共享边界线的状态不足以被视为过渡到相交状态。

要感受阈值是如何工作的，请尝试滚动下面的盒子，每一个带颜色盒子的四个边角都会展示自身在根元素中的可见程度百分比，所以在你滚动根元素的时候你将会看到四个边角的数值一直在发生变化。每一个盒子都有不同的阈值：

* 第一个盒子为每个可见度百分点设置了一个阈值；也就是说，`IntersectionObserver.thresholds` (en-US) 数组为 `[0.00, 0.01, 0.02, /*...,*/ 0.99, 1.00]`。
* 第二个盒子只有一个阈值，位于 50% 刻度处。
* 第三个盒子每隔 10% 的可见度设置一个阈值（0%、10%、20% 等）。
* 最后一个盒子每 25% 设置一个阈值。
```

<template id="boxTemplate">
  <div class="sampleBox">
    <div class="label topLeft"></div>
    <div class="label topRight"></div>
    <div class="label bottomLeft"></div>
    <div class="label bottomRight"></div>
  </div>
</template>

<main>
  <div class="contents">
    <div class="wrapper"></div>
  </div>
</main>
```

```
.contents {
  position: absolute;
  width: 700px;
  height: 1725px;
}

.wrapper {
  position: relative;
  top: 600px;
}

.sampleBox {
  position: relative;
  left: 175px;
  width: 150px;
  background-color: rgb(245, 170, 140);
  border: 2px solid rgb(201, 126, 17);
  padding: 4px;
  margin-bottom: 6px;
}

#box1 {
  height: 200px;
}

#box2 {
  height: 75px;
}

#box3 {
  height: 150px;
}

#box4 {
  height: 100px;
}

.label {
  font:
    14px "Open Sans",
    "Arial",
    sans-serif;
  position: absolute;
  margin: 0;
  background-color: rgba(255, 255, 255, 0.7);
  border: 1px solid rgba(0, 0, 0, 0.7);
  width: 3em;
  height: 18px;
  padding: 2px;
  text-align: center;
}

.topLeft {
  left: 2px;
  top: 2px;
}

.topRight {
  right: 2px;
  top: 2px;
}

.bottomLeft {
  bottom: 2px;
  left: 2px;
}

.bottomRight {
  bottom: 2px;
  right: 2px;
}
```

```
let observers = [];

startup = () => {
  let wrapper = document.querySelector(".wrapper");

  // 观察器选项

  let observerOptions = {
    root: null,
    rootMargin: "0px",
    threshold: [],
  };

  // 每个方框的阈值集数组。第一个方框的阈值是通过编程设置的，因为有很多个（每个百分点）。

  let thresholdSets = [
    [],
    [0.5],
    [0.0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0],
    [0, 0.25, 0.5, 0.75, 1.0],
  ];

  for (let i = 0; i <= 1.0; i += 0.01) {
    thresholdSets[0].push(i);
  }

  // 添加每个盒子，为每个盒子创建一个新的观察器

  for (let i = 0; i < 4; i++) {
    let template = document
      .querySelector("#boxTemplate")
      .content.cloneNode(true);
    let boxID = `box${i + 1}`;
    template.querySelector(".sampleBox").id = boxID;
    wrapper.appendChild(document.importNode(template, true));

    // 为该盒子设置观察器

    observerOptions.threshold = thresholdSets[i];
    observers[i] = new IntersectionObserver(
      intersectionCallback,
      observerOptions,
    );
    observers[i].observe(document.querySelector(`#${boxID}`));
  }

  // 滚动至开始位置

  document.scrollingElement.scrollTop =
    wrapper.firstElementChild.getBoundingClientRect().top + window.scrollY;
  document.scrollingElement.scrollLeft = 750;
};

intersectionCallback = (entries) => {
  entries.forEach((entry) => {
    let box = entry.target;
    let visiblePct = `${Math.floor(entry.intersectionRatio \* 100)}%`;

    box.querySelector(".topLeft").innerHTML = visiblePct;
    box.querySelector(".topRight").innerHTML = visiblePct;
    box.querySelector(".bottomLeft").innerHTML = visiblePct;
    box.querySelector(".bottomRight").innerHTML = visiblePct;
  });
};

startup();
```

#### 剪切和相交矩形

浏览器计算最终交叉点矩形的过程如下；这一切都已经事先完成了，但了解这些步骤有助于更好地准确把握交叉点出现的时间。

1. 在目标元素上调用 `getBoundingClientRect()` 以获得目标元素的边界矩形（即完全包围组成该元素的每个组件的边界框的最小矩形）。这是最大的交集矩形。其余步骤将删除不相交的部分。
2. 从目标块的直接父块开始向外移动，将每个包含块的剪切（如果有）应用到交叉矩形。一个块的剪切是根据两个块的交点和 `overflow` 属性指定的剪切模式（如果有）确定的。将 `overflow` 设置为 `visible` 以外的任何值都会导致剪切发生。
3. 如果其中一个包含元素是嵌套浏览上下文（如 `<iframe>` 中包含的文档）的根元素，则交集矩形会剪切到包含上下文的视口，并通过容器的包含块继续向上递归。因此，如果到达 `<iframe>` 的顶层，交集矩形会剪切到框架的视口，然后框架的父元素会成为向交集根递归的下一个块。
4. 当递归向上到达交点根时，得到的矩形将映射到交点根的坐标空间。
5. 然后通过与根交集矩形相交来更新得到的矩形。
6. 最后，将该矩形映射到目标的 `document` 坐标空间。
### 交集变化回调

当根元素中可见的目标元素数量超过某个可见度阈值时，`IntersectionObserver` 对象的回调将被执行。回调的输入是由所有 `IntersectionObserverEntry` 对象组成的数组（每次跨阈值产生一个），以及对 `IntersectionObserver` 对象本身的引用。

阈值列表中的每个条目都是一个 `IntersectionObserverEntry` 对象，描述了一个被跨越的阈值；也就是说，每个条目都描述了给定元素与根元素相交的程度、元素是否被视为相交以及发生转变的方向。

下面的代码片段显示了一个回调，该回调会记录元素从与根不相交过渡到至少相交 75% 的次数。阈值为 0.0（默认值）时，当 `isIntersecting` (en-US) 的布尔值发生变化时，回调将被近似调用。因此，该代码段首先检查过渡是否为正值，然后确定 `intersectionRatio` (en-US) 是否高于 75%，如果高于 75%，就会递增计数器。

```js
const intersectionCallback = (entries) => {
  entries.forEach((entry) => {
    if (entry.isIntersecting) {
      let elem = entry.target;

      if (entry.intersectionRatio >= 0.75) {
        intersectionCounter++;
      }
    }
  });
};
```

接口
--

`IntersectionObserver`

交叉观察器 API 的主要接口。它提供了创建和管理观察器的方法，观察器可以针对相同的交叉点配置观察任意数量的目标元素。每个观察器都可以异步观察一个或多个目标元素与共享的祖先元素或其顶层 `Document` 的视口之间的交集变化。祖先或视口被称为**根**。

`IntersectionObserverEntry`

描述目标元素与其根容器在特定过渡时刻的交集。这种类型的对象只能通过两种方式获得：作为 `IntersectionObserver` 回调的输入，或通过调用 `IntersectionObserver.takeRecords()` 获得。

一个简单的示例
-------

这个简单的示例会使目标元素在可见度变高或变低时改变颜色和透明度。在使用交叉观察器 API 为元素可见性计时 (en-US)中，可以找到一个更广泛的示例，展示如何对一组元素（如广告）对用户的可见时间进行计时，并通过记录统计数据或更新元素对该信息做出反应。

### HTML

这个示例的 HTML 代码非常简短，主要元素是我们要针对的盒子（其 ID 为 `"box"`），以及盒子中的一些内容。

```html
<div id="box">
  <div class="vertical">来看看<strong>这个盒子</strong>吧！</div>
</div>
```

### CSS

在本示例中，CSS 并不是非常重要；它将元素排列出来，并确定 `background-color` 和 `border` 属性可以参与 CSS 过渡，我们将使用 CSS 过渡来影响元素的变化，使其变得或多或少模糊不清。

```css
#box {
  background-color: rgba(40, 40, 190, 1);
  border: 4px solid rgb(20, 20, 120);
  transition:
    background-color 1s,
    border 1s;
  width: 350px;
  height: 350px;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 20px;
}

.vertical {
  color: white;
  font: 32px "Arial";
}

.extra {
  width: 350px;
  height: 350px;
  margin-top: 10px;
  border: 4px solid rgb(20, 20, 120);
  text-align: center;
  padding: 20px;
}
```

### JavaScript

最后，让我们来看看使用交叉观察器 API 来实现目标的 JavaScript 代码。

#### 初始设置

首先，声明一些变量并设置观察器。

```js
const numSteps = 20.0;

let boxElement;
let prevRatio = 0.0;
let increasingColor = "rgba(40, 40, 190, ratio)";
let decreasingColor = "rgba(190, 40, 40, ratio)";

// 设定好一切
window.addEventListener(
  "load",
  (event) => {
    boxElement = document.querySelector("#box");

    createObserver();
  },
  false,
);
```

我们准备的常量和变量有：

`numSteps`

一个常数，表示我们希望在 0.0 和 1.0 可见度比率之间设置的阈值。

`prevRatio`

这个变量将用来记录上次越过阈值时的可见度比率；这将让我们知道目标元素的可见度是变高了还是变低了。

`increasingColor`

一个字符串，用于定义当可见度比率增加时，我们将应用于目标元素的颜色。字符串中的“ratio”一词将用目标元素当前的可见度比率代替，这样，元素不仅会改变颜色，而且会随着遮挡程度的降低而变得越来越不透明。

`decreasingColor`

同样，这也是一个字符串，它定义了当可见度比率降低时我们将应用的颜色。

我们调用 `Window.addEventListener()` 开始监听 `load` 事件；页面加载完成后，我们使用 `querySelector()` 获取 ID 为 `"box"` 的元素引用，然后调用我们稍后将创建的 `createObserver()` 方法来处理交叉观察器的构建和设置。

#### 创建交叉观察器

一旦页面加载完成，`createObserver()` 方法将被调用，以实际创建新的 `IntersectionObserver` 并开始观察目标元素。

```js
function createObserver() {
  let observer;

  let options = {
    root: null,
    rootMargin: "0px",
    threshold: buildThresholdList(),
  };

  observer = new IntersectionObserver(handleIntersect, options);
  observer.observe(boxElement);
}
```

首先要设置一个包含观察器设置的 `options` 对象。我们希望观察目标元素相对于文档视口的可见性变化，因此 `root` 为 `null`。我们不需要边距，因此边距偏移量 `rootMargin` 被指定为“0px”。这将导致观察器在不增加（或减少）空间的情况下观察目标元素边界与视口边界之间交点的变化。

可见度比率阈值列表 `threshold` 由函数 `buildThresholdList()` 构建。在本例中，阈值列表是通过编程构建的，因为阈值有很多，而且数量是可以调整的。

一旦 `options` 准备就绪，我们就可以创建新的观察器，调用 `IntersectionObserver()` 构造函数，指定当交叉点越过某个阈值时调用的函数 `handleIntersect()` 和我们的选项集。然后，我们在返回的观察器上调用 `observe()` ，并向其传递所需的目标元素。

我们可以选择监控多个元素相对于视口的可见性交叉变化，如果我们想这样做的话，可以为每个元素调用 `observer.observe()`。

#### 建立阈值比率数组

建立阈值列表的 `buildThresholdList()` 函数看起来像这样：

```js
function buildThresholdList() {
  let thresholds = [];
  let numSteps = 20;

  for (let i = 1.0; i <= numSteps; i++) {
    let ratio = i / numSteps;
    thresholds.push(ratio);
  }

  thresholds.push(0);
  return thresholds;
}
```

通过为 1 到 `numSteps` 之间的每个整数 `i` 向 `thresholds` 数组推送值 `i/numSteps` 来建立阈值数组，每个阈值都是 0.0 到 1.0 之间的比率。它还会推 0 以包含该值。根据 `numSteps` 的默认值（20），结果是下面的阈值列表：

| # | 比率 | # | 比率 |
| --- | --- | --- | --- |
| 0 | 0.05 | 11 | 0.6 |
| 1 | 0.1 | 12 | 0.65 |
| 2 | 0.15 | 13 | 0.7 |
| 3 | 0.2 | 14 | 0.75 |
| 4 | 0.25 | 15 | 0.8 |
| 5 | 0.3 | 16 | 0.85 |
| 6 | 0.35 | 17 | 0.9 |
| 7 | 0.4 | 18 | 0.95 |
| 8 | 0.45 | 19 | 1 |
| 9 | 0.5 | 20 | 0 |
| 10 | 0.55 |

当然，我们也可以将阈值数组硬编码到我们的代码中，通常这也是你最终要做的。但这个示例为添加配置控制来调整粒度等留出了空间。

#### 处理交集变化

当浏览器检测到目标元素（在我们的例子中是 ID 为 `"box"` 的元素）被揭开或遮盖，以致其可见性比例超过了列表中的某个阈值时，浏览器就会调用我们的处理函数 `handleIntersect()`：

```js
function handleIntersect(entries, observer) {
  entries.forEach((entry) => {
    if (entry.intersectionRatio > prevRatio) {
      entry.target.style.backgroundColor = increasingColor.replace(
        "ratio",
        entry.intersectionRatio,
      );
    } else {
      entry.target.style.backgroundColor = decreasingColor.replace(
        "ratio",
        entry.intersectionRatio,
      );
    }

    prevRatio = entry.intersectionRatio;
  });
}
```

对于 `entries` 列表中的每个 `IntersectionObserverEntry`，我们都会查看该条目中的 `intersectionRatio` (en-US) 是否上升，如果是，我们就将目标的 `background-color` 设置为 `increasingColor` 中的字符串（记住，是 `"rgba(40, 40, 190, ratio)"`），并用条目的 `intersectionRatio` 替换“ratio”。结果是：不仅颜色发生了变化，目标元素的透明度也发生了变化；随着交集比率的降低，背景色的 alpha 值也会随之降低，从而使元素更加透明。

同样，如果 `intersectionRatio` 正在下降，我们就会使用字符串 `decreasingColor`，并在设置目标元素的 `background-color` 之前用 `intersectionRatio` 替换其中的“ratio”。

最后，为了跟踪交叉比是上升还是下降，我们会在变量 `prevRatio` 中记住当前的交叉比。

### 结果

下面是生成的内容。上下滚动本页，注意滚动时方框外观的变化。

在使用交叉观察器 API 为元素可见性计时 (en-US)中有一个更广泛的示例。

规范
--

| Specification |
| --- |
| Intersection Observer # intersection-observer-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* 交叉观察器 polyfill
* 使用交叉观察器 API 为元素可见性计时 (en-US)
* `IntersectionObserver` 和 `IntersectionObserverEntry`


ByteLengthQueuingStrategy - Web API 接口参考

ByteLengthQueuingStrategy
=========================

Streams API 的 **`ByteLengthQueuingStrategy`** 接口提供了一个队列策略，该队列策略提供了内置的字节长度并且可以在构造流的时候使用。

构造函数
----

`ByteLengthQueuingStrategy()`

创建一个新的 `ByteLengthQueuingStrategy` 对象实例。

实例属性
----

`ByteLengthQueuingStrategy.highWaterMark` 只读

在应用背压之前，内部队列可以包含的字节总数。

实例方法
----

`ByteLengthQueuingStrategy.size()`

返回给定分块的 `byteLength` 属性。

示例
--

```js
const queueingStrategy = new ByteLengthQueuingStrategy({ highWaterMark: 1 });

const readableStream = new ReadableStream(
  {
    start(controller) {
      // …
    },
    pull(controller) {
      // …
    },
    cancel(err) {
      console.log("stream error:", err);
    },
  },
  queueingStrategy,
);

const size = queueingStrategy.size(chunk);
```

规范
--

| Specification |
| --- |
| Streams Standard # blqs-class |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* Stream API
* 内置队列和队列策略
* `ByteLengthQueuingStrategy()` 构造函数


History API - Web API 接口参考

History API
===========

**History API** 通过 `history` 全局对象提供了对浏览器会话的历史记录（不要与 WebExtensions 的 history 混淆）的访问功能。它暴露了很多有用的方法和属性，使你可以在用户的历史记录中来回导航，而且可以操作历史记录栈中的内容。

**备注：** 该 API 仅在主线程（`Window`）中可用。无法在 `Worker` 或 `Worklet` (en-US) 上下文中访问它。

概念和用法
-----

使用 `back()`、`forward()` 和 `go()` 方法可以在用户历史记录中前后跳转。

### 向前和向后跳转

在历史记录中向后跳转：

```js
history.back();
```

这和用户点击浏览器的回退（`**Back**`）按钮的效果相同。

类似地，你可以向前跳转（如同用户点击了前进（`**Forward**`）按钮）：

```js
history.forward();
```

### 跳转到历史记录中的指定位置

你可以用 `go()` 方法从会话历史记录中加载某一特定页面，该页面使用与当前页面的相对位置来标识（当前页面的相对位置为 `0`）。

向后跳转一个页面（等价于调用 `back()`）：

```js
history.go(-1);
```

向前跳转一个页面，就像调用 `forward()`：

```js
history.go(1);
```

类似地，你可以传递参数值 `2` 并向前跳转 2 个页面，等等。

`go()` 方法的另一个用途是，在调用它时传递 `0` 或不传递任何参数以刷新当前页面：

```js
// 以下语句都具有刷新页面的效果
history.go(0);
history.go();
```

你可以通过查看 `length` 属性的值来确定历史记录栈中的页面数量：

```js
const numberOfEntries = history.length;
```

接口
--

`History`

允许操作浏览器*会话的历史记录*（即加载了当前页面的标签页或框架（frame）中访问过的页面）。

`PopStateEvent` (en-US)

`popstate` 事件的接口。

示例
--

以下示例为 `popstate` 事件分配了一个监听器。然后它演示了一些 history 对象的方法：对当前标签页浏览记录的添加、替换和跳转。

```js
window.addEventListener("popstate", (event) => {
  alert(`位置：${document.location}，状态：${JSON.stringify(event.state)}`);
});

history.pushState({ page: 1 }, "标题 1", "?page=1");
history.pushState({ page: 2 }, "标题 2", "?page=2");
history.replaceState({ page: 3 }, "标题 3", "?page=3");
history.back(); // 显示警告“位置：http://example.com/example.html?page=1，状态：{"page":1}”
history.back(); // 显示警告“位置：http://example.com/example.html，状态：null”
history.go(2); // 显示警告“位置：http://example.com/example.html?page=3，状态：{"page":3}”
```

规范
--

| Specification |
| --- |
| HTML Standard # the-history-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `history` 全局对象
* `popstate` 事件


GestureEvent - Web API 接口参考

GestureEvent
============

**非标准:** 该特性是非标准的，请尽量不要在生产环境中使用它！

**`GestureEvent`** 是 WebKit 的专有接口，提供多点触控的信息。这个接口的事件包括 `gesturestart` (en-US)、`gesturechange` (en-US) 和 `gestureend` (en-US).

`GestureEvent` 继承自 `UIEvent`，后者又继承自 `Event`。

构造函数
----

`GestureEvent()`

Creates a `GestureEvent` object.

属性
--

*This interface also inherits properties of its parents, `UIEvent` and `Event`.*

`GestureEvent.rotation` 只读

Change in rotation (in degrees) since the event's beginning. Positive values indicate clockwise rotation; negative values indicate anticlockwise rotation. Initial value: `0.0`

`GestureEvent.scale` 只读

Distance between two digits since the event's beginning. Expressed as a floating-point multiple of the initial distance between the digits at the beginning of the gesture. Values below 1.0 indicate an inward pinch (zoom out). Values above 1.0 indicate an outward unpinch (zoom in). Initial value: `1.0`

方法
--

*This interface also inherits methods of its parents, `UIEvent` and `Event`.*

`GestureEvent.initGestureEvent()`

Initializes the value of an `GestureEvent`. If the event has already being dispatched, this method does nothing.

手势事件类型
------

* `gesturestart` (en-US)
* `gesturechange` (en-US)
* `gestureend` (en-US)
规范
--

*不属于任何规范*。苹果在 Safari Developer Library 中描述了这个接口。

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* `MSGestureEvent`
* `MSGestureStart`
* `MSGestureEnd`
* `MSGestureTap`
* `MSGestureHold`
* `MSGestureChange`
* `MSInertiaStart`


FontFaceSet - Web API 接口参考

FontFaceSet
===========

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

CSS 字体加载 API 的 **`FontFaceSet`** 管理着字体们的加载和可查询的字体们下载状态。

Properties
----------

`FontFaceSet.status` (en-US) 只读

表示 font-face's 的加载状态，可能是 `'loading'` 或 `'loaded'`

Events
------

`FontFaceSet.onloading` (en-US)

当 `loading` 相关事件发生时触发 `EventListener`，表示 font-face 集已经开始加载了。

`FontFaceSet.onloadingdone` (en-US)

当 `loading` 相关事件发生时触发 `EventListener`，表示 font-face 集已经完成加载了。

`FontFaceSet.onloadingerror` (en-US)

当 `loading` 相关事件发生时触发 `EventListener`，表示 font-face 集加载时产生了一个错误。

Methods
-------

`FontFaceSet.add()` (en-US)

向字体集添加一个字体。

`FontFaceSet.check()`

一个`Boolean` (en-US) 用于表示一个字体是否加载完成，但它不回初始化你的加载。

`FontFaceSet.clear()` (en-US)

移除字体集的所有字体。

`FontFaceSet.delete()` (en-US)

从字体集中移除一个字体。

`FontFaceSet.load()` (en-US)

返回解析为请求的字体的列表的 `Promise`。

`FontFaceSet.ready()` (en-US)

准备操作已完成且开始解析字体时返回一个 `Promise` 。

规范
--

| Specification |
| --- |
| CSS Font Loading Module Level 3 # FontFaceSet-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


Bluetooth - Web API 接口参考

Bluetooth
=========

**非标准:** 该特性是非标准的，请尽量不要在生产环境中使用它！

Web Bluetooth API (en-US) 的\*\*`Bluetooth`\*\*`接口`返回指代`BluetoothDevice` (en-US)带有指定选项的对象的`Promise`。

接口
--
```

interface Bluetooth {
  Promise<BluetoothDevice> requestDevice(RequestDeviceOptions options);
};
Bluetooth implements EventTarget;
Bluetooth implements BluetoothDeviceEventHandlers;
Bluetooth implements CharacteristicEventHandlers;
Bluetooth implements ServiceEventHandlers;
```

特性
--

无

方法
--

`Bluetooth.requestDevice()`

返回一个包含指定选项的`BluetoothDevice` (en-US)对象的`Promise`。

详细说明
----

| Specification |
| --- |
| Web Bluetooth # bluetooth |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


Animation - Web API 接口参考

Animation
=========

Baseline 2022
-------------

Newly availableSince September 2022, this feature works across the latest devices and browser versions. This feature might not work in older devices or browsers.

* Learn more
* See full compatibility
* Report feedback
**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

Web 动画 API的**动画**接口表示一个单个动画播放器并且提供用于一个动画节点或源的回放控制和一个时间轴。

构造函数
----

`Animation()`

创建一个新的 Animation 对象实例。

属性
--

`Animation.currentTime`

动画的当前时间值（以毫秒为单位），无论是正在运行还是已暂停。如果动画缺少`timeline`或尚未播放，其值为 null。

`Animation.effect`

获取或设置与此动画相关联的`KeyframeEffect` (en-US)。

`Animation.finished` 只读

返回此动画的当前完成的状态。

`Animation.id`

获取或设置用于标识动画的字符串。

`Animation.playState` 只读

返回描述动画播放状态的枚举值。

`Animation.playbackRate` (en-US)

返回或设置动画的播放速率。

`Animation.ready` (en-US) 只读

返回此动画的当前就绪状态。

`Animation.startTime` (en-US)

获取或设置动画播放应开始的预定时间。

`Animation.timeline` (en-US)

获取或设置与此动画相关联的`timeline`。

### 事件处理程序

`Animation.oncancel`

获取并设置取消事件的事件处理程序。

`Animation.onfinish` (en-US)

获取并设置完成事件的事件处理程序。

方法
--

`Animation.cancel()`

清除此动画的所有`keyframeEffects` (en-US)，并中止播放。

`Animation.finish()` (en-US)

设置动画中止播放。

`Animation.pause()` (en-US)

暂停播放动画。.

`Animation.play()`

开始或恢复播放动画，或者如果之前完成，则重新开始动画。

`Animation.reverse()` (en-US)

反转播放动画，直到播放到动画开始时停止。如果动画完成或未播放，它将从头到尾播放。

规范
--

| Specification |
| --- |
| Web Animations # the-animation-interface |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


SVGAnimateElement - Web API 接口参考

SVGAnimateElement
=================

**`SVGAnimateElement`** 接口对应于 `<animate>` 元素。

属性
--

*该接口没有属性，但从其父级继承属性，*

*`SVGAnimationElement` (en-US).*

方法
--

*该接口没有方法，但从其父级继承方法，*

*`SVGAnimationElement` (en-US).*

规范
--

| Specification |
| --- |
| SVG Animations Level 2 # InterfaceSVGAnimateElement |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


屏幕捕捉 API - Web API 接口参考

屏幕捕捉 API
========

屏幕捕获 API 对现有的媒体捕获和流 API 进行了补充，让用户选择一个屏幕或屏幕的一部分（如一个窗口）作为媒体流进行捕获。然后，该流可以被记录或通过网络与他人共享。

屏幕捕捉 API 的概念和用法
---------------

屏幕捕捉 API 使用起来相对简单。其唯一的方法是`MediaDevices.getDisplayMedia()`，它的任务是以捕获的形式要求用户选择一个屏幕或屏幕的一部分的`MediaStream`。

要开始从屏幕上捕捉视频，你需要在 `getDisplayMedia()` 的实例上调用 `Media` `navigator.mediaDevices`：

```js
captureStream =
  await navigator.mediaDevices.getDisplayMedia(displayMediaOptions);
```

The `Promise` returned by `getDisplayMedia()` resolves to a `MediaStream` which streams the captured media.

See the article Using the Screen Capture API for a more in-depth look at how to use the API to capture screen contents as a stream.

增加现有接口
------

屏幕捕捉 API 没有自己的任何接口，而是在现有的 `MediaDevices` 接口上添加了一个方法。

### MediaDevices 接口

`MediaDevices.getDisplayMedia()`

The `getDisplayMedia()` method is added to the `MediaDevices` interface. Similar to `getUserMedia()`, this method creates a promise that resolves with a `MediaStream` containing the display area selected by the user, in a format that matches the specified options.

Additions to existing dictionaries
----------------------------------

The Screen Capture API adds properties to the following dictionaries defined by other specifications.

### MediaTrackConstraints

`MediaTrackConstraints.cursor` (en-US)

A `ConstrainDOMString` (en-US) indicating whether or not the cursor should be included in the captured display surface's stream, and if it should always be visible or if it should only be visible while the mouse is in motion.

`MediaTrackConstraints.displaySurface` (en-US)

A `ConstrainDOMString` (en-US) indicating what type of display surface is to be captured. The value is one of `application`, `browser`, `monitor`, or `window`.

`MediaTrackConstraints.logicalSurface` (en-US)

Indicates whether or not the video in the stream represents a logical display surface (that is, one which may not be entirely visible onscreen, or may be completely offscreen). A value of `true` indicates a logical display surface is to be captured.

### MediaTrackSettings

`MediaTrackSettings.cursor` (en-US)

A string which indicates whether or not the display surface currently being captured includes the mouse cursor, and if so, whether it's only visible while the mouse is in motion or if it's always visible. The value is one of `always`, `motion`, or `never`.

`MediaTrackSettings.displaySurface` (en-US)

A string indicating what type of display surface is currently being captured. The value is one of `application`, `browser`, `monitor`, or `window`.

`MediaTrackSettings.logicalSurface` (en-US)

A Boolean value which is `true` if the video being captured doesn't directly correspond to a single onscreen display area.

### MediaTrackSupportedConstraints

`MediaTrackSupportedConstraints.cursor` (en-US)

A Boolean which is `true` if the user agent and device support the `MediaTrackConstraints.cursor` (en-US) constraint.

`MediaTrackSupportedConstraints.displaySurface` (en-US)

A Boolean which is `true` if the current environment supports the `MediaTrackConstraints.displaySurface` (en-US) constraint.

`MediaTrackSupportedConstraints.logicalSurface` (en-US)

A Boolean which is `true` if the current environment supports the constraint `MediaTrackConstraints.logicalSurface` (en-US).

Dictionaries
------------

The following dictionaries are defined by the Screen Capture API.

`CursorCaptureConstraint`

An enumerated string type used to provide the value for the `cursor` property for the settings and constraints. The possible values are `always`, `motion`, and `never`.

`DisplayCaptureSurfaceType`

An enumerated string type which is used to identify the kind of display surface to capture. This type is used for the `displaySurface` property in the constraints and settings objects, and has the possible values `application`, `browser`, `monitor`, and `window`.

Feature Policy validation
-------------------------

User agents that support Feature Policy (either using HTTP's `Permissions-Policy` header or the `<iframe>` attribute `allow`) can specify a desire to use the Screen Capture API using the policy control directive `display-capture`:

```html
<iframe allow="display-capture" src="/some-other-document.html"></iframe>
```

The default allow list is `self`, which lets the any content within the document use Screen Capture.

See Using Feature Policy for a more in-depth explanation of how Feature Policy is used.

规范
--

| Specification |
| --- |
| Screen Capture # dom-mediadevices-getdisplaymedia |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

参见
--

* Using the Screen Capture API (en-US)
* `MediaDevices.getDisplayMedia()`


AudioScheduledSourceNode - Web API 接口参考

AudioScheduledSourceNode
========================

`AudioScheduledSourceNode` 接口作为 web 音频 API 的一部分，是几种具有在特定时刻开始与停止能力的音频源节点接口的父接口。更具体地来说，这个接口定义了`start()` (en-US) 和`stop()` 方法，以及`onended` (en-US)事件

**备注：** 你不能直接创建`AudioScheduledSourceNode`。而是应该使用继承于它的子接口，如`AudioBufferSourceNode`, `OscillatorNode`和`ConstantSourceNode` (en-US).

除非另有说明，基于`AudioScheduledSourceNode`节点的输出在没有播放时处于静默状态（这种状态在 start() 之前与 stop() 之后调用）。静默状态总是由一个全 0 值流组成。

Properties
----------

*Inherits properties from its parent interface, `AudioNode`, and adds the following properties:*

### Event handlers

`onended` (en-US)

A function to be called when the `ended` event is fired, indicating that the node has finished playing.

Methods
-------

*Inherits methods from its parent interface, `AudioNode`, and adds the following methods:*

`start()` (en-US)

Schedules the node to begin playing the constant sound at the specified time. If no time is specified, the node begins playing immediately.

`stop()`

Schedules the node to stop playing at the specified time. If no time is specified, the node stops playing at once.

Specification
-------------

| Specification |
| --- |
| Web Audio API # AudioScheduledSourceNode |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Using the Web Audio API
* `AudioNode`


Node - Web API 接口参考

Node
====

**`Node`** 是一个接口，各种类型的 DOM API 对象会从这个接口继承。它允许我们使用相似的方式对待这些不同类型的对象；比如，继承同一组方法，或者用同样的方式测试。

以下接口都从 `Node` 继承其方法和属性：

`Document`, `Element`, `Attr`, `CharacterData` (which `Text` (en-US), `Comment`, and `CDATASection` inherit), `ProcessingInstruction` (en-US), `DocumentFragment`, `DocumentType`, `Notation`, `Entity`, `EntityReference`
在方法和属性不相关的特定情况下，这些接口可能返回 `null`。它们可能会抛出异常 - 例如，当将子节点添加到不允许子节点存在的节点时。

EventTarget

Node属性
--

从其父类型 *`EventTarget`*[1] 继承属性。

`Node.baseURI`只读

返回一个表示 base URL 的`DOMString`。不同语言中的 base URL 的概念都不一样。在 HTML 中，base URL 表示协议和域名，以及一直到最后一个'/'之前的文件目录。

`Node.baseURIObject` (en-US)
非标准

(不适用于网页内容) 只读的 `nsIURI` 对象表示元素的 base URI.

`Node.childNodes`只读

返回一个包含了该节点所有子节点的实时的`NodeList`。`NodeList` 是动态变化的。如果该节点的子节点发生了变化，`NodeList`对象就会自动更新。

`Node.firstChild` 只读

返回该节点的第一个子节点`Node`，如果该节点没有子节点则返回`null`。

`Node.isConnected`只读

返回一个布尔值用来检测该节点是否已连接 (直接或者间接) 到一个上下文对象上，比如通常 DOM 情况下的`Document`对象，或者在 shadow DOM 情况下的`ShadowRoot`对象。

`Node.lastChild` 只读

返回该节点的最后一个子节点`Node`，如果该节点没有子节点则返回`null`。

`Node.nextSibling` 只读

返回与该节点同级的下一个节点 `Node`，如果没有返回`null`。

`Node.nodeName` 只读

返回一个包含该节点名字的`DOMString`。节点的名字的结构和节点类型不同。比如`HTMLElement`的名字跟它所关联的标签对应，就比如`HTMLAudioElement`的就是 `'audio'` ，`Text` (en-US)节点对应的是 `'#text'` 还有`Document`节点对应的是 `'#document'`。

`Node.nodeType`只读

返回一个与该节点类型对应的`无符号短整型`的值，可能的值如下：

| Name | Value |
| --- | --- |
| `ELEMENT_NODE` | `1` |
| `ATTRIBUTE_NODE`
已弃用
 | `2` |
| `TEXT_NODE` | `3` |
| `CDATA_SECTION_NODE` | `4` |
| `ENTITY_REFERENCE_NODE`
已弃用
 | `5` |
| `ENTITY_NODE`
已弃用
 | `6` |
| `PROCESSING_INSTRUCTION_NODE` | `7` |
| `COMMENT_NODE` | `8` |
| `DOCUMENT_NODE` | `9` |
| `DOCUMENT_TYPE_NODE` | `10` |
| `DOCUMENT_FRAGMENT_NODE` | `11` |
| `NOTATION_NODE`
已弃用
 | `12` |

`Node.nodeValue`

返回或设置当前节点的值。

`Node.ownerDocument` 只读

返回这个元素属于的 `Document`对象。如果没有 Document 对象与之关联，返回 null。

`Node.parentNode` 只读

返回一个当前节点 `Node`的父节点。如果没有这样的节点，比如说像这个节点是树结构的顶端或者没有插入一棵树中，这个属性返回 null。

`Node.parentElement` 只读

返回一个当前节点的父节点 `Element` 。如果当前节点没有父节点或者说父节点不是一个元素 (`Element`), 这个属性返回 null。

`Node.previousSibling` 只读

返回一个当前节点同辈的前一个节点 ( `Node`) ，或者返回 null（如果不存在这样的一个节点的话）。

`Node.textContent`

返回或设置一个元素内所有子节点及其后代的文本内容。

### 废弃的属性

`Node.localName` (en-US)
已弃用
只读

返回一个表示元素名称的本土化表示方法的 `DOMString` 。

**备注：** 在 Firefox 3.5 以及更早的版本中，HTML 元素的 localName 属性的返回值都是大写的（XHTML 例外）。在后续版本中，这种情况就不存在了。无论是 HTML 还是 XHTML 中，均返回小写的 localName。

`Node.namespaceURI` (en-US)
已弃用
只读

该节点命名空间的`URL`，如果没有命名空间则为`null`。

**备注：** 在 Firefox 3.5 以及更早的版本中，HTML 的元素都没有命名空间。而在最新的版本中，无论是 HTML 还是 XML 文档树，所有元素的命名空间统一为 `http://www.w3.org/1999/xhtml/`。

`Node.nodePrincipal` (en-US)
非标准

已弃用

返回节点优先级 `nsIPrincipal` 。

`Node.prefix` (en-US)
已弃用
只读

返回一个节点命名空间的前缀 `DOMString` , 当前缀不存在时返回 `null` 。

`Node.rootNode` (en-US)
已弃用
只读

返回一个 DOM 树中顶层节点的 `Node` 对象，如果顶层节点不 DOM 树中，则返回当前节点。该属性已被 `Node.getRootNode()` 方法所代替。

方法
--

从其父类型 *`EventTarget`*[1] 继承方法。

`Node.appendChild()`

 将指定的 childNode 参数作为最后一个子节点添加到当前节点。
 如果参数引用了 DOM 树上的现有节点，则节点将从当前位置分离，并附加到新位置。

`Node.cloneNode()`

克隆一个 `Node`，并且可以选择是否克隆这个节点下的所有内容。默认情况下，节点下的内容会被克隆。

`Node.compareDocumentPosition()`

比较当前节点与文档中的另一节点的位置。

`Node.contains()`

返回一个 `Boolean` 布尔值，来表示传入的节点是否为该节点的后代节点。

`Node.getRootNode()`

返回上下文对象的根节点。如果 shadow root 节点存在的话，也可以在返回的节点中包含它。

`Node.hasChildNodes()`

返回一个`Boolean` 布尔值，来表示该元素是否包含有子节点。

`Node.insertBefore()`

在当前节点下增加一个子节点 `Node`，并使该子节点位于参考节点的前面。

`Node.isDefaultNamespace()`

返回一个 `Boolean` 类型值。接受一个命名空间 URI 作为参数，当参数所指代的命名空间是默认命名空间时返回 true，否则返回 false。

`Node.isEqualNode()`

返回一个 `Boolean` 类型值。当两个 node 节点为相同类型的节点且定义的数据点匹配时（即属性和属性值相同，节点值相同）返回 true，否则返回 false。

`Node.isSameNode()`

返回一个 `Boolean` 类型值。返回这两个节点的引用比较结果。

`Node.lookupPrefix()`

返回包含参数 URI 所对应的命名空间前缀的 `DOMString`，若不存在则返回 null。如果存在多个可匹配的前缀，则返回结果和浏览器具体实现有关。

`Node.lookupNamespaceURI()`

接受一个前缀，并返回前缀所对应节点命名空间 URI。如果 URI 不存在则返回 null。传入 null 作为 prefix 参数将返回默认命名空间。

`Node.normalize()`

对该元素下的所有文本子节点进行整理，合并相邻的文本节点并清除空文本节点。

`Node.removeChild()`

移除当前节点的一个子节点。这个子节点必须存在于当前节点中。

`Node.replaceChild()`

对选定的节点，替换一个子节点 `Node` 为另外一个节点。

### 废弃的方法

`Node.getFeature()`
已弃用
`Node.getUserData()`
已弃用

允许用户从节点的 `DOMUserData` 获得数据。

`Node.hasAttributes()`
已弃用

返回一个 `Boolean` 指定该元素是否存在某一属性。

`Node.setUserData()`
已弃用

允许用户在一个节点上设置或移除 `DOMUserData` 。

示例
--

### 移除某个节点的所有子节点

```js
function removeAllChildren(element) {
  while (element.firstChild) {
    element.removeChild(element.firstChild);
  }
}
```

#### 使用示例

```js
/\* ... an alternative to document.body.innerHTML = "" ... \*/
removeAllChildren(document.body);
```

### 遍历所有子节点

下面这个函数使用递归的方式遍历一个节点的所有子节点（包括这个根节点自身）。

```js
function eachNode(rootNode, callback) {
  if (!callback) {
    var nodes = [];
    eachNode(rootNode, function (node) {
      nodes.push(node);
    });
    return nodes;
  }

  if (false === callback(rootNode)) return false;

  if (rootNode.hasChildNodes()) {
    var nodes = rootNode.childNodes;
    for (var i = 0, l = nodes.length; i < l; ++i)
      if (false === eachNode(nodes[i], callback)) return;
  }
}
```

#### 语法
```

eachNode(rootNode, callback);
```

#### 描述

使用递归的方式对 `rootNode` 的所有后代节点执行回调函数（包括 `rootNode` 自身）

如果没有设定 `callback`，这函数会返回一个`Array`，包含 `rootNode` 和它的所有后代节点。

如果设定了 `callback`（回调函数），如果回调函数在调用中返回 `Boolean` `false`，则当前层级的遍历会中止，同时恢复上一层级的遍历。这个可以用来在找到需要的节点之后中断循环（比如用来查找包含指定文本的文本节点）

#### 参数

`rootNode`

需要进行后代节点遍历的 `Node` 对象。

`callback`

一个可选的回调函数，接受一个节点作为唯一参数。如果没有设定， `eachNode` 返回一个包含了 `rootNode` 所有后代节点以及 `rootNode` 自身的`Array`

#### 使用示例

下述例子会打印出 ID 为 `"box"` 的 `<div>` 标签内的所有 `<span>` 标签的 `textContent` 属性：

```html
<div id="box">
  <span>Foo</span>
  <span>Bar</span>
  <span>Baz</span>
</div>
```

```js
var box = document.getElementById("box");
eachNode(box, function (node) {
  if (null != node.textContent) {
    console.log(node.textContent);
  }
});
```

用户终端上会显示如下字符：

```js
"\n\t", "Foo", "\n\t", "Bar", "\n\t", "Baz";
```

**备注：** 空格是构成 `Text` (en-US)节点的一部分，意味着缩进和换行在 `Element` 节点之间形成单独的 `Text` 。

#### 真实案例

下述例子反应了 `eachNode` 函数是如何在真实场景中使用的：搜索网页中的文本。我们使用一个包装函数 `grep` 去执行搜索：

```js
function grep(parentNode, pattern) {
  var matches = [];
  var endScan = false;

  eachNode(parentNode, function (node) {
    if (endScan) return false;

    // Ignore anything which isn't a text node
    if (node.nodeType !== Node.TEXT\_NODE) return;

    if ("string" === typeof pattern) {
      if (-1 !== node.textContent.indexOf(pattern)) matches.push(node);
    } else if (pattern.test(node.textContent)) {
      if (!pattern.global) {
        endScan = true;
        matches = node;
      } else matches.push(node);
    }
  });

  return matches;
}
```

例如：找到所有包含错别字的 `Text` (en-US)：

```js
var typos = ["teh", "adn", "btu", "adress", "youre", "msitakes"];
var pattern = new RegExp("\\b(" + typos.join("|") + ")\\b", "gi");
var mistakes = grep(document.body, pattern);
console.log(mistakes);
```

规范
--

| Specification |
| --- |
| DOM Standard # interface-node |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.


SpeechGrammar - Web API 接口参考

SpeechGrammar
=============

**实验性:** **这是一项实验性技术**
在将其用于生产之前，请仔细检查浏览器兼容性表格。

Web Speech API 的 **`SpeechGrammar`** 接口 表示了语音识别对象服务想要识别的一系列词语或模式。

文法通过 JSpeech Grammar Format (**JSGF**.) 来定义，其他格式的文法会在以后支持。

构造函数
----

`SpeechGrammar.SpeechGrammar()`

创建一个新的 `SpeechGrammar` 对象。

属性
--

`SpeechGrammar.src`

设置或返回 `SpeechGrammar` 对象实例中包含文法的字符串。

`SpeechGrammar.weight` 可选

设置或返回 `SpeechGrammar` 对象的权重。

示例
--

```js
var grammar =
  "#JSGF V1.0; grammar colors; public <color> = aqua | azure | beige | bisque | black | blue | brown | chocolate | coral | crimson | cyan | fuchsia | ghostwhite | gold | goldenrod | gray | green | indigo | ivory | khaki | lavender | lime | linen | magenta | maroon | moccasin | navy | olive | orange | orchid | peru | pink | plum | purple | red | salmon | sienna | silver | snow | tan | teal | thistle | tomato | turquoise | violet | white | yellow ;";
var recognition = new SpeechRecognition();
var speechRecognitionList = new SpeechGrammarList();
speechRecognitionList.addFromString(grammar, 1);
recognition.grammars = speechRecognitionList;

console.log(speechRecognitionList[0].src); // 应该返回和上面语法变量一样的内容
console.log(speechRecognitionList[0].weight); // 应该返回 1 - 与上面第四行所设置的权重一致
```

规范
--

| Specification |
| --- |
| Web Speech API # speechreco-speechgrammar |

浏览器兼容性
------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

相关链接
----

* Web Speech API


Plugin - Web API 接口参考

Plugin
======

**警告：** **已废弃**
 该特性已经从 HTML5.2 标准中删除，虽然一些浏览器目前仍然支持它，但也许会在未来的某个时间停止支持，请尽量不要使用该特性。

插件接口提供有关浏览器插件的信息。

**备注：** 在最新版本的浏览器中插件对象本身的属性不可枚举。

属性
--

| 名称 | 描述 | 返回值类型 | 兼容性 |
| --- | --- | --- | --- |
| `Plugin.description` | 一个人类可读的插件描述。 **只读。** | `DOMString` | DOM 0 |
| `Plugin.filename` | 插件文件名。**只读。** | `DOMString` | DOM 0 |
| `Plugin.name` | 插件名。**只读。** | `DOMString` | DOM 0 |
| `Plugin.version` | 插件版本号字符串。**只读。** | `DOMString` | Gecko browsers only (Firefox 4+) |

方法
--

`Plugin.item`

返回支持的 MIME 类型的索引号。

`Plugin.namedItem`

返回支持的 MIME 类型。

规范
--

| Specification |
| --- |
| HTML Standard # dom-plugin |