← Volver a la documentación

Documentación del servidor

QuantumHy

Activo

Hytale • Version 0.4.0

Instalación, claves de config, radio adaptativo de chunks y entidades, freeze de expand, gobernador de presión y convivencia con LeanCore en Hytale 0.7.

Instalación, configuración y comportamiento en tiempo de ejecución de QuantumHy.


Resumen

QuantumHy es un mod de FPS del lado del servidor para Hytale 0.7. El cliente es nativo y no se puede modificar, pero el servidor decide cuánto tiene que renderizar cada cliente, así que QuantumHy lo recorta por jugador. Cada pocos segundos muestrea la densidad de entidades alrededor de cada jugador, la suaviza y la usa para reducir el radio de visión en chunks y el radio de stream de entidades. Cada jugador puede activar o desactivar la optimización para sí mismo sin cambiar a los demás.

Nunca infla la visión más allá de lo que el jugador pidió. El radio no vuelve en el instante en que la densidad parece abierta: el expand se congela hasta que la carga esté calmada, el disco de density esté al menos a medio cargar, el jugador no esté volando y el mundo no esté bajo presión MSPT. Solo ayuda donde está instalado, nunca en un servidor remoto al que solo te conectas.


Instalación

  1. Descarga QuantumHy-0.4.0.jar desde la pestaña Files de CurseForge
  2. Coloca el JAR en la carpeta mods/ del servidor, o en Windows: %AppData%\Hytale\UserData\Mods
  3. Inicia el servidor. La config se genera como QuantumHy.json en la carpeta de datos del plugin
  4. Observa el registro del servidor por la línea de setup (ver Comprobando que funciona)

Comandos

/q status
/q optimize on
/q optimize off
/q help

Aliases: /quantumhy, /qhy. Un jugador común solo ve su modo y última decisión en /q status. Los admins y la consola ven el diagnóstico completo. /q optimize on|off solo cambia al jugador que lo ejecuta y guarda la elección por UUID.


Cómo funciona

En cada pasada (5s por defecto) QuantumHy hace el trabajo por jugador en el hilo del mundo dueño:

  1. Muestrea la densidad (a veces se omite). Cuenta entidades en un disco de densityScanChunkRadius chunks (dx²+dz² ≤ r²). El barrido de 49 columnas se omite en la primera pasada, en vuelo (2+ chunks/pasada), en streaming, con caché reciente del mismo chunk, y mientras ya está en el mínimo con expand congelado. La caché de un jugador quieto caduca tras 15 segundos.
  2. La suaviza. Una muestra válida pasa por una media móvil exponencial (densitySmoothing).
  3. La convierte en un factor de reducción. La densidad usa smoothstep entre densityLowPerChunk y densityHighPerChunk. Se combina con shrink por chunk-load (sections cargadas + cargando) y un suelo baseline. El factor combinado solo aumenta el shrink hasta que el expand está permitido (ratchet).
  4. Rampa dos palancas. La visión en chunks se mueve como máximo +1 / −2 por pasada (−4 bajo presión). El radio de entidades usa el mismo factor; en shrink completo ([min]) baja a minEntityViewBlocks en una escritura. Las escrituras paran después de worldPassBudgetMs o durante streaming.

El expand solo se permite tras expandHysteresisPasses pasadas calmadas, disco de density ≥ 50% cargado, sin streaming, sin desplazamiento rápido y sin presión MSPT.

entityLodAggressiveness es aparte y global. El valor 1.0 mantiene el LOD del motor. Los valores superiores a 1.0 son un override explícito del admin, y solo entonces la presión MSPT aplica pressureLodMultiplier.


Configuración

Archivos de runtime: QuantumHy.json y PlayerPreferences.json en la carpeta de datos del plugin, creados en el primer arranque. Las instalaciones nuevas reciben configVersion 8.

