mirror of
https://github.com/quinton-ashley/java2js
synced 2024-12-29 10:11:54 +01:00
1.1.4
This commit is contained in:
parent
ae0e57da70
commit
213f552d52
51
README.md
51
README.md
@ -1,14 +1,45 @@
|
|||||||
# Java to Javascript for QuintOS
|
# Java to Javascript
|
||||||
|
|
||||||
I've built on top of the [java-to-javascript](https://github.com/wyattades/java-to-javascript) transpiler by @wyattades and got inspiration from the JDK (Java Development Kit) implementation in [java2javascript](https://github.com/java2script/java2script) by @BobHanson, @zhourenjian, @abego, and others.
|
I've built on top of the [java-to-javascript](https://github.com/wyattades/java-to-javascript) transpiler by @wyattades and got inspiration from the barebones JDK (Java Development Kit) implementation in [java2javascript](https://github.com/java2script/java2script) by @BobHanson, @zhourenjian, @abego, and others.
|
||||||
|
|
||||||
My purpose in creating this project is to allow intro level CS students to write Java code but still use my [QuintOS](https://github.com/quinton-ashley/quintos) retro game engine library which is web based. Yes, I went to all this trouble just so some teenagers don't have to run their programs in a boring Java console! I made a barebones JDK implementation in modern Javascript to acheive this.
|
I created this project so intro level computer science students could write Java code but still use my [QuintOS](https://github.com/quinton-ashley/quintos) retro game engine library, which is web based. Yes, I went to all this trouble just so my students don't have to run their programs in a boring Java console! To achieve this I've been working on a JDK implementation in modern Javascript.
|
||||||
|
|
||||||
|
## Java Classes Included in the JS JDK
|
||||||
|
|
||||||
|
| java.io | | |
|
||||||
|
| ------- | ----------- | ----------- |
|
||||||
|
| File | InputStream | PrintStream |
|
||||||
|
|
||||||
|
| java.lang | | |
|
||||||
|
| --------- | ------------- | --------- |
|
||||||
|
| Boolean | Byte | Character |
|
||||||
|
| Double | Exception | Float |
|
||||||
|
| Integer | Long | Short |
|
||||||
|
| String | StringBuilder | System |
|
||||||
|
| Thread | Throwable | |
|
||||||
|
|
||||||
|
| java.security | | |
|
||||||
|
| ------------- | --- | --- |
|
||||||
|
| MessageDigest | | |
|
||||||
|
|
||||||
|
| java.time | | |
|
||||||
|
| --------- | --- | --- |
|
||||||
|
| Instant | | |
|
||||||
|
|
||||||
|
| java.util | | |
|
||||||
|
| ------------------ | ---------------------- | ----------- |
|
||||||
|
| AbstractCollection | AbstractList | AbstractMap |
|
||||||
|
| AbstractSet | ArrayList | Arrays |
|
||||||
|
| Collections | Formatter | HashMap |
|
||||||
|
| HashSet | IllegalFormatException | Itr |
|
||||||
|
| LinkedList | Random | Scanner |
|
||||||
|
| Set | Stack | |
|
||||||
|
|
||||||
## API
|
## API
|
||||||
|
|
||||||
### jdk.init(root)
|
### jdk.init(root)
|
||||||
|
|
||||||
- root is the local path or url to the parent folder of the jdk, by default it links to 'https://unpkg.com/java2js' (this package) so you don't need to change it
|
- root (optional) can be a local path or url to the parent folder of the JS `jdk` folder, by default it links to 'https://unpkg.com/java2js' (this package) so you don't need to change it
|
||||||
|
|
||||||
This function imports much of the standard Java lang classes into the global scope. You must use it before translating or running files.
|
This function imports much of the standard Java lang classes into the global scope. You must use it before translating or running files.
|
||||||
|
|
||||||
@ -26,16 +57,22 @@ Loads the JS class file but doesn't run the main method.
|
|||||||
|
|
||||||
### jdk.run(jvmArgs)
|
### jdk.run(jvmArgs)
|
||||||
|
|
||||||
Runs the main method with the given JVM arguments.
|
Runs the main method with optional JVM arguments.
|
||||||
|
|
||||||
## Known limitations
|
## Known limitations
|
||||||
|
|
||||||
- casting to int truncation workaround requires parenthesis around the number being cast
|
- casting to int truncation workaround requires parenthesis around the number being cast `int x = (int) (Math.random() * 100);`
|
||||||
|
|
||||||
- no support for method overloading, though a workaround might be possible by making a function with the og name route to each of the variations of the overloaded function
|
- no support for method overloading, though a workaround might be possible by making a function with the og name route to each of the variations of the overloaded function
|
||||||
|
|
||||||
- no support for private/public methods yet, though this could be done since they are included in modern JavaScript classes
|
- no support for private/public methods yet, though this could be done since they are included in modern JavaScript classes
|
||||||
|
|
||||||
|
- no three dimensional arrays
|
||||||
|
|
||||||
|
- no third level static classes
|
||||||
|
|
||||||
|
- not much error checking
|
||||||
|
|
||||||
## Contribute
|
## Contribute
|
||||||
|
|
||||||
I've only done a barebones implementation of Java 17 JDK, a lot is missing, so if you are interested in adding more please go for it and submit a pull request!
|
I've only done a partial implementation of the Java 17 JDK in JavaScript, so if you're interested in adding more please go for it and submit a pull request!
|
||||||
|
89
jdk.js
89
jdk.js
@ -80,7 +80,10 @@
|
|||||||
lang.push('java.lang.' + name);
|
lang.push('java.lang.' + name);
|
||||||
}
|
}
|
||||||
await this.import(lang);
|
await this.import(lang);
|
||||||
} catch (e) {}
|
} catch (ror) {
|
||||||
|
console.error(ror);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
// make java.lang classes global
|
// make java.lang classes global
|
||||||
for (let name in this.java.lang) {
|
for (let name in this.java.lang) {
|
||||||
@ -130,40 +133,32 @@
|
|||||||
for (let className of classNames) {
|
for (let className of classNames) {
|
||||||
// log('importing ' + className);
|
// log('importing ' + className);
|
||||||
let imp = this.imports[className];
|
let imp = this.imports[className];
|
||||||
if (imp) {
|
if (!imp) {
|
||||||
// class is ready for use
|
imp = this.imports[className] = {};
|
||||||
if (imp.ready) ready++;
|
imp.load = null;
|
||||||
// class file loaded but not ready yet
|
imp.classPath = className.split('.');
|
||||||
continue;
|
|
||||||
|
let src = this.root + '/jdk';
|
||||||
|
for (let part of imp.classPath) {
|
||||||
|
src += '/' + part;
|
||||||
|
}
|
||||||
|
src += '.js';
|
||||||
|
|
||||||
|
const loadJS = () => {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
const script = document.createElement('script');
|
||||||
|
document.body.appendChild(script);
|
||||||
|
script.onload = resolve;
|
||||||
|
script.onerror = reject;
|
||||||
|
script.async = true;
|
||||||
|
script.src = src;
|
||||||
|
});
|
||||||
|
};
|
||||||
|
await loadJS();
|
||||||
}
|
}
|
||||||
imp = this.imports[className] = {};
|
if (!imp.ready) await imp.load();
|
||||||
imp.load = null;
|
|
||||||
imp.classPath = className.split('.');
|
|
||||||
|
|
||||||
let src = this.root + '/jdk';
|
|
||||||
for (let part of imp.classPath) {
|
|
||||||
src += '/' + part;
|
|
||||||
}
|
|
||||||
src += '.js';
|
|
||||||
|
|
||||||
const loadJS = () => {
|
|
||||||
return new Promise((resolve, reject) => {
|
|
||||||
const script = document.createElement('script');
|
|
||||||
document.body.appendChild(script);
|
|
||||||
script.onload = resolve;
|
|
||||||
script.onerror = reject;
|
|
||||||
script.async = true;
|
|
||||||
script.src = src;
|
|
||||||
});
|
|
||||||
};
|
|
||||||
|
|
||||||
await loadJS();
|
|
||||||
|
|
||||||
await imp.load();
|
|
||||||
|
|
||||||
classes.push(this.getClass(imp.classPath));
|
classes.push(this.getClass(imp.classPath));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (classNames.length == 1) classes = classes[0];
|
if (classNames.length == 1) classes = classes[0];
|
||||||
return classes;
|
return classes;
|
||||||
}
|
}
|
||||||
@ -186,13 +181,17 @@
|
|||||||
return '(' + p1.replace(/( |\t){0,3}(.*)(\r*\n|$)/gm, '"$2\\n"+').slice(0, -1) + ')';
|
return '(' + p1.replace(/( |\t){0,3}(.*)(\r*\n|$)/gm, '"$2\\n"+').slice(0, -1) + ')';
|
||||||
});
|
});
|
||||||
|
|
||||||
|
let arrToString = '';
|
||||||
|
|
||||||
// hacky support for Array literals
|
// hacky support for Array literals
|
||||||
file = file.replace(/new\s*\w*\s*\[\s*\]\s*\{([^}]*)}/gm, 'Array.of($1)');
|
file = file.replace(/new\s*\w*\s*\[\s*\]\s*\{([^}]*)}/gm, 'Array.of($1)');
|
||||||
|
|
||||||
|
// 2D arrays
|
||||||
file = file.replace(/new\s*\w*(\s*\[\s*\])*\s*\{([^}]*)\}/gm, (match, p1, p2) => {
|
file = file.replace(/new\s*\w*(\s*\[\s*\])*\s*\{([^}]*)\}/gm, (match, p1, p2) => {
|
||||||
return 'Array.of(' + p2.replace(/\{([^\}]*)\}/gm, 'Array.of($1)') + ')';
|
return 'Array.of(' + p2.replace(/\{([^\}]*)\}/gm, 'Array.of($1)') + ')';
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Array with defined length
|
||||||
file = file.replace(/new\s*\w*\s*\[\s*(\d)+\s*\]\s*/gm, 'new Array($1)');
|
file = file.replace(/new\s*\w*\s*\[\s*(\d)+\s*\]\s*/gm, 'new Array($1)');
|
||||||
|
|
||||||
// workaround hack for converting lambda expressions to Runnables
|
// workaround hack for converting lambda expressions to Runnables
|
||||||
@ -19210,13 +19209,21 @@
|
|||||||
case 'ArrayCreation':
|
case 'ArrayCreation':
|
||||||
return `new Array()`;
|
return `new Array()`;
|
||||||
case 'ArrayAccess':
|
case 'ArrayAccess':
|
||||||
|
let arr = expr.array;
|
||||||
// TODO support for three dimensional arrays
|
// TODO support for three dimensional arrays
|
||||||
if (expr.array.array) {
|
if (arr.array) {
|
||||||
return `${assignParent(expr.array.array.identifier)}[${parseExpr(expr.array.index)}][${parseExpr(
|
return `${assignParent(arr.array.identifier)}[${parseExpr(arr.index)}][${parseExpr(expr.index)}]`;
|
||||||
expr.index
|
|
||||||
)}]`;
|
|
||||||
}
|
}
|
||||||
return `${assignParent(expr.array.identifier)}[${parseExpr(expr.index)}]`;
|
if (arr.identifier) {
|
||||||
|
return `${assignParent(arr.identifier)}[${parseExpr(expr.index)}]`;
|
||||||
|
}
|
||||||
|
// TODO support for third level subclasses
|
||||||
|
if (arr.qualifier.qualifier) {
|
||||||
|
return `${assignParent(arr.qualifier.qualifier.identifier)}.${arr.qualifier.name.identifier}.${
|
||||||
|
arr.name.identifier
|
||||||
|
}[${parseExpr(expr.index)}]`;
|
||||||
|
}
|
||||||
|
return `${assignParent(arr.qualifier.identifier)}.${arr.name.identifier}[${parseExpr(expr.index)}]`;
|
||||||
case 'ParenthesizedExpression':
|
case 'ParenthesizedExpression':
|
||||||
return `(${parseExpr(expr.expression)})`;
|
return `(${parseExpr(expr.expression)})`;
|
||||||
default:
|
default:
|
||||||
@ -19372,13 +19379,17 @@
|
|||||||
return classData;
|
return classData;
|
||||||
};
|
};
|
||||||
|
|
||||||
const classToJs = ({ name: className, vars, superclass, methods, abstract }) => {
|
const classToJs = ({ name: className, vars, superclass, methods, abstract, classes }) => {
|
||||||
if (abstract) return '';
|
if (abstract) return '';
|
||||||
|
|
||||||
const initVars = [];
|
const initVars = [];
|
||||||
const classProps = [];
|
const classProps = [];
|
||||||
const staticVars = [];
|
const staticVars = [];
|
||||||
|
|
||||||
|
for (const cl of classes) {
|
||||||
|
staticVars.push(`${classToJs(cl)}\n${className}.${cl.name}=${cl.name};`);
|
||||||
|
}
|
||||||
|
|
||||||
for (const var_ of vars) {
|
for (const var_ of vars) {
|
||||||
if (var_.value === undefined) var_.value = literalInitializers[var_.type] || 'null';
|
if (var_.value === undefined) var_.value = literalInitializers[var_.type] || 'null';
|
||||||
if (var_.static) {
|
if (var_.static) {
|
||||||
@ -19404,7 +19415,7 @@
|
|||||||
? initVars.join('') + (block ? opts.separator : '')
|
? initVars.join('') + (block ? opts.separator : '')
|
||||||
: '';
|
: '';
|
||||||
let method = `${name}(${parameters}){${preblock}${block}}`;
|
let method = `${name}(${parameters}){${preblock}${block}}`;
|
||||||
if (typeof QuintOS != 'undefined' && /(System|alert|prompt|eraseRect)/gm.test(block))
|
if (typeof QuintOS != 'undefined' && /(alert|prompt|erase|eraseRect|text|textRect|frame)/gm.test(block))
|
||||||
method = 'async ' + method;
|
method = 'async ' + method;
|
||||||
classProps.push(method);
|
classProps.push(method);
|
||||||
}
|
}
|
||||||
|
@ -21,7 +21,7 @@ jdk.imports['java.io.PrintStream'].load = async () => {
|
|||||||
);
|
);
|
||||||
let md = MessageDigest.getInstance();
|
let md = MessageDigest.getInstance();
|
||||||
let str = '[Ljava.lang.';
|
let str = '[Ljava.lang.';
|
||||||
let hash = md.digest(arr.toString()).slice(0, 8);
|
let hash = md.digest(arr.join(',')).slice(0, 8);
|
||||||
if (arr.length == 0) {
|
if (arr.length == 0) {
|
||||||
return str + 'Array;@' + hash;
|
return str + 'Array;@' + hash;
|
||||||
}
|
}
|
||||||
@ -36,6 +36,8 @@ jdk.imports['java.io.PrintStream'].load = async () => {
|
|||||||
let str;
|
let str;
|
||||||
if (Array.isArray(arg)) {
|
if (Array.isArray(arg)) {
|
||||||
str = this._printArray(arg);
|
str = this._printArray(arg);
|
||||||
|
} else if (typeof arg == 'undefined' || arg == null) {
|
||||||
|
str = 'null';
|
||||||
} else {
|
} else {
|
||||||
str = arg.toString();
|
str = arg.toString();
|
||||||
}
|
}
|
||||||
@ -57,7 +59,7 @@ jdk.imports['java.io.PrintStream'].load = async () => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
printf(format, ...args) {
|
printf(format, ...args) {
|
||||||
let str = String.format(format, args);
|
let str = String.format(format, ...args);
|
||||||
return this._print(str);
|
return this._print(str);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
71
jdk/java/util/AbstractCollection.js
Normal file
71
jdk/java/util/AbstractCollection.js
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
jdk.imports['java.util.AbstractCollection'].load = async () => {
|
||||||
|
const Itr = await jdk.import('java.util.Itr');
|
||||||
|
|
||||||
|
class AbstractCollection {
|
||||||
|
constructor(co) {
|
||||||
|
this.arr = co || [];
|
||||||
|
}
|
||||||
|
|
||||||
|
add(idx, elem) {
|
||||||
|
if (typeof elem == 'undefined') {
|
||||||
|
return this.arr.push(idx);
|
||||||
|
} else {
|
||||||
|
return this.arr.splice(idx, 0, elem);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
addAll(idx, vals) {
|
||||||
|
this.arr.splice(idx, 0, ...vals);
|
||||||
|
}
|
||||||
|
|
||||||
|
clear() {
|
||||||
|
this.arr = [];
|
||||||
|
}
|
||||||
|
|
||||||
|
contains(val) {
|
||||||
|
return this.arr.indexOf(val) != -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
// containsAll(elems) {}
|
||||||
|
|
||||||
|
isEmpty() {
|
||||||
|
return this.arr.length == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
iterator() {
|
||||||
|
return new Itr(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
// parallelStream() {}
|
||||||
|
|
||||||
|
remove(idxOrElem) {
|
||||||
|
let index = idxOrElem;
|
||||||
|
if (typeof idxOrElem != 'number') {
|
||||||
|
index = this.arr.indexOf(idxOrElem);
|
||||||
|
}
|
||||||
|
return this.arr.splice(index, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
removeAll() {
|
||||||
|
this.arr = [];
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// removeIf() {}
|
||||||
|
|
||||||
|
// retainAll(collection) {}
|
||||||
|
|
||||||
|
size() {
|
||||||
|
return this.arr.length;
|
||||||
|
}
|
||||||
|
|
||||||
|
toArray() {
|
||||||
|
return this.arr;
|
||||||
|
}
|
||||||
|
|
||||||
|
toString() {
|
||||||
|
return '[' + this.arr.join(', ') + ']';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
jdk.java.util.AbstractCollection = AbstractCollection;
|
||||||
|
};
|
@ -1,87 +1,32 @@
|
|||||||
jdk.imports['java.util.AbstractList'].load = async () => {
|
jdk.imports['java.util.AbstractList'].load = async () => {
|
||||||
const Itr = await jdk.import('java.util.Itr');
|
let AbstractCollection = await jdk.import('java.util.AbstractCollection');
|
||||||
|
|
||||||
class AbstractList {
|
class AbstractList extends AbstractCollection {
|
||||||
constructor(arr) {
|
constructor(...args) {
|
||||||
// TODO
|
super(...args);
|
||||||
this.arr = arr || [];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
addAll(index, vals) {
|
// equals(o) {}
|
||||||
this.arr.splice(index, 0, ...vals);
|
|
||||||
|
get(idx) {
|
||||||
|
return this.arr[idx];
|
||||||
}
|
}
|
||||||
|
|
||||||
clear() {
|
indexOf(elem) {
|
||||||
this.arr = [];
|
return this.arr.indexOf(elem);
|
||||||
|
}
|
||||||
|
|
||||||
|
lastIndexOf(elem) {
|
||||||
|
return this.arr.lastIndexOf(elem);
|
||||||
}
|
}
|
||||||
|
|
||||||
poll() {
|
poll() {
|
||||||
return this.arr.shift();
|
return this.arr.shift();
|
||||||
}
|
}
|
||||||
|
|
||||||
remove(indexOrElem) {
|
set(idx, elem) {
|
||||||
let index = indexOrElem;
|
this.arr[idx] = elem;
|
||||||
if (typeof indexOrElem != 'number') {
|
return elem;
|
||||||
index = this.arr.indexOf(indexOrElem);
|
|
||||||
}
|
|
||||||
return this.arr.splice(index, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
removeAll() {
|
|
||||||
this.arr = [];
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
toArray() {
|
|
||||||
return this.arr;
|
|
||||||
}
|
|
||||||
|
|
||||||
toString() {
|
|
||||||
return '[' + this.arr.toString() + ']';
|
|
||||||
}
|
|
||||||
|
|
||||||
size() {
|
|
||||||
return this.arr.length;
|
|
||||||
}
|
|
||||||
|
|
||||||
add(index, elem) {
|
|
||||||
if (typeof elem == 'undefined') {
|
|
||||||
return this.arr.push(index);
|
|
||||||
} else {
|
|
||||||
return this.arr.splice(index, 0, elem);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
get(index) {
|
|
||||||
return this.arr[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
contains(val) {
|
|
||||||
return this.arr.indexOf(val) != -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// containsAll(elems) {
|
|
||||||
// }
|
|
||||||
|
|
||||||
isEmpty() {
|
|
||||||
return this.arr.length == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
set(index, element) {
|
|
||||||
this.arr[index] = element;
|
|
||||||
return element;
|
|
||||||
}
|
|
||||||
|
|
||||||
indexOf(element) {
|
|
||||||
return this.arr.indexOf(element);
|
|
||||||
}
|
|
||||||
|
|
||||||
lastIndexOf(element) {
|
|
||||||
return this.arr.lastIndexOf(element);
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator() {
|
|
||||||
return new Itr(this);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
jdk.java.util.AbstractList = AbstractList;
|
jdk.java.util.AbstractList = AbstractList;
|
||||||
|
80
jdk/java/util/AbstractMap.js
Normal file
80
jdk/java/util/AbstractMap.js
Normal file
@ -0,0 +1,80 @@
|
|||||||
|
jdk.imports['java.util.AbstractMap'].load = async () => {
|
||||||
|
let AbstractCollection = await jdk.import('java.util.AbstractCollection');
|
||||||
|
let Set = await jdk.import('java.util.Set');
|
||||||
|
|
||||||
|
class AbstractMap {
|
||||||
|
constructor(co) {
|
||||||
|
this.map = co || {};
|
||||||
|
class SimpleEntry {
|
||||||
|
constructor(key, val) {
|
||||||
|
this.key = key;
|
||||||
|
this.val = val;
|
||||||
|
}
|
||||||
|
|
||||||
|
getKey() {
|
||||||
|
return this.key;
|
||||||
|
}
|
||||||
|
|
||||||
|
getValue() {
|
||||||
|
return this.val;
|
||||||
|
}
|
||||||
|
|
||||||
|
toString() {
|
||||||
|
return this.key + '=' + this.val;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
this.SimpleEntry = SimpleEntry;
|
||||||
|
}
|
||||||
|
|
||||||
|
clear() {
|
||||||
|
this.map = {};
|
||||||
|
}
|
||||||
|
|
||||||
|
containsKey(key) {
|
||||||
|
return this.map.hasOwnProperty(key);
|
||||||
|
}
|
||||||
|
|
||||||
|
containsValue(val) {
|
||||||
|
return Object.values(this.map).find((x) => x == val) ? true : false;
|
||||||
|
}
|
||||||
|
|
||||||
|
get(key) {
|
||||||
|
return this.map[key] || null;
|
||||||
|
}
|
||||||
|
|
||||||
|
isEmpty() {
|
||||||
|
return Object.keys(this.map).length == 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
entrySet() {
|
||||||
|
let set = new Set();
|
||||||
|
for (let key in this.map) {
|
||||||
|
set.add(new this.SimpleEntry(key, this.map[key]));
|
||||||
|
}
|
||||||
|
return set;
|
||||||
|
}
|
||||||
|
|
||||||
|
put(key, value) {
|
||||||
|
const previous_val = this.map[key];
|
||||||
|
this.map[key] = value;
|
||||||
|
return previous_val || null;
|
||||||
|
}
|
||||||
|
|
||||||
|
remove(key) {
|
||||||
|
if (!this.map[key]) return null;
|
||||||
|
const val = this.map[key];
|
||||||
|
delete this.map[key];
|
||||||
|
return val;
|
||||||
|
}
|
||||||
|
|
||||||
|
values() {
|
||||||
|
const co = new AbstractCollection(Object.values(this.map));
|
||||||
|
return co;
|
||||||
|
}
|
||||||
|
|
||||||
|
size() {
|
||||||
|
return Object.keys(this.map).length;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
jdk.java.util.AbstractMap = AbstractMap;
|
||||||
|
};
|
17
jdk/java/util/AbstractSet.js
Normal file
17
jdk/java/util/AbstractSet.js
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
jdk.imports['java.util.AbstractSet'].load = async () => {
|
||||||
|
let AbstractCollection = await jdk.import('java.util.AbstractCollection');
|
||||||
|
|
||||||
|
class AbstractSet extends AbstractCollection {
|
||||||
|
constructor(...args) {
|
||||||
|
super(...args);
|
||||||
|
}
|
||||||
|
|
||||||
|
add(elem) {
|
||||||
|
if (this.arr.includes(elem)) return;
|
||||||
|
super.add(elem);
|
||||||
|
}
|
||||||
|
|
||||||
|
// equals(o) {}
|
||||||
|
}
|
||||||
|
jdk.java.util.AbstractSet = AbstractSet;
|
||||||
|
};
|
@ -3,7 +3,7 @@ jdk.imports['java.util.ArrayList'].load = async () => {
|
|||||||
|
|
||||||
class ArrayList extends AbstractList {
|
class ArrayList extends AbstractList {
|
||||||
constructor(...args) {
|
constructor(...args) {
|
||||||
super(args);
|
super(...args);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
jdk.java.util.ArrayList = ArrayList;
|
jdk.java.util.ArrayList = ArrayList;
|
||||||
|
@ -1,59 +1,9 @@
|
|||||||
jdk.imports['java.util.HashMap'].load = async () => {
|
jdk.imports['java.util.HashMap'].load = async () => {
|
||||||
class HashMap {
|
let AbstractMap = await jdk.import('java.util.AbstractMap');
|
||||||
constructor() {
|
|
||||||
this.content = {};
|
|
||||||
}
|
|
||||||
|
|
||||||
get(key) {
|
class HashMap extends AbstractMap {
|
||||||
return this.content[key];
|
constructor(...args) {
|
||||||
}
|
super(...args);
|
||||||
|
|
||||||
put(key, value) {
|
|
||||||
const previous_val = this.content[key];
|
|
||||||
this.content[key] = value;
|
|
||||||
return previous_val;
|
|
||||||
}
|
|
||||||
|
|
||||||
containsKey(key) {
|
|
||||||
return this.content.hasOwnProperty(key);
|
|
||||||
}
|
|
||||||
|
|
||||||
remove(key) {
|
|
||||||
const tmp = this.content[key];
|
|
||||||
delete this.content[key];
|
|
||||||
return tmp;
|
|
||||||
}
|
|
||||||
|
|
||||||
keySet() {
|
|
||||||
const result = new HashSet();
|
|
||||||
for (const p in this.content) {
|
|
||||||
if (this.content.hasOwnProperty(p)) {
|
|
||||||
result.add(p);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
isEmpty() {
|
|
||||||
return Object.keys(this.content).length == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
values() {
|
|
||||||
const result = new HashSet();
|
|
||||||
for (const p in this.content) {
|
|
||||||
if (this.content.hasOwnProperty(p)) {
|
|
||||||
result.add(this.content[p]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
clear() {
|
|
||||||
this.content = {};
|
|
||||||
}
|
|
||||||
|
|
||||||
size() {
|
|
||||||
return Object.keys(this.content).length;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
jdk.java.util.HashMap = HashMap;
|
jdk.java.util.HashMap = HashMap;
|
||||||
|
@ -1,72 +1,12 @@
|
|||||||
jdk.imports['java.util.HashSet'].load = async () => {
|
jdk.imports['java.util.HashSet'].load = async () => {
|
||||||
class HashSet {
|
let AbstractSet = await jdk.import('java.util.AbstractSet');
|
||||||
constructor() {
|
|
||||||
this.content = {};
|
class HashSet extends AbstractSet {
|
||||||
|
constructor(...args) {
|
||||||
|
super(...args);
|
||||||
}
|
}
|
||||||
|
|
||||||
add(val) {
|
// equals(o) {}
|
||||||
this.content[val] = val;
|
|
||||||
}
|
|
||||||
|
|
||||||
clear() {
|
|
||||||
this.content = {};
|
|
||||||
}
|
|
||||||
|
|
||||||
contains(val) {
|
|
||||||
return this.content.hasOwnProperty(val);
|
|
||||||
}
|
|
||||||
|
|
||||||
containsAll(elems) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
addAll(vals) {
|
|
||||||
const tempArray = vals.toArray(null);
|
|
||||||
for (let i = 0; i < tempArray.length; i++) {
|
|
||||||
this.content[tempArray[i]] = tempArray[i];
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
remove(val) {
|
|
||||||
let b = false;
|
|
||||||
if (this.content[val]) {
|
|
||||||
b = true;
|
|
||||||
}
|
|
||||||
delete this.content[val];
|
|
||||||
return b;
|
|
||||||
}
|
|
||||||
|
|
||||||
removeAll() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
size() {
|
|
||||||
return Object.keys(this.content).length;
|
|
||||||
}
|
|
||||||
|
|
||||||
isEmpty() {
|
|
||||||
return this.size() == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
toArray(a) {
|
|
||||||
const _this = this;
|
|
||||||
return Object.keys(this.content).map((key) => _this.content[key]);
|
|
||||||
}
|
|
||||||
|
|
||||||
iterator() {
|
|
||||||
return new java.util.Itr(this);
|
|
||||||
}
|
|
||||||
|
|
||||||
forEach(f) {
|
|
||||||
for (const p in this.content) {
|
|
||||||
f(this.content[p]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
get(index) {
|
|
||||||
return this.content[index];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
jdk.java.util.HashSet = HashSet;
|
jdk.java.util.HashSet = HashSet;
|
||||||
};
|
};
|
||||||
|
@ -3,7 +3,7 @@ jdk.imports['java.util.LinkedList'].load = async () => {
|
|||||||
|
|
||||||
class LinkedList extends AbstractList {
|
class LinkedList extends AbstractList {
|
||||||
constructor(...args) {
|
constructor(...args) {
|
||||||
super(args);
|
super(...args);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
jdk.java.util.LinkedList = LinkedList;
|
jdk.java.util.LinkedList = LinkedList;
|
||||||
|
12
jdk/java/util/Set.js
Normal file
12
jdk/java/util/Set.js
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
jdk.imports['java.util.Set'].load = async () => {
|
||||||
|
let AbstractSet = await jdk.import('java.util.AbstractSet');
|
||||||
|
|
||||||
|
class Set extends AbstractSet {
|
||||||
|
constructor(...args) {
|
||||||
|
super(...args);
|
||||||
|
}
|
||||||
|
|
||||||
|
// equals(o) {}
|
||||||
|
}
|
||||||
|
jdk.java.util.Set = Set;
|
||||||
|
};
|
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "java2js",
|
"name": "java2js",
|
||||||
"version": "1.1.3",
|
"version": "1.1.4",
|
||||||
"description": "Converts Java to JavaScript with support for p5.js and QuintOS.",
|
"description": "Converts Java to JavaScript with support for p5.js and QuintOS.",
|
||||||
"main": "jdk.js",
|
"main": "jdk.js",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user