1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
|
---
title: 你的第一个拓展
slug: Mozilla/Add-ons/WebExtensions/Your_first_WebExtension
tags:
- WebExtentions
- 指南
translation_of: Mozilla/Add-ons/WebExtensions/Your_first_WebExtension
---
<div>{{AddonSidebar}}</div>
<p>在这篇文章中,我们将为 Firefox 创建一个扩展。这个扩展只是给从 "firefox.org" 或其任意子域名加载的任何页面添加一个红色边框。</p>
<p>该示例的源代码位于 GitHub:<a href="https://github.com/mdn/webextensions-examples/tree/master/borderify">https://github.com/mdn/webextensions-examples/tree/master/borderify</a></p>
<p>首先,你需要 Firefox 45 或更高版本。</p>
<h2 id="编写扩展">编写扩展</h2>
<p>创建一个新的目录并切换到该目录。例如,在你的命令行/终端,你可以这么做:</p>
<pre class="brush: bash">mkdir borderify
cd borderify</pre>
<h3 id="manifest.json">manifest.json</h3>
<p>现在,在 "borderify" 目录内直接创建文件 "manifest.json"。文件内容如下:</p>
<pre class="brush: json line-numbers language-json"><code class="language-json"><span class="punctuation token">{</span>
<span class="key token">"manifest_version":</span> <span class="number token">2</span><span class="punctuation token">,</span>
<span class="key token">"name":</span> <span class="string token">"Borderify"</span><span class="punctuation token">,</span>
<span class="key token">"version":</span> <span class="string token">"1.0"</span><span class="punctuation token">,</span>
<span class="key token">"description":</span> <span class="string token">"Adds a red border to all webpages matching mozilla.org."</span><span class="punctuation token">,</span>
<span class="key token">"icons":</span> <span class="punctuation token">{</span>
<span class="key token">"48":</span> <span class="string token">"icons/border-48.png"</span>
<span class="punctuation token">}</span><span class="punctuation token">,</span>
<span class="key token">"content_scripts":</span> <span class="punctuation token">[</span>
<span class="punctuation token">{</span>
<span class="key token">"matches":</span> <span class="punctuation token">[</span><span class="string token">"*://*.mozilla.org/*"</span><span class="punctuation token">]</span><span class="punctuation token">,</span>
<span class="key token">"js":</span> <span class="punctuation token">[</span><span class="string token">"borderify.js"</span><span class="punctuation token">]</span>
<span class="punctuation token">}</span>
<span class="punctuation token">]</span>
<span class="punctuation token">}</span></code></pre>
<ul>
<li>前三个键:<code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/manifest_version">manifest_version</a></code>、<code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/name">name</a></code> 和 <code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/version">version</a></code> 是强制的,包含有扩展的基本元数据.</li>
<li><code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/description">description</a></code> 是可选的,但建议使用「该描述将显示在附加组件管理器上」.</li>
<li><code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/icons">icons</a></code> 是可选的,但建议使用「它允许你给扩展指定一个图标,将显示在附加组件管理器上」.</li>
</ul>
<p>这里最有意思的键是 <code><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/content_scripts">content_scripts</a></code>,它告诉 Firefox 加载脚本到其 URL 匹配特定模式的网页。本例中,我们要求 Firefox 加载脚本 "borderify.js" 到任何来自 "mozilla.org" 或其子域的 HTTP 或 HTTPS 页面。</p>
<ul>
<li><a href="/zh-CN/Add-ons/WebExtensions/Content_scripts">进一步了解内容脚本 content script</a></li>
<li><a href="/zh-CN/Add-ons/WebExtensions/Match_patterns">进一步了解模式匹配 pattern matching</a></li>
</ul>
<div class="warning">
<p><a href="/zh-CN/Add-ons/WebExtensions/WebExtensions_and_the_Add-on_ID#When_do_you_need_an_Add-on_ID">某些情况下,你需要给你的扩展指定一个 ID</a>。如果你需要指定一个附加组件 ID,请在 <code>manifest.json</code> 中添加 <code><a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/manifest.json/browser_specific_settings">browser_specific_settings</a></code> 键,并设置其 <code>gecko.id</code> 属性:</p>
<pre class="brush: json">"browser_specific_settings": {
"gecko": {
"id": "borderify@example.com"
}
}</pre>
</div>
<h3 id="iconsborder-48.png">icons/border-48.png</h3>
<p>扩展应该有一个图标。这将显示在附加组件管理器加载项的列表中。我们的 manifest.json 保证了会有一个图标 "icons/border-48.png"。</p>
<p>在 "borderify" 目录下直接创建 "icons" 目录,并在 "icons" 目录下保存一个名为 "border-48.png"的图标. 你可以使用<a href="https://github.com/mdn/webextensions-examples/blob/master/borderify/icons/border-48.png">我们的示例</a>中的,来自谷歌材料设计中的图标,遵循 <a href="http://creativecommons.org/licenses/by-sa/3.0/">Creative Commons Attribution-ShareAlike</a> 协议。</p>
<p>如果您选择使用自己的图标,它也应该是 48×48 像素。你也可以为高分辨率显示器提供一个 96x96 的像素图标,在 manifest.json 的 <code>icons</code> 对象中添加 <code>96</code> 属性即可:</p>
<pre class="brush: json line-numbers language-json"><code class="language-json"><span class="key token">"icons":</span> <span class="punctuation token">{</span>
<span class="key token">"48":</span> <span class="string token">"icons/border-48.png",
"96": "icons/border-96.png"</span>
<span class="punctuation token">}</span></code></pre>
<p>或者,也可以在这里提供一个 SVG 文件,它会被正确地缩放。(不过:如果你正在使用 SVG 并且你的图标包含文字,有可能想要用你的 SVG 编辑器的“转换为路径”工具来拼和文字,这样图标会以一个恒定的大小/位置来缩放。)</p>
<ul>
<li><a href="/zh-CN/Add-ons/WebExtensions/manifest.json/icons">了解更多关于指定图标的内容</a></li>
</ul>
<h3 id="borderify.js">borderify.js</h3>
<p>最后,在 "borderify" 目录下直接创建 "borderify.js" 文件,并写入下面的内容:</p>
<pre class="brush: js">document.body.style.border = "5px solid red";</pre>
<p>manifest.json 文件中 <code>content_scripts</code> 的键给出了一条模式匹配,该脚本便会被加载到匹配的页面中。该脚本会像页面加载自己的脚本一样被加载,可以直接访问该文档。</p>
<ul>
<li><a href="/zh-CN/Add-ons/WebExtensions/Content_scripts">了解更多关于内容脚本的内容。</a></li>
</ul>
<h2 id="测试一下">测试一下</h2>
<p>首先,仔细检查文件是否在正确的位置:</p>
<pre>borderify/
icons/
border-48.png
borderify.js
manifest.json</pre>
<h3 id="安装">安装</h3>
<p>打开 Firefox 的 <a href="/zh-CN/docs/Tools/about:debugging">about:debugging</a> 页面,点击”This Firefox" (在新版本的Firefox里),点击 "临时加载附加组件(Load Temporary Add-on)" 按钮,并选择你的附加组件目录:</p>
<p>{{EmbedYouTube("cer9EUKegG4")}}</p>
<p>附加组件将会被安装,直到下次重启浏览器失效。</p>
<p>或者,你可以通过 <a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/Getting_started_with_web-ext">web-ext</a> 工具从命令行来运行扩展。</p>
<h3 id="测试">测试</h3>
<p>现在尝试访问"mozilla.org", 你将会在页面上看到有个红色的边框</p>
<p>{{EmbedYouTube("rxBQl2Z9IBQ")}}</p>
<div class="note">
<p>不要在 addons.mozilla.org 上尝试!内容脚本(Content Script) 当前在那个域名下是被限制的。</p>
</div>
<p>尝试一下编辑内容脚本更改边框的颜色,或做页面内容别的修改,保存内容脚本,然后通过单击 <strong>about:debugging</strong> 页面下的 “刷新” 按钮重新加载附加的文件。你可以马上看到的变化:</p>
<p>{{EmbedYouTube("NuajE60jfGY")}}</p>
<ul>
<li><a href="/zh-CN/Add-ons/WebExtensions/Temporary_Installation_in_Firefox">学习更多关于加载附加组件</a></li>
</ul>
<h2 id="打包和发布">打包和发布</h2>
<p>为了给其他人使用你的插件,您需要打包,并将其提交给 Mozilla 进行签名。要了解更多有关,请参考 <a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/Publishing_your_WebExtension">"发布你的扩展"</a>。</p>
<h2 id="下一步">下一步</h2>
<p>现在,你已经在开发 Firefox 的一个 Web 扩展的过程中得到了一些想法,尝试:</p>
<ul>
<li><a href="/zh-CN/Add-ons/WebExtensions/Your_second_WebExtension">写一个更加复杂的WebExtension</a></li>
<li><a href="/zh-CN/Add-ons/WebExtensions/Anatomy_of_a_WebExtension">阅读更多关于WebExtensions的剖析</a></li>
<li><a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/Examples">探索更多关于扩展的示例</a></li>
<li><a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/What_next_">发现开发,测试,和发布扩展需要的东西</a></li>
<li><a href="/zh-CN/docs/Mozilla/Add-ons/WebExtensions/What_next_#Continue_your_learning_experience">进一步的学习</a></li>
</ul>
<div id="SL_balloon_obj" style="display: block;">
<div class="SL_ImTranslatorLogo" id="SL_button" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%; display: none; opacity: 1; left: 556px; top: 6804px;"></div>
<div id="SL_shadow_translation_result2" class="hidden"></div>
<div id="SL_shadow_translator" class="hidden">
<div id="SL_planshet">
<div id="SL_arrow_up" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;"></div>
<div id="SL_Bproviders">
<div class="SL_BL_LABLE_ON" id="SL_P0" title="Google">G</div>
<div class="SL_BL_LABLE_ON" id="SL_P1" title="Microsoft">M</div>
<div class="SL_BL_LABLE_ON" id="SL_P2" title="Translator">T</div>
</div>
<div id="SL_alert_bbl" class="hidden">
<div id="SLHKclose" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;"></div>
<div id="SL_alert_cont"></div>
</div>
<div id="SL_TB">
<table id="SL_tables">
<tbody>
<tr>
<td class="SL_td"><input></td>
<td class="SL_td"><select><option value="auto">检测语言</option><option value="eo">世界语</option><option value="zh-CN">中文简体</option><option value="zh-TW">中文繁体</option><option value="da">丹麦语</option><option value="uk">乌克兰语</option><option value="uz">乌兹别克语</option><option value="ur">乌尔都语</option><option value="hy">亚美尼亚语</option><option value="ig">伊博语</option><option value="ru">俄语</option><option value="bg">保加利亚语</option><option value="si">僧伽罗语</option><option value="hr">克罗地亚语</option><option value="is">冰岛语</option><option value="gl">加利西亚语</option><option value="ca">加泰罗尼亚语</option><option value="hu">匈牙利语</option><option value="zu">南非祖鲁语</option><option value="kn">卡纳达语</option><option value="hi">印地语</option><option value="su">印尼巽他语</option><option value="jw">印尼爪哇语</option><option value="id">印尼语</option><option value="gu">古吉拉特语</option><option value="kk">哈萨克语</option><option value="tr">土耳其语</option><option value="tg">塔吉克语</option><option value="sr">塞尔维亚语</option><option value="st">塞索托语</option><option value="cy">威尔士语</option><option value="bn">孟加拉语</option><option value="ceb">宿务语</option><option value="ne">尼泊尔语</option><option value="eu">巴斯克语</option><option value="af">布尔语(南非荷兰语)</option><option value="iw">希伯来语</option><option value="el">希腊语</option><option value="de">德语</option><option value="it">意大利语</option><option value="yi">意第绪语</option><option value="la">拉丁语</option><option value="lv">拉脱维亚语</option><option value="no">挪威语</option><option value="cs">捷克语</option><option value="sk">斯洛伐克语</option><option value="sl">斯洛文尼亚语</option><option value="sw">斯瓦希里语</option><option value="pa">旁遮普语</option><option value="ja">日语</option><option value="ka">格鲁吉亚语</option><option value="mi">毛利语</option><option value="fr">法语</option><option value="pl">波兰语</option><option value="bs">波斯尼亚语</option><option value="fa">波斯语</option><option value="te">泰卢固语</option><option value="ta">泰米尔语</option><option value="th">泰语</option><option value="ht">海地克里奥尔语</option><option value="ga">爱尔兰语</option><option value="et">爱沙尼亚语</option><option value="sv">瑞典语</option><option value="be">白俄罗斯语</option><option value="lt">立陶宛语</option><option value="so">索马里语</option><option value="yo">约鲁巴语</option><option value="my">缅甸语</option><option value="ro">罗马尼亚语</option><option value="lo">老挝语</option><option value="fi">芬兰语</option><option value="hmn">苗语</option><option value="en">英语</option><option value="nl">荷兰语</option><option value="tl">菲律宾语</option><option value="pt">葡萄牙语</option><option value="mn">蒙古语</option><option value="es">西班牙语</option><option value="ha">豪萨语</option><option value="vi">越南语</option><option value="az">阿塞拜疆语</option><option value="sq">阿尔巴尼亚语</option><option value="ar">阿拉伯语</option><option value="ko">韩语</option><option value="mk">马其顿语</option><option value="mg">马尔加什语</option><option value="mr">马拉地语</option><option value="ml">马拉雅拉姆语</option><option value="ms">马来语</option><option value="mt">马耳他语</option><option value="km">高棉语</option><option value="ny">齐切瓦语</option></select></td>
<td class="SL_td">
<div id="SL_switch_b" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="切换语言"></div>
</td>
<td class="SL_td"><select><option value="eo">世界语</option><option selected value="zh-CN">中文简体</option><option value="zh-TW">中文繁体</option><option value="da">丹麦语</option><option value="uk">乌克兰语</option><option value="uz">乌兹别克语</option><option value="ur">乌尔都语</option><option value="hy">亚美尼亚语</option><option value="ig">伊博语</option><option value="ru">俄语</option><option value="bg">保加利亚语</option><option value="si">僧伽罗语</option><option value="hr">克罗地亚语</option><option value="is">冰岛语</option><option value="gl">加利西亚语</option><option value="ca">加泰罗尼亚语</option><option value="hu">匈牙利语</option><option value="zu">南非祖鲁语</option><option value="kn">卡纳达语</option><option value="hi">印地语</option><option value="su">印尼巽他语</option><option value="jw">印尼爪哇语</option><option value="id">印尼语</option><option value="gu">古吉拉特语</option><option value="kk">哈萨克语</option><option value="tr">土耳其语</option><option value="tg">塔吉克语</option><option value="sr">塞尔维亚语</option><option value="st">塞索托语</option><option value="cy">威尔士语</option><option value="bn">孟加拉语</option><option value="ceb">宿务语</option><option value="ne">尼泊尔语</option><option value="eu">巴斯克语</option><option value="af">布尔语(南非荷兰语)</option><option value="iw">希伯来语</option><option value="el">希腊语</option><option value="de">德语</option><option value="it">意大利语</option><option value="yi">意第绪语</option><option value="la">拉丁语</option><option value="lv">拉脱维亚语</option><option value="no">挪威语</option><option value="cs">捷克语</option><option value="sk">斯洛伐克语</option><option value="sl">斯洛文尼亚语</option><option value="sw">斯瓦希里语</option><option value="pa">旁遮普语</option><option value="ja">日语</option><option value="ka">格鲁吉亚语</option><option value="mi">毛利语</option><option value="fr">法语</option><option value="pl">波兰语</option><option value="bs">波斯尼亚语</option><option value="fa">波斯语</option><option value="te">泰卢固语</option><option value="ta">泰米尔语</option><option value="th">泰语</option><option value="ht">海地克里奥尔语</option><option value="ga">爱尔兰语</option><option value="et">爱沙尼亚语</option><option value="sv">瑞典语</option><option value="be">白俄罗斯语</option><option value="lt">立陶宛语</option><option value="so">索马里语</option><option value="yo">约鲁巴语</option><option value="my">缅甸语</option><option value="ro">罗马尼亚语</option><option value="lo">老挝语</option><option value="fi">芬兰语</option><option value="hmn">苗语</option><option value="en">英语</option><option value="nl">荷兰语</option><option value="tl">菲律宾语</option><option value="pt">葡萄牙语</option><option value="mn">蒙古语</option><option value="es">西班牙语</option><option value="ha">豪萨语</option><option value="vi">越南语</option><option value="az">阿塞拜疆语</option><option value="sq">阿尔巴尼亚语</option><option value="ar">阿拉伯语</option><option value="ko">韩语</option><option value="mk">马其顿语</option><option value="mg">马尔加什语</option><option value="mr">马拉地语</option><option value="ml">马拉雅拉姆语</option><option value="ms">马来语</option><option value="mt">马耳他语</option><option value="km">高棉语</option><option value="ny">齐切瓦语</option></select></td>
<td class="SL_td">
<div id="SL_TTS_voice" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="聆听翻译"></div>
</td>
<td class="SL_td">
<div class="SL_copy" id="SL_copy" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="复制译文"></div>
</td>
<td class="SL_td">
<div id="SL_bbl_font_patch"></div>
<div class="SL_bbl_font" id="SL_bbl_font" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="字体大小"></div>
</td>
<td class="SL_td">
<div id="SL_bbl_help" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="帮助"></div>
</td>
<td class="SL_td">
<div class="SL_pin_off" id="SL_pin" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="固定弹出窗口"></div>
</td>
</tr>
</tbody>
</table>
</div>
</div>
<div id="SL_shadow_translation_result"></div>
<div class="SL_loading" id="SL_loading" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;"></div>
<div id="SL_player2"></div>
<div id="SL_alert100">文本转语音功能仅限200个字符</div>
<div id="SL_Balloon_options" style="background: rgb(255, 255, 255) repeat scroll 0% 0%;">
<div id="SL_arrow_down" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;"></div>
<table id="SL_tbl_opt" style="width: 100%;">
<tbody>
<tr>
<td><input></td>
<td>
<div id="SL_BBL_IMG" style="background: rgba(0, 0, 0, 0) repeat scroll 0% 0%;" title="显示翻译器的按钮 3 秒"></div>
</td>
<td><a class="SL_options" title="显示选项">选项</a> : <a class="SL_options" title="翻译历史记录">历史</a> : <a class="SL_options" title="反馈">反馈</a> : <a class="SL_options" href="https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=GD9D8CPW8HFA2" title="作出一点点贡献">Donate</a></td>
<td><span id="SL_Balloon_Close" title="关闭">关闭</span></td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
|