ClavePor defectoQué hace
enabledtrueInterruptor maestro. Cuando es false, QuantumHy nunca toca ningún radio de visión.
verboseLogfalseRegistra cada pasada con la densidad y la decisión de visión de cada jugador. Off en instalaciones nuevas.
checkForUpdatestrueAl arrancar, lee la página de QuantumHy y avisa a operadores o durkz.quantumhy.admin si hay un JAR más nuevo.
tickIntervalSeconds5Cada cuánto revisa a cada jugador.
initialDelaySeconds20Espera este tiempo tras el arranque antes de la primera pasada.
targetClientViewRadius0Tope fijo en chunks. 0 significa sin tope, solo adapta por densidad.
minClientViewRadius6Nunca baja a nadie por debajo de este radio en chunks.
maxClientViewRadius32Tope para el límite fijo (el propio radio de visión del jugador sigue ganando).
adaptiveTerrainViewEnabledtrueAdapta el radio de visión del terreno durante el juego normal.
emergencyTerrainTrimEnabledtruePermite un recorte temporal del terreno tras presión visual sostenida.
clientRenderCapEnabledtrueLimita la distancia de dibujado y la niebla del cliente al radio recortado. Requiere reinicio.
clientStrainEnabledtrueAlivia el radio y el envío de chunks para un cliente que se queda atrás. Requiere reinicio.
clientStrainFrameLagLowMs25Retraso del bucle principal del cliente (ms) donde la saturación empieza a contar (unos 40 FPS).
clientStrainFrameLagHighMs60Retraso tratado como saturación total (unos 16 FPS).
clientStrainQueueLow64Cola de paquetes del cliente donde la saturación empieza a contar.
clientStrainQueueHigh512Cola de paquetes tratada como saturación total.
effectBudgetEnabledtruePresupuesto de partículas y sonidos 3D lejanos por jugador. Requiere reinicio.
effectBudgetPerSecond120Efectos lejanos que cada jugador puede recibir por segundo.
effectProtectRadius16Los efectos dentro de estos bloques nunca se descartan.
effectSoftRadius48Gastada la mitad del presupuesto, los efectos más allá de esto caen primero.
effectMaxDistance0Corte fijo en bloques para efectos posicionales. 0 = solo presupuesto.
distantUpdateThrottleEnabledfalseEnvía updates de posición de entidades lejanas con menos frecuencia. La posición más reciente siempre llega. Requiere reinicio.
distantUpdateNearBlocks32Las entidades más cerca que esto reciben todos los updates.
distantUpdateFarBlocks64Las entidades más allá de esto reciben 1 de cada 4 updates.
densityScanChunkRadius4Cuántos chunks a cada lado contar entidades.
densityLowPerChunk1.0Entidades ponderadas por chunk en o por debajo de esto: sin shrink por densidad.
densityHighPerChunk4.0Entidades ponderadas por chunk en o por encima de esto: bajado al mínimo.
densityRingWeightingtrueLos chunks centrales cuentan al 100%, los anillos exteriores menos.
densityRingEdgeWeight0.55Peso en el anillo del borde (1.0 = conteo plano).
baselineShrinkFraction0.10Shrink mínimo incluso con densidad “abierta” (0 = off).
chunkLoadShrinkEnabledtrueShrink extra por el recuento de sections cargadas + en streaming.
chunkLoadLowChunks2800Sections loaded+loading en o por debajo de esto: sin shrink por chunk-load. También es donde se asienta la visión en calma (alrededor de view 10 en 0.7).
chunkLoadHighChunks5900En este recuento de sections o por encima: shrink por chunk-load al máximo (alrededor de view 14).
densitySmoothing0.4Peso de la muestra más nueva en la EMA, en (0, 1]. 1.0 lo desactiva.
adaptEntityRadiustrueTambién reduce el radio de stream de entidades por jugador, no solo los chunks.
minEntityViewBlocks48Límite inferior del radio de entidades, en bloques (16 bloques = 1 chunk).
entityLodAggressiveness1.0Override global explícito de LOD. 1.0 mantiene el valor del motor.
maxEntityVerticalDistance32Descarta entidades demasiado lejos arriba/abajo del jugador. 0 = off.
maxVisibleEntitiesPerPlayer80Tope de entidades streameadas por jugador en multitudes. 0 = off.
holdSpawnOnLoadingChunksfalsePausa el spawn ambiental durante un backlog pesado de sections. Control global del admin.
minViewRadiusDelta2Cambio mínimo (chunks) antes de enviar una actualización. Los expands +1 siguen aplicándose.
maxExpandChunksPerPass1Máximo de chunks que el radio de visión sube en una pasada.
maxShrinkChunksPerPass2Máximo que baja en una pasada (duplicado bajo presión).
maxExpandEntityBlocksPerPass16Máximo de bloques que el radio de entidades sube en una pasada.
expandHysteresisPasses2Pasadas calmadas exigidas antes de permitir expand.
worldPassBudgetMs8Presupuesto de reloj para escrituras de radio en el hilo del mundo. 0 lo desactiva.
pressureExitRequiresLastTicktruePressure solo sale cuando el promedio de 10s y el último tick están calmados.
respectStreamingGracetrueRetiene recortes mientras el jugador todavía transmite sections.
streamingBacklogThreshold80Cuántas sections cargando cuentan como “todavía transmitiendo”.
smoothChunkStreamingtrueLimita la velocidad a la que llegan sections a cada cliente gestionado.
maxChunksPerSecond128Tope de sections por segundo. 0 mantiene el valor del motor.
maxChunksPerTick8Tope de sections por tick (el motor usa 40 en 0.6).
streamCatchUpEnabledtrueEleva temporalmente los límites tras un viaje rápido mientras el MSPT está sano.
streamCatchUpIntervalMs250Intervalo del controlador ligero de streaming.
streamCatchUpPerSecond256Límite sano de catch-up en sections por segundo.
streamCatchUpPerTick12Límite sano de catch-up en sections por tick.
streamCatchUpHoldMs1500Tiempo mínimo de catch-up tras movimiento rápido.
leanCoreTakeovertrueSi LeanCore está instalado, le toma el radio de visión.
yieldToLeanCoreViewRadiusfalseDeja el radio de visión del cliente enteramente a LeanCore.
pressureGovernorEnabledtrueAprieta las palancas de render cuando el MSPT del mundo se mantiene alto.
pressureMsptEnter48Promedio de 10s de MSPT en este valor o por encima entra en pressure.
pressureMsptExit43MSPT en este valor o por debajo sale de pressure.
pressureSustainSeconds4Cuánto debe mantenerse alto el MSPT antes de apretar.
pressureCooldownSeconds15Cuánto debe mantenerse bajo el MSPT antes de restaurar.
pressureDensityMultiplier1.45Bajo presión, los umbrales de densidad se aprietan por este factor.
pressureChunkRateMultiplier0.75Bajo presión, multiplica los topes de streaming de chunks.
pressureLodMultiplier1.15Multiplicador de presión usado solo con LOD global explícito superior a 1.0.
pressureVerticalTrimBlocks8Bajo presión, resta de maxEntityVerticalDistance.
pressureWorldLeversfalseBajo presión, pausa spawn de NPC y tick de bloques (se restaura al salir).
pressureTrimClientEffectsfalseBajo presión, recorta bloom/sunshaft (se aplaza si el último tick es un hitch).
pressureEffectScale0.5Multiplicador de las intensidades de efecto mientras están recortadas.
pressureItemMergefalseBajo presión, junta ítems soltados desde más lejos para que los montones sean menos entidades. Requiere reinicio.
pressureItemMergeRadius4.0Radio de merge en bloques mientras eso está activo (por defecto del motor es 2).
leanCoreMemoryAwaretrueCon LeanCore, reduce el radio mientras su tier de heap está en TIGHT o CRITICAL. Solo lectura.

