browser-extension-settings 0.0.3 → 0.0.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/common.ts CHANGED
@@ -1,2 +1,3 @@
1
+ export const besVersion = 12
1
2
  export const openButton = `<svg viewBox="0 0 60.2601318359375 84.8134765625" version="1.1" xmlns="http://www.w3.org/2000/svg" class=" glyph-box" style="height: 9.62969px; width: 6.84191px;"><g transform="matrix(1 0 0 1 -6.194965820312518 77.63671875)"><path d="M66.4551-35.2539C66.4551-36.4746 65.9668-37.5977 65.0391-38.4766L26.3672-76.3672C25.4883-77.1973 24.4141-77.6367 23.1445-77.6367C20.6543-77.6367 18.7012-75.7324 18.7012-73.1934C18.7012-71.9727 19.1895-70.8496 19.9707-70.0195L55.5176-35.2539L19.9707-0.488281C19.1895 0.341797 18.7012 1.41602 18.7012 2.68555C18.7012 5.22461 20.6543 7.12891 23.1445 7.12891C24.4141 7.12891 25.4883 6.68945 26.3672 5.81055L65.0391-32.0312C65.9668-32.959 66.4551-34.0332 66.4551-35.2539Z"></path></g></svg>`
2
3
  export const openInNewTabButton = `<svg viewBox="0 0 72.127685546875 72.2177734375" version="1.1" xmlns="http://www.w3.org/2000/svg" class=" glyph-box" style="height: 8.19958px; width: 8.18935px;"><g transform="matrix(1 0 0 1 -12.451127929687573 71.3388671875)"><path d="M84.5703-17.334L84.5215-66.4551C84.5215-69.2383 82.7148-71.1914 79.7852-71.1914L30.6641-71.1914C27.9297-71.1914 26.0742-69.0918 26.0742-66.748C26.0742-64.4043 28.1738-62.4023 30.4688-62.4023L47.4609-62.4023L71.2891-63.1836L62.207-55.2246L13.8184-6.73828C12.9395-5.85938 12.4512-4.73633 12.4512-3.66211C12.4512-1.31836 14.5508 0.878906 16.9922 0.878906C18.1152 0.878906 19.1895 0.488281 20.0684-0.439453L68.5547-48.877L76.6113-58.0078L75.7324-35.2051L75.7324-17.1387C75.7324-14.8438 77.7344-12.6953 80.127-12.6953C82.4707-12.6953 84.5703-14.6973 84.5703-17.334Z"></path></g></svg>`
@@ -1,4 +1,11 @@
1
- import { $, addElement, createElement } from "browser-extension-utils"
1
+ import {
2
+ $,
3
+ $$,
4
+ addClass,
5
+ addElement,
6
+ createElement,
7
+ removeClass,
8
+ } from "browser-extension-utils"
2
9
  import { openButton, openInNewTabButton } from "./common"
3
10
 
4
11
  type InstalledExtension = {
@@ -27,6 +34,11 @@ const relatedExtensions: RelatedExtension[] = [
27
34
  description: "在新标签页中打开第三方网站链接,图片链接转图片标签等",
28
35
  url: "https://greasyfork.org/scripts/464541",
29
36
  },
37
+ {
38
+ id: "v2ex.rep",
39
+ title: "V2EX.REP - 专注提升 V2EX 主题回复浏览体验",
40
+ url: "https://greasyfork.org/scripts/466589",
41
+ },
30
42
  {
31
43
  id: "v2ex.min",
32
44
  title: "v2ex.min - V2EX 极简风格",
@@ -38,25 +50,72 @@ const getInstalledExtesionList = () => {
38
50
  return $(".extension_list_container .installed_extension_list")
39
51
  }
40
52
 
53
+ const getRelatedExtesionList = () => {
54
+ return $(".extension_list_container .related_extension_list")
55
+ }
56
+
57
+ const isInstalledExtension = (id: string) => {
58
+ const list = getInstalledExtesionList()
59
+ if (!list) {
60
+ return false
61
+ }
62
+
63
+ const installed = $(`[data-extension-id="${id}"]`, list)
64
+ return Boolean(installed)
65
+ }
66
+
41
67
  export const addCurrentExtension = (extension: InstalledExtension) => {
42
68
  const list = getInstalledExtesionList()
43
69
  if (!list) {
44
70
  return
45
71
  }
46
72
 
47
- const id = extension.id
48
- const added = $(`[data-extension-id="${id}"]`, list)
49
- if (added) {
73
+ if (isInstalledExtension(extension.id)) {
50
74
  return
51
75
  }
52
76
 
53
77
  const element = createInstalledExtension(extension)
54
78
  list.append(element)
79
+
80
+ const list2 = getRelatedExtesionList()
81
+ if (list2) {
82
+ updateRelatedExtensions(list2)
83
+ }
84
+ }
85
+
86
+ export const activeExtension = (id: string) => {
87
+ const list = getInstalledExtesionList()
88
+ if (!list) {
89
+ return false
90
+ }
91
+
92
+ for (const element of $$(".active", list)) {
93
+ removeClass(element, "active")
94
+ }
95
+
96
+ const installed = $(`[data-extension-id="${id}"]`, list)
97
+ if (installed) {
98
+ addClass(installed, "active")
99
+ }
100
+ }
101
+
102
+ export const activeExtensionList = () => {
103
+ const extensionListContainer = $(".extension_list_container")
104
+ if (extensionListContainer) {
105
+ addClass(extensionListContainer, "bes_active")
106
+ }
107
+ }
108
+
109
+ export const deactiveExtensionList = () => {
110
+ const extensionListContainer = $(".extension_list_container")
111
+ if (extensionListContainer) {
112
+ removeClass(extensionListContainer, "bes_active")
113
+ }
55
114
  }
56
115
 
57
116
  const createInstalledExtension = (installedExtension: InstalledExtension) => {
58
117
  const div = createElement("div", {
59
- class: "related_extension",
118
+ class: "installed_extension",
60
119
  "data-extension-id": installedExtension.id,
61
120
  })
62
121
  const a = addElement(div, "a", {
@@ -71,6 +130,33 @@ const createInstalledExtension = (installedExtension: InstalledExtension) => {
71
130
  return div
72
131
  }
73
132
 
133
+ const updateRelatedExtensions = (container: HTMLElement) => {
134
+ container.innerHTML = ""
135
+
136
+ for (const relatedExtension of relatedExtensions) {
137
+ // console.log(relatedExtension)
138
+
139
+ if (isInstalledExtension(relatedExtension.id)) {
140
+ continue
141
+ }
142
+
143
+ const div4 = addElement(container, "div", {
144
+ class: "related_extension",
145
+ })
146
+
147
+ const a = addElement(div4, "a", {
148
+ href: relatedExtension.url,
149
+ target: "_blank",
150
+ })
151
+
152
+ addElement(a, "span", {
153
+ textContent: relatedExtension.title,
154
+ })
155
+ const svg = addElement(a, "svg")
156
+ svg.outerHTML = openInNewTabButton
157
+ }
158
+ }
159
+
74
160
  export function createExtensionList(installedExtensions: InstalledExtension[]) {
75
161
  const div = createElement("div", {
76
162
  class: "extension_list_container thin_scrollbar",
@@ -82,7 +168,11 @@ export function createExtensionList(installedExtensions: InstalledExtension[]) {
82
168
  class: "installed_extension_list",
83
169
  })
84
170
  for (const installedExtension of installedExtensions) {
85
- console.log(installedExtension)
171
+ // console.log(installedExtension)
172
+
173
+ if (isInstalledExtension(installedExtension.id)) {
174
+ continue
175
+ }
86
176
 
87
177
  const element = createInstalledExtension(installedExtension)
88
178
  div2.append(element)
@@ -92,24 +182,7 @@ export function createExtensionList(installedExtensions: InstalledExtension[]) {
92
182
  const div3 = addElement(div, "div", {
93
183
  class: "related_extension_list",
94
184
  })
95
- for (const relatedExtension of relatedExtensions) {
96
- console.log(relatedExtension)
97
-
98
- const div4 = addElement(div3, "div", {
99
- class: "related_extension",
100
- })
101
-
102
- const a = addElement(div4, "a", {
103
- href: relatedExtension.url,
104
- target: "_blank",
105
- })
106
-
107
- addElement(a, "span", {
108
- textContent: relatedExtension.title,
109
- })
110
- const svg = addElement(a, "svg")
111
- svg.outerHTML = openInNewTabButton
112
- }
185
+ updateRelatedExtensions(div3)
113
186
 
114
187
  return div
115
188
  }
package/lib/settings.ts CHANGED
@@ -6,6 +6,7 @@ import {
6
6
  import {
7
7
  $,
8
8
  $$,
9
+ addClass,
9
10
  addElement,
10
11
  addEventListener,
11
12
  addStyle,
@@ -15,7 +16,14 @@ import {
15
16
  } from "browser-extension-utils"
16
17
  import styleText from "data-text:./style.scss"
17
18
  import { createSwitchOption } from "./switch"
18
- import { createExtensionList, addCurrentExtension } from "./extension-list"
19
+ import {
20
+ createExtensionList,
21
+ addCurrentExtension,
22
+ activeExtension,
23
+ activeExtensionList,
24
+ deactiveExtensionList,
25
+ } from "./extension-list"
26
+ import { besVersion } from "./common"
19
27
 
20
28
  const prefix = "browser_extension_settings_"
21
29
 
@@ -28,13 +36,19 @@ type SettingsOptions = {
28
36
  relatedExtensions?: RelatedExtension[]
29
37
  }
30
38
 
31
- type SettingsTable = Record<string, SettingsSwitchItem>
39
+ type SettingsTable = Record<string, SettingsSwitchItem | SettingsInputItem>
32
40
 
33
41
  type SettingsSwitchItem = {
34
42
  title: string
35
43
  defaultValue: boolean
36
44
  }
37
45
 
46
+ type SettingsInputItem = {
47
+ title: string
48
+ defaultValue: string
49
+ type: string
50
+ }
51
+
38
52
  type RelatedExtension = {
39
53
  id: string
40
54
  title: string
@@ -48,11 +62,14 @@ type InstalledExtension = {
48
62
  version: string
49
63
  }
50
64
 
51
- const settingsElementId =
52
- prefix + "main_" + String(Math.round(Math.random() * 10_000))
65
+ const randomId = String(Math.round(Math.random() * 10_000))
66
+ const settingsContainerId = prefix + "container_" + randomId
67
+ const settingsElementId = prefix + "main_" + randomId
53
68
  const getSettingsElement = () => $("#" + settingsElementId)
54
69
  const getSettingsStyle: () => string = () =>
55
- styleText.replace(/browser_extension_settings_main/gm, settingsElementId)
70
+ styleText
71
+ .replace(/browser_extension_settings_container/gm, settingsContainerId)
72
+ .replace(/browser_extension_settings_main/gm, settingsElementId)
56
73
  const storageKey = "settings"
57
74
 
58
75
  let settingsOptions: SettingsOptions
@@ -80,7 +97,17 @@ export function getSettingsValue(key: string): boolean | string | undefined {
80
97
  : settingsTable[key]?.defaultValue
81
98
  }
82
99
 
83
- const modalHandler = (event) => {
100
+ const closeModal = () => {
101
+ const settingsContainer = getSettingsContainer()
102
+ if (settingsContainer) {
103
+ settingsContainer.style.display = "none"
104
+ }
105
+
106
+ removeEventListener(document, "click", onDocumentClick)
107
+ removeEventListener(document, "keydown", onDocumentKeyDown)
108
+ }
109
+
110
+ const onDocumentClick = (event) => {
84
111
  let target = event.target as HTMLElement
85
112
  const settingsContainer = getSettingsContainer()
86
113
  if (settingsContainer) {
@@ -91,11 +118,30 @@ const modalHandler = (event) => {
91
118
  if (target === settingsContainer) {
92
119
  return
93
120
  }
121
+ }
94
122
 
95
- settingsContainer.style.display = "none"
123
+ closeModal()
124
+ }
125
+
126
+ const onDocumentKeyDown = (event) => {
127
+ if (event.defaultPrevented) {
128
+ return // 如果事件已经在进行中,则不做任何事。
129
+ }
130
+
131
+ switch (event.key) {
132
+ case "Escape": {
133
+ // 按“ESC”键时要做的事。
134
+ closeModal()
135
+ break
136
+ }
137
+
138
+ default: {
139
+ return
140
+ } // 什么都没按就退出吧。
96
141
  }
97
142
 
98
- removeEventListener(document, "click", modalHandler)
143
+ // 取消默认动作,从而避免处理两次。
144
+ event.preventDefault()
99
145
  }
100
146
 
101
147
  async function updateOptions() {
@@ -131,17 +177,27 @@ async function updateOptions() {
131
177
  }
132
178
 
133
179
  function getSettingsContainer() {
134
- return (
135
- $(`#${prefix}container`) ||
136
- addElement(doc.body, "div", {
137
- id: `${prefix}container`,
138
- })
139
- )
180
+ const container = $(`.${prefix}container`)
181
+ if (container) {
182
+ const theVersion = Number.parseInt(container.dataset.besVersion || "0", 10)
183
+ if (theVersion < besVersion) {
184
+ container.id = settingsContainerId
185
+ container.dataset.besVersion = String(besVersion)
186
+ }
187
+
188
+ return container
189
+ }
190
+
191
+ return addElement(doc.body, "div", {
192
+ id: settingsContainerId,
193
+ class: `${prefix}container`,
194
+ "data-bes-version": besVersion,
195
+ })
140
196
  }
141
197
 
142
198
  function getSettingsWrapper() {
143
199
  return (
144
- $(`#${prefix}container .${prefix}wrapper`) ||
200
+ $(`.${prefix}container .${prefix}wrapper`) ||
145
201
  addElement(getSettingsContainer(), "div", {
146
202
  class: `${prefix}wrapper`,
147
203
  })
@@ -149,6 +205,11 @@ function getSettingsWrapper() {
149
205
  }
150
206
 
151
207
  function initExtensionList() {
208
+ if (!doc.body) {
209
+ setTimeout(initExtensionList, 100)
210
+ return
211
+ }
212
+
152
213
  const wrapper = getSettingsWrapper()
153
214
  if (!$(".extension_list_container", wrapper)) {
154
215
  const list = createExtensionList([])
@@ -180,7 +241,7 @@ function createSettingsElement() {
180
241
  textContent: "Settings",
181
242
  class: "navigation_go_previous",
182
243
  onclick() {
183
- console.log(1)
244
+ activeExtensionList()
184
245
  },
185
246
  })
186
247
 
@@ -267,17 +328,34 @@ function createSettingsElement() {
267
328
  return settingsMain
268
329
  }
269
330
 
270
- function addSideMenu(options) {
271
- console.log("doc.body", doc.body)
331
+ function addSideMenu() {
332
+ if (!doc.body) {
333
+ setTimeout(addSideMenu, 100)
334
+ return
335
+ }
336
+
272
337
  const menu =
273
338
  $("#browser_extension_side_menu") ||
274
339
  addElement(doc.body, "div", {
275
340
  id: "browser_extension_side_menu",
276
- "data-version": 1,
341
+ "data-bes-version": besVersion,
277
342
  })
343
+
344
+ const button = $("button[data-bes-version]", menu)
345
+
346
+ if (button) {
347
+ const theVersion = Number.parseInt(button.dataset.besVersion || "0", 10)
348
+ if (theVersion >= besVersion) {
349
+ return
350
+ }
351
+
352
+ button.remove()
353
+ }
354
+
278
355
  addElement(menu, "button", {
279
356
  type: "button",
280
- title: options.title ? "设置 - " + options.title : "设置",
357
+ "data-bes-version": besVersion,
358
+ title: "设置",
281
359
  onclick() {
282
360
  setTimeout(showSettings, 1)
283
361
  },
@@ -291,7 +369,10 @@ export async function showSettings() {
291
369
  await updateOptions()
292
370
  settingsContainer.style.display = "block"
293
371
 
294
- addEventListener(document, "click", modalHandler)
372
+ addEventListener(document, "click", onDocumentClick)
373
+ addEventListener(document, "keydown", onDocumentKeyDown)
374
+ activeExtension(settingsOptions.id)
375
+ deactiveExtensionList()
295
376
  }
296
377
 
297
378
  export const initSettings = async (options: SettingsOptions) => {
@@ -308,5 +389,5 @@ export const initSettings = async (options: SettingsOptions) => {
308
389
  settings = await getSettings()
309
390
  addStyle(getSettingsStyle())
310
391
  initExtensionList()
311
- addSideMenu(options)
392
+ addSideMenu()
312
393
  }
package/lib/style.scss CHANGED
@@ -78,6 +78,10 @@
78
78
  background-color: #e4e4e6;
79
79
  }
80
80
 
81
+ &.active a {
82
+ cursor: default;
83
+ }
84
+
81
85
  &:first-of-type {
82
86
  border-top: none;
83
87
  border-top-right-radius: 10px;
@@ -183,6 +187,7 @@
183
187
  }
184
188
 
185
189
  .option_groups textarea {
190
+ font-size: 12px;
186
191
  margin: 10px 0 10px 0;
187
192
  height: 100px;
188
193
  width: 100%;
@@ -332,6 +337,7 @@
332
337
  top: 80px;
333
338
  right: 0;
334
339
  padding-top: 20px;
340
+ z-index: 10000;
335
341
  }
336
342
 
337
343
  #browser_extension_side_menu:hover {
@@ -354,3 +360,25 @@
354
360
  #browser_extension_side_menu button:active {
355
361
  opacity: 100%;
356
362
  }
363
+
364
+ @media (max-width: 500px) {
365
+ #browser_extension_settings_container {
366
+ right: 10px;
367
+
368
+ .extension_list_container {
369
+ display: none;
370
+ }
371
+ .extension_list_container.bes_active {
372
+ display: block;
373
+ }
374
+ .extension_list_container.bes_active + div {
375
+ display: none;
376
+ }
377
+ }
378
+
379
+ #browser_extension_settings_main {
380
+ a.navigation_go_previous {
381
+ display: block;
382
+ }
383
+ }
384
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "browser-extension-settings",
3
- "version": "0.0.3",
3
+ "version": "0.0.5",
4
4
  "description": "Settings module for developing browser extensions and userscripts",
5
5
  "type": "module",
6
6
  "main": "./lib/index.ts",