2025-04-07 日报 Day149

2025-04-07 日报 Day149

Yuyang 前端小白🥬

今日的鸡汤

“等闲识得东风面,万紫千红总是春”,这是生命繁衍的律动。

今日学习内容

1、JS 红皮书 P627-635 第二十章:JavaScript API

今日笔记

1、 媒体元素: HTML5 引入了


每个元素至少要求有一个 src 属性,以表示要加载的媒体文件。我们也可以指定表示视频播放器大小的 width 和 height 属性,以及在视频加载期间显示图片 URI 的 poster 属性。另外,controls属性如果存在,则表示浏览器应该显示播放界面,让用户可以直接控制媒体。开始和结束标签之间的内容是在媒体播放器不可用时显示的替代内容。
由于浏览器支持的媒体格式不同,因此可以指定多个不同的媒体源。为此,需要从元素中删除 src属性,使用一个或多个元素代替,如下面的例子所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
<!-- 嵌入视频 --> 
<video id="myVideo">
<source src="conference.webm" type="video/webm; codecs='vp8, vorbis'">
<source src="conference.ogv" type="video/ogg; codecs='theora, vorbis'">
<source src="conference.mpg">
Video player not available.
</video>
<!-- 嵌入音频 -->
<audio id="myAudio">
<source src="song.ogg" type="audio/ogg">
<source src="song.mp3" type="audio/mpeg">
Audio player not available.
</audio>
  • 属性:
  • 事件: 除了有很多属性,媒体元素还有很多事件。这些事件会监控由于媒体回放或用户交互导致的不同属性的变化。下表列出了这些事件。
    事件 何时触发
    abort 当媒体加载被中止时触发。
    canplay 回放可以开始,readyState 为 2
    canplaythrough 回放可以继续,不应该中断,readState 为 3
    canshowcurrentframe 已经下载当前帧,readyState 为 1
    dataunavailable 不能回放,因为没有数据,readyState 为 0
    ended 当媒体播放到结尾时触发。
    2、自定义媒体播放器: 使用
1
2
3
4
5
6
7
8
9
10
11
12
<div class="mediaplayer"> 
<div class="video">
<video id="player" src="movie.mov" poster="mymovie.jpg"
width="300" height="200">
Video player not available.
</video>
</div>
<div class="controls">
<input type="button" value="Play" id="video-btn">
<span id="curtime">0</span>/<span id="duration">0</span>
</div>
</div>

3、检测编解码器: 如前所述,并不是所有浏览器都支持

1
2
3
4
let audio = new Audio("sound.mp3"); 
EventUtil.addHandler(audio, "canplaythrough", function(event) {
audio.play();
});

