@unvt/charites 0.3.0 → 0.4.0
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/.eslintrc.js +1 -1
- package/.github/workflows/build-docs.yml +4 -4
- package/.github/workflows/build.yml +8 -7
- package/dist/cli/build.js +4 -4
- package/dist/cli/convert.js +2 -2
- package/dist/cli/init.js +3 -3
- package/dist/cli/serve.js +7 -3
- package/dist/commands/build.js +7 -12
- package/dist/commands/convert.js +2 -12
- package/dist/commands/init.js +1 -1
- package/dist/commands/serve.js +65 -12
- package/dist/lib/build-sprite.js +6 -8
- package/dist/lib/error.js +2 -1
- package/dist/lib/tileinfo-importer/index.js +1 -0
- package/dist/lib/yaml-writer.js +21 -12
- package/dist/types/index.js +6 -2
- package/docs/Pipfile.lock +136 -193
- package/docs/source/index.rst +2 -2
- package/docs/source/install/img/windows-guide-01.png +0 -0
- package/docs/source/install/index.rst +1 -0
- package/docs/source/install/install.rst +1 -0
- package/docs/source/install/install_on_nanban.rst +1 -1
- package/docs/source/install/installation_guide_for_windows.rst +52 -0
- package/docs/source/install/recommended_environment.rst +2 -2
- package/docs/source/usage/commandline_interface.rst +21 -8
- package/docs/source/usage/example2.rst +166 -0
- package/docs/source/usage/img/example02-001.png +0 -0
- package/docs/source/usage/img/example02-002.png +0 -0
- package/docs/source/usage/img/example02-003.png +0 -0
- package/docs/source/usage/img/example02-004.png +0 -0
- package/docs/source/usage/img/example02-005.png +0 -0
- package/docs/source/usage/img/example02-006.png +0 -0
- package/docs/source/usage/img/example02-007.png +0 -0
- package/docs/source/usage/img/example02-008.png +0 -0
- package/docs/source/usage/img/example02-009.png +0 -0
- package/docs/source/usage/img/example02-010.png +0 -0
- package/docs/source/usage/img/example02-011.png +0 -0
- package/docs/source/usage/img/example02-012.png +0 -0
- package/docs/source/usage/img/example02-013.png +0 -0
- package/docs/source/usage/img/example02-014.png +0 -0
- package/docs/source/usage/img/example02-015.png +0 -0
- package/docs/source/usage/img/example02-016.png +0 -0
- package/docs/source/usage/img/example02-017.png +0 -0
- package/docs/source/usage/img/example02-018.png +0 -0
- package/docs/source/usage/index.rst +1 -0
- package/package.json +31 -29
- package/provider/default/app.js +1 -3
- package/provider/default/index.html +2 -2
- package/provider/default/shared.js +11 -2
- package/provider/geolonia/app.js +1 -3
- package/provider/mapbox/app.js +1 -3
- package/src/cli/init.ts +1 -1
- package/src/cli/serve.ts +9 -2
- package/src/commands/build.ts +2 -6
- package/src/commands/convert.ts +2 -10
- package/src/commands/init.ts +1 -1
- package/src/commands/serve.ts +80 -11
- package/src/lib/build-sprite.ts +2 -6
- package/src/lib/get-sprite-slug.ts +1 -1
- package/src/lib/tileinfo-importer/base-importer.ts +1 -1
- package/src/lib/tileinfo-importer/metadata-importer.ts +1 -1
- package/src/lib/tileinfo-importer/tilejson-importer.ts +1 -1
- package/src/lib/validate-style.ts +1 -1
- package/src/lib/yaml-parser.ts +1 -1
- package/src/lib/yaml-writer.ts +23 -14
- package/test/build.spec.ts +2 -2
- package/test/command.serve.spec.ts +103 -0
- package/test/convert.spec.ts +24 -4
- package/test/data/convert.json +7 -0
- package/test/init.spec.ts +7 -5
- package/test/util/charitesCmd.ts +3 -1
- package/test/util/execPromise.ts +51 -1
- package/test/util/index.ts +3 -0
- package/test/validate-style.spec.ts +1 -1
|
@@ -0,0 +1,166 @@
|
|
|
1
|
+
Example 2: Import existing style.json and edit it with charites
|
|
2
|
+
===================================================================
|
|
3
|
+
This is an example of using charites for importing an existing style.json and editing it as yaml files, and exporting them back to a json style.
|
|
4
|
+
|
|
5
|
+
Condition
|
|
6
|
+
------------------------
|
|
7
|
+
- OS: Windows 10
|
|
8
|
+
- Charites version: 0.3.0
|
|
9
|
+
- Running on WindowsPowershell
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
Steps
|
|
13
|
+
-----
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
Step 1. Import style json into a series of YAML files
|
|
17
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
18
|
+
|
|
19
|
+
If your style json is in the Internet, it may need to downloat it from the Internet before you convert because charites cannot directly convert json a file in the Internet. Use curl.exe (in WindowsPowershell) or curl (in bash environment).
|
|
20
|
+
|
|
21
|
+
.. code-block::
|
|
22
|
+
|
|
23
|
+
curl.exe -O https://ubukawa.github.io/cmv-test/style1.json
|
|
24
|
+
charites convert style1.json editing/style.yml
|
|
25
|
+
|
|
26
|
+
Then, you will see a series of yaml files are converted from the source json. You will obtain an overall YAML that contains a list of style layers with the style yamls in the layer directory.
|
|
27
|
+
In this case, we will have "style.yml" in "editing" directory together with a lot of yaml files for layers in "layers" directory.
|
|
28
|
+
|
|
29
|
+
.. image:: ./img/example02-001.png
|
|
30
|
+
:scale: 75%
|
|
31
|
+
:align: center
|
|
32
|
+
|
|
33
|
+
.. image:: ./img/example02-002.png
|
|
34
|
+
:scale: 75%
|
|
35
|
+
:align: center
|
|
36
|
+
|
|
37
|
+
(Tips) It is good to know that if your source json has some folder structure in its layer ids, that structure would be maintained when you import.
|
|
38
|
+
|
|
39
|
+
.. image:: ./img/example02-005.png
|
|
40
|
+
:scale: 75%
|
|
41
|
+
:align: center
|
|
42
|
+
|
|
43
|
+
.. image:: ./img/example02-003.png
|
|
44
|
+
:scale: 75%
|
|
45
|
+
:align: center
|
|
46
|
+
|
|
47
|
+
.. image:: ./img/example02-004.png
|
|
48
|
+
:scale: 75%
|
|
49
|
+
:align: center
|
|
50
|
+
|
|
51
|
+
Step 2. Checking an overall yaml (style.yml in this case)
|
|
52
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
53
|
+
Check the style.yml by opening it with Notepad or any text editor. You will see it like this:
|
|
54
|
+
|
|
55
|
+
.. image:: ./img/example02-006.png
|
|
56
|
+
:scale: 75%
|
|
57
|
+
:align: center
|
|
58
|
+
|
|
59
|
+
Although it is not often seen, we need to check one thing. Sometimes, if id for each layer is too long, YAML automatically uses ">-" and break the line to improve human's readability. ">-" would pretend an actual line break in YAML, however, it will cause some problem for Charites, so please fix line brakes with ">-" in the layers if you find them.
|
|
60
|
+
This is often seen in style files from Esri vector tile because it has detailed folder structure sometimes.
|
|
61
|
+
|
|
62
|
+
.. image:: ./img/example02-007.png
|
|
63
|
+
:scale: 75%
|
|
64
|
+
:align: center
|
|
65
|
+
|
|
66
|
+
.. image:: ./img/example02-008.png
|
|
67
|
+
:scale: 75%
|
|
68
|
+
:align: center
|
|
69
|
+
|
|
70
|
+
You can extract layers and use "replace" tool to remove ">-" and unnecessary line changes.
|
|
71
|
+
|
|
72
|
+
.. image:: ./img/example02-009.png
|
|
73
|
+
:scale: 75%
|
|
74
|
+
:align: center
|
|
75
|
+
|
|
76
|
+
.. image:: ./img/example02-010.png
|
|
77
|
+
:scale: 75%
|
|
78
|
+
:align: center
|
|
79
|
+
|
|
80
|
+
If you obtain the list of layers without ">-", you are ready to go to the next step.
|
|
81
|
+
|
|
82
|
+
.. image:: ./img/example02-011.png
|
|
83
|
+
:scale: 75%
|
|
84
|
+
:align: center
|
|
85
|
+
|
|
86
|
+
.. note::
|
|
87
|
+
|
|
88
|
+
You may also need to check paths in "sprite", "glyphs" and "sources." They would be written as relative paths, so you may need to adjust these paths so that charites in your local PC can access to them. In addition, if you are importing styles from ArcGIS server, reference to the source should be modifyed (use "tiles" instead of "url"). The "tiles" URL will be provided by adding "/tile/{z}/{y}/{x}.pbf" in the end of Esri vector tile server URL.
|
|
89
|
+
|
|
90
|
+
|
|
91
|
+
Step 3. Serve YAML files for live preview
|
|
92
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
93
|
+
|
|
94
|
+
Run the "charites serve" command to serve your YAML files in the localhost. By default, its port is 8080.
|
|
95
|
+
|
|
96
|
+
.. code-block::
|
|
97
|
+
|
|
98
|
+
charites serve editing/style.yml
|
|
99
|
+
|
|
100
|
+
A window would automatically appears in the windows environment, but if not please open "http://localhost:8080" to access your live view. You can stop the live preview by pressing ctrl + c.
|
|
101
|
+
|
|
102
|
+
.. image:: ./img/example02-012.png
|
|
103
|
+
:scale: 75%
|
|
104
|
+
:align: center
|
|
105
|
+
|
|
106
|
+
Step 4. Editing YAML files to change style
|
|
107
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
108
|
+
You can change/edit the map style by editing YAML files. If you edit and save your update, charites automatically finds your updates to reflect them into the live view.
|
|
109
|
+
|
|
110
|
+
.. image:: ./img/example02-016.png
|
|
111
|
+
:scale: 75%
|
|
112
|
+
:align: center
|
|
113
|
+
|
|
114
|
+
Here are some tips for efficient style editing.
|
|
115
|
+
|
|
116
|
+
(Tips 1) Legend control
|
|
117
|
+
########################
|
|
118
|
+
There is a legend control in the lower left of the screen. You can turn on/off any layers so that your edit would be easy. It will also help you to identify layers that should be edited.
|
|
119
|
+
You can enlarge the window by clicking the button, and reduce its size by clicking "x" in the window. You can also choose to list only rendered layers or not in the window.
|
|
120
|
+
|
|
121
|
+
.. image:: ./img/example02-013.png
|
|
122
|
+
:scale: 75%
|
|
123
|
+
:align: center
|
|
124
|
+
|
|
125
|
+
(Tips 2) Showing tile boundary
|
|
126
|
+
###############################
|
|
127
|
+
It would be alos helpful to show the tile boundary. There are checkbox in the upper left, and you can turn on/off. You will see tile border and its xyx in z/x/y order together with tile size. This would be useful when you also think about optimization of your vector tile.
|
|
128
|
+
|
|
129
|
+
.. image:: ./img/example02-014.png
|
|
130
|
+
:scale: 75%
|
|
131
|
+
:align: center
|
|
132
|
+
|
|
133
|
+
(Tips 3) Showing collision boxes
|
|
134
|
+
#################################
|
|
135
|
+
It would be alos helpful to show the collision boxes. If a box is red, it indicates a collision with others. When you adjust label location/size, this is good.
|
|
136
|
+
|
|
137
|
+
.. image:: ./img/example02-015.png
|
|
138
|
+
:scale: 75%
|
|
139
|
+
:align: center
|
|
140
|
+
|
|
141
|
+
(Tips 4) Use of "#" (comment tag) to specify error
|
|
142
|
+
###################################################
|
|
143
|
+
If there is a layer contains some error, the web map may not appears. In such a case, use a YAML comment tag "#" to comment out a layer (or layers) to specify the layer contains an error. The comment tag is also useful to tentatively change colors, etc.
|
|
144
|
+
|
|
145
|
+
(Tips 5) Use of inclusion of other YAML file for efficinet edit
|
|
146
|
+
################################################################
|
|
147
|
+
If you repeatedly use the same expression (color, font, etc) for several layers, it is conveninet to use a reference to a common expression. You can do it by using inclusion of an independent YAML file with "!!inc/file hogehoge.yml". This is particular important if you manage your style with YAML files.
|
|
148
|
+
|
|
149
|
+
.. image:: ./img/example02-017.png
|
|
150
|
+
:scale: 75%
|
|
151
|
+
:align: center
|
|
152
|
+
|
|
153
|
+
.. image:: ./img/example02-018.png
|
|
154
|
+
:scale: 75%
|
|
155
|
+
:align: center
|
|
156
|
+
|
|
157
|
+
Step 5. Exporting style json from YAML files
|
|
158
|
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
|
159
|
+
Once you have edited your style with YAML files, you can now export it back to json by running the following command.
|
|
160
|
+
|
|
161
|
+
.. code-block::
|
|
162
|
+
|
|
163
|
+
charites build editing/style.yml out.json
|
|
164
|
+
|
|
165
|
+
Congratulations. You will obtain the updated style json, and all done.
|
|
166
|
+
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@unvt/charites",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.4.0",
|
|
4
4
|
"description": "",
|
|
5
5
|
"bin": {
|
|
6
6
|
"charites": "dist/cli.js"
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
"build": "tsc -p .",
|
|
10
10
|
"watch": "tsc -w",
|
|
11
11
|
"lint": "eslint --fix .",
|
|
12
|
-
"test": "npm run build && mocha -r ts-node/register test/*.ts",
|
|
12
|
+
"test": "npm run build && mocha --timeout 5000 -r ts-node/register test/*.ts",
|
|
13
13
|
"test:watch": "npm test -- --watch --watch-files src/**/*.ts --watch-files test/**/*.ts",
|
|
14
14
|
"test:e2e": "npx playwright test",
|
|
15
15
|
"command": "./node_modules/.bin/ts-node ./src/cli.ts"
|
|
@@ -17,41 +17,43 @@
|
|
|
17
17
|
"author": "",
|
|
18
18
|
"license": "MIT",
|
|
19
19
|
"dependencies": {
|
|
20
|
-
"@mapbox/mapbox-gl-style-spec": "^13.
|
|
21
|
-
"@maplibre/maplibre-gl-style-spec": "^
|
|
22
|
-
"@unvt/sprite-one": "^0.0.8",
|
|
20
|
+
"@mapbox/mapbox-gl-style-spec": "^13.27.0",
|
|
21
|
+
"@maplibre/maplibre-gl-style-spec": "^17.0.2",
|
|
23
22
|
"@types/jsonminify": "^0.4.1",
|
|
24
|
-
"
|
|
25
|
-
"
|
|
26
|
-
"
|
|
23
|
+
"@unvt/sprite-one": "^0.0.9",
|
|
24
|
+
"axios": "^1.2.2",
|
|
25
|
+
"commander": "^9.4.1",
|
|
26
|
+
"glob": "^8.0.3",
|
|
27
27
|
"js-yaml": "^4.0.0",
|
|
28
|
-
"jsonminify": "^0.4.
|
|
29
|
-
"node-watch": "^0.7.
|
|
28
|
+
"jsonminify": "^0.4.2",
|
|
29
|
+
"node-watch": "^0.7.3",
|
|
30
30
|
"open": "^8.2.1",
|
|
31
|
-
"ws": "^8.
|
|
31
|
+
"ws": "^8.11.0",
|
|
32
32
|
"yaml-include": "^1.2.1"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
|
-
"@playwright/test": "^1.
|
|
36
|
-
"@types/chai": "^4.
|
|
35
|
+
"@playwright/test": "^1.29.1",
|
|
36
|
+
"@types/chai": "^4.3.4",
|
|
37
37
|
"@types/chai-as-promised": "^7.1.5",
|
|
38
38
|
"@types/fs-extra": "^9.0.13",
|
|
39
|
-
"@types/js-yaml": "^4.0.
|
|
40
|
-
"@types/
|
|
41
|
-
"@types/
|
|
42
|
-
"@types/
|
|
43
|
-
"@
|
|
44
|
-
"@typescript-eslint/
|
|
45
|
-
"
|
|
39
|
+
"@types/js-yaml": "^4.0.5",
|
|
40
|
+
"@types/mapbox__point-geometry": "^0.1.2",
|
|
41
|
+
"@types/mocha": "^10.0.1",
|
|
42
|
+
"@types/node": "^18.11.18",
|
|
43
|
+
"@types/ws": "^8.5.4",
|
|
44
|
+
"@typescript-eslint/eslint-plugin": "^5.47.1",
|
|
45
|
+
"@typescript-eslint/parser": "^5.47.1",
|
|
46
|
+
"chai": "^4.3.7",
|
|
46
47
|
"chai-as-promised": "^7.1.1",
|
|
47
|
-
"eslint": "^
|
|
48
|
-
"eslint-config-prettier": "^
|
|
49
|
-
"eslint-plugin-prettier": "^
|
|
50
|
-
"fs-extra": "^
|
|
51
|
-
"kill-port-process": "^3.0
|
|
52
|
-
"mocha": "^
|
|
53
|
-
"
|
|
54
|
-
"
|
|
55
|
-
"
|
|
48
|
+
"eslint": "^8.31.0",
|
|
49
|
+
"eslint-config-prettier": "^8.5.0",
|
|
50
|
+
"eslint-plugin-prettier": "^4.2.1",
|
|
51
|
+
"fs-extra": "^11.1.0",
|
|
52
|
+
"kill-port-process": "^3.1.0",
|
|
53
|
+
"mocha": "^10.2.0",
|
|
54
|
+
"node-abort-controller": "^3.0.1",
|
|
55
|
+
"prettier": "^2.8.1",
|
|
56
|
+
"ts-node": "^10.9.1",
|
|
57
|
+
"typescript": "^4.9.4"
|
|
56
58
|
}
|
|
57
59
|
}
|
package/provider/default/app.js
CHANGED
|
@@ -9,9 +9,7 @@
|
|
|
9
9
|
if (zoom) options.zoom = zoom
|
|
10
10
|
const map = new maplibregl.Map(options)
|
|
11
11
|
|
|
12
|
-
window._charites.initializeWebSocket(
|
|
13
|
-
map.setStyle(JSON.parse(message.data))
|
|
14
|
-
})
|
|
12
|
+
window._charites.initializeWebSocket(map)
|
|
15
13
|
|
|
16
14
|
map.addControl(new maplibregl.NavigationControl(), 'top-right')
|
|
17
15
|
|
|
@@ -2,10 +2,10 @@
|
|
|
2
2
|
<html id="charites-default">
|
|
3
3
|
<head>
|
|
4
4
|
<link rel="stylesheet" href="/app.css" />
|
|
5
|
-
<link href='https://unpkg.com/maplibre-gl@
|
|
5
|
+
<link href='https://unpkg.com/maplibre-gl@2.4.0/dist/maplibre-gl.css' rel='stylesheet' />
|
|
6
6
|
<link href='https://watergis.github.io/maplibre-gl-legend/maplibre-gl-legend.css' rel='stylesheet' />
|
|
7
7
|
<title>Charites Live Preview</title>
|
|
8
|
-
<script src='https://unpkg.com/maplibre-gl@
|
|
8
|
+
<script src='https://unpkg.com/maplibre-gl@2.4.0/dist/maplibre-gl.js'></script>
|
|
9
9
|
<script src="https://watergis.github.io/maplibre-gl-legend/maplibre-gl-legend.js"></script>
|
|
10
10
|
</head>
|
|
11
11
|
<body>
|
|
@@ -1,9 +1,18 @@
|
|
|
1
1
|
;(async () => {
|
|
2
2
|
window._charites = {
|
|
3
|
-
initializeWebSocket: function (
|
|
3
|
+
initializeWebSocket: function (map) {
|
|
4
4
|
const socket = new WebSocket(`ws://${window.location.host}`)
|
|
5
5
|
|
|
6
|
-
socket.addEventListener('message',
|
|
6
|
+
socket.addEventListener('message', (message) => {
|
|
7
|
+
const data = JSON.parse(message.data)
|
|
8
|
+
if (data.event === 'styleUpdate') {
|
|
9
|
+
map.setStyle(`http://${window.location.host}/style.json`)
|
|
10
|
+
} else if (data.event === 'spriteUpdate') {
|
|
11
|
+
map.setStyle(`http://${window.location.host}/style.json`, {
|
|
12
|
+
diff: false,
|
|
13
|
+
})
|
|
14
|
+
}
|
|
15
|
+
})
|
|
7
16
|
},
|
|
8
17
|
parseMapStyle: async function () {
|
|
9
18
|
const mapStyleUrl = `http://${window.location.host}/style.json`
|
package/provider/geolonia/app.js
CHANGED
|
@@ -9,9 +9,7 @@
|
|
|
9
9
|
if (zoom) options.zoom = zoom
|
|
10
10
|
const map = new geolonia.Map(options)
|
|
11
11
|
|
|
12
|
-
window._charites.initializeWebSocket(
|
|
13
|
-
map.setStyle(JSON.parse(message.data))
|
|
14
|
-
})
|
|
12
|
+
window._charites.initializeWebSocket(map)
|
|
15
13
|
|
|
16
14
|
map.addControl(
|
|
17
15
|
new MaplibreLegendControl(
|
package/provider/mapbox/app.js
CHANGED
|
@@ -11,9 +11,7 @@
|
|
|
11
11
|
if (zoom) options.zoom = zoom
|
|
12
12
|
const map = new mapboxgl.Map(options)
|
|
13
13
|
|
|
14
|
-
window._charites.initializeWebSocket(
|
|
15
|
-
map.setStyle(JSON.parse(message.data))
|
|
16
|
-
})
|
|
14
|
+
window._charites.initializeWebSocket(map)
|
|
17
15
|
|
|
18
16
|
map.addControl(new mapboxgl.NavigationControl(), 'top-right')
|
|
19
17
|
|
package/src/cli/init.ts
CHANGED
|
@@ -6,7 +6,7 @@ const program = new Command()
|
|
|
6
6
|
program
|
|
7
7
|
.name('init')
|
|
8
8
|
.arguments('<file>')
|
|
9
|
-
.description('initialize a style
|
|
9
|
+
.description('initialize a style YAML')
|
|
10
10
|
.option(
|
|
11
11
|
'-t, --tilejson-urls <tilejson_urls>',
|
|
12
12
|
'an URL for TileJSON. It will create empty layers from vector_layers property of TileJSON. Please use comma (,) in case multiple TileJSONs require.',
|
package/src/cli/serve.ts
CHANGED
|
@@ -17,12 +17,19 @@ program
|
|
|
17
17
|
'--mapbox-access-token [mapboxAccessToken]',
|
|
18
18
|
'Your Mapbox Access Token (required if using the `mapbox` provider)',
|
|
19
19
|
)
|
|
20
|
+
.option(
|
|
21
|
+
'-i, --sprite-input [<icon input directory>]',
|
|
22
|
+
'directory path of icon source to build icons. The default <icon source> is `icons/`',
|
|
23
|
+
)
|
|
20
24
|
.option('--port [port]', 'Specify custom port')
|
|
21
|
-
.
|
|
25
|
+
.option('--no-open', "Don't open the preview in the default browser")
|
|
26
|
+
.action(async (source: string, serveOptions: serveOptions) => {
|
|
22
27
|
const options: serveOptions = program.opts()
|
|
23
28
|
options.provider = serveOptions.provider
|
|
24
29
|
options.mapboxAccessToken = serveOptions.mapboxAccessToken
|
|
25
30
|
options.port = serveOptions.port
|
|
31
|
+
options.spriteInput = serveOptions.spriteInput
|
|
32
|
+
options.open = serveOptions.open
|
|
26
33
|
if (!fs.existsSync(defaultSettings.configFile)) {
|
|
27
34
|
fs.writeFileSync(
|
|
28
35
|
defaultSettings.configFile,
|
|
@@ -30,7 +37,7 @@ program
|
|
|
30
37
|
)
|
|
31
38
|
}
|
|
32
39
|
try {
|
|
33
|
-
serve(source, program.opts())
|
|
40
|
+
await serve(source, program.opts())
|
|
34
41
|
} catch (e) {
|
|
35
42
|
error(e)
|
|
36
43
|
}
|
package/src/commands/build.ts
CHANGED
|
@@ -6,7 +6,7 @@ import { buildSprite } from '../lib/build-sprite'
|
|
|
6
6
|
import { getSpriteSlug } from '../lib/get-sprite-slug'
|
|
7
7
|
import { defaultValues } from '../lib/defaultValues'
|
|
8
8
|
import jsonminify from 'jsonminify'
|
|
9
|
-
import { StyleSpecification } from '@maplibre/maplibre-gl-style-spec
|
|
9
|
+
import { StyleSpecification } from '@maplibre/maplibre-gl-style-spec'
|
|
10
10
|
import watch from 'node-watch'
|
|
11
11
|
|
|
12
12
|
export interface buildOptions {
|
|
@@ -94,11 +94,7 @@ export async function build(
|
|
|
94
94
|
}
|
|
95
95
|
}
|
|
96
96
|
|
|
97
|
-
|
|
98
|
-
fs.writeFileSync(destinationPath, style)
|
|
99
|
-
} catch (err) {
|
|
100
|
-
throw `${destinationPath}: Permission denied`
|
|
101
|
-
}
|
|
97
|
+
fs.writeFileSync(destinationPath, style)
|
|
102
98
|
}
|
|
103
99
|
|
|
104
100
|
export function buildWatch(
|
package/src/commands/convert.ts
CHANGED
|
@@ -45,11 +45,7 @@ export function convert(source: string, destination: string) {
|
|
|
45
45
|
const style = JSON.parse(lines.join(''))
|
|
46
46
|
const destinationPath = getDestinationPath(destination)
|
|
47
47
|
|
|
48
|
-
|
|
49
|
-
writeYaml(destinationPath, style, false)
|
|
50
|
-
} catch (err) {
|
|
51
|
-
throw `${destinationPath}: Permission denied`
|
|
52
|
-
}
|
|
48
|
+
writeYaml(destinationPath, style, false)
|
|
53
49
|
})
|
|
54
50
|
} else {
|
|
55
51
|
sourcePath = path.resolve(process.cwd(), source)
|
|
@@ -67,10 +63,6 @@ export function convert(source: string, destination: string) {
|
|
|
67
63
|
|
|
68
64
|
const destinationPath = getDestinationPath(destination, sourcePath)
|
|
69
65
|
|
|
70
|
-
|
|
71
|
-
writeYaml(destinationPath, style, false)
|
|
72
|
-
} catch (err) {
|
|
73
|
-
throw `${destinationPath}: Permission denied`
|
|
74
|
-
}
|
|
66
|
+
writeYaml(destinationPath, style, false)
|
|
75
67
|
}
|
|
76
68
|
}
|
package/src/commands/init.ts
CHANGED
package/src/commands/serve.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import path from 'path'
|
|
2
2
|
import fs from 'fs'
|
|
3
|
+
import os from 'os'
|
|
3
4
|
import http from 'http'
|
|
4
5
|
import open from 'open'
|
|
5
6
|
import { WebSocketServer } from 'ws'
|
|
@@ -8,14 +9,17 @@ import watch from 'node-watch'
|
|
|
8
9
|
import { parser } from '../lib/yaml-parser'
|
|
9
10
|
import { validateStyle } from '../lib/validate-style'
|
|
10
11
|
import { defaultValues } from '../lib/defaultValues'
|
|
12
|
+
import { buildSprite } from '../lib/build-sprite'
|
|
11
13
|
|
|
12
14
|
export interface serveOptions {
|
|
13
15
|
provider?: string
|
|
14
16
|
mapboxAccessToken?: string
|
|
15
17
|
port?: string
|
|
18
|
+
spriteInput?: string
|
|
19
|
+
open?: boolean
|
|
16
20
|
}
|
|
17
21
|
|
|
18
|
-
export function serve(source: string, options: serveOptions) {
|
|
22
|
+
export async function serve(source: string, options: serveOptions) {
|
|
19
23
|
let port = process.env.PORT || 8080
|
|
20
24
|
if (options.port) {
|
|
21
25
|
port = Number(options.port)
|
|
@@ -42,11 +46,44 @@ export function serve(source: string, options: serveOptions) {
|
|
|
42
46
|
throw `Provider is mapbox, but the Mapbox Access Token is not set. Please provide it using --mapbox-access-token, or set it in \`~/.charites/config.yml\` (see the Global configuration section of the documentation for more information)`
|
|
43
47
|
}
|
|
44
48
|
|
|
45
|
-
|
|
49
|
+
let spriteOut: string | undefined = undefined
|
|
50
|
+
let spriteRefresher: (() => Promise<void>) | undefined = undefined
|
|
51
|
+
if (options.spriteInput) {
|
|
52
|
+
spriteOut = await fs.promises.mkdtemp(path.join(os.tmpdir(), 'charites-'))
|
|
53
|
+
spriteRefresher = async () => {
|
|
54
|
+
if (
|
|
55
|
+
typeof options.spriteInput === 'undefined' ||
|
|
56
|
+
typeof spriteOut === 'undefined'
|
|
57
|
+
) {
|
|
58
|
+
return
|
|
59
|
+
}
|
|
60
|
+
await buildSprite(options.spriteInput, spriteOut, 'sprite')
|
|
61
|
+
}
|
|
62
|
+
await spriteRefresher()
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
const server = http.createServer(async (req, res) => {
|
|
46
66
|
const url = (req.url || '').replace(/\?.*/, '')
|
|
47
67
|
const defaultProviderDir = path.join(defaultValues.providerDir, 'default')
|
|
48
68
|
const providerDir = path.join(defaultValues.providerDir, provider)
|
|
49
69
|
|
|
70
|
+
if (
|
|
71
|
+
typeof spriteOut !== 'undefined' &&
|
|
72
|
+
url.match(/^\/sprite(@2x)?\.(json|png)/)
|
|
73
|
+
) {
|
|
74
|
+
res.statusCode = 200
|
|
75
|
+
if (url.endsWith('.json')) {
|
|
76
|
+
res.setHeader('Content-Type', 'application/json; charset=UTF-8')
|
|
77
|
+
} else {
|
|
78
|
+
res.setHeader('Content-Type', 'image/png')
|
|
79
|
+
}
|
|
80
|
+
res.setHeader('Cache-Control', 'no-store')
|
|
81
|
+
const filename = path.basename(url)
|
|
82
|
+
const fsStream = fs.createReadStream(path.join(spriteOut, filename))
|
|
83
|
+
fsStream.pipe(res)
|
|
84
|
+
return
|
|
85
|
+
}
|
|
86
|
+
|
|
50
87
|
switch (url) {
|
|
51
88
|
case '/':
|
|
52
89
|
res.statusCode = 200
|
|
@@ -61,12 +98,18 @@ export function serve(source: string, options: serveOptions) {
|
|
|
61
98
|
let style
|
|
62
99
|
try {
|
|
63
100
|
style = parser(sourcePath)
|
|
101
|
+
if (typeof spriteOut !== 'undefined') {
|
|
102
|
+
style.sprite = `http://${
|
|
103
|
+
req.headers.host || `localhost:${port}`
|
|
104
|
+
}/sprite`
|
|
105
|
+
}
|
|
64
106
|
validateStyle(style, provider)
|
|
65
107
|
} catch (error) {
|
|
66
108
|
console.log(error)
|
|
67
109
|
}
|
|
68
110
|
res.statusCode = 200
|
|
69
111
|
res.setHeader('Content-Type', 'application/json; charset=UTF-8')
|
|
112
|
+
res.setHeader('Cache-Control', 'no-store')
|
|
70
113
|
res.end(JSON.stringify(style))
|
|
71
114
|
break
|
|
72
115
|
case '/app.css':
|
|
@@ -116,30 +159,56 @@ export function serve(source: string, options: serveOptions) {
|
|
|
116
159
|
console.log(`Provider: ${provider}`)
|
|
117
160
|
console.log(`Loading your style: ${sourcePath}`)
|
|
118
161
|
console.log(`Your map is running on http://localhost:${port}/\n`)
|
|
119
|
-
open
|
|
162
|
+
if (options.open) {
|
|
163
|
+
open(`http://localhost:${port}`)
|
|
164
|
+
}
|
|
120
165
|
})
|
|
121
166
|
|
|
122
167
|
const wss = new WebSocketServer({ server })
|
|
123
168
|
|
|
124
169
|
wss.on('connection', (ws) => {
|
|
125
|
-
watch(
|
|
170
|
+
const watcher = watch(
|
|
126
171
|
path.dirname(sourcePath),
|
|
127
|
-
{ recursive: true, filter: /\.yml$/ },
|
|
172
|
+
{ recursive: true, filter: /\.yml$|\.svg$/i },
|
|
128
173
|
(event, file) => {
|
|
129
174
|
console.log(`${(event || '').toUpperCase()}: ${file}`)
|
|
130
175
|
try {
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
176
|
+
if (file?.toLowerCase().endsWith('.yml')) {
|
|
177
|
+
ws.send(
|
|
178
|
+
JSON.stringify({
|
|
179
|
+
event: 'styleUpdate',
|
|
180
|
+
}),
|
|
181
|
+
)
|
|
182
|
+
} else if (
|
|
183
|
+
file?.toLowerCase().endsWith('.svg') &&
|
|
184
|
+
typeof spriteRefresher !== 'undefined'
|
|
185
|
+
) {
|
|
186
|
+
spriteRefresher().then(() => {
|
|
187
|
+
ws.send(
|
|
188
|
+
JSON.stringify({
|
|
189
|
+
event: 'spriteUpdate',
|
|
190
|
+
}),
|
|
191
|
+
)
|
|
192
|
+
})
|
|
136
193
|
}
|
|
137
|
-
ws.send(JSON.stringify(style))
|
|
138
194
|
} catch (e) {
|
|
139
195
|
// Nothing to do
|
|
140
196
|
}
|
|
141
197
|
},
|
|
142
198
|
)
|
|
199
|
+
ws.on('close', () => {
|
|
200
|
+
watcher.close()
|
|
201
|
+
})
|
|
202
|
+
})
|
|
203
|
+
|
|
204
|
+
process.on('SIGINT', () => {
|
|
205
|
+
console.log('Cleaning up...')
|
|
206
|
+
server.close()
|
|
207
|
+
if (typeof spriteOut !== 'undefined') {
|
|
208
|
+
fs.rmSync(spriteOut, { recursive: true })
|
|
209
|
+
spriteOut = undefined
|
|
210
|
+
}
|
|
211
|
+
process.exit(0)
|
|
143
212
|
})
|
|
144
213
|
|
|
145
214
|
return server
|
package/src/lib/build-sprite.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { generateSprite } from '@unvt/sprite-one'
|
|
2
|
-
|
|
2
|
+
import path from 'path'
|
|
3
3
|
|
|
4
4
|
export async function buildSprite(
|
|
5
5
|
svgPath: string,
|
|
@@ -8,10 +8,6 @@ export async function buildSprite(
|
|
|
8
8
|
): Promise<void> {
|
|
9
9
|
const pxRatios = [1, 2]
|
|
10
10
|
const outPath = path.join(publicPath, iconSlug)
|
|
11
|
-
|
|
12
|
-
await generateSprite(outPath, [svgPath], pxRatios)
|
|
13
|
-
} catch (error) {
|
|
14
|
-
throw error
|
|
15
|
-
}
|
|
11
|
+
await generateSprite(outPath, [svgPath], pxRatios)
|
|
16
12
|
return
|
|
17
13
|
}
|