Files
Use AddonFiles to keep files. Do not use java.io.File or java.nio.file: they make the label Red.
AddonFiles gives your addon one folder with a quota. It gives the results on the main thread.
Permission: files. Without it, each call gives a SecurityException to your code.
permissions=filesfiles.quotaMiB=16The folder
Section titled “The folder”Your folder is Zomboid/viewpoint-addons/<id>/. You cannot name a file outside it. Viewpoint never loads code from this
folder.
On the addon’s Files tab, the player can:
- open the folder;
- see its size and the download log;
- delete it.
Use it
Section titled “Use it”AddonFiles files = ctx.files();
files.read("counter.txt") .then(bytes -> { int n = Integer.parseInt(new String(bytes, StandardCharsets.US_ASCII)); files.write("counter.txt", Integer.toString(n + 1).getBytes(StandardCharsets.US_ASCII)); }) .otherwise(error -> files.write("counter.txt", "1".getBytes(StandardCharsets.US_ASCII)));The first time, the file is not there: the read fails, and otherwise writes the first number. A test compiles this code and
runs it against the real AddonFiles.
| Method | Result |
|---|---|
read(name) | Pending<byte[]>. Fails if the file does not exist. |
write(name, bytes) | Pending<Void>. Viewpoint copies bytes at the call. If the game stops during a write, the old file stays complete. |
delete(name) | Pending<Void>. A file that is not there is not an error. |
exists(name) | Pending<Boolean>. |
list(prefix) | Pending<List<String>>. The names that start with the prefix, in order. A file that the player put in the folder, with a name that is not a valid name, is not in the list. |
usage() | Pending<AddonFiles.Usage>. The bytes and the files in the folder, and the quotaBytes. |
Pending<T>
Section titled “Pending<T>”Viewpoint does the disk work on a different thread. Pending<T> gives you the result.
| Member | Meaning |
|---|---|
then(Consumer<T>) | Runs if the work is successful. Gives the same Pending. |
otherwise(Consumer<Throwable>) | Runs if the work fails. Gives the same Pending. |
isDone() | true when the work is complete. |
The callbacks run on the main thread, in a frame after the work is complete. You can chain then and otherwise. If
the addon goes off before a callback runs, Viewpoint does not run that callback.
- Use lower-case letters, digits,
-and_. - Use
/to put a file in a subfolder. Keep the names short and the subfolders few. - Use one extension from this list:
png,jpg,json,txt,csv,properties,ogg,wav,obj,mtl,bin,dat.
If Viewpoint does not accept a name, the call throws IllegalArgumentException immediately. You get no Pending. Use a
simple lower-case name with an extension from the list.
Limits
Section titled “Limits”| Limit | Value |
|---|---|
| The folder | 64 MiB by default. A larger files.quotaMiB needs the player’s consent. |
| One file | 16 MiB |
| Files and folders together | 1,000. A folder that a delete leaves empty goes with it. |
If a write goes over a limit, its Pending fails with an error. Viewpoint does not delete files to make space.
Viewpoint also limits what waits. At most 256 calls wait for their result, and at most 32 MiB of data is in transfer (a
write that has not finished, or a read that you have not taken). A call over a limit throws IllegalStateException; make
the next call in the callback of an earlier one. The errors name your file, never a path on the player’s computer.
Call AddonFiles and its Pending on the main thread. From any other thread a call throws IllegalStateException.
A link, a junction or a special file in your folder is not followed. A call that meets one fails. Your addon cannot make one.