gdcore-tools 1.0.2 → 1.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/README.md +11 -0
- package/examples/create-objects-from-json/game.json +257 -257
- package/examples/export-game/game.json +204 -204
- package/package-lock.json +223 -223
- package/package.json +32 -32
- package/src/EventsFunctionsExtensionsLoader/MetadataDeclarationHelpers.js +442 -449
- package/src/EventsFunctionsExtensionsLoader/index.js +373 -354
- package/src/JsExtensionsLoader/LocalJsExtensionsFinder.js +0 -3
- package/src/LocalFileSystem.js +39 -39
- package/src/WrappedGD.js +138 -0
- package/src/downloadGD.js +65 -29
- package/src/index.js +10 -110
|
@@ -18,9 +18,6 @@ const checkIfPathHasJsExtensionModule = (extensionFolderPath) => {
|
|
|
18
18
|
};
|
|
19
19
|
|
|
20
20
|
const findJsExtensionModules = (extensionsRoot) => {
|
|
21
|
-
console.info(
|
|
22
|
-
`Searching for JS extensions (file called JsExtension.js) in ${extensionsRoot}...`
|
|
23
|
-
);
|
|
24
21
|
return new Promise(async (resolve, reject) => {
|
|
25
22
|
const extensionFolders = await fs.readdirAsync(extensionsRoot);
|
|
26
23
|
|
package/src/LocalFileSystem.js
CHANGED
|
@@ -1,28 +1,28 @@
|
|
|
1
|
-
const fs = require(
|
|
2
|
-
const path = require(
|
|
3
|
-
const os = require(
|
|
1
|
+
const fs = require("fs-extra");
|
|
2
|
+
const path = require("path");
|
|
3
|
+
const os = require("os");
|
|
4
4
|
|
|
5
|
-
exports.
|
|
6
|
-
mkDir: function(path) {
|
|
5
|
+
module.exports.makeFS = (gd) => ({
|
|
6
|
+
mkDir: function (path) {
|
|
7
7
|
try {
|
|
8
8
|
fs.mkdirsSync(path);
|
|
9
9
|
} catch (e) {
|
|
10
|
-
console.error(
|
|
10
|
+
console.error("mkDir(" + path + ") failed: " + e);
|
|
11
11
|
return false;
|
|
12
12
|
}
|
|
13
13
|
return true;
|
|
14
14
|
},
|
|
15
|
-
dirExists: function(path) {
|
|
15
|
+
dirExists: function (path) {
|
|
16
16
|
return fs.existsSync(path);
|
|
17
17
|
},
|
|
18
|
-
clearDir: function(path) {
|
|
18
|
+
clearDir: function (path) {
|
|
19
19
|
var files = [];
|
|
20
20
|
var that = this;
|
|
21
21
|
try {
|
|
22
22
|
if (fs.existsSync(path)) {
|
|
23
23
|
files = fs.readdirSync(path);
|
|
24
|
-
files.forEach(function(file) {
|
|
25
|
-
var curPath = path +
|
|
24
|
+
files.forEach(function (file) {
|
|
25
|
+
var curPath = path + "/" + file;
|
|
26
26
|
if (fs.lstatSync(curPath).isDirectory()) {
|
|
27
27
|
// recurse
|
|
28
28
|
that.clearDir(curPath);
|
|
@@ -31,31 +31,31 @@ exports.fs = {
|
|
|
31
31
|
try {
|
|
32
32
|
fs.unlinkSync(curPath);
|
|
33
33
|
} catch (e) {
|
|
34
|
-
console.error(
|
|
34
|
+
console.error("fs.unlinkSync(" + curPath + ") failed: " + e);
|
|
35
35
|
}
|
|
36
36
|
}
|
|
37
37
|
});
|
|
38
38
|
}
|
|
39
39
|
} catch (e) {
|
|
40
|
-
console.error(
|
|
40
|
+
console.error("clearDir(" + path + ") failed: " + e);
|
|
41
41
|
}
|
|
42
42
|
},
|
|
43
|
-
getTempDir: function() {
|
|
43
|
+
getTempDir: function () {
|
|
44
44
|
return os.tmpdir();
|
|
45
45
|
},
|
|
46
|
-
fileNameFrom: function(fullpath) {
|
|
46
|
+
fileNameFrom: function (fullpath) {
|
|
47
47
|
if (this._isExternalURL(fullpath)) return fullpath;
|
|
48
48
|
|
|
49
49
|
fullpath = this._translateURL(fullpath);
|
|
50
50
|
return path.basename(fullpath);
|
|
51
51
|
},
|
|
52
|
-
dirNameFrom: function(fullpath) {
|
|
53
|
-
if (this._isExternalURL(fullpath)) return
|
|
52
|
+
dirNameFrom: function (fullpath) {
|
|
53
|
+
if (this._isExternalURL(fullpath)) return "";
|
|
54
54
|
|
|
55
55
|
fullpath = this._translateURL(fullpath);
|
|
56
56
|
return path.dirname(fullpath);
|
|
57
57
|
},
|
|
58
|
-
makeAbsolute: function(filename, baseDirectory) {
|
|
58
|
+
makeAbsolute: function (filename, baseDirectory) {
|
|
59
59
|
if (this._isExternalURL(filename)) return filename;
|
|
60
60
|
|
|
61
61
|
filename = this._translateURL(filename);
|
|
@@ -64,23 +64,23 @@ exports.fs = {
|
|
|
64
64
|
|
|
65
65
|
return path.resolve(baseDirectory, path.normalize(filename));
|
|
66
66
|
},
|
|
67
|
-
makeRelative: function(filename, baseDirectory) {
|
|
67
|
+
makeRelative: function (filename, baseDirectory) {
|
|
68
68
|
if (this._isExternalURL(filename)) return filename;
|
|
69
69
|
|
|
70
70
|
filename = this._translateURL(filename);
|
|
71
71
|
return path.relative(baseDirectory, path.normalize(filename));
|
|
72
72
|
},
|
|
73
|
-
isAbsolute: function(fullpath) {
|
|
73
|
+
isAbsolute: function (fullpath) {
|
|
74
74
|
if (this._isExternalURL(fullpath)) return true;
|
|
75
75
|
|
|
76
76
|
if (fullpath.length === 0) return true;
|
|
77
77
|
fullpath = this._translateURL(fullpath);
|
|
78
78
|
return (
|
|
79
|
-
(fullpath.length > 0 && fullpath.charAt(0) ===
|
|
80
|
-
(fullpath.length > 1 && fullpath.charAt(1) ===
|
|
79
|
+
(fullpath.length > 0 && fullpath.charAt(0) === "/") ||
|
|
80
|
+
(fullpath.length > 1 && fullpath.charAt(1) === ":")
|
|
81
81
|
);
|
|
82
82
|
},
|
|
83
|
-
copyFile: function(source, dest) {
|
|
83
|
+
copyFile: function (source, dest) {
|
|
84
84
|
//URL are not copied.
|
|
85
85
|
if (this._isExternalURL(source)) return true;
|
|
86
86
|
|
|
@@ -88,52 +88,52 @@ exports.fs = {
|
|
|
88
88
|
try {
|
|
89
89
|
if (source !== dest) fs.copySync(source, dest);
|
|
90
90
|
} catch (e) {
|
|
91
|
-
console.error(
|
|
91
|
+
console.error("copyFile(" + source + ", " + dest + ") failed: " + e);
|
|
92
92
|
return false;
|
|
93
93
|
}
|
|
94
94
|
return true;
|
|
95
95
|
},
|
|
96
|
-
writeToFile: function(file, contents) {
|
|
96
|
+
writeToFile: function (file, contents) {
|
|
97
97
|
try {
|
|
98
98
|
fs.outputFileSync(file, contents);
|
|
99
99
|
} catch (e) {
|
|
100
|
-
console.error(
|
|
100
|
+
console.error("writeToFile(" + file + ", ...) failed: " + e);
|
|
101
101
|
return false;
|
|
102
102
|
}
|
|
103
103
|
return true;
|
|
104
104
|
},
|
|
105
|
-
readFile: function(file) {
|
|
105
|
+
readFile: function (file) {
|
|
106
106
|
try {
|
|
107
107
|
var contents = fs.readFileSync(file);
|
|
108
108
|
return contents.toString();
|
|
109
109
|
} catch (e) {
|
|
110
|
-
console.error(
|
|
111
|
-
return
|
|
110
|
+
console.error("readFile(" + file + ") failed: " + e);
|
|
111
|
+
return "";
|
|
112
112
|
}
|
|
113
113
|
},
|
|
114
|
-
readDir: function(path, ext) {
|
|
114
|
+
readDir: function (path, ext) {
|
|
115
115
|
ext = ext.toUpperCase();
|
|
116
|
-
var output = new
|
|
116
|
+
var output = new gd.VectorString();
|
|
117
117
|
try {
|
|
118
118
|
var files = [];
|
|
119
119
|
if (fs.existsSync(path)) {
|
|
120
120
|
files = fs.readdirSync(path);
|
|
121
|
-
files.forEach(function(file) {
|
|
121
|
+
files.forEach(function (file) {
|
|
122
122
|
if (
|
|
123
123
|
ext.length === 0 ||
|
|
124
124
|
file.toUpperCase().indexOf(ext, file.length - ext.length) !== -1
|
|
125
125
|
) {
|
|
126
|
-
output.push_back(path +
|
|
126
|
+
output.push_back(path + "/" + file);
|
|
127
127
|
}
|
|
128
128
|
});
|
|
129
129
|
}
|
|
130
130
|
} catch (e) {
|
|
131
|
-
console.error(
|
|
131
|
+
console.error("readDir(" + path + "," + ext + ") failed: " + e);
|
|
132
132
|
}
|
|
133
133
|
|
|
134
134
|
return output;
|
|
135
135
|
},
|
|
136
|
-
fileExists: function(filename) {
|
|
136
|
+
fileExists: function (filename) {
|
|
137
137
|
filename = this._translateURL(filename);
|
|
138
138
|
try {
|
|
139
139
|
const stat = fs.statSync(filename);
|
|
@@ -142,17 +142,17 @@ exports.fs = {
|
|
|
142
142
|
return false;
|
|
143
143
|
}
|
|
144
144
|
},
|
|
145
|
-
_isExternalURL: function(filename) {
|
|
146
|
-
return filename.substr(0, 4) ===
|
|
145
|
+
_isExternalURL: function (filename) {
|
|
146
|
+
return filename.substr(0, 4) === "http" || filename.substr(0, 4) === "ftp";
|
|
147
147
|
},
|
|
148
148
|
/**
|
|
149
149
|
* Return the filename associated to the URL on the server, relative to the games directory.
|
|
150
150
|
* (i.e: Transform g/mydirectory/myfile.png to mydirectory/myfile.png).
|
|
151
151
|
*/
|
|
152
|
-
_translateURL: function(filename) {
|
|
153
|
-
if (filename.substr(0, 2) ===
|
|
152
|
+
_translateURL: function (filename) {
|
|
153
|
+
if (filename.substr(0, 2) === "g/" || filename.substr(0, 2) === "g\\")
|
|
154
154
|
filename = filename.substr(2);
|
|
155
155
|
|
|
156
156
|
return filename;
|
|
157
157
|
},
|
|
158
|
-
};
|
|
158
|
+
});
|
package/src/WrappedGD.js
ADDED
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
const EventEmitter = require("events");
|
|
2
|
+
const loadExtensions = require("./JsExtensionsLoader/LocalJsExtensionsLoader");
|
|
3
|
+
const projectLoader = require("./LocalProjectOpener");
|
|
4
|
+
const { makeLoader } = require("./EventsFunctionsExtensionsLoader/index");
|
|
5
|
+
const {
|
|
6
|
+
makeLocalEventsFunctionCodeWriter,
|
|
7
|
+
} = require("./EventsFunctionsExtensionsLoader/LocalEventsFunctionCodeWriter");
|
|
8
|
+
const saveProject = require("./LocalProjectWriter");
|
|
9
|
+
const assignIn = require("lodash/assignIn");
|
|
10
|
+
const { getGD, getRuntimePath } = require("./downloadGD");
|
|
11
|
+
const { join, resolve } = require("path");
|
|
12
|
+
const { makeFS } = require("./LocalFileSystem");
|
|
13
|
+
|
|
14
|
+
class WrappedGD extends EventEmitter {
|
|
15
|
+
constructor(version) {
|
|
16
|
+
super();
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* The raw gd namespace.
|
|
20
|
+
*/
|
|
21
|
+
this.gd = null;
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* The GDevelop abstract file system.
|
|
25
|
+
* @private
|
|
26
|
+
*/
|
|
27
|
+
this.fs = null;
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* The Events Functions loader
|
|
31
|
+
* @private
|
|
32
|
+
*/
|
|
33
|
+
this.eventsFunctionsLoader = null;
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* The Events Functions loader.
|
|
37
|
+
* @private
|
|
38
|
+
*/
|
|
39
|
+
this.eventsFunctionsWriter = makeLocalEventsFunctionCodeWriter();
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* The path to the current version.
|
|
43
|
+
* @private
|
|
44
|
+
*/
|
|
45
|
+
this.versionPath = getRuntimePath(version);
|
|
46
|
+
|
|
47
|
+
// Begin async loading of GDCore and extensions
|
|
48
|
+
getGD(version, {
|
|
49
|
+
print: (message) => this.emit("print", message),
|
|
50
|
+
printErr: (e) => this.emit("error", e),
|
|
51
|
+
onAbort: (e) => this.emit("error", e),
|
|
52
|
+
})
|
|
53
|
+
.then((gd) => {
|
|
54
|
+
this.gd = gd;
|
|
55
|
+
return loadExtensions(
|
|
56
|
+
gd,
|
|
57
|
+
join(this.versionPath, "Runtime", "Extensions")
|
|
58
|
+
);
|
|
59
|
+
})
|
|
60
|
+
.then(() => {
|
|
61
|
+
this.fs = assignIn(new this.gd.AbstractFileSystemJS(), makeFS(this.gd));
|
|
62
|
+
this.eventsFunctionsLoader = makeLoader(
|
|
63
|
+
this.gd
|
|
64
|
+
).loadProjectEventsFunctionsExtensions;
|
|
65
|
+
})
|
|
66
|
+
.then(() => this.emit("ready"))
|
|
67
|
+
.catch((e) => this.emit("initError", e));
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Loads a project json file.
|
|
72
|
+
* @param {string} projectLocation The path to the json file
|
|
73
|
+
*/
|
|
74
|
+
loadProject(projectLocation) {
|
|
75
|
+
return projectLoader
|
|
76
|
+
.loadProjectFiles(projectLocation)
|
|
77
|
+
.then((projectFile) => {
|
|
78
|
+
projectFile.content.properties.projectFile = projectLocation;
|
|
79
|
+
return projectLoader.loadSerializedProject(
|
|
80
|
+
this.gd,
|
|
81
|
+
projectFile.content
|
|
82
|
+
);
|
|
83
|
+
})
|
|
84
|
+
.then(async (project) => {
|
|
85
|
+
await this.reloadEventsFunctions(project);
|
|
86
|
+
project.setProjectFile(resolve(projectLocation));
|
|
87
|
+
return project;
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
/**
|
|
92
|
+
* Saves a project to a json file.
|
|
93
|
+
* @param {*} project The loaded project
|
|
94
|
+
* @param {string} [fileName] The name of the file to save. Defaults to "game.json".
|
|
95
|
+
* @param {string} [pathName] The path to save to. Defaults to "./".
|
|
96
|
+
*/
|
|
97
|
+
saveProject(project, fileName, pathName) {
|
|
98
|
+
pathName = pathName || "./";
|
|
99
|
+
fileName = join(pathName, fileName || "game.json");
|
|
100
|
+
return saveProject(this.gd, project, fileName, pathName);
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Exports a project.
|
|
105
|
+
* @param {*} project The loaded project.
|
|
106
|
+
* @param {string} outputDir The output directory.
|
|
107
|
+
* @param {Object<string>} options Options to pass to the exporter.
|
|
108
|
+
*/
|
|
109
|
+
exportProject(project, outputDir, options) {
|
|
110
|
+
const gd = this.gd;
|
|
111
|
+
const exporter = new gd.Exporter(this.fs, this.versionPath);
|
|
112
|
+
const exportOptions = new gd.MapStringBoolean();
|
|
113
|
+
for (let key in options) {
|
|
114
|
+
exportOptions.set(key, options[key]);
|
|
115
|
+
}
|
|
116
|
+
exporter.exportWholePixiProject(project, outputDir, exportOptions);
|
|
117
|
+
exportOptions.delete();
|
|
118
|
+
exporter.delete();
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
/**
|
|
122
|
+
* Reload and generate events based extensions in a project.
|
|
123
|
+
* @param {*} project
|
|
124
|
+
*/
|
|
125
|
+
reloadEventsFunctions(project) {
|
|
126
|
+
return this.eventsFunctionsLoader(project, this.eventsFunctionsWriter);
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
/**
|
|
130
|
+
* Returns the path to the runtime files.
|
|
131
|
+
* @returns {string}
|
|
132
|
+
*/
|
|
133
|
+
getRuntimePath() {
|
|
134
|
+
return join(this.versionPath, "Runtime");
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
module.exports = WrappedGD;
|
package/src/downloadGD.js
CHANGED
|
@@ -1,18 +1,20 @@
|
|
|
1
|
-
const https = require("follow-redirects").https;
|
|
2
1
|
const fs = require("fs-extra-promise");
|
|
3
2
|
const path = require("path");
|
|
4
3
|
const { request } = require("@octokit/request");
|
|
5
|
-
const
|
|
4
|
+
const { https } = require("follow-redirects");
|
|
6
5
|
|
|
7
6
|
const getRuntimePath = (version) => path.join(__dirname, "Versions", version);
|
|
8
7
|
|
|
9
|
-
const downloadFile = (file, savePath) =>
|
|
8
|
+
const downloadFile = (file, savePath, required = true) =>
|
|
10
9
|
new Promise((resolve) => {
|
|
11
10
|
https.get(file, function (response) {
|
|
12
11
|
if (response.statusCode !== 200) {
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
12
|
+
if (required)
|
|
13
|
+
throw new Error(
|
|
14
|
+
`❌ Cannot download ${file}! Error ${response.statusCode}: ${response.statusMessage}`
|
|
15
|
+
);
|
|
16
|
+
// Silently fail if the file is not required
|
|
17
|
+
else return resolve(true);
|
|
16
18
|
}
|
|
17
19
|
response.pipe(fs.createWriteStream(savePath)).addListener("close", () => {
|
|
18
20
|
resolve();
|
|
@@ -49,6 +51,7 @@ const findLatestVersion = () => {
|
|
|
49
51
|
* @param {string} versionTag The GDevelop version tag
|
|
50
52
|
*/
|
|
51
53
|
const downloadVersion = async function (versionTag) {
|
|
54
|
+
const StreamZip = require("node-stream-zip");
|
|
52
55
|
const tasks = [];
|
|
53
56
|
const gdPath = getRuntimePath(versionTag);
|
|
54
57
|
|
|
@@ -63,14 +66,28 @@ const downloadVersion = async function (versionTag) {
|
|
|
63
66
|
.then(() => fs.removeAsync(gdPath))
|
|
64
67
|
.finally(() => fs.mkdirAsync(gdPath));
|
|
65
68
|
|
|
66
|
-
|
|
67
|
-
await request("GET /repos/4ian/GDevelop/
|
|
68
|
-
|
|
69
|
+
let commit = (
|
|
70
|
+
await request("GET /repos/4ian/GDevelop/commits/{ref}", {
|
|
71
|
+
ref: (
|
|
72
|
+
await request("GET /repos/4ian/GDevelop/git/ref/tags/{tag}", {
|
|
73
|
+
tag: versionTag,
|
|
74
|
+
})
|
|
75
|
+
).data.object.sha,
|
|
69
76
|
})
|
|
70
|
-
).data
|
|
77
|
+
).data;
|
|
78
|
+
|
|
79
|
+
// Go up to the latest commit for which libGD.js was built
|
|
80
|
+
while (commit.commit.message.indexOf("[skip ci]") !== -1) {
|
|
81
|
+
commit = (
|
|
82
|
+
await request("GET /repos/4ian/GDevelop/commits/{ref}", {
|
|
83
|
+
ref: commit.parents[0].sha,
|
|
84
|
+
})
|
|
85
|
+
).data;
|
|
86
|
+
console.log(commit.commit.message, commit.parents);
|
|
87
|
+
}
|
|
71
88
|
|
|
72
89
|
// Fetch the file with the GDJS Runtime and extensions
|
|
73
|
-
console.info(`🕗 Starting download of GDevelop '${versionTag}'...`);
|
|
90
|
+
console.info(`🕗 Starting download of GDevelop Runtime '${versionTag}'...`);
|
|
74
91
|
const zipPath = path.join(gdPath, "gd.zip");
|
|
75
92
|
tasks.push(
|
|
76
93
|
downloadFile(
|
|
@@ -78,15 +95,15 @@ const downloadVersion = async function (versionTag) {
|
|
|
78
95
|
zipPath
|
|
79
96
|
)
|
|
80
97
|
.then(async () => {
|
|
81
|
-
console.info(`✅ Done downloading GDevelop '${versionTag}'`);
|
|
82
|
-
console.info(`🕗 Extracting GDevelop '${versionTag}'...`);
|
|
98
|
+
console.info(`✅ Done downloading GDevelop Runtime '${versionTag}'`);
|
|
99
|
+
console.info(`🕗 Extracting GDevelop Runtime '${versionTag}'...`);
|
|
83
100
|
await fs.mkdirAsync(path.join(gdPath, "Runtime"));
|
|
84
101
|
await fs.mkdirAsync(path.join(gdPath, "Runtime", "Extensions"));
|
|
85
102
|
const zip = new StreamZip({
|
|
86
103
|
file: zipPath,
|
|
87
104
|
storeEntries: true,
|
|
88
105
|
});
|
|
89
|
-
const prefix = `4ian-GDevelop-${
|
|
106
|
+
const prefix = `4ian-GDevelop-${commit.sha.slice(0, 7)}/`;
|
|
90
107
|
return Promise.all([
|
|
91
108
|
new Promise((resolve) => {
|
|
92
109
|
zip.on("ready", () => {
|
|
@@ -95,7 +112,10 @@ const downloadVersion = async function (versionTag) {
|
|
|
95
112
|
path.join(gdPath, "Runtime", "Extensions"),
|
|
96
113
|
(e) => {
|
|
97
114
|
if (e)
|
|
98
|
-
console.error(
|
|
115
|
+
console.error(
|
|
116
|
+
"❌ Error while extracting the GDevelop Runtime extensions! ",
|
|
117
|
+
e
|
|
118
|
+
);
|
|
99
119
|
else resolve();
|
|
100
120
|
}
|
|
101
121
|
);
|
|
@@ -108,7 +128,10 @@ const downloadVersion = async function (versionTag) {
|
|
|
108
128
|
path.join(gdPath, "Runtime"),
|
|
109
129
|
(e) => {
|
|
110
130
|
if (e)
|
|
111
|
-
console.error(
|
|
131
|
+
console.error(
|
|
132
|
+
"❌ Error while extracting the GDevelop Runtime! ",
|
|
133
|
+
e
|
|
134
|
+
);
|
|
112
135
|
else resolve();
|
|
113
136
|
}
|
|
114
137
|
);
|
|
@@ -134,20 +157,31 @@ const downloadVersion = async function (versionTag) {
|
|
|
134
157
|
// Download the fitting libGD version
|
|
135
158
|
const libGDPath =
|
|
136
159
|
"https://s3.amazonaws.com/gdevelop-gdevelop.js/master/commit/" +
|
|
137
|
-
|
|
160
|
+
commit.sha +
|
|
138
161
|
"/";
|
|
139
|
-
console.info(`🕗 Starting download of
|
|
162
|
+
console.info(`🕗 Starting download of GDevelop Core...`);
|
|
140
163
|
tasks.push(
|
|
141
|
-
downloadFile(
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
).then(() => console.info(`✅ Done downloading libGD.js`))
|
|
164
|
+
downloadFile(libGDPath + "libGD.js", path.join(gdPath, "libGD.js")).then(
|
|
165
|
+
() => console.info(`✅ Done downloading libGD.js`)
|
|
166
|
+
)
|
|
145
167
|
);
|
|
146
168
|
tasks.push(
|
|
147
169
|
downloadFile(
|
|
148
170
|
libGDPath + "libGD.js.mem",
|
|
149
|
-
path.join(gdPath, "libGD.js.mem")
|
|
150
|
-
|
|
171
|
+
path.join(gdPath, "libGD.js.mem"),
|
|
172
|
+
false
|
|
173
|
+
).then(
|
|
174
|
+
(errored) => !errored && console.info(`✅ Done downloading libGD.js.mem`)
|
|
175
|
+
)
|
|
176
|
+
);
|
|
177
|
+
tasks.push(
|
|
178
|
+
downloadFile(
|
|
179
|
+
libGDPath + "libGD.wasm",
|
|
180
|
+
path.join(gdPath, "libGD.wasm"),
|
|
181
|
+
false
|
|
182
|
+
).then(
|
|
183
|
+
(errored) => !errored && console.info(`✅ Done downloading libGD.wasm`)
|
|
184
|
+
)
|
|
151
185
|
);
|
|
152
186
|
|
|
153
187
|
return Promise.all(tasks).then(() =>
|
|
@@ -161,7 +195,7 @@ const downloadVersion = async function (versionTag) {
|
|
|
161
195
|
* Returning `gd` doesn't work, so a hacky workaround with global is used.
|
|
162
196
|
* @param {string} [versionTag] The GDevelop version to use. If not precised, the latest is used.
|
|
163
197
|
*/
|
|
164
|
-
const getGD = async function (versionTag) {
|
|
198
|
+
const getGD = async function (versionTag, gdOptions) {
|
|
165
199
|
const runtimePath = getRuntimePath(versionTag);
|
|
166
200
|
// Download the version if it isn't present
|
|
167
201
|
try {
|
|
@@ -171,10 +205,12 @@ const getGD = async function (versionTag) {
|
|
|
171
205
|
await downloadVersion(versionTag).catch(console.error);
|
|
172
206
|
}
|
|
173
207
|
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
208
|
+
const gd = require(path.join(runtimePath, "libGD.js"))(gdOptions);
|
|
209
|
+
return new Promise((resolve) => {
|
|
210
|
+
gd.then(() => {
|
|
211
|
+
// Make sure gd is not thenable as the promise would think it is one as well.
|
|
212
|
+
delete gd.then;
|
|
213
|
+
resolve(gd);
|
|
178
214
|
});
|
|
179
215
|
});
|
|
180
216
|
};
|
package/src/index.js
CHANGED
|
@@ -1,116 +1,16 @@
|
|
|
1
|
-
const
|
|
2
|
-
const
|
|
3
|
-
const eventsFunctionsLoader = require("./EventsFunctionsExtensionsLoader/index")
|
|
4
|
-
.loadProjectEventsFunctionsExtensions;
|
|
5
|
-
const eventFunctionsWriter = require("./EventsFunctionsExtensionsLoader/LocalEventsFunctionCodeWriter")
|
|
6
|
-
.makeLocalEventsFunctionCodeWriter;
|
|
7
|
-
const saveProject = require("./LocalProjectWriter");
|
|
8
|
-
const localFileSystem = require("./LocalFileSystem").fs;
|
|
9
|
-
const assignIn = require("lodash/assignIn");
|
|
10
|
-
const { getGD, getRuntimePath, findLatestVersion } = require("./downloadGD");
|
|
11
|
-
const { join, resolve } = require("path");
|
|
12
|
-
|
|
13
|
-
class WrappedGD {
|
|
14
|
-
constructor(gd, versionPath) {
|
|
15
|
-
/**
|
|
16
|
-
* The raw gd namespace.
|
|
17
|
-
*/
|
|
18
|
-
this.gd = gd;
|
|
19
|
-
|
|
20
|
-
/**
|
|
21
|
-
* The path to the current version.
|
|
22
|
-
* @private
|
|
23
|
-
*/
|
|
24
|
-
this.versionPath = versionPath;
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
/**
|
|
28
|
-
* Loads a project json file.
|
|
29
|
-
* @param {string} projectLocation The path to the json file
|
|
30
|
-
*/
|
|
31
|
-
loadProject(projectLocation) {
|
|
32
|
-
let project;
|
|
33
|
-
return projectLoader
|
|
34
|
-
.loadProjectFiles(projectLocation)
|
|
35
|
-
.then((projectFile) => {
|
|
36
|
-
projectFile.content.properties.projectFile = projectLocation;
|
|
37
|
-
return projectLoader.loadSerializedProject(
|
|
38
|
-
this.gd,
|
|
39
|
-
projectFile.content
|
|
40
|
-
);
|
|
41
|
-
})
|
|
42
|
-
.then((projectLoaded) => {
|
|
43
|
-
project = projectLoaded;
|
|
44
|
-
project.setProjectFile(resolve(projectLocation));
|
|
45
|
-
return eventsFunctionsLoader(project, eventFunctionsWriter());
|
|
46
|
-
})
|
|
47
|
-
.then(() => project);
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
/**
|
|
51
|
-
* Saves a project to a json file.
|
|
52
|
-
* @param {*} project The loaded project
|
|
53
|
-
* @param {string} [fileName] The name of the file to save. Defaults to "game.json".
|
|
54
|
-
* @param {string} [pathName] The path to save to. Defaults to "./".
|
|
55
|
-
*/
|
|
56
|
-
saveProject(project, fileName, pathName) {
|
|
57
|
-
pathName = pathName || "./";
|
|
58
|
-
fileName = join(pathName, fileName || "game.json");
|
|
59
|
-
return saveProject(this.gd, project, fileName, pathName);
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
/**
|
|
63
|
-
* Exports a project.
|
|
64
|
-
* @param {*} project The loaded project.
|
|
65
|
-
* @param {string} outputDir The output directory.
|
|
66
|
-
* @param {Object<string>} options Options to pass to the exporter.
|
|
67
|
-
*/
|
|
68
|
-
exportProject(project, outputDir, options) {
|
|
69
|
-
const gd = this.gd;
|
|
70
|
-
const fileSystem = assignIn(new gd.AbstractFileSystemJS(), localFileSystem);
|
|
71
|
-
const exporter = new gd.Exporter(fileSystem, this.versionPath);
|
|
72
|
-
const exportOptions = new gd.MapStringBoolean();
|
|
73
|
-
for (let key in options) {
|
|
74
|
-
exportOptions.set(key, options[key]);
|
|
75
|
-
}
|
|
76
|
-
exporter.exportWholePixiProject(project, outputDir, exportOptions);
|
|
77
|
-
exportOptions.delete();
|
|
78
|
-
exporter.delete();
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
/**
|
|
82
|
-
* Returns the path to the runtime files.
|
|
83
|
-
* @returns {string}
|
|
84
|
-
*/
|
|
85
|
-
getRuntimePath() {
|
|
86
|
-
return join(this.path, "Runtime");
|
|
87
|
-
}
|
|
88
|
-
}
|
|
1
|
+
const { findLatestVersion } = require("./downloadGD");
|
|
2
|
+
const WrappedGD = require("./WrappedGD");
|
|
89
3
|
|
|
90
4
|
const loadGD = async (version) => {
|
|
91
|
-
let gd;
|
|
92
5
|
if (version === undefined) version = await findLatestVersion();
|
|
93
|
-
return (
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
join(getRuntimePath(version), "Runtime", "Extensions")
|
|
102
|
-
);
|
|
103
|
-
})
|
|
104
|
-
/*
|
|
105
|
-
.then(() => {
|
|
106
|
-
const exts = gd.JsPlatform.get().getAllPlatformExtensions();
|
|
107
|
-
for (let i = 0; i < exts.size(); i++) console.log(exts.at(i).getName());
|
|
108
|
-
})
|
|
109
|
-
*/
|
|
110
|
-
.then(() => {
|
|
111
|
-
return new WrappedGD(gd, getRuntimePath(version));
|
|
112
|
-
})
|
|
113
|
-
);
|
|
6
|
+
return new Promise((resolve, reject) => {
|
|
7
|
+
const wgd = new WrappedGD(version);
|
|
8
|
+
wgd.once("ready", () => {
|
|
9
|
+
wgd.removeAllListeners();
|
|
10
|
+
resolve(wgd);
|
|
11
|
+
});
|
|
12
|
+
wgd.once("initError", reject);
|
|
13
|
+
});
|
|
114
14
|
};
|
|
115
15
|
|
|
116
16
|
module.exports = loadGD;
|