update heatmap

This commit is contained in:
Harvey Zack committed 2023-05-02 19:14:14 +08:00
1 parent db5a7d3567
commit 56af4ca4a4
8 files changed
+134 -33

No files matched your search

@@ -163,7 +163,7 @@ function artplayerPluginDanmuku(option) {
checkVersion(art);
const danmuku = new (0, _danmukuDefault.default)(art, option);
(0, _settingDefault.default)(art, danmuku);
if (option.heatmap) (0, _heatmapDefault.default)(art, danmuku);
if (option.heatmap) (0, _heatmapDefault.default)(art, danmuku, option.heatmap);
return {
name: "artplayerPluginDanmuku",
emit: danmuku.emit.bind(danmuku),
@@ -187,7 +187,7 @@ function artplayerPluginDanmuku(option) {
exports.default = artplayerPluginDanmuku;
artplayerPluginDanmuku.env = "development";
artplayerPluginDanmuku.version = "5.0.1";
artplayerPluginDanmuku.build = "2023-05-02 15:25:00";
artplayerPluginDanmuku.build = "2023-05-02 18:01:36";
if (typeof window !== "undefined") window["artplayerPluginDanmuku"] = artplayerPluginDanmuku;
},{"./danmuku":"cv7fe","./setting":"cI0ih","./heatmap":"bZziT","@parcel/transformer-js/src/esmodule-helpers.js":"5dUr6"}],"cv7fe":[function(require,module,exports) {
@@ -274,7 +274,7 @@ class Danmuku {
maxWidth: "number",
mount: "undefined|htmldivelement",
theme: "string",
heatmap: "boolean",
heatmap: "object|boolean",
beforeEmit: "function"
};
}
@@ -1192,18 +1192,25 @@ const line = (pointA, pointB)=>{
angle: Math.atan2(lengthY, lengthX)
};
};
function heatmap(art, danmuku) {
function heatmap(art, danmuku, option) {
const { query } = art.constructor.utils;
art.controls.add({
name: "heatmap",
position: "top",
html: "",
style: {
height: "50px",
height: "100px",
width: "100%",
pointerEvents: "none"
},
mounted ($heatmap) {
let $start = null;
let $stop = null;
function update() {
$start = null;
$stop = null;
$heatmap.innerHTML = "";
if (danmuku.danmus.length === 0) return;
const svg = {
w: $heatmap.offsetWidth,
h: $heatmap.offsetHeight
@@ -1213,22 +1220,30 @@ function heatmap(art, danmuku) {
xMax: svg.w,
yMin: 0,
yMax: 128,
scale: 0.2,
minHeight: Math.floor(svg.h * 0.1),
scale: 0.25,
opacity: 0.2,
minHeight: Math.floor(svg.h * 0.05),
sampling: Math.floor(svg.w / 100),
fill: "rgba(255, 255, 255, 0.5)",
smoothing: 0.2,
flattening: 0
flattening: 0.2
};
if (typeof option === "object") Object.assign(options, option);
const points = [];
const gap = art.duration / svg.w;
for(let x = 0; x <= svg.w; x += options.sampling){
const y = danmuku.danmus.filter(({ time })=>time > x * gap && time <= (x + options.sampling) * gap).length;
points.push([
x,
y + options.minHeight
y
]);
}
const lastPoint = points[points.length - 1];
const lastX = lastPoint[0];
const lastY = lastPoint[1];
if (lastX !== svg.w) points.push([
svg.w,
lastY
]);
const yPoints = points.map((point)=>point[1]);
const yMin = Math.min(...yPoints);
const yMax = Math.max(...yPoints);
@@ -1236,7 +1251,7 @@ function heatmap(art, danmuku) {
for(let i = 0; i < points.length; i++){
const point = points[i];
const y = point[1];
point[1] = y * (y > yMid ? 1 + options.scale : 1 - options.scale);
point[1] = y * (y > yMid ? 1 + options.scale : 1 - options.scale) + options.minHeight;
}
const controlPoint = (current, previous, next, reverse)=>{
const p = previous || current;
@@ -1268,14 +1283,38 @@ function heatmap(art, danmuku) {
});
const pathD = pointsPositions.reduce((acc, e, i, a)=>i === 0 ? `M ${a[a.length - 1][0]},${svg.h} L ${e[0]},${svg.h} L ${e[0]},${e[1]}` : `${acc} ${bezierCommand(e, i, a)}`, "");
$heatmap.innerHTML = `
<svg viewBox="0 0 ${svg.w} ${svg.h}">
<path style="fill: var(--art-progress-color, ${options.fill})" d="${pathD}"></path>
</svg>
<svg viewBox="0 0 ${svg.w} ${svg.h}">
<defs>
<linearGradient id="heatmap-solids" x1="0%" y1="0%" x2="100%" y2="0%">
<stop offset="0%" style="stop-color:var(--art-theme);stop-opacity:${options.opacity}" />
<stop offset="0%" style="stop-color:var(--art-theme);stop-opacity:${options.opacity}" id="heatmap-start" />
<stop offset="0%" style="stop-color:var(--art-progress-color);stop-opacity:1" id="heatmap-stop" />
<stop offset="100%" style="stop-color:var(--art-progress-color);stop-opacity:1" />
</linearGradient>
</defs>
<path fill="url(#heatmap-solids)" d="${pathD}"></path>
</svg>
`;
$start = query("#heatmap-start", $heatmap);
$stop = query("#heatmap-stop", $heatmap);
$start.setAttribute("offset", `${art.played * 100}%`);
$stop.setAttribute("offset", `${art.played * 100}%`);
}
art.on("video:timeupdate", ()=>{
if ($start && $stop) {
$start.setAttribute("offset", `${art.played * 100}%`);
$stop.setAttribute("offset", `${art.played * 100}%`);
}
});
art.on("setBar", (type, percentage)=>{
if ($start && $stop && type === "played") {
$start.setAttribute("offset", `${percentage * 100}%`);
$stop.setAttribute("offset", `${percentage * 100}%`);
}
});
art.on("ready", update);
art.on("resize", update);
art.emit("artplayerPluginDanmuku:loaded", update);
art.on("artplayerPluginDanmuku:loaded", update);
}
});
}