@brillout/docpress 0.5.39 → 0.5.40-commit-1ba896e

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.
Files changed (143) hide show
  1. package/MobileHeader.tsx +68 -0
  2. package/PageLayout.css +42 -0
  3. package/PageLayout.tsx +39 -0
  4. package/algolia/DocSearch.css +34 -0
  5. package/algolia/DocSearch.ts +62 -0
  6. package/autoScrollNav.ts +36 -0
  7. package/components/CodeBlockTransformer.css +9 -0
  8. package/components/CodeBlockTransformer.tsx +18 -0
  9. package/components/Comment.tsx +7 -0
  10. package/components/Consulting.tsx +47 -0
  11. package/components/Contributors.tsx +113 -0
  12. package/components/EditPageNote.tsx +18 -0
  13. package/components/HorizontalLine.tsx +20 -0
  14. package/components/ImportMeta.tsx +11 -0
  15. package/components/Link.tsx +144 -0
  16. package/components/Note.css +54 -0
  17. package/components/Note.tsx +78 -0
  18. package/components/P.css +8 -0
  19. package/components/P.tsx +8 -0
  20. package/components/ReadingRecommendation.tsx +56 -0
  21. package/components/RepoLink.tsx +24 -0
  22. package/components/Sponsors/label.draft.svg +108 -0
  23. package/components/Sponsors.tsx +218 -0
  24. package/components/Supporters.tsx +136 -0
  25. package/{dist/components → components}/features/FeatureList.css +10 -2
  26. package/components/features/FeatureList.tsx +114 -0
  27. package/components/features/initFeatureList.ts +66 -0
  28. package/components/index.ts +15 -0
  29. package/config/getConfig.ts +18 -0
  30. package/config/resolveConfig/resolveHeading.ts +0 -0
  31. package/config/resolvePageContext.ts +186 -0
  32. package/css/button.css +7 -0
  33. package/css/code/block.css +36 -0
  34. package/css/code/inline.css +27 -0
  35. package/css/code.css +20 -0
  36. package/css/colorize-on-hover.css +29 -0
  37. package/css/font.css +25 -0
  38. package/css/heading.css +45 -0
  39. package/css/index.css +12 -0
  40. package/css/link.css +17 -0
  41. package/css/reset.css +12 -0
  42. package/css/table.css +14 -0
  43. package/css/tooltip.css +11 -0
  44. package/data/maintainersList.tsx +92 -0
  45. package/data/sponsorsList.ts +147 -0
  46. package/dist/markdownHeadingsVitePlugin.d.ts +13 -0
  47. package/dist/markdownHeadingsVitePlugin.js +170 -0
  48. package/dist/utils/assert.d.ts +6 -0
  49. package/dist/utils/assert.js +48 -0
  50. package/dist/utils/determineSectionUrlHash.d.ts +4 -0
  51. package/dist/utils/determineSectionUrlHash.js +38 -0
  52. package/dist/vite.config.d.ts +3 -0
  53. package/dist/vite.config.js +32 -0
  54. package/index.ts +4 -0
  55. package/installSectionUrlHashs.ts +60 -0
  56. package/markdownHeadingsVitePlugin.ts +150 -0
  57. package/navigation/Navigation-highlight.css +41 -0
  58. package/navigation/Navigation-items.css +119 -0
  59. package/navigation/Navigation-layout.css +127 -0
  60. package/navigation/Navigation.client.ts +43 -0
  61. package/navigation/Navigation.css +3 -0
  62. package/navigation/Navigation.tsx +211 -0
  63. package/navigation/NavigationHeader.tsx +111 -0
  64. package/navigation/navigation-fullscreen/NavigationFullscreenButton.css +32 -0
  65. package/navigation/navigation-fullscreen/NavigationFullscreenButton.tsx +44 -0
  66. package/navigation/navigation-fullscreen/initNavigationFullscreen.ts +116 -0
  67. package/package.json +27 -47
  68. package/parseEmojis.ts +35 -0
  69. package/parseTitle.ts +139 -0
  70. package/renderer/client.ts +4 -0
  71. package/renderer/onRenderHtml.tsx +69 -0
  72. package/renderer/usePageContext.tsx +25 -0
  73. package/tsconfig.json +15 -0
  74. package/tsconfig.vite-config.json +7 -0
  75. package/types/Config.ts +46 -0
  76. package/types/Heading.ts +49 -0
  77. package/utils/Emoji/Emoji.ts +224 -0
  78. package/utils/Emoji/assets.ts +9 -0
  79. package/utils/Emoji/index.ts +1 -0
  80. package/utils/Emoji/mountain.svg +1 -0
  81. package/utils/assert.ts +51 -0
  82. package/utils/client.ts +2 -0
  83. package/utils/determineSectionUrlHash.ts +44 -0
  84. package/utils/filesystemPathHandling.ts +42 -0
  85. package/utils/filter.ts +12 -0
  86. package/utils/isBrowser.ts +5 -0
  87. package/utils/jsxToTextContent.ts +11 -0
  88. package/utils/objectAssign.ts +9 -0
  89. package/utils/server.ts +7 -0
  90. package/vite.config.ts +36 -0
  91. package/bin.js +0 -3
  92. package/dist/chunk-2ZTPUQGS.js +0 -58
  93. package/dist/chunk-3QC7HYIF.js +0 -7
  94. package/dist/chunk-MGOI4AFO.js +0 -165
  95. package/dist/chunk-NVJING6T.js +0 -91
  96. package/dist/chunk-QWL3MA4E.js +0 -171
  97. package/dist/chunk-UN23G34B.js +0 -157
  98. package/dist/cli/index.d.ts +0 -1
  99. package/dist/cli/index.js +0 -34
  100. package/dist/components/features/FeatureList.d.ts +0 -13
  101. package/dist/components/features/FeatureList.js +0 -7
  102. package/dist/components/features/initFeatureList.d.ts +0 -3
  103. package/dist/components/features/initFeatureList.js +0 -59
  104. package/dist/devServer-JKH6U5PF.js +0 -36
  105. package/dist/index.css +0 -120
  106. package/dist/index.d.ts +0 -225
  107. package/dist/index.js +0 -948
  108. package/dist/renderer/_default.page.client.css +0 -318
  109. package/dist/renderer/_default.page.client.d.ts +0 -1
  110. package/dist/renderer/_default.page.client.js +0 -218
  111. package/dist/renderer/_default.page.server.css +0 -310
  112. package/dist/renderer/_default.page.server.d.ts +0 -22
  113. package/dist/renderer/_default.page.server.js +0 -665
  114. package/readme.md +0 -5
  115. /package/{dist/label-MP75CTIA.svg → components/Sponsors/label.svg} +0 -0
  116. /package/{dist/medalBronze-CO4CTUR4.svg → components/Sponsors/medalBronze.svg} +0 -0
  117. /package/{dist/medalGold-UP6A73FL.svg → components/Sponsors/medalGold.svg} +0 -0
  118. /package/{dist/medalSilver-FAPGGOBN.svg → components/Sponsors/medalSilver.svg} +0 -0
  119. /package/{dist/chevron-R2IYJD62.svg → components/features/chevron.svg} +0 -0
  120. /package/{dist/Inter-Var-IOAEQULN.ttf → css/Inter-Var.ttf} +0 -0
  121. /package/{dist/alignable-B4QZV4X7.svg → data/sponsorsList/companyLogos/alignable.svg} +0 -0
  122. /package/{dist/bluefin-JQABZFGV.svg → data/sponsorsList/companyLogos/bluefin.svg} +0 -0
  123. /package/{dist/burdaforward-EUGURYZY.png → data/sponsorsList/companyLogos/burdaforward.png} +0 -0
  124. /package/{dist/contra-WLZBOPBV.svg → data/sponsorsList/companyLogos/contra.svg} +0 -0
  125. /package/{dist/ecosia-OYRLTR5T.svg → data/sponsorsList/companyLogos/ecosia.svg} +0 -0
  126. /package/{dist/inlang-GFRWND6X.png → data/sponsorsList/companyLogos/inlang.png} +0 -0
  127. /package/{dist/optimizers-SFEZF3NW.svg → data/sponsorsList/companyLogos/optimizers.svg} +0 -0
  128. /package/{dist/sourcegraph-YR2HADLS.svg → data/sponsorsList/companyLogos/sourcegraph.svg} +0 -0
  129. /package/{dist/changelog-IPI5F42D.svg → icons/changelog.svg} +0 -0
  130. /package/{dist/discord-JD33TUSF.svg → icons/discord.svg} +0 -0
  131. /package/{dist/github-P5ZSKN2N.svg → icons/github.svg} +0 -0
  132. /package/{dist/heart-OINVKOXO.svg → icons/heart.svg} +0 -0
  133. /package/{dist/languages-KXPKJFQL.svg → icons/languages.svg} +0 -0
  134. /package/{dist/people-72KKQHU4.svg → icons/people.svg} +0 -0
  135. /package/{dist/twitter-I7DXDN3J.svg → icons/twitter.svg} +0 -0
  136. /package/{dist/chevron-K3WPYLOP.svg → navigation/navigation-fullscreen/chevron.svg} +0 -0
  137. /package/{dist/close-IQXTDOHV.svg → navigation/navigation-fullscreen/close.svg} +0 -0
  138. /package/{dist/compass-2RWQU3E4.svg → utils/Emoji/compass.svg} +0 -0
  139. /package/{dist/engine-6Q6VSCVA.png → utils/Emoji/engine.png} +0 -0
  140. /package/{dist/mechanical-arm-TR7IQQMG.svg → utils/Emoji/mechanical-arm.svg} +0 -0
  141. /package/{dist/road-fork-3WZLW3HB.svg → utils/Emoji/road-fork.svg} +0 -0
  142. /package/{dist/shield-CU45RG5C.svg → utils/Emoji/shield.svg} +0 -0
  143. /package/{dist/typescript-ALIPKLRM.svg → utils/Emoji/typescript.svg} +0 -0
@@ -0,0 +1,54 @@
1
+ blockquote {
2
+ --color: 0, 0, 0;
3
+ --color-strengh-bg: 0.7;
4
+ --color-strengh-border: 1.5;
5
+ border-left: 8px solid rgba(var(--color), calc(0.06 * var(--color-strengh-border)));
6
+ background-color: rgba(var(--color), calc(0.03 * var(--color-strengh-bg)));
7
+ margin-left: 0;
8
+ margin-right: 0;
9
+ padding: 4px 16px;
10
+ }
11
+ blockquote.note-color-red {
12
+ --color-strengh-bg: 1.7;
13
+ --color-strengh-border: 6;
14
+ --color: 190, 25, 49;
15
+ }
16
+ blockquote.note-color-yellow {
17
+ --color-strengh-bg: 4;
18
+ --color-strengh-border: 8;
19
+ --color: 255, 204, 50;
20
+ }
21
+ .blockquote-content {
22
+ display: inline;
23
+ }
24
+ blockquote.custom-icon > .blockquote-content > :first-child {
25
+ /* E.g. for <Warning> so that the warning icon is on the same line as the first paragraph.
26
+ * We assume the second element to have a top margin.
27
+ */
28
+ display: inline;
29
+ }
30
+
31
+ /************************/
32
+ /*** Icon Positioning ***/
33
+ /************************/
34
+ blockquote.type-construction img[src^="https://twemoji."]
35
+ {
36
+ margin-right: 2px;
37
+ }
38
+ blockquote.type-warning img[src^="https://twemoji."]
39
+ {
40
+ position: relative;
41
+ top: -1px;
42
+ margin-right: 2px;
43
+ }
44
+ blockquote.type-danger img[src^="https://twemoji."]
45
+ {
46
+ margin-right: 2px;
47
+ }
48
+ blockquote > p:first-child::before,
49
+ /* blockquote > p:first-of-type::before, */
50
+ blockquote > div.paragraph:first-child::before {
51
+ font-family: emoji;
52
+ content: 'ℹ️';
53
+ margin-right: 7px;
54
+ }
@@ -0,0 +1,78 @@
1
+ export { Warning }
2
+ export { Construction }
3
+ export { Danger }
4
+ export { NoteWithoutIcon }
5
+ export { NoteWithCustomIcon }
6
+ /* Use markdown instead:
7
+ * ```diff
8
+ * - <Note>Some note</Note>
9
+ * + > Some note
10
+ * ```
11
+ export { Note }
12
+ */
13
+
14
+ import React from 'react'
15
+ import { assert } from '../utils/assert'
16
+ /* Imorted in /src/css/index.css instead
17
+ import './Note.css'
18
+ */
19
+
20
+ function Warning({ children }: { children: React.ReactNode }) {
21
+ return <NoteGeneric type="warning">{children}</NoteGeneric>
22
+ }
23
+ function Construction({ children }: { children: React.ReactNode }) {
24
+ return <NoteGeneric type="construction">{children}</NoteGeneric>
25
+ }
26
+ function Danger({ children }: { children: React.ReactNode }) {
27
+ return <NoteGeneric type="danger">{children}</NoteGeneric>
28
+ }
29
+ function NoteWithoutIcon({ children }: { children: React.ReactNode }) {
30
+ return <NoteGeneric icon={null}>{children}</NoteGeneric>
31
+ }
32
+ type CustomIcon = JSX.Element | string
33
+ function NoteWithCustomIcon({ icon, children }: { children: React.ReactNode; icon: CustomIcon }) {
34
+ if (!icon) throw new Error(`<NoteWithCustomIcon icon={/*...*/}> property 'icon' is \`${icon}\` which is forbidden`)
35
+ return <NoteGeneric icon={icon}>{children}</NoteGeneric>
36
+ }
37
+
38
+ function NoteGeneric({
39
+ type,
40
+ icon,
41
+ children
42
+ }: {
43
+ icon?: null | CustomIcon
44
+ type?: 'danger' | 'warning' | 'construction'
45
+ children: React.ReactNode
46
+ }) {
47
+ assert(icon === null || icon || type, { icon, type })
48
+
49
+ let className = 'custom-icon'
50
+ if (type) {
51
+ className = `${className} type-${type}`
52
+ }
53
+ if (!icon && type) {
54
+ let classColor = ''
55
+ if (type === 'danger') {
56
+ icon = ':no_entry:'
57
+ classColor = 'note-color-red'
58
+ }
59
+ if (type === 'warning') {
60
+ icon = ':warning:'
61
+ classColor = 'note-color-yellow'
62
+ }
63
+ if (type === 'construction') {
64
+ icon = ':construction:'
65
+ classColor = 'note-color-yellow'
66
+ }
67
+ assert(icon)
68
+ assert(classColor)
69
+ className = `${className} ${classColor}`
70
+ }
71
+ return (
72
+ <blockquote className={className}>
73
+ <div style={{ marginBottom: 20 }} />
74
+ {icon} <div className="blockquote-content">{children}</div>
75
+ <div style={{ marginTop: 20 }} />
76
+ </blockquote>
77
+ )
78
+ }
@@ -0,0 +1,8 @@
1
+ /* Copied from Chrome's user agent stylesheet */
2
+ div.paragraph {
3
+ display: block;
4
+ margin-block-start: 1em;
5
+ margin-block-end: 1em;
6
+ margin-inline-start: 0px;
7
+ margin-inline-end: 0px;
8
+ }
@@ -0,0 +1,8 @@
1
+ import React from 'react'
2
+ import './P.css'
3
+
4
+ export { P }
5
+
6
+ function P(props: React.HTMLProps<HTMLDivElement>) {
7
+ return <div {...props} className={'paragraph'} />
8
+ }
@@ -0,0 +1,56 @@
1
+ import React from 'react'
2
+ import { Link } from './Link'
3
+
4
+ export { ReadingRecommendation }
5
+
6
+ function ReadingRecommendation({ tour, links }: { tour?: true; links?: string[] }) {
7
+ links ??= []
8
+ if (!links.length) tour = true
9
+ const multiple = links.length + (tour ? 1 : 0) > 1
10
+ const intro = <b>Reading Recommendation{multiple ? '.' : ': '}</b>
11
+ return (
12
+ <blockquote>
13
+ {(() => {
14
+ if (!multiple) {
15
+ const link = tour ? <TourLink /> : <Link href={links[0]} />
16
+ return (
17
+ <p>
18
+ {intro}
19
+ {link}
20
+ </p>
21
+ )
22
+ }
23
+ return (
24
+ <>
25
+ <p> {intro}</p>
26
+ <ul
27
+ style={{
28
+ marginLeft: 18,
29
+ marginTop: 11
30
+ }}
31
+ >
32
+ {tour && (
33
+ <li>
34
+ <TourLink />
35
+ </li>
36
+ )}
37
+ {links.map((link, i) => (
38
+ <li key={i}>
39
+ <Link href={link} />
40
+ </li>
41
+ ))}
42
+ </ul>
43
+ </>
44
+ )
45
+ })()}
46
+ </blockquote>
47
+ )
48
+ }
49
+
50
+ function TourLink() {
51
+ return (
52
+ <>
53
+ <Link href={'/react-tour'} noBreadcrumb={true} /> or <Link href={'/vue-tour'} noBreadcrumb={true} />
54
+ </>
55
+ )
56
+ }
@@ -0,0 +1,24 @@
1
+ import React from 'react'
2
+ import { assert } from '../utils/server'
3
+ import { usePageContext } from '../renderer/usePageContext'
4
+
5
+ export { RepoLink }
6
+ export { isRepoLink }
7
+
8
+ function isRepoLink(href: string) {
9
+ return ['/examples/', '/docs/', '/boilerplates/', '.github/', '/test/'].some((start) => href.startsWith(start))
10
+ }
11
+
12
+ function RepoLink({ path, text, editMode }: { path: string; text?: string | JSX.Element; editMode?: true }) {
13
+ const pageContext = usePageContext()
14
+ assert(isRepoLink(path), { path })
15
+ text = text || path
16
+ if (!path.startsWith('/')) {
17
+ path = '/' + path
18
+ }
19
+ const viewMode = path.endsWith('/') || editMode ? 'tree' : 'blob'
20
+ const { githubRepository } = pageContext.config.projectInfo
21
+ assert(githubRepository.startsWith('https://github.com/'))
22
+ const href = `${githubRepository}/${viewMode}/main${path}`
23
+ return <a href={href}>{text}</a>
24
+ }
@@ -0,0 +1,108 @@
1
+ <?xml version="1.0" encoding="UTF-8" standalone="no"?>
2
+ <!-- Created with Inkscape (http://www.inkscape.org/) -->
3
+
4
+ <svg
5
+ xmlns:dc="http://purl.org/dc/elements/1.1/"
6
+ xmlns:cc="http://creativecommons.org/ns#"
7
+ xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
8
+ xmlns:svg="http://www.w3.org/2000/svg"
9
+ xmlns="http://www.w3.org/2000/svg"
10
+ xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
11
+ xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
12
+ width="210mm"
13
+ height="297mm"
14
+ viewBox="0 0 210 297"
15
+ version="1.1"
16
+ id="svg8"
17
+ inkscape:version="0.92.4 (5da689c313, 2019-01-14)"
18
+ sodipodi:docname="label.draft.svg">
19
+ <defs
20
+ id="defs2" />
21
+ <sodipodi:namedview
22
+ id="base"
23
+ pagecolor="#ffffff"
24
+ bordercolor="#666666"
25
+ borderopacity="1.0"
26
+ inkscape:pageopacity="0.0"
27
+ inkscape:pageshadow="2"
28
+ inkscape:zoom="0.9899495"
29
+ inkscape:cx="461.6406"
30
+ inkscape:cy="96.846632"
31
+ inkscape:document-units="mm"
32
+ inkscape:current-layer="layer1"
33
+ showgrid="false"
34
+ inkscape:window-width="1366"
35
+ inkscape:window-height="736"
36
+ inkscape:window-x="0"
37
+ inkscape:window-y="16"
38
+ inkscape:window-maximized="1" />
39
+ <metadata
40
+ id="metadata5">
41
+ <rdf:RDF>
42
+ <cc:Work
43
+ rdf:about="">
44
+ <dc:format>image/svg+xml</dc:format>
45
+ <dc:type
46
+ rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
47
+ <dc:title></dc:title>
48
+ </cc:Work>
49
+ </rdf:RDF>
50
+ </metadata>
51
+ <g
52
+ inkscape:label="Layer 1"
53
+ inkscape:groupmode="layer"
54
+ id="layer1">
55
+ <path
56
+ style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
57
+ d="m 51.40476,117.83928 13.530744,-23.435929 0.01098,0.0063 v 0"
58
+ id="path815"
59
+ inkscape:connector-curvature="0" />
60
+ <path
61
+ style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
62
+ d="M 78.309972,119.26576 90.337099,96.280583 h 32.339611"
63
+ id="path817"
64
+ inkscape:connector-curvature="0"
65
+ sodipodi:nodetypes="ccc" />
66
+ <path
67
+ style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
68
+ d="M 71.815475,146.56548 H 85.96596 c 0.676332,-0.0209 3.30147,-0.005 3.934153,-0.83721 0.426501,-0.36462 1.272256,-1.92024 1.602106,-2.49156 l 4.177131,-7.23501 c 0,0 0.679705,-1.34341 1.817605,-2.11076 0.472523,-0.30451 3.063205,-0.4009 3.063205,-0.4009 h 13.21067"
69
+ id="path819"
70
+ inkscape:connector-curvature="0"
71
+ sodipodi:nodetypes="cccccccc" />
72
+ <path
73
+ sodipodi:nodetypes="cccccccc"
74
+ inkscape:connector-curvature="0"
75
+ id="path859"
76
+ d="m 145.52085,146.56548 h -14.15049 c -0.67633,-0.0209 -3.30147,-0.005 -3.93415,-0.83721 -0.4265,-0.36462 -1.27226,-1.92024 -1.60211,-2.49156 l -4.17713,-7.23501 c 0,0 -0.67971,-1.34341 -1.81761,-2.11076 -0.47252,-0.30451 -3.0632,-0.4009 -3.0632,-0.4009 h -13.21068"
77
+ style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
78
+ <path
79
+ sodipodi:nodetypes="ccccccccc"
80
+ inkscape:connector-curvature="0"
81
+ id="path967"
82
+ d="m 118.49554,172.57638 -47.05804,0 h 10.748698 c 0.676332,-0.0209 3.30147,-0.005 3.934153,-0.83721 0.426501,-0.36462 1.272256,-1.92024 1.602106,-2.49156 l 4.177131,-7.23501 c 0,0 0.679705,-1.34341 1.817605,-2.11076 0.472523,-0.30451 3.063205,-0.4009 3.063205,-0.4009 l 22.282102,0"
83
+ style="fill:none;stroke:#000000;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1" />
84
+ <path
85
+ style="fill:#f0f0f0;stroke:none;stroke-width:0.99999994px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;fill-opacity:1"
86
+ d="M 365.78516 702.83789 C 365.78516 702.83789 355.99294 703.20261 354.20703 704.35352 C 349.90631 707.25374 347.33789 712.33203 347.33789 712.33203 L 331.54883 739.67578 C 330.30215 741.8351 327.10611 747.71566 325.49414 749.09375 C 323.1029 752.23911 313.18122 752.17882 310.625 752.25781 L 392.14258 752.25781 L 447.85742 752.25781 L 529.375 752.25781 C 526.81879 752.17882 516.89709 752.23911 514.50586 749.09375 C 512.89389 747.71566 509.69785 741.8351 508.45117 739.67578 L 492.66211 712.33203 C 492.66211 712.33203 490.09369 707.25374 485.79297 704.35352 C 484.00707 703.20261 474.2168 702.83789 474.2168 702.83789 L 450 702.83789 L 390 702.83789 L 365.78516 702.83789 z "
87
+ transform="scale(0.26458333)"
88
+ id="path977" />
89
+ <path
90
+ id="path982"
91
+ d="m 96.780656,212.41754 c 0,0 -2.590858,0.0965 -3.06338,0.40101 -1.137899,0.76735 -1.81746,2.11098 -1.81746,2.11098 l -4.177523,7.2347 c -0.32985,0.57132 -1.175469,2.12722 -1.60197,2.49184 -0.632682,0.83221 -3.257793,0.81625 -3.934126,0.83715 h 21.568193 30.61622 21.56819 c -0.67633,-0.0209 -3.30145,-0.005 -3.93413,-0.83715 -0.4265,-0.36462 -1.27212,-1.92052 -1.60197,-2.49184 l -4.17752,-7.2347 c 0,0 -0.67956,-1.34363 -1.81746,-2.11098 -0.47252,-0.30452 -3.06286,-0.40101 -3.06286,-0.40101 h -6.40736 -31.75 z"
92
+ style="fill:#f0f0f0;fill-opacity:1;stroke:none;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
93
+ inkscape:connector-curvature="0"
94
+ sodipodi:nodetypes="ccccccccccccccccc" />
95
+ <path
96
+ sodipodi:nodetypes="ccccccccccccccccc"
97
+ inkscape:connector-curvature="0"
98
+ style="fill:#f0f0f0;fill-opacity:1;stroke:none;stroke-width:0.26458332px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
99
+ d="m 96.780656,244.16756 c 0,0 -2.590858,0.0965 -3.06338,0.40101 -1.137899,0.76735 -1.81746,2.11098 -1.81746,2.11098 l -4.177523,7.2347 c -0.32985,0.57132 -1.175469,2.12722 -1.60197,2.49184 -0.632682,0.83221 -3.257793,0.81625 -3.934126,0.83715 h 21.568193 25.32455 21.56819 c -0.67633,-0.0209 -3.30145,-0.005 -3.93413,-0.83715 -0.4265,-0.36462 -1.27212,-1.92052 -1.60197,-2.49184 l -4.17752,-7.2347 c 0,0 -0.67956,-1.34363 -1.81746,-2.11098 -0.47252,-0.30452 -3.06286,-0.40101 -3.06286,-0.40101 h -6.40736 -26.45833 z"
100
+ id="path984" />
101
+ <path
102
+ id="path878"
103
+ d="m 103.72033,265.33423 c 0,0 -2.25707,0.0965 -2.66872,0.40101 -0.9913,0.76735 -1.583315,2.11098 -1.583315,2.11098 l -3.639329,7.2347 c -0.287355,0.57132 -1.024032,2.12722 -1.395586,2.49184 -0.551173,0.83221 -2.838088,0.81625 -3.427289,0.83715 h 18.789539 22.06196 18.78954 c -0.5892,-0.0209 -2.87612,-0.005 -3.42729,-0.83715 -0.37156,-0.36462 -1.10823,-1.92052 -1.39559,-2.49184 l -3.63932,-7.2347 c 0,0 -0.59202,-1.34363 -1.58332,-2.11098 -0.41164,-0.30452 -2.66827,-0.40101 -2.66827,-0.40101 h -5.58189 -23.04968 z"
104
+ style="fill:#f0f0f0;fill-opacity:1;stroke:none;stroke-width:0.24695262px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
105
+ inkscape:connector-curvature="0"
106
+ sodipodi:nodetypes="ccccccccccccccccc" />
107
+ </g>
108
+ </svg>
@@ -0,0 +1,218 @@
1
+ export { Sponsors }
2
+ export type { Sponsor }
3
+
4
+ import React from 'react'
5
+ import iconHeart from '../icons/heart.svg'
6
+ import { usePageContext } from '../renderer/usePageContext'
7
+ import { assert, Emoji } from '../utils/server'
8
+ import { Supporter, SupporterSection, SectionDescription, Individuals, SupporterImg, CallToAction } from './Supporters'
9
+ import medalGold from './Sponsors/medalGold.svg'
10
+ import medalSilver from './Sponsors/medalSilver.svg'
11
+ import medalBronze from './Sponsors/medalBronze.svg'
12
+ import labelBgImg from './Sponsors/label.svg'
13
+ import { sponsorsList } from '../data/sponsorsList'
14
+
15
+ type Plan = 'indie' | 'bronze' | 'silver' | 'gold' | 'platinum'
16
+
17
+ type SponsorCompany = {
18
+ companyName: string
19
+ companyLogo: string
20
+ website: string
21
+ plan: Plan
22
+ divSize?: Partial<DivSize>
23
+ github: string
24
+ }
25
+ type SponsorIndividual = {
26
+ username: string
27
+ }
28
+ type Sponsor = SponsorCompany | SponsorIndividual
29
+
30
+ type DivSize = {
31
+ width: number
32
+ height: number
33
+ padding: number
34
+ }
35
+
36
+ function Sponsors() {
37
+ const pageContext = usePageContext()
38
+ const { projectInfo } = pageContext.config
39
+ const sponsorGithubAccount = pageContext.config.sponsorGithubAccount || 'brillout'
40
+ const sponsorsCompanies = sponsorsList.filter(isCompany)
41
+ const sponsorsIndividuals = sponsorsList.filter(isIndividual)
42
+ return (
43
+ <SupporterSection>
44
+ <CallToAction iconUrl={iconHeart} text="Sponsor" href={`https://github.com/sponsors/${sponsorGithubAccount}`} />
45
+ <div></div>
46
+ <SectionDescription>
47
+ {projectInfo.projectName} is free and open source, made possible by wonderful sponsors.
48
+ </SectionDescription>
49
+ <div style={{ display: 'flex', flexWrap: 'wrap', justifyContent: 'space-evenly', alignItems: 'end' }}>
50
+ {sponsorsCompanies.map((sponsor, i) => (
51
+ <SponsorDiv sponsor={sponsor} key={i} />
52
+ ))}
53
+ </div>
54
+ <Individuals>
55
+ {sponsorsIndividuals.map((sponsor, i) => (
56
+ <SponsorDiv sponsor={sponsor} key={i} />
57
+ ))}
58
+ </Individuals>
59
+ </SupporterSection>
60
+ )
61
+ }
62
+
63
+ function SponsorDiv({ sponsor }: { sponsor: Sponsor }) {
64
+ if (isIndividual(sponsor)) {
65
+ return <Supporter username={sponsor.username} />
66
+ }
67
+ return <CompanyDiv sponsor={sponsor} />
68
+ }
69
+
70
+ function CompanyDiv({ sponsor }: { sponsor: Sponsor }) {
71
+ assert(isCompany(sponsor))
72
+ const imgSrc = sponsor.companyLogo
73
+ const imgAlt = sponsor.companyName
74
+ const { width, height, padding } = getSize(sponsor)
75
+ const marginHeight = 20
76
+ const marginWidth = 10
77
+ return (
78
+ <a
79
+ href={sponsor.website}
80
+ style={{
81
+ margin: `${marginHeight}px ${marginWidth}px`
82
+ }}
83
+ >
84
+ <Label sponsor={sponsor} />
85
+ <div
86
+ style={{
87
+ backgroundColor: '#f0f0f0',
88
+ borderRadius: 7,
89
+ overflow: 'hidden',
90
+ width,
91
+ maxWidth: `calc(100vw - 2 * var(--main-view-padding) - 2 * ${marginWidth}px)`,
92
+ height,
93
+ display: 'flex',
94
+ alignItems: 'center',
95
+ flexDirection: 'column',
96
+ justifyContent: 'center'
97
+ }}
98
+ >
99
+ <SupporterImg {...{ imgSrc, imgAlt, width, height, padding }} />
100
+ </div>
101
+ </a>
102
+ )
103
+ }
104
+
105
+ function Label({ sponsor }: { sponsor: Sponsor }) {
106
+ assert(isCompany(sponsor))
107
+ const labelBg = getLabelBg(sponsor)
108
+ const labelIcon = getLabelIcon(sponsor)
109
+ const labelText = getLabelText(sponsor)
110
+ return (
111
+ <div
112
+ style={{
113
+ top: 0,
114
+ display: 'flex',
115
+ justifyContent: 'center',
116
+ alignItems: 'center',
117
+ position: 'relative',
118
+ paddingBottom: 1
119
+ }}
120
+ >
121
+ {labelBg}
122
+ {labelIcon}
123
+ {labelText}
124
+ </div>
125
+ )
126
+ }
127
+
128
+ function getLabelBg(sponsor: SponsorCompany) {
129
+ const height = sponsor.plan === 'platinum' ? 32 : 24
130
+ return <img src={labelBgImg} style={{ height, position: 'absolute', bottom: 0, zIndex: -1 }} />
131
+ }
132
+
133
+ function getLabelText(sponsor: SponsorCompany) {
134
+ if (sponsor.plan === 'platinum') {
135
+ return <></>
136
+ }
137
+ let letterSpacing: number | undefined = undefined
138
+ if (['bronze', 'silver', 'gold', 'indie'].includes(sponsor.plan)) {
139
+ letterSpacing = 1
140
+ }
141
+ /*
142
+ if (sponsor.plan === 'indie') {
143
+ letterSpacing = 2
144
+ }
145
+ */
146
+ return (
147
+ <>
148
+ {' '}
149
+ <span
150
+ style={{
151
+ zIndex: 1,
152
+ fontSize: '0.82em',
153
+ position: 'relative',
154
+ top: 0,
155
+ fontWeight: 500,
156
+ color: '#666',
157
+ letterSpacing
158
+ }}
159
+ >
160
+ {capitalizeFirstLetter(sponsor.plan)}
161
+ </span>
162
+ </>
163
+ )
164
+ }
165
+
166
+ function getLabelIcon(sponsor: SponsorCompany) {
167
+ let medalSrc: string
168
+ if (sponsor.plan === 'platinum') {
169
+ return <Emoji name="trophy" style={{ fontSize: '1.3em' }} />
170
+ } else if (sponsor.plan === 'indie') {
171
+ return <Emoji name="ribbon" style={{ fontSize: '0.9em' /*, position: 'relative', top: -1*/ }} />
172
+ } else if (sponsor.plan === 'gold') {
173
+ medalSrc = medalGold
174
+ } else if (sponsor.plan === 'silver') {
175
+ medalSrc = medalSilver
176
+ } else if (sponsor.plan === 'bronze') {
177
+ medalSrc = medalBronze
178
+ } else {
179
+ assert(false)
180
+ }
181
+ return <img src={medalSrc} style={{ height: 15, zIndex: 1, marginRight: 5 }} />
182
+ }
183
+
184
+ function getSize(sponsor: SponsorCompany): DivSize {
185
+ const { plan } = sponsor
186
+ let divSize: DivSize | undefined
187
+ if (plan === 'platinum') {
188
+ divSize = { width: 500, height: 180, padding: 100 }
189
+ }
190
+ if (plan === 'gold') {
191
+ divSize = { width: 400, height: 150, padding: 95 }
192
+ }
193
+ if (plan === 'silver') {
194
+ divSize = { width: 300, height: 100, padding: 45 }
195
+ }
196
+ if (plan === 'bronze') {
197
+ divSize = { width: 200, height: 70, padding: 30 }
198
+ }
199
+ if (plan === 'indie') {
200
+ divSize = { width: 140, height: 50, padding: 20 }
201
+ }
202
+ assert(divSize)
203
+ if (sponsor.divSize) {
204
+ Object.assign(divSize, sponsor.divSize)
205
+ }
206
+ return divSize
207
+ }
208
+
209
+ function capitalizeFirstLetter(word: string): string {
210
+ return word[0].toUpperCase() + word.slice(1)
211
+ }
212
+
213
+ function isCompany(sponsor: Sponsor): sponsor is SponsorCompany {
214
+ return !isIndividual(sponsor)
215
+ }
216
+ function isIndividual(sponsor: Sponsor): sponsor is SponsorIndividual {
217
+ return 'username' in sponsor
218
+ }
@@ -0,0 +1,136 @@
1
+ // supporters = sponsors + contributors
2
+
3
+ export { Supporter, SupporterSection, SectionDescription, Individuals, SupporterImg, CallToAction }
4
+
5
+ import React from 'react'
6
+
7
+ type Children = (string | JSX.Element) | (string | JSX.Element)[]
8
+
9
+ function SupporterSection({ children }: { children?: Children }) {
10
+ return (
11
+ <div
12
+ style={{
13
+ textAlign: 'center',
14
+ marginTop: 19
15
+ }}
16
+ >
17
+ {children}
18
+ </div>
19
+ )
20
+ }
21
+
22
+ function SectionDescription({ children }: { children?: Children }) {
23
+ return (
24
+ <div
25
+ style={{
26
+ maxWidth: 400,
27
+ display: 'inline-block',
28
+ marginTop: 12,
29
+ marginBottom: 12
30
+ }}
31
+ >
32
+ {children}
33
+ </div>
34
+ )
35
+ }
36
+
37
+ function Individuals({ children }: { children?: Children }) {
38
+ return (
39
+ <div
40
+ style={{
41
+ display: 'flex',
42
+ flexWrap: 'wrap',
43
+ justifyContent: 'center',
44
+ alignItems: 'end',
45
+ margin: '17px auto',
46
+ maxWidth: 700
47
+ }}
48
+ >
49
+ {children}
50
+ </div>
51
+ )
52
+ }
53
+
54
+ // Individual sponsor or small contributor
55
+ function Supporter({ username, avatarUrl }: { username: string; avatarUrl?: string }) {
56
+ const website = `https://github.com/${username}`
57
+ const width = 30
58
+ const height = 30
59
+ const marginWidth = 5
60
+ const marginHeight = 5
61
+ return (
62
+ <a
63
+ href={website}
64
+ style={{
65
+ margin: `${marginHeight}px ${marginWidth}px`
66
+ }}
67
+ >
68
+ <div
69
+ style={{
70
+ borderRadius: 7,
71
+ overflow: 'hidden',
72
+ width,
73
+ height,
74
+ display: 'flex',
75
+ alignItems: 'center',
76
+ flexDirection: 'column',
77
+ justifyContent: 'center'
78
+ }}
79
+ >
80
+ <SupporterImg {...{ username, avatarUrl, width, height }} />
81
+ </div>
82
+ </a>
83
+ )
84
+ }
85
+
86
+ function SupporterImg({
87
+ imgSrc, // has precedence over avatarUrl
88
+ avatarUrl, // has precedence over username
89
+ username,
90
+ imgAlt,
91
+ width,
92
+ height,
93
+ padding = 0
94
+ }: {
95
+ imgSrc?: string
96
+ avatarUrl?: string
97
+ username?: string
98
+ imgAlt?: string
99
+ width: number
100
+ height: number
101
+ padding?: number
102
+ }) {
103
+ const size = Math.max(width, height)
104
+ if (avatarUrl) {
105
+ imgSrc = imgSrc || `${avatarUrl}&size=${size}`
106
+ }
107
+ if (username) {
108
+ imgSrc = imgSrc || `https://github.com/${username}.png?size=${size}`
109
+ imgAlt = imgAlt || username
110
+ }
111
+ return (
112
+ <img
113
+ style={{ width: `calc(100% - ${padding}px)`, height: height - padding, zIndex: 2, objectFit: 'contain' }}
114
+ src={imgSrc}
115
+ alt={imgAlt}
116
+ />
117
+ )
118
+ }
119
+
120
+ function CallToAction({ iconUrl, text, href }: { iconUrl: string; text: string; href: string }) {
121
+ return (
122
+ <a
123
+ className="button"
124
+ style={{
125
+ color: 'inherit',
126
+ display: 'inline-flex',
127
+ alignItems: 'center',
128
+ padding: '5px 10px',
129
+ marginBottom: 10
130
+ }}
131
+ href={href}
132
+ >
133
+ <img src={iconUrl} height={22} /> <span style={{ marginLeft: 7, fontSize: '1.07em' }}>{text}</span>
134
+ </a>
135
+ )
136
+ }