Permisos

PermisoQuién
durkz.quantumhy.adminAvisos de update y /q status completo. Los operadores del servidor lo heredan a través de *.

Usándolo con LeanCore

QuantumHy y LeanCore pueden ambos ajustar el radio de visión del cliente, y solo uno debe hacerlo. Por defecto QuantumHy lo toma: al arrancar detecta LeanCore y apaga la gobernanza de radio de visión de LeanCore (viewRadiusGovernanceEnabled, liteViewRadiusEnabled, motionViewRadiusBoostEnabled), y luego pasa a controlar el radio él mismo. LeanCore conserva el radio de simulación, el throughput de chunks y la memoria. No hace falta ningún cambio de config en ninguno de los dos lados. LeanCore es una dependencia opcional: cuando no está presente, QuantumHy se ejecuta por su cuenta.

  • leanCoreTakeover: false deja a LeanCore en paz. Entonces ambos pueden pelear por el radio de visión.
  • yieldToLeanCoreViewRadius: true hace que QuantumHy se quede fuera del radio de visión del cliente por completo y deja que LeanCore lo conserve.

Recomendado

  • En solitario o tu propio servidor: deja los valores por defecto. Solo pierdes distancia de visión cuando hay aglomeración real o el mundo está hitching.
  • Quieres FPS en todas partes: pon targetClientViewRadius entre 12 y 16 para limitar la distancia de visión incluso en campo abierto.
  • Granjas de mobs / eventos pesados: mantén adaptEntityRadius: true; es lo que sostiene los frames cuando hay cientos de entidades en pantalla.
  • Elección personal: usa /q optimize off para restaurar y detener las palancas por jugador para ti. Usa /q optimize on para reactivarlas.
  • Activa verboseLog solo para diagnosticar; por defecto está off.
  • Deja checkForUpdates activo salvo que no quieras el aviso de JAR nuevo para operadores.

Comprobando que funciona

  1. Inicia el servidor y busca la línea de setup: QuantumHy 0.4.0 setup. config: verboseLog=false tickInterval=5s ... densityLow=1.0/ch densityHigh=4.0/ch baseline=10% ... entityLod=1.00x ... expand=1 shrink=2 ... budget=8ms
  2. Luego la línea de inicio del runtime: QuantumHy runtime started (interval=5s, hardCap=0, min=6, max=32, scan=4, entityRadius=true).
  3. Si LeanCore está presente: LeanCore detected: took over the client view radius (governance turned off). Si no: LeanCore not detected after 3 checks: QuantumHy owns the client view radius standalone.
  4. Con verboseLog=true, cada pasada registra una línea por jugador. Leyéndola: Durkz_z 32/49ch 0.7/ch~0.5 cl 6=6 ent 48=48 [hold] significa 32 entidades en 49 chunks, visión en chunks retenida en 6, radio de entidades en 48 bloques, expand congelado (hold). Otros motivos comunes: [min], [pressure], [baseline], [chunk-load], [density].
  5. El radio no salta 6→13 en una pasada. Bajo presión o volando deberías ver [pressure] o [hold], no 6->7 [baseline].

Licencia

Licencia MIT