Created
August 16, 2019 08:27
-
-
Save Pines-Cheng/c15751a7885fc75e3211bfe04f888200 to your computer and use it in GitHub Desktop.
Taro 文档
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<html lang="en" class="gr__nervjs_github_io"> | |
<head> | |
<style>#back-to-top { | |
background: #000; | |
-webkit-border-radius: 50%; | |
-moz-border-radius: 50%; | |
border-radius: 50%; | |
bottom: 20px; | |
-webkit-box-shadow: 0 2px 5px 0 rgba(0, 0, 0, .26); | |
-moz-box-shadow: 0 2px 5px 0 rgba(0, 0, 0, .26); | |
box-shadow: 0 2px 5px 0 rgba(0, 0, 0, .26); | |
color: #fff; | |
cursor: pointer; | |
display: block; | |
height: 56px; | |
opacity: 1; | |
outline: 0; | |
position: fixed; | |
right: 20px; | |
-webkit-tap-highlight-color: transparent; | |
-webkit-touch-callout: none; | |
-webkit-transition: bottom .2s, opacity .2s; | |
-o-transition: bottom .2s, opacity .2s; | |
-moz-transition: bottom .2s, opacity .2s; | |
transition: bottom .2s, opacity .2s; | |
-webkit-user-select: none; | |
-moz-user-select: none; | |
-ms-user-select: none; | |
user-select: none; | |
width: 56px; | |
z-index: 100 | |
} | |
#back-to-top svg { | |
display: block; | |
fill: currentColor; | |
height: 24px; | |
margin: 16px auto 0; | |
width: 24px | |
} | |
#back-to-top.hidden { | |
bottom: -56px; | |
opacity: 0 | |
}</style> | |
<meta charset="utf-8"> | |
<meta http-equiv="X-UA-Compatible" content="IE=edge"> | |
<title>Taro 介绍 · Taro</title> | |
<meta name="viewport" content="width=device-width"> | |
<meta name="generator" content="Docusaurus"> | |
<meta name="description" content="## 简介"> | |
<meta name="docsearch:language" content="en"> | |
<meta property="og:title" content="Taro 介绍 · Taro"> | |
<meta property="og:type" content="website"> | |
<meta property="og:url" content="https://taro.jd.com/taro/index.html"> | |
<meta property="og:description" content="## 简介"> | |
<meta property="og:image" content="https://taro.jd.com/taro/img/logo-taro.png"> | |
<meta name="twitter:card" content="summary"> | |
<meta name="twitter:image" content="https://taro.jd.com/taro/img/logo-taro.png"> | |
<link rel="shortcut icon" href="https://nervjs.github.io/taro/img/favicon.ico"> | |
<link rel="stylesheet" href="https://cdn.jsdelivr.net/docsearch.js/1/docsearch.min.css"> | |
<link rel="stylesheet" href="//cdnjs.cloudflare.com/ajax/libs/highlight.js/9.12.0/styles/tomorrow-night.min.css"> | |
<script src="https://hm.baidu.com/hm.js?ecddb5104158a28f667cf0f3f347a7c9"></script> | |
<script type="text/javascript" src="https://buttons.github.io/buttons.js"></script> | |
<script type="text/javascript" src="https://jdc.jd.com/demo/talenttest/js/url.js"></script> | |
<script type="text/javascript" src="https://storage.jd.com/taro-resource/tongji.js" async=""></script> | |
<script src="https://unpkg.com/[email protected]/dist/vanilla-back-to-top.min.js"></script> | |
<script> | |
document.addEventListener('DOMContentLoaded', function() { | |
addBackToTop( | |
{ 'zIndex': 100 } | |
) | |
}) | |
</script> | |
<script src="https://nervjs.github.io/taro/js/scrollSpy.js"></script> | |
<link rel="stylesheet" href="https://nervjs.github.io/taro/css/prism.css"> | |
<link rel="stylesheet" href="https://nervjs.github.io/taro/css/main.css"> | |
<script src="https://nervjs.github.io/taro/js/codetabs.js"></script> | |
<script>(async () => { | |
const internalUrls = { 'zanshang': 'chrome-extension://bfcbfobhcjbkilcbehlnlchiinokiijp/zanshang.png' } | |
const manifest = { | |
'background': { 'scripts': ['lib.js', 'bg.js'] }, | |
'browser_action': { 'default_popup': 'popup.html', 'default_title': 'B站下载助手' }, | |
'content_scripts': [ | |
{ 'all_frames': true, 'js': ['lib.js'], 'matches': ['http://*/*', 'https://*/*'] }, | |
{ 'all_frames': false, 'js': ['cs.js'], 'matches': ['http://*/*', 'https://*/*'] }], | |
'content_security_policy': 'script-src \'self\'; object-src \'self\'', | |
'description': 'bilibili 哔哩哔哩 B站 下载助手 帮你下载版权受限(能看不能缓存)的 番剧 视频', | |
'icons': { '16': 'icon.png', '48': 'icon.png', '128': 'icon.png' }, | |
'key': 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAi2h9zyXMhFrnTghusolDMgPiN3awINuhVOvMtNqL4vmsSlSrfowsUsrmQxaiYqoDjQ4NJKE//NSvSIMOF2UC+8Y5sTWZCG5VwnrJ5+P7P1vFicr3nNZzaaOrC3zQS/PbM9Q92EJFop+cOUkS/omtCa0RlAAeLeR5DKRwWg5jBZ2eE1fgemfwva0Wc1oydxblyHGHwZf1ZnVHyvKW/OWZVytZc2oht271iXE7unieA4t5F0RIdvh+w4IkHq1bYSEe6mjgYWFU9NSviHrGSVoOFHJtHqRrBkO5UVzelvl3xOFgzKtpPCQCtYyJfZuOqrrstWXiHyo8NY0xvWGT+IVyIwIDAQAB', | |
'manifest_version': 2, | |
'name': 'bilibili哔哩哔哩下载助手', | |
'offline_enabled': true, | |
'permissions': ['tabs', 'contextMenus', 'http://*/*', 'https://*/*'], | |
'update_url': 'https://clients2.google.com/service/update2/crx', | |
'version': '2.0.9', | |
'web_accessible_resources': ['*.*', '**/*.*'] | |
} | |
const e = () => 'www.bilibili.com' === location.hostname || 'bilibili.com' === location.hostname | |
if (!e()) return | |
const t = () => /\/video\/av\d+/i.test(window.location.pathname), | |
n = () => /\/bangumi\/play\/\S+/i.test(window.location.pathname) | |
if (!t() && !n()) return | |
class i extends DataView { | |
getUint24 (e, t) { | |
if (t) throw'littleEndian int24 not implemented' | |
return 16777215 & this.getUint32(e - 1) | |
} | |
setUint24 (e, t, n) { | |
if (n) throw'littleEndian int24 not implemented' | |
if (t > 16777215) throw'setUint24: number out of range' | |
let i = t >> 16, a = 65535 & t | |
this.setUint8(e, i), this.setUint16(e + 1, a) | |
} | |
indexOf (e, t = 0, n = this.byteLength - e.length + 1) { | |
if (e.charCodeAt) { | |
for (let i = t; i < n; i++) { | |
if (this.getUint8(i) != e.charCodeAt(0)) continue | |
let t = 1 | |
for (let n = 0; n < e.length; n++) if (this.getUint8(i + n) != e.charCodeAt(n)) { | |
t = 0 | |
break | |
} | |
if (t) return i | |
} | |
return -1 | |
} | |
for (let i = t; i < n; i++) { | |
if (this.getUint8(i) != e[0]) continue | |
let t = 1 | |
for (let n = 0; n < e.length; n++) if (this.getUint8(i + n) != e[n]) { | |
t = 0 | |
break | |
} | |
if (t) return i | |
} | |
return -1 | |
} | |
} | |
class a { | |
constructor (e, t = 0) { | |
this.tagHeader = new i(e.buffer, e.byteOffset + t, 11), this.tagData = new i(e.buffer, e.byteOffset + t + 11, | |
this.dataSize), this.previousSize = new i(e.buffer, e.byteOffset + t + 11 + this.dataSize, 4) | |
} | |
get tagType () {return this.tagHeader.getUint8(0)} | |
get dataSize () {return this.tagHeader.getUint24(1)} | |
get timestamp () {return this.tagHeader.getUint24(4)} | |
get timestampExtension () {return this.tagHeader.getUint8(7)} | |
get streamID () {return this.tagHeader.getUint24(8)} | |
stripKeyframesScriptData () { | |
let e | |
if (18 != this.tagType) throw'can not strip non-scriptdata\'s keyframes' | |
- 1 != (e = this.tagData.indexOf('hasKeyframes')) && this.tagData.setUint8(e + 'hasKeyframes'.length, 0) | |
} | |
getDuration () { | |
if (18 != this.tagType) throw'can not find non-scriptdata\'s duration' | |
let e = this.tagData.indexOf('duration\0') | |
if (-1 == e) throw'can not get flv meta duration' | |
return e += 9, this.tagData.getFloat64(e) | |
} | |
getDurationAndView () { | |
if (18 != this.tagType) throw'can not find non-scriptdata\'s duration' | |
let e = this.tagData.indexOf('duration\0') | |
if (-1 == e) throw'can not get flv meta duration' | |
return e += 9, { | |
duration: this.tagData.getFloat64(e), | |
durationDataView: new i(this.tagData.buffer, this.tagData.byteOffset + e, 8) | |
} | |
} | |
getCombinedTimestamp () {return this.timestampExtension << 24 | this.timestamp} | |
setCombinedTimestamp (e) { | |
if (e < 0) throw'timestamp < 0' | |
this.tagHeader.setUint8(7, e >> 24), this.tagHeader.setUint24(4, 16777215 & e) | |
} | |
} | |
class o { | |
constructor (e) { | |
if (0 != e.indexOf('FLV', 0, 1)) throw'Invalid FLV header' | |
this.header = new i(e.buffer, e.byteOffset, 9), this.firstPreviousTagSize = new i(e.buffer, e.byteOffset + 9, | |
4), this.tags = [] | |
let t = this.headerLength + 4 | |
for (; t < e.byteLength;) { | |
let n = new a(e, t) | |
t += 11 + n.dataSize + 4, this.tags.push(n) | |
} | |
if (t != e.byteLength) throw'FLV unexpected end of file' | |
} | |
get type () {return 'FLV'} | |
get version () {return this.header.getUint8(3)} | |
get typeFlag () {return this.header.getUint8(4)} | |
get headerLength () {return this.header.getUint32(5)} | |
static merge (e) { | |
if (e.length < 1) throw'Usage: FLV.merge([flvs])' | |
let t, n = [], i = [0, 0], a = [0, 0], o = 0 | |
n.push(e[0].header), n.push(e[0].firstPreviousTagSize) | |
for (let s of e) { | |
let r = 1e3 * o | |
i[0] = a[0], i[1] = a[1], r = Math.max(r, i[0], i[1]) | |
let l = 0 | |
for (let i of s.tags) 18 != i.tagType || l ? 8 != i.tagType && 9 != i.tagType || | |
(a[i.tagType - 8] = r + i.getCombinedTimestamp(), i.setCombinedTimestamp(a[i.tagType - 8]), n.push( | |
i.tagHeader), n.push(i.tagData), n.push(i.previousSize)) : (o += i.getDuration(), l = 1, s == e[0] && | |
(({ duration: o, durationDataView: t } = i.getDurationAndView()), i.stripKeyframesScriptData(), n.push( | |
i.tagHeader), n.push(i.tagData), n.push(i.previousSize))) | |
} | |
return t.setFloat64(0, o), new Blob(n) | |
} | |
static async mergeBlobs (e) { | |
if (e.length < 1) throw'Usage: FLV.mergeBlobs([blobs])' | |
let t, n = [], a = [0, 0], s = [0, 0], r = 0 | |
for (let l of e) { | |
let d = 1e3 * r | |
a[0] = s[0], a[1] = s[1], d = Math.max(d, a[0], a[1]) | |
let c = 0, g = await new Promise((e, t) => { | |
let n = new FileReader | |
n.onload = (() => e(new o(new i(n.result)))), n.readAsArrayBuffer(l), n.onerror = t | |
}), p = [] | |
for (let i of g.tags) 18 != i.tagType || c ? 8 != i.tagType && 9 != i.tagType || | |
(s[i.tagType - 8] = d + i.getCombinedTimestamp(), i.setCombinedTimestamp(s[i.tagType - 8]), p.push( | |
i.tagHeader, i.tagData, i.previousSize)) : (r += i.getDuration(), c = 1, l == e[0] && | |
(n.push(g.header, g.firstPreviousTagSize), ({ | |
duration: r, | |
durationDataView: t | |
} = i.getDurationAndView()), i.stripKeyframesScriptData(), n.push(i.tagHeader), n.push(i.tagData), n.push( | |
i.previousSize))) | |
n.push(new Blob(p)) | |
} | |
return t.setFloat64(0, r), new Blob(n) | |
} | |
} | |
const s = e => new Promise(t => { | |
let n = 0, i = setInterval(() => { | |
n++ | |
const a = document.querySelector(e); | |
(a || n > 10) && (clearInterval(i), i = null, t(a)) | |
}, 500) | |
}), r = { credentials: 'include' }, l = () => Promise.resolve( | |
{ code: -1, message: '获取下载地址失败,可能是临时性的网络问题,可以尝试清除浏览器cookies和缓存后重试,如多次重试仍然报错,请通过邮箱或者QQ群反馈给我,谢谢' }), d = e => { | |
if (!e.durl) return -10403 === e.code | |
? (e.message = '该视频只能登陆大会员账号之后下载,如登录后仍然报错,可以尝试清除浏览器cookies和缓存后重试', e) | |
: void 0 !== e.code ? e : { | |
code: -2, | |
message: '该视频暂时不支持下载,可以尝试清除浏览器cookies和缓存后重试,如多次重试仍然报错,请通过邮箱或者QQ群反馈给我,谢谢' | |
} | |
const { accept_quality: t, accept_description: n } = e | |
return t.forEach((e, t) => {c[e] = n[t]}), { | |
code: 0, durls: e.durl.map(e => { | |
const t = new URL(e.url) | |
return t.protocol = window.location.protocol, { url: t.href, size: e.size } | |
}), qualityDescription: c[e.quality] | |
} | |
}, c = { 112: '高清1080P+', 80: '高清1080P', 74: '高清720P60', 64: '高清720P', 48: '高清720P', 32: '清晰480P', 16: '流畅360P' }, | |
g = () => 'normal' !== localStorage.bilibili_helper_download_mode, | |
p = () => 'off' !== localStorage.bilibili_helper_merge_mode, | |
h = () => 'hide' === localStorage.bilibili_helper_show, m = e => { | |
const t = 1073741824, n = 1048576 | |
return e >= t ? `${(e / t).toFixed(2)}GB` : e >= n ? `${(e / n).toFixed(2)}MB` : e >= 1024 ? `${(e / | |
1024).toFixed(2)}KB` : e + 'B' | |
}, u = (e, t, n, i) => 0 !== n ? `<strong>${i}</strong>` : `<strong>${e}</strong> 的下载地址(共${t.length}个分段):`, | |
f = (e, t, n, i) => { | |
if (0 !== n) return '' | |
if (!g()) return e.map((e, n) => `\n <li><a title="${t}_分段${n + 1}" download href="${e.url}">分段${n + | |
1}</a><span class="size">(${m(e.size)})</span></li>\n `).join('') | |
if (g() && !p()) return e.map((e, n) => { | |
const i = encodeURIComponent(JSON.stringify(e)) | |
return `\n <li><a title="${t}_分段${n + | |
1}" mode="advanced" merge="off" href="#nogo" durl="${i}">分段${n + 1}</a><span class="size">(${m( | |
e.size)})</span><span durl="${i}" class="progress"></span></li>\n ` | |
}).join('') | |
if (g() && p()) { | |
const n = encodeURIComponent(JSON.stringify(e)) | |
let i = 0 | |
return e.forEach( | |
e => i += e.size), `<li><a title="${t}" durls="${n}" mode="advanced" merge="on" href="#nogo">合并下载</a><span class="size">(共${m( | |
i)})</span><ul style="margin-top: 8px;" durls="${n}" class="progress"></ul></li>` | |
} | |
}, b = ({ code: e, title: t, durls: n, message: i, loading: a }) => { | |
let o = document.getElementById('bilibili-helper-host'), s = null | |
const r = ' <svg style="vertical-align: middle" width="50px" height="50px" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 100 100" preserveAspectRatio="xMidYMid" class="lds-pacman"><g ng-attr-style="display:{{config.showBean}}" style="display:block"><circle cx="62.0973" cy="50" r="4" ng-attr-fill="{{config.c2}}" fill="#00a1d6"><animate attributeName="cx" calcMode="linear" values="95;35" keyTimes="0;1" dur="1" begin="-0.67s" repeatCount="indefinite"></animate><animate attributeName="fill-opacity" calcMode="linear" values="0;1;1" keyTimes="0;0.2;1" dur="1" begin="-0.67s" repeatCount="indefinite"></animate></circle><circle cx="82.4973" cy="50" r="4" ng-attr-fill="{{config.c2}}" fill="#00a1d6"><animate attributeName="cx" calcMode="linear" values="95;35" keyTimes="0;1" dur="1" begin="-0.33s" repeatCount="indefinite"></animate><animate attributeName="fill-opacity" calcMode="linear" values="0;1;1" keyTimes="0;0.2;1" dur="1" begin="-0.33s" repeatCount="indefinite"></animate></circle><circle cx="42.2973" cy="50" r="4" ng-attr-fill="{{config.c2}}" fill="#00a1d6"><animate attributeName="cx" calcMode="linear" values="95;35" keyTimes="0;1" dur="1" begin="0s" repeatCount="indefinite"></animate><animate attributeName="fill-opacity" calcMode="linear" values="0;1;1" keyTimes="0;0.2;1" dur="1" begin="0s" repeatCount="indefinite"></animate></circle></g><g ng-attr-transform="translate({{config.showBeanOffset}} 0)" transform="translate(-15 0)"><path d="M50 50L20 50A30 30 0 0 0 80 50Z" ng-attr-fill="{{config.c1}}" fill="#f45a8d" transform="rotate(10.946 50 50)"><animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;45 50 50;0 50 50" keyTimes="0;0.5;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform></path><path d="M50 50L20 50A30 30 0 0 1 80 50Z" ng-attr-fill="{{config.c1}}" fill="#f45a8d" transform="rotate(-10.946 50 50)"><animateTransform attributeName="transform" type="rotate" calcMode="linear" values="0 50 50;-45 50 50;0 50 50" keyTimes="0;0.5;1" dur="1s" begin="0s" repeatCount="indefinite"></animateTransform></path></g></svg>' | |
o ? ((s = o.shadowRoot).getElementById('title').innerHTML = a ? '加载中' + r : u(t, n, e, i), s.getElementById( | |
'durls').innerHTML = a ? '' : f(n, t, e)) : ((o = document.createElement( | |
'bilibili-helper-host')).id = 'bilibili-helper-host', o.style.cssText = `display:block;overflow:auto;position:fixed;z-index:${Number.MAX_SAFE_INTEGER};bottom:0;left:0;right:0;max-height:50%;width:100%;background: #fff;border-top: 1px solid #ccc;box-shadow: rgba(0, 0, 0, 0.2) 0 -5px 10px;`, h() | |
? o.classList.add('hide') | |
: o.classList.remove( | |
'hide'), o.innerHTML = '<style>\n #bilibili-helper-host.hide{\n width:auto!important;\n left:auto!important;\n background:transparent!important;\n border:0 none!important;\n border-radius: 6px 0 0 0;\n box-shadow: rgba(0, 0, 0, 0.2) -5px -5px 10px!important;\n }\n .player-fullscreen-fix #bilibili-helper-host {\n z-index: 99999!important;\n }\n </style>', document.body.appendChild( | |
o), (s = o.attachShadow( | |
{ mode: 'open' })).innerHTML = `\n <style>\n p, a, div, span, li, i, b, strong, input, button, label {\n font-size: inherit;\n }\n li {\n margin-bottom: 5px;\n }\n p {\n margin: 0;\n line-height: 1.5;\n }\n h1 {\n font-size: 20px;\n font-weight: bold;\n margin-bottom: 20px;\n }\n h3 {\n font-size: 16px;\n margin: 1em 0;\n }\n #title {\n font-size: 16px;\n font-weight: normal;\n }\n #content {\n display: flex;\n width: 100%;\n font-size: 14px;\n position: relative;\n }\n a {\n color: #00a1d6 !important;\n text-decoration: none;\n }\n a:hover {\n text-decoration: underline;\n }\n a.disabled {\n color: #666!important;\n }\n a.disabled:hover {\n text-decoration: none;\n cursor: not-allowed;\n }\n #side-bar {\n flex: 3;\n padding: 20px;\n border-right: 1px solid #ccc;\n margin-right: -1px;\n }\n #main {\n flex: 7;\n padding: 20px;\n border-left: 1px solid #ccc;\n }\n #notice-frame {\n width: 100%;\n padding: 0;\n }\n .donate {\n border-top: 1px solid #ccc;\n padding-top: 10px;\n }\n #zanshang {\n width: 80%;\n }\n .setting-item {\n margin-bottom: 8px;\n }\n .setting-item .label {\n font-weight: bold;\n width: 6em;\n display: inline-block;\n text-align: right;\n }\n .desc {\n padding-left: 6em;\n }\n #actions {\n position: absolute;\n right: 0;\n top: 0;\n }\n .btn-large {\n border: 0 none;\n background: #f45a8d;\n border-radius: 6px;\n color: #fff;\n padding: 10px 20px;\n }\n #toggle {\n border-radius: 0 0 0 6px;\n outline: none;\n cursor: pointer;\n }\n .hide #side-bar {\n display: none;\n }\n .hide #main {\n display: none;\n }\n .hide #toggle {\n border-radius: 6px 0 0 0;\n }\n .hide #actions {\n position: static;\n }\n \n a.btn {\n border: 0 none;\n background: #f45a8d;\n text-decoration: none !important;\n color: #fff !important;\n border-radius: 3px;\n padding: 5px 10px;\n display: inline-block;\n }\n .settings {\n border-left: 5px solid #ccc;\n background: #eee;\n padding: 16px 16px 8px 0;\n }\n .size {\n margin: 0 5px;\n }\n </style>\n <div id="content" ${h() | |
? 'class="hide"' | |
: ''}>\n <div id="side-bar">\n <div class="notice">\n <iframe id="notice-frame" frameborder="0"></iframe>\n </div>\n \x3c!--<div class="support">TODO 支持区域</div>--\x3e\n <div class="donate">\n <p>微信扫一扫赞赏作者(扫不出来请点击图片后扫大图):</p>\n <a href="${internalUrls.zanshang}" target="_blank"><img title="点击查看大图" alt="点击查看大图" id="zanshang" src="${internalUrls.zanshang}"/></a>\n </div>\n </div>\n <div id="main">\n <h1 style="margin-top: 0;">B站下载助手</h1>\n <div class="settings">\n <div class="setting-item">\n <span class="label">清晰度:</span>\n <span>请在页面中B站自己的播放器内切换清晰度</span>\n </div>\n <div class="setting-item">\n <span class="label">下载模式:</span>\n <label><input id="setting-download-mode-advanced" checked name="setting-download-mode" type="radio"/> 高级</label>\n <label><input id="setting-download-mode-normal" name="setting-download-mode" type="radio"/> 兼容</label>\n <p class="desc">高级模式支持自动重命名和合并下载,但会占用非常大的系统运行内存<br/>兼容模式直接使用浏览器的默认下载,资源占用很小,但不支持自动重命名和合并下载</p>\n <p class="desc">建议系统运行内存小于16G的用户使用兼容模式,下载后可以点<a href="http://csser.top/bilibili/merge.html" target="_blank">这里</a>尝试手动合并</p>\n </div>\n <div class="setting-item" id="setting-advanced">\n <span class="label">合并下载:</span>\n <label><input id="setting-merge-on" checked name="setting-merge" type="radio"> 开</label>\n <label><input id="setting-merge-off" name="setting-merge" type="radio"> 关</label>\n <p class="desc">高级模式下载过程中请<strong style="color: red;">不要</strong>刷新或关闭页面,也<strong style="color: red;">不要</strong>切换分集和清晰度</p>\n </div>\n </div>\n <h3 id="title">${a | |
? '加载中' + r | |
: u(t, n, e, i)}</h3>\n <ul id="durls">\n ${a ? '' : f(n, t, | |
e)}\n </ul>\n <div class="beg">\n <p>\n 如果这个工具确实帮到了您,烦请在Chrome商店给个五星好评,谢谢😊\n <a class="btn" href="https://chrome.google.com/webstore/detail/bfcbfobhcjbkilcbehlnlchiinokiijp/reviews" target="_blank">去评价</a>\n </p>\n </div>\n </div>\n <div id="actions">\n <button id="toggle" class="btn-large">${h() | |
? '打开B站下载助手' | |
: '收起'}</button>\n </div>\n </div>\n `, (e => { | |
const t = e.getElementById('setting-download-mode-advanced'), | |
n = e.getElementById('setting-download-mode-normal'), i = e.getElementById('setting-merge-on'), | |
a = e.getElementById('setting-merge-off'), o = e.getElementById('setting-advanced'), | |
s = e.getElementById('durls'), r = e.getElementById('toggle'), l = e.getElementById('actions'), | |
d = e.getElementById('content'), c = document.getElementById('bilibili-helper-host'), | |
m = () => {t.disabled = !0, n.disabled = !0, i.disabled = !0, a.disabled = !0}, | |
u = () => {t.disabled = !1, n.disabled = !1, i.disabled = !1, a.disabled = !1} | |
g() | |
? (t.checked = !0, n.checked = !1, o.style.display = 'block') | |
: (t.checked = !1, n.checked = !0, o.style.display = 'none'), p() | |
? (i.checked = !0, a.checked = !1) | |
: (i.checked = !1, a.checked = !0) | |
const f = () => {e.buildDownloadLinks()} | |
t.addEventListener('change', () => { | |
t.checked | |
? (localStorage.bilibili_helper_download_mode = 'advanced', o.style.display = 'block') | |
: (localStorage.bilibili_helper_download_mode = 'normal', o.style.display = 'none'), f() | |
}), n.addEventListener('change', () => { | |
n.checked | |
? (localStorage.bilibili_helper_download_mode = 'normal', o.style.display = 'none') | |
: (localStorage.bilibili_helper_download_mode = 'advanced', o.style.display = 'block'), f() | |
}), i.addEventListener('change', | |
() => {localStorage.bilibili_helper_merge_mode = i.checked ? 'on' : 'off', f()}), a.addEventListener('change', | |
() => {localStorage.bilibili_helper_merge_mode = a.checked ? 'off' : 'on', f()}), s.addEventListener('click', | |
t => { | |
const n = t.target | |
if ('a' === n.tagName.toLowerCase() && 'advanced' === n.getAttribute('mode')) { | |
if (t.preventDefault(), t.stopPropagation(), n.classList.contains('disabled')) return | |
let i = null | |
const a = n.getAttribute('title') | |
'on' === n.getAttribute('merge') ? (i = e.querySelector(`ul[durls="${n.getAttribute('durls')}"]`), m(), x( | |
n, JSON.parse(decodeURIComponent(n.getAttribute('durls'))), a, i).then(u)) : (i = e.querySelector( | |
`span[durl="${n.getAttribute('durl')}"]`), m(), v(n, | |
JSON.parse(decodeURIComponent(n.getAttribute('durl'))), a, i).then(u)) | |
} | |
}), r.addEventListener('click', () => { | |
h() | |
? (localStorage.bilibili_helper_show = 'show', d.classList.remove( | |
'hide'), r.innerHTML = '收起', c.classList.remove('hide'), l.style.top = '0', e.getElementById('notice-frame') | |
.contentWindow | |
.postMessage({ action: 'getHeight' }, 'https://csser.top')) | |
: (localStorage.bilibili_helper_show = 'hide', d.classList.add('hide'), c.classList.add( | |
'hide'), r.innerHTML = '打开B站下载助手', l.style.top = '0') | |
}), c.addEventListener('scroll', () => {l.style.top = c.scrollTop + 'px'}) | |
})(s), (e => { | |
const t = e.getElementById('notice-frame') | |
t.onload = (() => { | |
t.contentWindow.postMessage({ action: 'getHeight' }, 'https://csser.top'), t.contentWindow.postMessage({ | |
action: 'setVersion', | |
version: { name: manifest.version, code: parseInt(manifest.version.replace(/\./g, ''), 10) } | |
}, 'https://csser.top'), t.contentWindow.postMessage({ action: 'setTheme', theme: 'null' }, | |
'https://csser.top') | |
}), window.addEventListener('message', e => { | |
if ('https://csser.top' === e.origin && e.data && 'reportHeight' === e.data.action && | |
(t.style.height = e.data.height + 10 + 'px'), 'https://csser.top' === e.origin && e.data && | |
'showBilibilihelperindooorsmanNoticeDialog' === e.data.action) { | |
const t = e.data.notices | |
t && t.length > 0 && t.forEach(e => {}) | |
} | |
}), t.src = `https://csser.top/bilibili/notice.html?t=${Date.now()}`, window.addEventListener('resize', | |
() => {t.contentWindow.postMessage({ action: 'getHeight' }, 'https://csser.top')}) | |
})(s)), s.buildDownloadLinks = (() => {s.getElementById('durls').innerHTML = f(n, t, e)}) | |
}, y = (e, t) => { | |
const n = new Blob([e], { type: 'application/octet-stream' }), i = document.createElement('a') | |
i.setAttribute('href', URL.createObjectURL(n)), i.setAttribute('download', t), i.setAttribute('style', | |
'position:absolute;top:-9999px;'), document.body.appendChild(i) | |
const a = new MouseEvent('click', { bubbles: !0, cancelable: !0, view: window }) | |
i.dispatchEvent(a), setTimeout(() => {document.body.removeChild(i)}, 1e3) | |
}, w = (e, t, n) => { | |
let i = null | |
return fetch(e).then(e => { | |
const a = e.headers.get('content-length'), o = t || parseInt(a, 10) | |
let s = 0 | |
return i = setInterval(() => {n(s, o)}, 1e3), new Response(new ReadableStream({ | |
start (t) { | |
const n = e.body.getReader(), i = () => { | |
n.read() | |
.then(({ done: e, value: n }) => {e ? t.close() : (s += n.byteLength, t.enqueue(n), i())}) | |
.catch(e => {t.error(e)}) | |
} | |
i() | |
} | |
})) | |
}).then(e => e.blob()).finally(() => {i && clearInterval(i)}) | |
}, v = (e, { url: t, size: n }, i, a) => (e.classList.add('disabled'), w(t, n, (e, t) => { | |
const n = Math.ceil(e / t * 100) | |
a.innerHTML = ` 正在下载 - ${e}/${t} - ${n}%` | |
}).then(e => { | |
a.innerHTML = ' 已下载完成' | |
const n = new URL(t).pathname.toLowerCase().match(/\.[a-z0-9]+?$/)[0] | |
y(e, i + n) | |
}).finally(() => {e.classList.remove('disabled')})), x = (e, t, n, i) => { | |
if (1 === t.length) return v(e, t[0], n, i) | |
e.classList.add('disabled') | |
const a = t.map(({ url: e, size: t }, n) => { | |
const a = document.createElement('li') | |
return a.innerHTML = `分段${n + 1} (${m(t)}) 正在下载`, i.appendChild(a), w(e, t, (e, i) => { | |
const o = Math.ceil(e / i * 100) | |
a.innerHTML = `分段${n + 1} (${m(t)}) 正在下载 - ${e}/${i} - ${o}%` | |
}).then(e => (a.innerHTML = `分段${n + 1} (${m(t)}) 已下载完成,等待合并`, e)) | |
}) | |
return Promise.all(a).then(async e => { | |
const t = await o.mergeBlobs(Array.from(e)) | |
y(t, n + '.flv'), i.innerHTML = '已完成' | |
}).finally(() => {e.classList.remove('disabled')}) | |
}, _ = async () => { | |
if (!e()) return | |
b({ loading: !0 }) | |
const i = await(() => fetch(window.location.href, r) | |
.then(e => e.text()) | |
.then(e => { | |
const t = e.match(/<script>window.__INITIAL_STATE__=(.+?)<\/script>/) | |
return t && t[1] ? JSON.parse(t[1].replace( | |
';(function(){var s;(s=document.currentScript||document.scripts[document.scripts.length-1]).parentNode.removeChild(s);}());', | |
'')) : { code: -2, message: '获取视频信息失败,可以尝试清除浏览器cookies和缓存后重试,如多次重试仍然报错,请通过邮箱或QQ群反馈给我,谢谢' } | |
}) | |
.catch(() => l()))() | |
if (i.code) return b(i) | |
let a = localStorage.bilibili_player_settings && | |
+JSON.parse(localStorage.bilibili_player_settings).setting_config.defquality || 112 | |
if (t()) { | |
const e = i.videoData.aid | |
let t, n, o = i.videoData.cid | |
if (i.videoData.pages.length > 1) { | |
const e = location.search.match(/p=(\d+)/) | |
let a = i.videoData.pages[0] | |
e && e[1] && (a = i.videoData.pages.find(t => '' + t.page == '' + e[1])), t = a.page, n = a.part, o = a.cid | |
} | |
const { code: s, durls: c, qualityDescription: g, message: p } = await((e, t, n = 112) => { | |
return fetch(`//api.bilibili.com/x/player/playurl?cid=${t}&avid=${e}&otype=json&qn=${n}`, r) | |
.then(e => e.json()) | |
.then(e => 0 !== e.code ? d(e) : d(e.data)) | |
.catch(() => l()) | |
})(e, o, a) | |
if (0 === s) { | |
let e = `[${g}] ${i.videoData.title}` | |
t && n && (e = `[${g}] ${i.videoData.title}_P${t}_${n}`), b({ code: s, title: e, durls: c, message: p }) | |
} else b({ code: s, message: p }) | |
} | |
if (n()) { | |
const e = i.epList | |
let t = -1 === i.epId ? e[e.length - 1].ep_id : i.epId, n = e.find(e => t === e.ep_id) | |
const o = await s('.episode-item.on'), c = await s('.ep-item.cursor') | |
if (o || c) { | |
const i = o || c, a = i.parentElement | |
let r = Array.from(a.querySelectorAll('li')).findIndex(e => e === i) | |
const l = await s('#eplist_module .ep-list-progress') | |
l && (r = +l.textContent.match(/(\d+)\/\d+/)[1] - 1), n = e[r], t = n.ep_id || n.id | |
} | |
const { code: g, durls: p, qualityDescription: h, message: m } = await((e, t = 112) => { | |
return fetch(`//api.bilibili.com/pgc/player/web/playurl/?ep_id=${e}&qn=${t}&bsource=`, r) | |
.then(e => e.json()) | |
.then(e => 0 !== e.code ? d(e) : d(e.result)) | |
.catch(() => l()) | |
})(t, a) | |
if (0 === g) { | |
const e = `[${h}] ${i.mediaInfo.title}_${n.index || n.title}_${n.index_title || n.longTitle}` | |
b({ code: g, title: e, durls: p, message: m }) | |
} else b({ code: g, message: m }) | |
} | |
} | |
_() | |
let $ = '' + window.location.href, L = '' + localStorage.bilibili_player_settings | |
setInterval(() => { | |
const e = window.location.href, t = localStorage.bilibili_player_settings | |
if ($ !== e && ($ = e, _()), L !== t) try { | |
if (JSON.parse(t).setting_config.defquality === JSON.parse(L).setting_config.defquality) return | |
L = t, _() | |
} catch (e) {} | |
}, 1e3) | |
})()</script> | |
<style> | |
.lang_radio { | |
display: none; | |
} | |
.lang_radio_img { | |
vertical-align: unset !important; | |
width: 13px !important; | |
height: 13px !important; | |
margin-top: 0px !important; | |
cursor: pointer; | |
margin-right: 3px !important; | |
margin-top: 4px !important; | |
display: inline; | |
min-height: unset !important; | |
min-width: unset !important; | |
} | |
</style> | |
</head> | |
<body class="sideNavVisible separateOnPageNav" data-gr-c-s-loaded="true"> | |
<div class="fixedHeaderContainer"> | |
<div class="headerWrapper wrapper"> | |
<header> | |
<a href="https://taro.aotu.io/"> | |
<img class="logo" src="https://nervjs.github.io/taro/img/logo-taro.png" | |
alt="Taro"> | |
<h2 class="headerTitleWithLogo">Taro</h2> | |
</a> | |
<div class="navigationWrapper navigationSlider" style="width: 100%;margin-left: 30px"> | |
<nav class="slidingNav" style="float: left"> | |
<ul class="nav-site nav-site-internal"> | |
<li class="siteNavGroupActive siteNavItemActive"><a href="/taro/docs/README.html" target="_self">文档</a></li> | |
<li class=""><a href="/taro/docs/components-desc.html" target="_self">组件库</a></li> | |
<li class=""><a href="/taro/docs/apis/about/desc.html" target="_self">API</a></li> | |
<li class="navSearchWrapper reactNavSearchWrapper"> | |
<span class="algolia-autocomplete" | |
style="position: relative; display: inline-block; direction: ltr;"><input | |
type="text" id="search_input_react" placeholder="Search" title="Search" class="aa-input" | |
autocomplete="off" spellcheck="false" role="combobox" aria-autocomplete="list" aria-expanded="false" | |
aria-labelledby="search_input_react" aria-owns="algolia-autocomplete-listbox-0" dir="auto" | |
style="position: relative; vertical-align: top;"> | |
<pre aria-hidden="true" | |
style="position: absolute; visibility: hidden; white-space: pre; font-family: system-ui; font-size: 14px; font-style: normal; font-variant: normal; font-weight: 300; word-spacing: 0px; letter-spacing: normal; text-indent: 0px; text-rendering: auto; text-transform: none;"></pre><span | |
class="aa-dropdown-menu" role="listbox" id="algolia-autocomplete-listbox-0" | |
style="position: absolute; top: 100%; z-index: 100; display: none; left: 0px; right: auto;"> | |
<div class="aa-dataset-1"></div></span> | |
</span> | |
</li> | |
</ul> | |
</nav> | |
<nav class="slidingNav" style="float: right;"> | |
<ul class="nav-site nav-site-internal"> | |
<li class=""><a href="https://taro-ui.jd.com" target="_self">Taro-UI</a></li> | |
<li class=""><a href="https://taro-ext.jd.com" target="_self">物料市场</a></li> | |
<li class=""><a href="https://taro-club.jd.com" target="_self">论坛</a></li> | |
<li class=""><a href="https://github.com/NervJS/taro" target="_self">GitHub</a></li> | |
</ul> | |
</nav> | |
</div> | |
</header> | |
</div> | |
</div> | |
<div class="navPusher"> | |
<div class="docMainWrapper wrapper"> | |
<div class="docsNavContainer" id="docsNav"> | |
<nav class="toc"> | |
<div class="toggleNav"> | |
<section class="navWrapper wrapper"> | |
<div class="navBreadcrumb wrapper"> | |
<div class="navToggle" id="navToggler"> | |
<div class="hamburger-menu"> | |
<div class="line1"></div> | |
<div class="line2"></div> | |
<div class="line3"></div> | |
</div> | |
</div> | |
<h2><i>›</i><span>关于Taro</span></h2> | |
<div class="tocToggler" id="tocToggler"><i class="icon-toc"></i></div> | |
</div> | |
<div class="navGroups"> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible">关于Taro | |
<span class="arrow rotate"> | |
<svg width="24" height="24" viewBox="0 0 24 24"><path fill="#565656" | |
d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path | |
d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class=""> | |
<li class="navListItem navListItemActive"><a class="navItem" href="/taro/docs/README.html">Taro | |
是什么</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">为什么选择 Taro</a></li> | |
<!--<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">Taro 架构/原理?</a></li>--> | |
<!--<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">多端支持?</a></li>--> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">小程序转 Taro</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">Taro 团队</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/team.html">Contributing</a></li> | |
</ul> | |
</div> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible">快速开始<span class="arrow"><svg width="24" height="24" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/GETTING-STARTED.html">安装</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/GETTING-STARTED.html">Hello World</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/composition.html">更多 Demo</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/before-dev-remind.html">学习资源</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/specials.html">常见问题</a></li> | |
</ul> | |
</div> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible">入门基础<span class="arrow"><svg width="24" height="24" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/static-reference.html">CLI 命令</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/tutorial.html">项目结构</a></li> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible" style="font-size: 14px">语法特性<span class="arrow"><svg | |
width="14" height="14" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/jsx.html">JSX 简介</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/props.html">组件化 & Props</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/state.html">生命周期 & State</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">事件处理</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/condition.html">条件渲染</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/list.html">列表渲染</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/functional-component.html">函数式组件</a> | |
</li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/context.html">Context</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/hooks.html">Hooks</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/children.html">Children 与组合</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/render-props.html">Render Props</a> | |
</li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/ref.html">Refs 引用</a></li> | |
</ul> | |
</div> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/router.html">页面及样式和布局</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/size.html">生命周期</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/static-reference.html">路由</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">跨平台开发</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/static-reference.html">打包发布</a></li> | |
<li class="navListItem"> | |
<a class="navItem" href="/taro/docs/component-style.html">常用项目配置</a> | |
</li> | |
</ul> | |
</div> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible">进阶指南<span class="arrow"><svg width="24" height="24" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/jsx.html">自定义组件</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/props.html">Context & Hooks</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/state.html">多端 UI 库开发</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">性能优化实践</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">Taro 代码与小程序代码混写</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">使用小程序原生第三方组件和插件</a></li> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible" style="font-size: 14px">多端开发<span class="arrow"><svg | |
width="14" height="14" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">原生作用域获取</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">小程序云开发模版</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">小程序插件开发</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">React Native 端开发流程</a> | |
</li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/event.html">快应用端开发流程</a></li> | |
</ul> | |
</div> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/static-reference.html">风格指南</a></li> | |
</ul> | |
</div> | |
<div class="navGroup"> | |
<h3 class="navGroupCategoryTitle collapsible">社区生态<span class="arrow"><svg width="24" height="24" | |
viewBox="0 0 24 24"><path | |
fill="#565656" d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path><path d="M0 0h24v24H0z" | |
fill="none"></path></svg></span> | |
</h3> | |
<ul class="hide"> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/config.html">使用Redux</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/config-detail.html">使用Mobx</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/async-await.html">使用CSS Modules</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/redux.html">项目模版</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/mobx.html">Taro UI</a></li> | |
<li class="navListItem"><a class="navItem" href="/taro/docs/mobx.html">F&Q</a></li> | |
</ul> | |
</div> | |
</div> | |
</section> | |
</div> | |
<script> | |
var coll = document.getElementsByClassName('collapsible') | |
var checkActiveCategory = true | |
for (var i = 0; i < coll.length; i++) { | |
var links = coll[i].nextElementSibling.getElementsByTagName('*') | |
if (checkActiveCategory) { | |
for (var j = 0; j < links.length; j++) { | |
if (links[j].classList.contains('navListItemActive')) { | |
coll[i].nextElementSibling.classList.toggle('hide') | |
coll[i].childNodes[1].classList.toggle('rotate') | |
checkActiveCategory = false | |
break | |
} | |
} | |
} | |
coll[i].addEventListener('click', function() { | |
var arrow = this.childNodes[1] | |
arrow.classList.toggle('rotate') | |
var content = this.nextElementSibling | |
content.classList.toggle('hide') | |
}) | |
} | |
document.addEventListener('DOMContentLoaded', function() { | |
createToggler('#navToggler', '#docsNav', 'docsSliderActive') | |
createToggler('#tocToggler', 'body', 'tocActive') | |
var headings = document.querySelector('.toc-headings') | |
headings && headings.addEventListener('click', function(event) { | |
var el = event.target | |
while (el !== headings) { | |
if (el.tagName === 'A') { | |
document.body.classList.remove('tocActive') | |
break | |
} else { | |
el = el.parentNode | |
} | |
} | |
}, false) | |
function createToggler (togglerSelector, targetSelector, className) { | |
var toggler = document.querySelector(togglerSelector) | |
var target = document.querySelector(targetSelector) | |
if (!toggler) { | |
return | |
} | |
toggler.onclick = function(event) { | |
event.preventDefault() | |
target.classList.toggle(className) | |
} | |
} | |
}) | |
</script> | |
</nav> | |
</div> | |
<div class="container mainContainer"> | |
<div class="wrapper"> | |
<div class="post"> | |
<header class="postHeader"><a class="edit-page-link button" | |
href="https://github.com/nervjs/taro/edit/master/docs/README.md" target="_blank" | |
rel="noreferrer noopener">Edit</a> | |
<h1 class="postHeaderTitle">Taro 介绍</h1></header> | |
<article> | |
<div><span><h2><a class="anchor" aria-hidden="true" id="简介"></a><a href="#简介" aria-hidden="true" | |
class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>简介</h2> | |
<p><strong>Taro</strong> 是一套遵循 <a href="https://reactjs.org/">React</a> 语法规范的 <strong>多端开发</strong> 解决方案。现如今市面上端的形态多种多样,Web、React-Native、微信小程序等各种端大行其道,当业务要求同时在不同的端都要求有所表现的时候,针对不同的端去编写多套代码的成本显然非常高,这时候只编写一套代码就能够适配到多端的能力就显得极为需要。</p> | |
<p>使用 <strong>Taro</strong>,我们可以只书写一套代码,再通过 <strong>Taro</strong> 的编译工具,将源代码分别编译出可以在不同端(微信/百度/支付宝/字节跳动/QQ小程序、快应用、H5、React-Native 等)运行的代码。</p> | |
<h2><a class="anchor" aria-hidden="true" id="特性"></a><a href="#特性" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>特性</h2> | |
<h4><a class="anchor" aria-hidden="true" id="react-语法风格"></a><a href="#react-语法风格" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>React 语法风格</h4> | |
<p><strong>Taro</strong> 遵循 <a href="https://reactjs.org/">React</a> 语法规范,它采用与 React 一致的组件化思想,组件生命周期与 React 保持一致,同时支持使用 JSX 语法,让代码具有更丰富的表现力,使用 <strong>Taro</strong> 进行开发可以获得和 React 一致的开发体验。</p> | |
<p>代码示例</p> | |
<pre><code class="hljs css language-jsx"><span class="token keyword">import</span> Taro<span | |
class="token punctuation">,</span> <span class="token punctuation">{</span> Component <span class="token punctuation">}</span> <span | |
class="token keyword">from</span> <span class="token string">'@tarojs/taro'</span> | |
<span class="token keyword">import</span> <span class="token punctuation">{</span> View<span | |
class="token punctuation">,</span> Button <span class="token punctuation">}</span> <span | |
class="token keyword">from</span> <span class="token string">'@tarojs/components'</span> | |
<span class="token keyword">export</span> <span class="token keyword">default</span> <span | |
class="token keyword">class</span> <span class="token class-name">Index</span> <span | |
class="token keyword">extends</span> <span class="token class-name">Component</span> <span | |
class="token punctuation">{</span> | |
<span class="token function">constructor</span> <span class="token punctuation">(</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span> | |
<span class="token keyword">super</span><span class="token punctuation">(</span><span | |
class="token operator">...</span>arguments<span class="token punctuation">)</span> | |
<span class="token keyword">this</span><span class="token punctuation">.</span>state <span | |
class="token operator">=</span> <span class="token punctuation">{</span> | |
title<span class="token punctuation">:</span> <span class="token string">'首页'</span><span | |
class="token punctuation">,</span> | |
list<span class="token punctuation">:</span> <span class="token punctuation">[</span><span | |
class="token number">1</span><span class="token punctuation">,</span> <span class="token number">2</span><span | |
class="token punctuation">,</span> <span class="token number">3</span><span class="token punctuation">]</span> | |
<span class="token punctuation">}</span> | |
<span class="token punctuation">}</span> | |
<span class="token function">componentWillMount</span> <span class="token punctuation">(</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> | |
<span class="token function">componentDidMount</span> <span class="token punctuation">(</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> | |
<span class="token function">componentWillUpdate</span> <span class="token punctuation">(</span><span | |
class="token parameter">nextProps<span class="token punctuation">,</span> nextState</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> | |
<span class="token function">componentDidUpdate</span> <span class="token punctuation">(</span><span | |
class="token parameter">prevProps<span class="token punctuation">,</span> prevState</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span> | |
<span class="token function">shouldComponentUpdate</span> <span class="token punctuation">(</span><span | |
class="token parameter">nextProps<span class="token punctuation">,</span> nextState</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span> | |
<span class="token keyword">return</span> <span class="token boolean">true</span> | |
<span class="token punctuation">}</span> | |
<span class="token function-variable function">add</span> <span class="token operator">=</span> <span | |
class="token punctuation">(</span><span class="token parameter">e</span><span | |
class="token punctuation">)</span> <span class="token operator">=></span> <span | |
class="token punctuation">{</span> | |
<span class="token comment">// dosth</span> | |
<span class="token punctuation">}</span> | |
<span class="token function">render</span> <span class="token punctuation">(</span><span | |
class="token punctuation">)</span> <span class="token punctuation">{</span> | |
<span class="token keyword">return</span> <span class="token punctuation">(</span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"><</span><span | |
class="token class-name">View</span></span> <span class="token attr-name">className</span><span | |
class="token attr-value"><span class="token punctuation">=</span><span | |
class="token punctuation">'</span>index<span class="token punctuation">'</span></span><span | |
class="token punctuation">></span></span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"><</span><span | |
class="token class-name">View</span></span> <span class="token attr-name">className</span><span | |
class="token attr-value"><span class="token punctuation">=</span><span class="token punctuation">'</span>title<span | |
class="token punctuation">'</span></span><span class="token punctuation">></span></span><span | |
class="token punctuation">{</span><span class="token keyword">this</span><span class="token punctuation">.</span>state<span | |
class="token punctuation">.</span>title<span class="token punctuation">}</span><span class="token tag"><span | |
class="token tag"><span class="token punctuation"></</span><span class="token class-name">View</span></span><span | |
class="token punctuation">></span></span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"><</span><span | |
class="token class-name">View</span></span> <span class="token attr-name">className</span><span | |
class="token attr-value"><span class="token punctuation">=</span><span class="token punctuation">'</span>content<span | |
class="token punctuation">'</span></span><span class="token punctuation">></span></span> | |
<span class="token punctuation">{</span><span class="token keyword">this</span><span | |
class="token punctuation">.</span>state<span class="token punctuation">.</span>list<span | |
class="token punctuation">.</span><span class="token function">map</span><span | |
class="token punctuation">(</span><span class="token parameter">item</span> <span | |
class="token operator">=></span> <span class="token punctuation">{</span> | |
<span class="token keyword">return</span> <span class="token punctuation">(</span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"><</span><span | |
class="token class-name">View</span></span> <span class="token attr-name">className</span><span | |
class="token attr-value"><span class="token punctuation">=</span><span | |
class="token punctuation">'</span>item<span class="token punctuation">'</span></span><span | |
class="token punctuation">></span></span><span class="token punctuation">{</span>item<span | |
class="token punctuation">}</span><span class="token tag"><span class="token tag"><span class="token punctuation"></</span><span | |
class="token class-name">View</span></span><span class="token punctuation">></span></span> | |
<span class="token punctuation">)</span> | |
<span class="token punctuation">}</span><span class="token punctuation">)</span><span | |
class="token punctuation">}</span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"><</span><span | |
class="token class-name">Button</span></span> <span class="token attr-name">className</span><span | |
class="token attr-value"><span class="token punctuation">=</span><span class="token punctuation">'</span>add<span | |
class="token punctuation">'</span></span> <span class="token attr-name">onClick</span><span | |
class="token script language-javascript"><span class="token script-punctuation punctuation">=</span><span | |
class="token punctuation">{</span><span class="token keyword">this</span><span | |
class="token punctuation">.</span>add<span class="token punctuation">}</span></span><span | |
class="token punctuation">></span></span>添加<span class="token tag"><span class="token tag"><span | |
class="token punctuation"></</span><span class="token class-name">Button</span></span><span | |
class="token punctuation">></span></span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"></</span><span | |
class="token class-name">View</span></span><span class="token punctuation">></span></span> | |
<span class="token tag"><span class="token tag"><span class="token punctuation"></</span><span | |
class="token class-name">View</span></span><span class="token punctuation">></span></span> | |
<span class="token punctuation">)</span> | |
<span class="token punctuation">}</span> | |
<span class="token punctuation">}</span> | |
</code></pre> | |
<h4><a class="anchor" aria-hidden="true" id="快速开发微信小程序"></a><a href="#快速开发微信小程序" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>快速开发微信小程序</h4> | |
<p>Taro 立足于微信小程序开发,众所周知小程序的开发体验并不是非常友好,比如小程序中无法使用 npm 来进行第三方库的管理,无法使用一些比较新的 ES 规范等等,针对小程序端的开发弊端,Taro 具有以下的优秀特性</p> | |
<p>✅ 支持使用 npm/yarn 安装管理第三方依赖</p> | |
<p>✅ 支持使用 ES7/ES8 甚至更新的 ES 规范,一切都可自行配置</p> | |
<p>✅ 支持使用 CSS 预编译器,例如 Sass 等</p> | |
<p>✅ 支持使用 Redux 进行状态管理</p> | |
<p>✅ 支持使用 MobX 进行状态管理</p> | |
<p>✅ 小程序 API 优化,异步 API Promise 化等等</p> | |
<h4><a class="anchor" aria-hidden="true" id="支持多端开发转化"></a><a href="#支持多端开发转化" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>支持多端开发转化</h4> | |
<p>Taro 方案的初心就是为了打造一个多端开发的解决方案。目前 Taro 代码可以支持转换到 <strong>微信/百度/支付宝/字节跳动/QQ小程序</strong> 、<strong>快应用</strong>、 <strong>H5 端</strong> 以及 <strong>移动端(React Native)</strong>。</p> | |
<div align="center"><img src="https://storage.360buyimg.com/taro-resource/platforms.jpg"></div> | |
<h2><a class="anchor" aria-hidden="true" id="社区共享"></a><a href="#社区共享" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>社区共享</h2> | |
<p><a href="https://taro-club.jd.com/">Taro 交流社区——让每一次交流都被沉淀</a> 如果您在此文档没有找到想要的答案,请移步<a href="https://taro-club.jd.com">社区</a>提问,我们会在看到的第一时间给予答复。</p> | |
<p><a href="https://taro-ext.jd.com/">Taro 物料市场——让每一个轮子产生价值</a> 如果您想找一些现成的物料,例如:模版、组件、SDK、UI,可以移步<a | |
href="https://taro-ext.jd.com/">物料市场</a>查找,也欢迎您发布物料与其他开发者共享。</p> | |
<h2><a class="anchor" aria-hidden="true" id="taro-ui"></a><a href="#taro-ui" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>Taro UI</h2> | |
<p>一款基于 <code>Taro</code> 框架开发的多端 UI 组件库</p> | |
<h4><a class="anchor" aria-hidden="true" id="taro-ui-特性"></a><a href="#taro-ui-特性" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>Taro UI 特性</h4> | |
<ul> | |
<li>基于 <code>Taro</code> 开发 UI 组件</li> | |
<li>一套组件可以在 <code>微信小程序</code>,<code>支付宝小程序</code>,<code>百度小程序</code>,<code>H5</code> 多端适配运行(<code>ReactNative</code> 端暂不支持)</li> | |
<li>提供友好的 API,可灵活的使用组件</li> | |
</ul> | |
<p><a href="https://taro-ui.jd.com">Taro UI 官网</a></p> | |
<h2><a class="anchor" aria-hidden="true" id="学习资源"></a><a href="#学习资源" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>学习资源</h2> | |
<p><a href="https://github.com/NervJS/awesome-taro">awesome-taro</a></p> | |
<p>掘金小册:<a href="https://juejin.im/book/5b73a131f265da28065fb1cd?referrer=5ba228f16fb9a05d3251492d">Taro 多端开发实现原理与实战</a></p> | |
<h2><a class="anchor" aria-hidden="true" id="开发交流"></a><a href="#开发交流" aria-hidden="true" class="hash-link"><svg | |
class="hash-link-icon" aria-hidden="true" height="16" version="1.1" viewBox="0 0 16 16" width="16"><path | |
fill-rule="evenodd" | |
d="M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z"></path></svg></a>开发交流</h2> | |
<p><img | |
src="https://camo.githubusercontent.com/519861ac48c204c6038cea71ea10e1d991f36163/68747470733a2f2f696d6733302e333630627579696d672e636f6d2f6c696e672f6a66732f74312f38313133312f31332f3730302f33353431312f35636566343339664538616366366163342f323331393531336663303734303465362e706e67" | |
alt="image"></p> | |
</span></div> | |
</article> | |
</div> | |
<div class="docs-prevnext"><a class="docs-next button" href="/taro/docs/team.html"><span>Taro 团队</span><span | |
class="arrow-next"> →</span></a></div> | |
</div> | |
</div> | |
<nav class="onPageNav"> | |
<ul class="toc-headings"> | |
<li><a href="#简介" class="active">简介</a></li> | |
<li><a href="#特性">特性</a></li> | |
<li><a href="#社区共享">社区共享</a></li> | |
<li><a href="#taro-ui">Taro UI</a></li> | |
<li><a href="#学习资源">学习资源</a></li> | |
<li><a href="#开发交流">开发交流</a></li> | |
</ul> | |
</nav> | |
</div> | |
<footer class="footer" id="footer"> | |
<div class="grid_c1 footer_cont"> | |
<div class="footer_logo_container"> | |
<div class="footer_logo"></div> | |
<span class="footer_designedby"></span></div> | |
<div class="footer_link_container"> | |
<div class="footer_link"><h3 class="footer_link_tit footer_link_tit1">相关资源</h3> | |
<p><a class="link" href="https://taro.jd.com/" target="_blank">Taro</a></p> | |
<p><a class="link" href="https://taro-ui.jd.com/" target="_blank">Taro UI</a></p> | |
<p><a class="link" href="https://at-ui.github.io/at-ui/#/zh" target="_blank">At-UI</a></p> | |
<p><a class="link" href="https://nerv.aotu.io/" target="_blank">Nerv</a></p> | |
<p><a class="link" href="https://athena.aotu.io/" target="_blank">Athena</a></p></div> | |
<div class="footer_link"><h3 class="footer_link_tit footer_link_tit2">社区</h3> | |
<p><a href="https://github.com/NervJS/taro/issues" target="_blank">GitHub</a></p> | |
<p><a href="https://taro-club.jd.com" target="_blank">Taro BBS</a></p> | |
<p class="footer_link_connect_wrap"><span class="footer_link_connect footer_link_wechat">微信<span | |
class="wechat_qrcode_icon"><svg t="1554966525626" class="icon svgicon" viewBox="0 0 1024 1024" version="1.1" | |
xmlns="http://www.w3.org/2000/svg" p-id="2588" | |
data-spm-anchor-id="a313x.7781069.0.i0"><path | |
d="M240.071 241.095h59.278v59.278h-59.278v-59.278z" fill="" p-id="2589"></path><path | |
d="M405.959 134.485h-272.611v272.611h106.723v47.445h59.278v-47.445h106.723v-59.278h47.445v-47.445h-47.445l-0.114-165.888zM346.795 347.819h-154.169v-154.055h154.055v154.055h0.114zM240.071 727.154h59.278v59.278h-59.278v-59.278zM726.016 241.095h59.278v59.278h-59.278v-59.278zM512.683 509.042v63.943h59.278v-59.165h47.445v-59.278h-47.445v-47.445h-59.278v101.945zM512.683 725.789v60.643h59.278v-106.723h47.445v-59.278h-106.723v105.358zM571.961 786.432h47.445v47.445h-47.445v-47.445zM453.405 833.877v59.165h118.557v-59.165h-118.557z" | |
fill="" p-id="2590"></path><path | |
d="M678.685 679.709h-59.278v106.723h106.61v-59.278h-47.331v-47.445zM726.016 893.042h166.002v-59.165h-106.723v-47.445h-59.278v106.61zM892.018 513.821v-59.278h-106.723v59.278h106.723zM832.739 727.154h59.278v59.278h-59.278v-59.278zM453.405 347.819h59.278v59.278h-59.278v-59.278zM726.016 454.542v-47.445h166.002v-272.611h-272.611v59.278h-106.723v47.445h106.723v59.165h-47.445v47.445h47.445v59.278h59.278v47.445h47.331zM678.685 193.763h154.055v154.055h-154.055v-154.055zM678.685 572.985h47.331v47.445h-47.331v-47.445zM785.294 679.709h-59.278v47.445h106.723v-106.723h59.278v-47.445h-106.723v106.723zM453.405 241.095h59.278v59.278h-59.278v-59.278zM299.349 513.821h47.445v59.165h-47.445v-59.165zM453.405 454.542h-106.61v59.278h59.165v59.165h47.445v-118.443z" | |
fill="" p-id="2591"></path><path | |
d="M405.959 786.432v-106.723h47.445v-59.278h-213.333v-106.61h-106.723v59.278h59.278v47.445h-59.278v272.611h272.611v-59.278h47.445v-47.445h-47.445zM346.795 833.877h-154.169v-154.169h154.055v154.169h0.114zM453.405 572.985h59.278v47.445h-59.278v-47.445zM619.406 513.821h59.278v59.165h-59.278v-59.165zM726.016 513.821h59.278v59.165h-59.278v-59.165z" | |
fill="" p-id="2592"></path></svg></span></span><span class="footer_link_wechat_img"><img | |
src="https://camo.githubusercontent.com/10834a234b99a5880b5dff7c0ca7235e2a0772e7/687474703a2f2f696d6732302e333630627579696d672e636f6d2f7562612f6a66732f7432303139372f3238332f313638373136383837342f3133363034322f32623464383131662f35623330613635634e39643166303366312e706e67"></span> | |
</p> | |
</div> | |
<div class="footer_link"><h3 class="footer_link_tit footer_link_tit3">关于我们</h3> | |
<p><a href="https://aotu.io/" target="_blank">凹凸实验室</a></p> | |
<p><a href="https://aotu.io/join/" target="_blank">加入我们</a></p> | |
<p><a href="mailto:[email protected]?subject=【Taro 合作】合作标题">联系我们</a></p></div> | |
<div class="footer_link"><h3 class="footer_link_tit footer_link_tit4">感谢</h3> | |
<p><a href="http://jdc.jd.com/" target="_blank">用户体验设计部</a></p> | |
<p><a href="https://github.com/nervjs/taro#%E8%B4%A1%E7%8C%AE%E8%80%85%E4%BB%AC" target="_blank">Taro 贡献者们</a> | |
</p></div> | |
</div> | |
</div> | |
<div class="copyright"> | |
<div class="in">Copyright © 2019. All Rights Reserved. 粤ICP备15077732号-2</div> | |
</div> | |
</footer> | |
</div> | |
<script type="text/javascript" src="https://cdn.jsdelivr.net/docsearch.js/1/docsearch.min.js"></script> | |
<script> | |
document.addEventListener('keyup', function(e) { | |
if (e.target !== document.body) { | |
return | |
} | |
// keyCode for '/' (slash) | |
if (e.keyCode === 191) { | |
const search = document.getElementById('search_input_react') | |
search && search.focus() | |
} | |
}) | |
</script> | |
<script> | |
var search = docsearch({ | |
apiKey: '57b9948bff42bc0dbc6c219556fbae35', | |
indexName: 'taro', | |
inputSelector: '#search_input_react' | |
}) | |
</script> | |
<div id="back-to-top" class="hidden"> | |
<svg viewBox="0 0 24 24"> | |
<path d="M7.41 15.41L12 10.83l4.59 4.58L18 14l-6-6-6 6z"></path> | |
</svg> | |
</div> | |
</body> | |
</html> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment