3,389
个编辑
MCBBS Wiki欢迎您共同参与编辑!在参与编辑之前请先阅读Wiki方针。
如果在编辑的过程中遇到了什么问题,可以去讨论板提问。
为了您能够无阻碍地参与编辑 未验证/绑定过邮箱的用户,请尽快绑定/验证。
MCBBS Wiki GitHub群组已上线!
您可以在回声洞中发表吐槽!
服务器状态监控。点击进入
本站由MCBBS用户自行搭建,与MCBBS及东银河系漫游指南(北京)科技有限公司没有从属关系。点此了解 MCBBS Wiki 不是什么>>
(创建页面,内容为“<noinclude><pre><span class="skinview3d salt">文件:1.8皮肤模板 第二层镂空.png</span> <span class="skinview3d salt">https://attachment.mcbbs.net/forum/202004/26/203149z2t4el4ctdh4t1dt.png</span> {{#Widget:SaltSkinPreviewer}}</pre> <span class="skinview3d salt">文件:1.8皮肤模板 第二层镂空.png</span> <span class="skinview3d salt">https://attachment.mcbbs.net/forum/202004/26/203149z2t4el4ctdh4t1dt.png</span> {{#Widget:SaltSkinPrev…”) 标签:2017年版源代码编辑 |
Salt lovely(留言 | 贡献) (代码重写) |
||
| 第1行: | 第1行: | ||
<noinclude><pre>< | <noinclude><pre><div class="salt salt-skin-view-3d" style="width: 250px; height: 350px;">[[文件:1.8皮肤模板 第二层镂空.png]]</div> | ||
< | <div class="salt salt-skin-view-3d" style="width: 400px; height: 400px;">https://minotar.net/skin/MHF_Steve</div> | ||
{{#Widget:SaltSkinPreviewer}}</pre> | {{#Widget:SaltSkinPreviewer}}</pre> | ||
< | <div class="salt salt-skin-view-3d" style="width: 250px; height: 350px;">[[文件:1.8皮肤模板 第二层镂空.png]]</div> | ||
< | <div class="salt salt-skin-view-3d" style="width: 400px; height: 400px;">https://minotar.net/skin/MHF_Steve</div> | ||
{{#Widget:SaltSkinPreviewer}} | {{#Widget:SaltSkinPreviewer}} | ||
这个预览功能使用了[https://github.com/bs-community/skinview3d bs-community的skinview3d开源库]于2020-12-31的版本,采用'''MIT许可证''' | 这个预览功能使用了[https://github.com/bs-community/skinview3d bs-community的skinview3d开源库]于2020-12-31的版本,采用'''MIT许可证''',Salt_lovely[https://github.com/Salt-lovely/skinview3d 编译上传于Github的版本]遵从原许可证。 | ||
主体功能实现于2022年8月20日重写,新版源代码详见[https://github.com/mcbbs-wiki/mcbbs-wiki-widget-repo Github仓库],旧版源代码已经随着盐酱的旧电脑一起随风飘散。 | |||
</noinclude><includeonly><script async> | |||
"use strict"; | |||
(() => { | |||
// src/utils/utils.ts | |||
function docReady(fn) { | |||
if (document.readyState === "loading") { | |||
window.addEventListener("DOMContentLoaded", fn); | |||
} else { | |||
fn(); | |||
} | |||
} | |||
function sleep(time = 500) { | |||
return new Promise((res) => { | |||
setTimeout(() => res(), time); | |||
}); | |||
} | |||
async function waitTill(what, interval = 500, safeTime = 12e4) { | |||
const startTime = Date.now(); | |||
while (!what()) { | |||
await sleep(interval); | |||
if (Date.now() - startTime > safeTime && !what()) | |||
throw new Error("Out Of Time"); | |||
} | |||
} | |||
// src/utils/resource.ts | |||
function addScript(url, asynchronous = false, key) { | |||
if (key && document.getElementById(key)) | |||
return; | |||
const scr = document.createElement("script"); | |||
scr.src = url; | |||
scr.async = asynchronous; | |||
if (key) | |||
scr.id = key; | |||
document.head.appendChild(scr); | |||
} | |||
// widget/SaltSkinPreviewer/widget.ts | |||
var filterWebsite = [ | |||
"https://mcbbs.wiki/", | |||
"https://attachment.mcbbs.net/", | |||
"https://minotar.net/" | |||
]; | |||
addScript("https://cdn.jsdelivr.net/gh/Salt-lovely/[email protected].2/bundles/skinview3d.bundle.js", true, "SaltSkinPreviewer"); | |||
docReady(async () => { | |||
await waitTill(() => { | |||
var _a; | |||
return (_a = window.skinview3d) == null ? void 0 : _a.SkinViewer; | |||
}); | |||
const skinList = Array.from(document.querySelectorAll(".salt.salt-skin-view-3d")); | |||
skinList.forEach((skin) => { | |||
var _a; | |||
skin.classList.remove("salt"); | |||
let src; | |||
if (skin.querySelector("img")) { | |||
src = (_a = skin.querySelector("img")) == null ? void 0 : _a.src; | |||
} else | |||
src = skin.textContent; | |||
if (!src || src.length < 10) | |||
return; | |||
if (!filterWebsite.some((site) => src.startsWith(site))) | |||
return; | |||
skin.innerHTML = ""; | |||
const canvas = document.createElement("canvas"); | |||
const option = { | |||
canvas, | |||
width: skin.offsetWidth, | |||
height: skin.offsetHeight, | |||
skin: src, | |||
fov: 50, | |||
zoom: 0.9 | |||
}; | |||
const viewer = new window.skinview3d.SkinViewer(option); | |||
viewer.globalLight.intensity = 0.5; | |||
viewer.cameraLight.intensity = 0.5; | |||
skin.appendChild(canvas); | |||
const animation = { | |||
idle: new window.skinview3d.IdleAnimation(), | |||
walk: new window.skinview3d.WalkingAnimation() | |||
}; | |||
const action = (() => { | |||
let curr = 0; | |||
const actions = [ | |||
(v) => { | |||
v.animation = animation.walk; | |||
v.animation.speed = 0.5; | |||
}, | |||
(v) => { | |||
v.animation = animation.walk; | |||
v.animation.speed = 1; | |||
}, | |||
(v) => { | |||
v.animation = animation.idle; | |||
v.animation.speed = 1; | |||
} | |||
]; | |||
return (v) => { | |||
actions[curr++](v); | |||
if (curr >= actions.length) | |||
curr = 0; | |||
}; | |||
})(); | |||
let pos = { x: 0, y: 0 }; | |||
skin.addEventListener("mousedown", (ev) => { | |||
const { x, y } = ev; | |||
pos = { x, y }; | |||
ev.preventDefault(); | |||
}); | |||
skin.addEventListener("mouseup", (ev) => { | |||
const { x, y } = ev; | |||
}) | if (Math.abs(pos.x - x) > 2 || Math.abs(pos.y - y) > 2) | ||
})() | return; | ||
if (ev.button === 0) | |||
action(viewer); | |||
else if (ev.button === 2) | |||
viewer.resetCameraPose(); | |||
ev.preventDefault(); | |||
}); | |||
action(viewer); | |||
skin.addEventListener("dblclick", () => { | |||
viewer.resetCameraPose(); | |||
}); | |||
}); | |||
}); | |||
})(); | |||
</script></includeonly> | </script></includeonly> | ||