Merge pull request #58 from Trivernis/release/1.0

Release/1.0
pull/59/head
Trivernis 4 years ago committed by GitHub
commit d5ce796f9e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -33,12 +33,12 @@ All features can be accessed with the command `/chunkmaster` or the aliases `/ch
- `/chunkmaster generate [world] [radius] [<square|circle>]` Starts the generation until the specified chunk count or the world border is reached. - `/chunkmaster generate [world] [radius] [<square|circle>]` Starts the generation until the specified chunk count or the world border is reached.
- `/chunkmaster list` Lists all running generation tasks - `/chunkmaster list` Lists all running generation tasks
- `/chunkmaster cancel <Task id>` Cancels the generation task with the specified id (if it is running). - `/chunkmaster cancel <Task id|world name>` Cancels the generation task with the specified id (if it is running).
- `/chunkmaster pause` Pauses all generation tasks until the resume command is executed. - `/chunkmaster pause` Pauses all generation tasks until the resume command is executed.
- `/chunkmaster resume` Resumes all paused generation tasks. - `/chunkmaster resume` Resumes all paused generation tasks.
- `/chunkmaster reload` Reloads the configuration file. - `/chunkmaster reload` Reloads the configuration file.
- `/chunkmaster tpchunk <X> <Z>` Teleports you to the specified chunk coordinates. - `/chunkmaster tpchunk <X> <Z>` Teleports you to the specified chunk coordinates.
- `/<command> setCenter [<world>] <chunkX> <chunkZ>` - sets the center chunk of the world - `/<command> setCenter [[<world>] <chunkX> <chunkZ>]]` - sets the center chunk of the world
- `/<command> getCenter [<world>]` - returns the center chunk of the world - `/<command> getCenter [<world>]` - returns the center chunk of the world
#### Examples #### Examples
@ -114,13 +114,12 @@ generation:
# The value should be a positive integer greater than 50. # The value should be a positive integer greater than 50.
mspt-pause-threshold: 500 mspt-pause-threshold: 500
# If the chunk generation process should pause on player join. # Pauses the generation if the number of players on the server is larger or equal
# to the configured value
# Notice that playing on a server that constantly generates chunks can be # Notice that playing on a server that constantly generates chunks can be
# very laggy and can cause it to crash. # very laggy and can cause it to crash.
# You could configure the values above so that the performance impact of the generation # The value should be a posivitve integer > 1.
# process is minimal. pause-on-player-count: 1
# The value should be a boolean <true/false>
pause-on-join: true
``` ```
### Spigot and Paper ### Spigot and Paper

@ -22,7 +22,7 @@ idea {
} }
group "net.trivernis" group "net.trivernis"
version "0.16-beta" version "1.0"
sourceCompatibility = 1.8 sourceCompatibility = 1.8

@ -75,7 +75,7 @@ class Chunkmaster: JavaPlugin() {
config.addDefault("generation.chunks-per-step", 2) config.addDefault("generation.chunks-per-step", 2)
config.addDefault("generation.chunk-skips-per-step", 100) config.addDefault("generation.chunk-skips-per-step", 100)
config.addDefault("generation.mspt-pause-threshold", 500L) config.addDefault("generation.mspt-pause-threshold", 500L)
config.addDefault("generation.pause-on-join", true) config.addDefault("generation.pause-on-player-count", 1)
config.addDefault("generation.max-pending-chunks", 10) config.addDefault("generation.max-pending-chunks", 10)
config.addDefault("generation.max-loaded-chunks", 10) config.addDefault("generation.max-loaded-chunks", 10)
config.addDefault("generation.ignore-worldborder", false) config.addDefault("generation.ignore-worldborder", false)

@ -1,16 +1,17 @@
package net.trivernis.chunkmaster package net.trivernis.chunkmaster
import net.trivernis.chunkmaster.lib.generation.GenerationTaskPaper
import org.bukkit.Server import org.bukkit.Server
import org.bukkit.event.EventHandler import org.bukkit.event.EventHandler
import org.bukkit.event.Listener import org.bukkit.event.Listener
import org.bukkit.event.player.PlayerJoinEvent import org.bukkit.event.player.PlayerJoinEvent
import org.bukkit.event.player.PlayerQuitEvent import org.bukkit.event.player.PlayerQuitEvent
import org.bukkit.event.world.WorldSaveEvent
class ChunkmasterEvents(private val chunkmaster: Chunkmaster, private val server: Server) : Listener { class ChunkmasterEvents(private val chunkmaster: Chunkmaster, private val server: Server) : Listener {
private val pauseOnJoin = chunkmaster.config.getBoolean("generation.pause-on-join") private val pauseOnPlayerCount: Int
get () {
return chunkmaster.config.getInt("generation.pause-on-player-count")
}
private var playerPaused = false private var playerPaused = false
/** /**
@ -18,21 +19,15 @@ class ChunkmasterEvents(private val chunkmaster: Chunkmaster, private val server
*/ */
@EventHandler @EventHandler
fun onPlayerQuit(event: PlayerQuitEvent) { fun onPlayerQuit(event: PlayerQuitEvent) {
if (pauseOnJoin) { if (server.onlinePlayers.size == pauseOnPlayerCount) {
if (server.onlinePlayers.size == 1 && server.onlinePlayers.contains(event.player) || if (!playerPaused) {
server.onlinePlayers.isEmpty() if (chunkmaster.generationManager.pausedTasks.isNotEmpty()) {
) { chunkmaster.logger.info(chunkmaster.langManager.getLocalized("RESUME_PLAYER_LEAVE"))
if (!playerPaused) {
if (chunkmaster.generationManager.pausedTasks.isNotEmpty()) {
chunkmaster.logger.info("Server is empty. Resuming chunk generation tasks.")
}
chunkmaster.generationManager.resumeAll()
} else if (chunkmaster.generationManager.paused){
chunkmaster.logger.info("Generation was manually paused. Not resuming automatically.")
playerPaused = chunkmaster.generationManager.paused
} else {
chunkmaster.logger.info("Generation tasks are already running.")
} }
chunkmaster.generationManager.resumeAll()
} else if (chunkmaster.generationManager.paused){
chunkmaster.logger.info(chunkmaster.langManager.getLocalized("PAUSE_MANUALLY"))
playerPaused = chunkmaster.generationManager.paused
} }
} }
} }
@ -42,14 +37,12 @@ class ChunkmasterEvents(private val chunkmaster: Chunkmaster, private val server
*/ */
@EventHandler @EventHandler
fun onPlayerJoin(event: PlayerJoinEvent) { fun onPlayerJoin(event: PlayerJoinEvent) {
if (pauseOnJoin) { if (server.onlinePlayers.size >= pauseOnPlayerCount) {
if (server.onlinePlayers.size == 1 || server.onlinePlayers.isEmpty()) { if (chunkmaster.generationManager.tasks.isNotEmpty()) {
if (chunkmaster.generationManager.tasks.isNotEmpty()) { chunkmaster.logger.info(chunkmaster.langManager.getLocalized("PAUSE_PLAYER_JOIN"))
chunkmaster.logger.info("Pausing generation tasks because of player join.")
}
playerPaused = chunkmaster.generationManager.paused
chunkmaster.generationManager.pauseAll()
} }
playerPaused = chunkmaster.generationManager.paused
chunkmaster.generationManager.pauseAll()
} }
} }
} }

@ -30,14 +30,21 @@ class CmdCancel(private val chunkmaster: Chunkmaster): Subcommand {
* Cancels the generation task if it exists. * Cancels the generation task if it exists.
*/ */
override fun execute(sender: CommandSender, args: List<String>): Boolean { override fun execute(sender: CommandSender, args: List<String>): Boolean {
return if (args.isNotEmpty() && args[0].toIntOrNull() != null) { return if (args.isNotEmpty()) {
if (chunkmaster.generationManager.removeTask(args[0].toInt())) { val index = if (args[0].toIntOrNull() != null) {
sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_CANCELED", args[0])) args[0].toInt()
} else {
chunkmaster.generationManager.tasks.find { it.generationTask.world.name == args[0] }?.id
}
if (index != null && chunkmaster.generationManager.removeTask(index)) {
sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_CANCELED", index))
true true
} else { } else {
sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_NOT_FOUND", args[0])) sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_NOT_FOUND", args[0]))
false false
} }
} else { } else {
sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_ID_REQUIRED")); sender.sendMessage(chunkmaster.langManager.getLocalized("TASK_ID_REQUIRED"));
false false

@ -29,26 +29,30 @@ class CmdSetCenter(private val chunkmaster: Chunkmaster): Subcommand {
val centerX: Int val centerX: Int
val centerZ: Int val centerZ: Int
if (args.size < 2) {
sender.sendMessage(chunkmaster.langManager.getLocalized("TOO_FEW_ARGUMENTS"))
return false
}
if (sender is Player) { if (sender is Player) {
if (args.size == 2) { when {
world = sender.world.name args.isEmpty() -> {
if (args[0].toIntOrNull() == null || args[1].toIntOrNull() == null) { world = sender.world.name
sender.sendMessage(chunkmaster.langManager.getLocalized("COORD_INVALID", args[0], args[1])) centerX = sender.location.chunk.x
return false centerZ = sender.location.chunk.z
} }
centerX = args[0].toInt() args.size == 2 -> {
centerZ = args[1].toInt() world = sender.world.name
} else { if (args[0].toIntOrNull() == null || args[1].toIntOrNull() == null) {
if (!validateThreeArgs(sender, args)) { sender.sendMessage(chunkmaster.langManager.getLocalized("COORD_INVALID", args[0], args[1]))
return false return false
}
centerX = args[0].toInt()
centerZ = args[1].toInt()
}
else -> {
if (!validateThreeArgs(sender, args)) {
return false
}
world = args[0]
centerX = args[1].toInt()
centerZ = args[2].toInt()
} }
world = args[0]
centerX = args[1].toInt()
centerZ = args[2].toInt()
} }
} else { } else {
if (args.size < 3) { if (args.size < 3) {

@ -19,7 +19,7 @@ class GenerationManager(private val chunkmaster: Chunkmaster, private val server
this.loadWorldCenters() this.loadWorldCenters()
} }
this.startAll() this.startAll()
if (!server.onlinePlayers.isEmpty()) { if (server.onlinePlayers.size >= chunkmaster.config.getInt("generation.pause-on-player-count")) {
this.pauseAll() this.pauseAll()
} }
} }
@ -239,7 +239,7 @@ class GenerationManager(private val chunkmaster: Chunkmaster, private val server
/** /**
* Overload that doesn't need an argument * Overload that doesn't need an argument
*/ */
fun loadWorldCenters() { private fun loadWorldCenters() {
loadWorldCenters(null) loadWorldCenters(null)
} }

@ -5,12 +5,13 @@ import net.trivernis.chunkmaster.lib.dynmap.*
import net.trivernis.chunkmaster.lib.shapes.Shape import net.trivernis.chunkmaster.lib.shapes.Shape
import org.bukkit.Chunk import org.bukkit.Chunk
import org.bukkit.World import org.bukkit.World
import java.lang.Exception
/** /**
* Interface for generation tasks. * Interface for generation tasks.
*/ */
abstract class GenerationTask( abstract class GenerationTask(
plugin: Chunkmaster, private val plugin: Chunkmaster,
startChunk: ChunkCoordinates, startChunk: ChunkCoordinates,
val shape: Shape val shape: Shape
) : ) :
@ -69,7 +70,11 @@ abstract class GenerationTask(
protected fun unloadLoadedChunks() { protected fun unloadLoadedChunks() {
for (chunk in loadedChunks) { for (chunk in loadedChunks) {
if (chunk.isLoaded) { if (chunk.isLoaded) {
chunk.unload(true) try {
chunk.unload(true)
} catch (e: Exception) {
plugin.logger.severe(e.toString())
}
} }
if (dynmapIntegration) { if (dynmapIntegration) {
dynmap?.triggerRenderOfVolume(chunk.getBlock(0, 0, 0).location, chunk.getBlock(15, 255, 15).location) dynmap?.triggerRenderOfVolume(chunk.getBlock(0, 0, 0).location, chunk.getBlock(15, 255, 15).location)

@ -4,6 +4,7 @@ import net.trivernis.chunkmaster.Chunkmaster
import net.trivernis.chunkmaster.lib.shapes.Shape import net.trivernis.chunkmaster.lib.shapes.Shape
import org.bukkit.Chunk import org.bukkit.Chunk
import org.bukkit.World import org.bukkit.World
import java.lang.Exception
import java.util.concurrent.CompletableFuture import java.util.concurrent.CompletableFuture
class GenerationTaskPaper( class GenerationTaskPaper(
@ -92,7 +93,11 @@ class GenerationTaskPaper(
} }
for (chunk in loadedChunks) { for (chunk in loadedChunks) {
if (chunk.isLoaded) { if (chunk.isLoaded) {
chunk.unload(true) try {
chunk.unload(true);
} catch (e: Exception){
plugin.logger.severe(e.toString())
}
} }
} }
} }

@ -56,4 +56,8 @@ COORD_INVALID = §cThe provided coordinate ('%s', '%s') is invalid!
CENTER_UPDATED = §9The center for world §2%s §9has been set to §2(%s, %s)§9. CENTER_UPDATED = §9The center for world §2%s §9has been set to §2(%s, %s)§9.
CENTER_INFO = §9The center for world §2%s §9is §2(%s, %s)§9. CENTER_INFO = §9The center for world §2%s §9is §2(%s, %s)§9.
PLUGIN_DETECTED = Detected %s version %s PLUGIN_DETECTED = Detected %s version %s
RESUME_PLAYER_LEAVE = The player count is smaller than the configured pause value. Resuming generation...
PAUSE_PLAYER_JOIN = The player count has reached the pause value. Pausing generation...
PAUSE_MANUALLY = Generation was manually paused. Not resuming automatically.

@ -51,9 +51,13 @@ TABLE_CREATE_ERROR = §cFehler beim erstellen der Tabelle %s.
UPDATE_TABLE_DEFINITION = Tabelle %s wurde mit sql %s geupdated. UPDATE_TABLE_DEFINITION = Tabelle %s wurde mit sql %s geupdated.
UPDATE_TABLE_FAILED = Fehler beim Updaten der Tabelle %s mit sql %s. UPDATE_TABLE_FAILED = Fehler beim Updaten der Tabelle %s mit sql %s.
TOO_FEW_ARGUMENTS = §cDu hast nicht genug arguments angegeben. TOO_FEW_ARGUMENTS = §cDu hast nicht genug Parameter angegeben.
COORD_INVALID = §cDie Koordinate ('%s', '%s') ist ungültig! COORD_INVALID = §cDie Koordinate ('%s', '%s') ist ungültig!
CENTER_UPDATED = §9Die Mitte der Welt §2%s §9wurde auf §2(%s, %s)§9 gesetzt. CENTER_UPDATED = §9Die Mitte der Welt §2%s §9wurde auf §2(%s, %s)§9 gesetzt.
CENTER_INFO = §9Die Mitte der Welt §2%s §9ist §2(%s, %s)§9. CENTER_INFO = §9Die Mitte der Welt §2%s §9ist §2(%s, %s)§9.
PLUGIN_DETECTED = Plugin %s in der Version %s gefunden! PLUGIN_DETECTED = Plugin %s in der Version %s gefunden!
RESUME_PLAYER_LEAVE = Die Anzahl der Spieler hat den festgelegen Wert zum Pausieren unterschritten. Setze Generieren fort...
PAUSE_PLAYER_JOIN = Die Anzahl der Spieler hat den festgelegten Wert zum Pausieren erreicht. Pausiere...
PAUSE_MANUALLY = Das Generieren wurde manuell pausiert und wird deswegen nicht automatisch fortgesetzt.

@ -56,4 +56,8 @@ COORD_INVALID = §cThe provided coordinate ('%s', '%s') is invalid!
CENTER_UPDATED = §9The center for world §2%s §9has been set to §2(%s, %s)§9. CENTER_UPDATED = §9The center for world §2%s §9has been set to §2(%s, %s)§9.
CENTER_INFO = §9The center for world §2%s §9is §2(%s, %s)§9. CENTER_INFO = §9The center for world §2%s §9is §2(%s, %s)§9.
PLUGIN_DETECTED = Detected %s version %s PLUGIN_DETECTED = Detected %s version %s
RESUME_PLAYER_LEAVE = The player count is smaller than the configured pause value. Resuming generation...
PAUSE_PLAYER_JOIN = The player count has reached the pause value. Pausing generation...
PAUSE_MANUALLY = Generation was manually paused. Not resuming automatically.

@ -1,6 +1,6 @@
main: net.trivernis.chunkmaster.Chunkmaster main: net.trivernis.chunkmaster.Chunkmaster
name: Chunkmaster name: Chunkmaster
version: '0.16-beta' version: '1.0'
description: Chunk commands plugin. description: Chunk commands plugin.
author: Trivernis author: Trivernis
website: trivernis.net website: trivernis.net
@ -14,13 +14,13 @@ commands:
permission: chunkmaster.chunkmaster permission: chunkmaster.chunkmaster
usage: | usage: |
/<command> generate [<world>] <radius> [<shape>] - generates chunks starting from the spawn until the chunk-count is reached /<command> generate [<world>] <radius> [<shape>] - generates chunks starting from the spawn until the chunk-count is reached
/<command> cancel <task-id> - cancels the generation task with the task-id /<command> cancel <task-id|world> - cancels the generation task with the task-id
/<command> list - lists all running and paused generation tasks /<command> list - lists all running and paused generation tasks
/<command> pause - pauses all generation tasks /<command> pause - pauses all generation tasks
/<command> resume - resumes all generation tasks /<command> resume - resumes all generation tasks
/<command> reload - reloads the configuration and restarts all tasks /<command> reload - reloads the configuration and restarts all tasks
/<command> tpchunk <chunkX> <chunkZ> - teleports you to the chunk with the given chunk coordinates /<command> tpchunk <chunkX> <chunkZ> - teleports you to the chunk with the given chunk coordinates
/<command> setCenter [<world>] <chunkX> <chunkZ> - sets the center chunk of the world /<command> setCenter [[<world>] <chunkX> <chunkZ>]] - sets the center chunk of the world
/<command> getCenter [<world>] - returns the center chunk of the world /<command> getCenter [<world>] - returns the center chunk of the world
aliases: aliases:
- chm - chm

Loading…
Cancel
Save