创建 Audio 的新实例就会开始下载指定的文件。下载完毕后,可以调用 play()来播放音频。
在 iOS 中调用 play()方法会弹出一个对话框,请求用户授权播放声音。为了连续播放,必须在onfinish 事件处理程序中立即调用 play()。
5、原生拖放: 关于拖放最有意思的可能就是可以跨窗格、跨浏览器容器,有时候甚至可以跨应用程序拖动元素。浏览器对拖放的支持可以让我们实现这些功能。

  • 拖放事件: 拖放事件几乎可以让开发者控制拖放操作的方方面面。关键的部分是确定每个事件是在哪里触发的。有的事件在被拖放元素上触发,有的事件则在放置目标上触发。在某个元素被拖动时,会(按顺序)触发以下事件:
    (1) dragstart
    (2) drag
    (3) dragend
    dragstart 事件触发后,只要目标还被拖动就会持续触发 drag 事件。这个事件类似于 mousemove,即随着鼠标移动而不断触发。当拖动停止时(把元素放到有效或无效的放置目标上),会触发 dragend事件。
    在把元素拖动到一个有效的放置目标上时,会依次触发以下事件:
    (1) dragenter
    (2) dragover
    (3) dragleave 或 drop
  • 自定义放置目标: 在把某个元素拖动到无效放置目标上时,会看到一个特殊光标(圆环中间一条斜杠)表示不能放下。即使所有元素都支持放置目标事件,这些元素默认也是不允许放置的。如果把元素拖动到不允许放置的目标上,无论用户动作是什么都不会触发 drop 事件。不过,通过覆盖 dragenter 和 dragover 事件的默认行为,可以把任何元素转换为有效的放置目标。例如,如果有一个 ID 为”droptarget”的
    元素,那么可以使用以下代码把它转换成一个放置目标:
    1
    2
    3
    4
    5
    6
    7
    let droptarget = document.getElementById("droptarget"); 
    droptarget.addEventListener("dragover", (event) => {
    event.preventDefault();
    });
    droptarget.addEventListener("dragenter", (event) => {
    event.preventDefault();
    });
    6、dataTransfer对象: dataTransfer 对象有两个主要方法:getData()和 setData()。顾名思义,getData()用于获取 setData()存储的值。setData()的第一个参数以及 getData()的唯一参数是一个字符串,表示要设置的数据类型:”text”或”URL”,如下所示:
    1
    2
    3
    4
    5
    6
    // 传递文本
    event.dataTransfer.setData("text", "some text");
    let text = event.dataTransfer.getData("text");
    // 传递 URL
    event.dataTransfer.setData("URL", "http://www.wrox.com/");
    let url = event.dataTransfer.getData("URL");
    7、dropEffect与effectAllowed: dataTransfer 对象不仅可以用于实现简单的数据传输,还可以用于确定能够对被拖动元素和放置目标执行什么操作。为此,可以使用两个属性:dropEffect 与 effectAllowed。
    8、可拖动能力: 默认情况下,图片、链接和文本是可拖动的,这意味着无须额外代码用户便可以拖动它们。文本只有在被选中后才可以拖动,而图片和链接在任意时候都是可以拖动的。
    我们也可以让其他元素变得可以拖动。HTML5 在所有 HTML 元素上规定了一个 draggable 属性,表示元素是否可以拖动。图片和链接的 draggable 属性自动被设置为 true,而其他所有元素此属性的默认值为 false。如果想让其他元素可拖动,或者不允许图片和链接被拖动,都可以设置这个属性。例如:
    1
    2
    3
    4
    <!-- 禁止拖动图片 --> 
    <img src="smile.gif" draggable="false" alt="Smiley face">
    <!-- 让元素可以拖动 -->
    <div draggable="true">...</div>
    9、Notifications API: Notifications API 用于向用户显示通知。无论从哪个角度看,这里的通知都很类似 alert()对话框:都使用 JavaScript API 触发页面外部的浏览器行为,而且都允许页面处理用户与对话框或通知弹层的交互。不过,通知提供更灵活的自定义能力。
    Notifications API 在 Service Worker 中非常有用。渐进 Web 应用(PWA,Progressive Web Application)通过触发通知可以在页面不活跃时向用户显示消息,看起来就像原生应用。
  • 通知权限: Notifications API 有被滥用的可能,因此默认会开启两项安全措施:
     通知只能在运行在安全上下文的代码中被触发;
     通知必须按照每个源的原则明确得到用户允许。
    用户授权显示通知是通过浏览器内部的一个对话框完成的。除非用户没有明确给出允许或拒绝的答复,否则这个权限请求对每个域只会出现一次。浏览器会记住用户的选择,如果被拒绝则无法重来。
    页面可以使用全局对象 Notification 向用户请求通知权限。这个对象有一个 requestPemission()方法,该方法返回一个期约,用户在授权对话框上执行操作后这个期约会解决。
    Notification.requestPermission()
    .then((permission) => {
    console.log(‘User responded to permission request:’, permission);
    });
    “granted”值意味着用户明确授权了显示通知的权限。除此之外的其他值意味着显示通知会静默失败。如果用户拒绝授权,这个值就是”denied”。一旦拒绝,就无法通过编程方式挽回,因为不可能再触发授权提示。
  • 显示和隐藏通知: Notification 构造函数用于创建和显示通知。最简单的通知形式是只显示一个标题,这个标题内容可以作为第一个参数传给 Notification 构造函数。以下面这种方式调用 Notification,应该会立即显示通知:
    1
    new Notification('Title text!'); 
    可以通过 options 参数对通知进行自定义,包括设置通知的主体、图片和振动等:
    1
    2
    3
    4
    5
    new Notification('Title text!', {
    body: 'Body text!',
    image: 'path/to/image.png',
    vibrate: true
    });
    调用这个构造函数返回的 Notification 对象的 close()方法可以关闭显示的通知。下面的例子展示了显示通知后 1000 毫秒再关闭它:
    1
    2
    const n = new Notification('I will close in 1000ms'); 
    setTimeout(() => n.close(), 1000);
  • 通知生命周期回调: 通知并非只用于显示文本字符串,也可用于实现交互。Notifications API 提供了 4 个用于添加回调的生命周期方法:
     onshow 在通知显示时触发;
     onclick 在通知被点击时触发;
     onclose 在通知消失或通过 close()关闭时触发;
     onerror 在发生错误阻止通知显示时触发。
    下面的代码将每个生命周期事件都通过日志打印了出来:
    1
    2
    3
    4
    5
    const n = new Notification('foo'); 
    n.onshow = () => console.log('Notification was shown!');
    n.onclick = () => console.log('Notification was clicked!');
    n.onclose = () => console.log('Notification was closed!');
    n.onerror = () => console.log('Notification experienced an error!');
此页目录
2025-04-07 日报 Day149