Merge branch 'Anuken-master'

This commit is contained in:
Felix Corvus
2019-09-25 11:40:22 +03:00
131 changed files with 6734 additions and 5476 deletions

12
.github/ISSUE_TEMPLATE/bug_report.md vendored Normal file
View File

@@ -0,0 +1,12 @@
---
name: Bug report
about: Create a report to help fix an issue.
---
[Platform]: # (Android/iOS/Mac/Windows/Linux/Web)
[Build]: # (The build number under the title in the main menu. Required.)
[Issue]: # (Explain your issue in detail, possibly including the steps to reproduce it.)
[Notes]: # (Other notes.)

View File

@@ -0,0 +1,7 @@
---
name: Feature request
about: Suggest an idea for this project
---
Do not make a new issue for feature requests. Instead, post it in #545.

1
.gitignore vendored
View File

@@ -4,6 +4,7 @@ logs/
/core/assets/bundles/output/ /core/assets/bundles/output/
/core/assets/.gifimages/ /core/assets/.gifimages/
/deploy/ /deploy/
/out/
/desktop/packr-out/ /desktop/packr-out/
/desktop/packr-export/ /desktop/packr-export/
/desktop/mindustry-saves/ /desktop/mindustry-saves/

View File

@@ -31,6 +31,10 @@ There are two ways to test the translation bundle:
1) Assuming you have the PC version downloaded, download your bundle file, name it `bundle.properties`, then place it in the same folder as the Mindustry desktop executable and run it. *You should get a popup message in-game confirming that you have loaded an external translation.* 1) Assuming you have the PC version downloaded, download your bundle file, name it `bundle.properties`, then place it in the same folder as the Mindustry desktop executable and run it. *You should get a popup message in-game confirming that you have loaded an external translation.*
2) For advanced users: simply download your fork of mindustry and compile/run the game. 2) For advanced users: simply download your fork of mindustry and compile/run the game.
#### Translating for stores (Steam, Google Play)
If you would like to translate the descriptions for Google Play or Steam, see the [Fastlane Metadata folder](https://github.com/Anuken/Mindustry/tree/master/fastlane/metadata) and submit a pull request for files there. On Google Play, you would create or edit the folder with the correct local code; for Steam, I have to update the translations manually, so just name the folder with the language name, and include the same files as the English folder does.
**And that's it.** **And that's it.**
*(...of course, that's never really it. Bother me on Discord when something inevitably goes wrong.)* *(...of course, that's never really it. Bother me on Discord when something inevitably goes wrong.)*

View File

@@ -80,7 +80,9 @@ android{
versionName versionNameResult versionName versionNameResult
versionCode vcode versionCode vcode
props['androidBuildCode'] = (vcode + 1).toString() if(project.hasProperty("release")){
props['androidBuildCode'] = (vcode + 1).toString()
}
props.store(file('../core/assets/version.properties').newWriter(), null) props.store(file('../core/assets/version.properties').newWriter(), null)
} }

View File

@@ -1,5 +1,6 @@
package io.anuke.mindustry; package io.anuke.mindustry;
import android.*;
import android.app.*; import android.app.*;
import android.content.*; import android.content.*;
import android.content.pm.*; import android.content.pm.*;
@@ -21,6 +22,7 @@ import io.anuke.mindustry.ui.dialogs.*;
import java.io.*; import java.io.*;
import java.lang.System; import java.lang.System;
import java.util.*;
import static io.anuke.mindustry.Vars.*; import static io.anuke.mindustry.Vars.*;
@@ -68,14 +70,16 @@ public class AndroidLauncher extends AndroidApplication{
@Override @Override
public void showFileChooser(boolean open, String extension, Consumer<FileHandle> cons){ public void showFileChooser(boolean open, String extension, Consumer<FileHandle> cons){
if(VERSION.SDK_INT >= 19){ if(VERSION.SDK_INT >= VERSION_CODES.Q){
Intent intent = new Intent(open ? Intent.ACTION_OPEN_DOCUMENT : Intent.ACTION_CREATE_DOCUMENT); Intent intent = new Intent(open ? Intent.ACTION_OPEN_DOCUMENT : Intent.ACTION_CREATE_DOCUMENT);
intent.addCategory(Intent.CATEGORY_OPENABLE); intent.addCategory(Intent.CATEGORY_OPENABLE);
intent.setType("*/*"); intent.setType(extension.equals("zip") ? "application/zip" : "*/*");
addResultListener(i -> startActivityForResult(intent, i), (code, in) -> { addResultListener(i -> startActivityForResult(intent, i), (code, in) -> {
if(code == Activity.RESULT_OK && in != null && in.getData() != null){ if(code == Activity.RESULT_OK && in != null && in.getData() != null){
Uri uri = in.getData(); Uri uri = in.getData();
if(uri.getPath().contains("(invalid)")) return;
Core.app.post(() -> Core.app.post(() -> cons.accept(new FileHandle(uri.getPath()){ Core.app.post(() -> Core.app.post(() -> cons.accept(new FileHandle(uri.getPath()){
@Override @Override
public InputStream read(){ public InputStream read(){
@@ -97,6 +101,24 @@ public class AndroidLauncher extends AndroidApplication{
}))); })));
} }
}); });
}else if(VERSION.SDK_INT >= VERSION_CODES.M && !(checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED &&
checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED)){
chooser = new FileChooser(open ? "$open" : "$save", file -> file.extension().equalsIgnoreCase(extension), open, file -> {
if(!open){
cons.accept(file.parent().child(file.nameWithoutExtension() + "." + extension));
}else{
cons.accept(file);
}
});
ArrayList<String> perms = new ArrayList<>();
if(checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED){
perms.add(Manifest.permission.WRITE_EXTERNAL_STORAGE);
}
if(checkSelfPermission(Manifest.permission.READ_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED){
perms.add(Manifest.permission.READ_EXTERNAL_STORAGE);
}
requestPermissions(perms.toArray(new String[0]), PERMISSION_REQUEST_CODE);
}else{ }else{
super.showFileChooser(open, extension, cons); super.showFileChooser(open, extension, cons);
} }

View File

@@ -30,7 +30,7 @@ allprojects{
arcHash = null arcHash = null
debugged = { debugged = {
return new File(projectDir.parent, '../debug').exists() && !project.hasProperty("release") && project.hasProperty("args") return new File(projectDir.parent, '../Mindustry-Debug').exists() && !project.hasProperty("release") && project.hasProperty("args")
} }
localArc = { localArc = {
@@ -38,7 +38,7 @@ allprojects{
} }
getArcHash = { getArcHash = {
return new Properties().with{ p -> p.load(new File((File)projectDir, 'gradle.properties').newReader()); return p }["archash"] return new Properties().with{ p -> p.load(file('gradle.properties').newReader()); return p }["archash"]
} }
arcModule = { String name -> arcModule = { String name ->
@@ -270,7 +270,6 @@ project(":tools"){
dependencies{ dependencies{
compile project(":core") compile project(":core")
//for render tests
compile "com.badlogicgames.gdx:gdx-platform:$gdxVersion:natives-desktop" compile "com.badlogicgames.gdx:gdx-platform:$gdxVersion:natives-desktop"
compile "com.badlogicgames.gdx:gdx-freetype-platform:$gdxVersion:natives-desktop" compile "com.badlogicgames.gdx:gdx-freetype-platform:$gdxVersion:natives-desktop"

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.0 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

View File

Before

Width:  |  Height:  |  Size: 95 B

After

Width:  |  Height:  |  Size: 95 B

View File

@@ -51,6 +51,7 @@ minimap = Minimap
close = Close close = Close
website = Website website = Website
quit = Quit quit = Quit
save.quit = Save & Quit
maps = Maps maps = Maps
maps.browse = Browse Maps maps.browse = Browse Maps
continue = Continue continue = Continue
@@ -125,6 +126,7 @@ server.version = [gray]v{0} {1}
server.custombuild = [accent]Custom Build server.custombuild = [accent]Custom Build
confirmban = Are you sure you want to ban this player? confirmban = Are you sure you want to ban this player?
confirmkick = Are you sure you want to kick this player? confirmkick = Are you sure you want to kick this player?
confirmvotekick = Are you sure you want to vote-kick this player?
confirmunban = Are you sure you want to unban this player? confirmunban = Are you sure you want to unban this player?
confirmadmin = Are you sure you want to make this player an admin? confirmadmin = Are you sure you want to make this player an admin?
confirmunadmin = Are you sure you want to remove admin status from this player? confirmunadmin = Are you sure you want to remove admin status from this player?
@@ -161,6 +163,7 @@ save.rename = Rename
save.rename.text = New name: save.rename.text = New name:
selectslot = Select a save. selectslot = Select a save.
slot = [accent]Slot {0} slot = [accent]Slot {0}
editmessage = Edit Message
save.corrupted = [accent]Save file corrupted or invalid!\nIf you have just updated your game, this is probably a change in the save format and [scarlet]not[] a bug. save.corrupted = [accent]Save file corrupted or invalid!\nIf you have just updated your game, this is probably a change in the save format and [scarlet]not[] a bug.
empty = <empty> empty = <empty>
on = On on = On
@@ -174,6 +177,7 @@ save.playtime = Playtime: {0}
warning = Warning. warning = Warning.
confirm = Confirm confirm = Confirm
delete = Delete delete = Delete
view.workshop = View In Workshop
ok = OK ok = OK
open = Open open = Open
customize = Customize Rules customize = Customize Rules
@@ -222,6 +226,7 @@ editor.oregen.info = Ore Generation:
editor.mapinfo = Map Info editor.mapinfo = Map Info
editor.author = Author: editor.author = Author:
editor.description = Description: editor.description = Description:
editor.nodescription = A map must have a description of at least 4 characters before being published.
editor.waves = Waves: editor.waves = Waves:
editor.rules = Rules: editor.rules = Rules:
editor.generation = Generation: editor.generation = Generation:
@@ -288,6 +293,7 @@ editor.resizemap = Resize Map
editor.mapname = Map Name: editor.mapname = Map Name:
editor.overwrite = [accent]Warning!\nThis overwrites an existing map. editor.overwrite = [accent]Warning!\nThis overwrites an existing map.
editor.overwrite.confirm = [scarlet]Warning![] A map with this name already exists. Are you sure you want to overwrite it? editor.overwrite.confirm = [scarlet]Warning![] A map with this name already exists. Are you sure you want to overwrite it?
editor.exists = A map with this name already exists.
editor.selectmap = Select a map to load: editor.selectmap = Select a map to load:
toolmode.replace = Replace toolmode.replace = Replace
@@ -482,6 +488,7 @@ bar.drilltierreq = Better Drill Required
bar.drillspeed = Drill Speed: {0}/s bar.drillspeed = Drill Speed: {0}/s
bar.efficiency = Efficiency: {0}% bar.efficiency = Efficiency: {0}%
bar.powerbalance = Power: {0}/s bar.powerbalance = Power: {0}/s
bar.powerstored = Stored: {0}/{1}
bar.poweramount = Power: {0} bar.poweramount = Power: {0}
bar.poweroutput = Power Output: {0} bar.poweroutput = Power Output: {0}
bar.items = Items: {0} bar.items = Items: {0}
@@ -532,6 +539,7 @@ setting.antialias.name = Antialias[lightgray] (requires restart)[]
setting.indicators.name = Enemy/Ally Indicators setting.indicators.name = Enemy/Ally Indicators
setting.autotarget.name = Auto-Target setting.autotarget.name = Auto-Target
setting.keyboard.name = Mouse+Keyboard Controls setting.keyboard.name = Mouse+Keyboard Controls
setting.touchscreen.name = Touchscreen Controls
setting.fpscap.name = Max FPS setting.fpscap.name = Max FPS
setting.fpscap.none = None setting.fpscap.none = None
setting.fpscap.text = {0} FPS setting.fpscap.text = {0} FPS
@@ -574,8 +582,8 @@ category.general.name = General
category.view.name = View category.view.name = View
category.multiplayer.name = Multiplayer category.multiplayer.name = Multiplayer
command.attack = Attack command.attack = Attack
command.rally = Rally
command.retreat = Retreat command.retreat = Retreat
command.patrol = Patrol
keybind.gridMode.name = Block Select keybind.gridMode.name = Block Select
keybind.gridModeShift.name = Category Select keybind.gridModeShift.name = Category Select
keybind.press = Press a key... keybind.press = Press a key...
@@ -794,10 +802,13 @@ block.hail.name = Hail
block.lancer.name = Lancer block.lancer.name = Lancer
block.conveyor.name = Conveyor block.conveyor.name = Conveyor
block.titanium-conveyor.name = Titanium Conveyor block.titanium-conveyor.name = Titanium Conveyor
block.armored-conveyor.name = Armored Conveyor
block.armored-conveyor.description = Moves items at the same speed as titanium conveyors, but possesses more armor. Does not accept inputs from the sides from anything but other conveyors.
block.junction.name = Junction block.junction.name = Junction
block.router.name = Router block.router.name = Router
block.distributor.name = Distributor block.distributor.name = Distributor
block.sorter.name = Sorter block.sorter.name = Sorter
block.message.name = Message
block.overflow-gate.name = Overflow Gate block.overflow-gate.name = Overflow Gate
block.silicon-smelter.name = Silicon Smelter block.silicon-smelter.name = Silicon Smelter
block.phase-weaver.name = Phase Weaver block.phase-weaver.name = Phase Weaver
@@ -973,6 +984,7 @@ unit.eruptor.description = A heavy mech designed to take down structures. Fires
unit.wraith.description = A fast, hit-and-run interceptor unit. Targets power generators. unit.wraith.description = A fast, hit-and-run interceptor unit. Targets power generators.
unit.ghoul.description = A heavy carpet bomber. Rips through enemy structures, targeting critical infrastructure. unit.ghoul.description = A heavy carpet bomber. Rips through enemy structures, targeting critical infrastructure.
unit.revenant.description = A heavy, hovering missile array. unit.revenant.description = A heavy, hovering missile array.
block.message.description = Stores a message. Used for communication between allies.
block.graphite-press.description = Compresses chunks of coal into pure sheets of graphite. block.graphite-press.description = Compresses chunks of coal into pure sheets of graphite.
block.multi-press.description = An upgraded version of the graphite press. Employs water and power to process coal quickly and efficiently. block.multi-press.description = An upgraded version of the graphite press. Employs water and power to process coal quickly and efficiently.
block.silicon-smelter.description = Reduces sand with pure coal. Produces silicon. block.silicon-smelter.description = Reduces sand with pure coal. Produces silicon.

View File

@@ -4,7 +4,7 @@ contributors = Překladatelé a Sponzoři
discord = Připoj se k Mindustry na Discordu! discord = Připoj se k Mindustry na Discordu!
link.discord.description = Oficiální Mindustry chatroom na Discordu! link.discord.description = Oficiální Mindustry chatroom na Discordu!
link.github.description = Zdrojový kód hry link.github.description = Zdrojový kód hry
link.changelog.description = List of update changes link.changelog.description = Seznam úprav
link.dev-builds.description = Nestabilní verze vývoje hry link.dev-builds.description = Nestabilní verze vývoje hry
link.trello.description = Oficiální Trello board pro plánované funkce link.trello.description = Oficiální Trello board pro plánované funkce
link.itch.io.description = itch.io stránka pro stažení PC nebo webové verze link.itch.io.description = itch.io stránka pro stažení PC nebo webové verze
@@ -12,55 +12,55 @@ link.google-play.description = Google Play store
link.wiki.description = Oficiální Mindustry wiki link.wiki.description = Oficiální Mindustry wiki
linkfail = Nepodařilo se otevřít odkaz!\nURL byla zkopírována do schránky. linkfail = Nepodařilo se otevřít odkaz!\nURL byla zkopírována do schránky.
screenshot = Snímek obrazovky uložen {0} screenshot = Snímek obrazovky uložen {0}
screenshot.invalid = Map too large, potentially not enough memory for screenshot. screenshot.invalid = Mapa je moc velká, nemusí být dost paměti pro snímek obrazovky.
gameover = Konec hry gameover = Konec hry
gameover.pvp = [accent] {0}[] Tým Vyhrál! gameover.pvp = [accent] {0}[] Tým Vyhrál!
highscore = [accent]Nový Rekord! highscore = [accent]Nový rekord!
load.sound = Sounds load.sound = Zvuky
load.map = Maps load.map = Mapy
load.image = Images load.image = Obrázky
load.content = Content load.content = Obsah
load.system = System load.system = System
stat.wave = Waves Defeated:[accent] {0} stat.wave = Vln poraženo:[accent] {0}
stat.enemiesDestroyed = Enemies Destroyed:[accent] {0} stat.enemiesDestroyed = Nepřátel zničeno:[accent] {0}
stat.built = Buildings Built:[accent] {0} stat.built = Budov postaveno:[accent] {0}
stat.destroyed = Buildings Destroyed:[accent] {0} stat.destroyed = Budov zničeno:[accent] {0}
stat.deconstructed = Buildings Deconstructed:[accent] {0} stat.deconstructed = Budov rozebráno:[accent] {0}
stat.delivered = Resources Launched: stat.delivered = Materiálu odesláno:
stat.rank = Final Rank: [accent]{0} stat.rank = Závěrečné hodnocení: [accent]{0}
launcheditems = [accent]Launched Items launcheditems = [accent]Odeslané předměty
map.delete = Jsi si jistý že chceš smazat mapu "[accent]{0}[]"? map.delete = Jsi si jistý že chceš smazat mapu "[accent]{0}[]"?
level.highscore = Nejvyšší skóre: [accent]{0} level.highscore = Nejvyšší skóre: [accent]{0}
level.select = Výběr levelu level.select = Výběr levelu
level.mode = Herní mód: level.mode = Herní mód:
showagain = Znovu neukazovat ! showagain = Znovu neukazovat !
coreattack = < Jádro je pod útokem! > coreattack = < Jádro je pod útokem! >
nearpoint = [[ [scarlet]LEAVE DROP POINT IMMEDIATELY[] ]\nannihilation imminent nearpoint = [[ [scarlet]IHNED OPUSŤTE PROSTOR VÝSADKŮ[] ]\nNebezpečí okamžité smrti
database = Core Database database = Databáze objektů
savegame = Uložit hru savegame = Uložit hru
loadgame = Načíst hru loadgame = Načíst hru
joingame = Připojit se ke hře joingame = Připojit se ke hře
addplayers = Přidat/Odebrat hráče addplayers = Přidat/Odebrat hráče
customgame = Vlastní hra customgame = Vlastní hra
newgame = New Game newgame = Nová hra
none = <none> none = <žádný>
minimap = Minimap minimap = Minimapa
close = Zavřít close = Zavřít
website = Website website = Web. stránky
quit = Ukončit quit = Ukončit
maps = Mapy maps = Mapy
continue = Pokračovat continue = Pokračovat
maps.none = [LIGHT_GRAY]Žádné mapy nebyly nalezeny! maps.none = [LIGHT_GRAY]Žádné mapy nebyly nalezeny!
about.button = O hře about.button = O hře
name = Name: name = Jméno:
noname = Nejdřív si vyber[accent] herní jméno[]. noname = Nejdřív si vyber[accent] herní jméno[].
filename = Jméno složky: filename = Jméno složky:
unlocked = Nový blok odemknut! unlocked = Nový blok odemknut!
completed = [accent]Completed completed = [accent]Dokončeno
techtree = Tech Tree techtree = Technologie
research.list = [LIGHT_GRAY]Research: research.list = [LIGHT_GRAY]Výzkum:
research = Research research = Zkoumej
researched = [LIGHT_GRAY]{0} researched. researched = [LIGHT_GRAY]{0} vyzkoumán(o).
players = {0} hráčů online players = {0} hráčů online
players.single = {0} hráč online players.single = {0} hráč online
server.closing = [accent]Zavírám server... server.closing = [accent]Zavírám server...
@@ -76,8 +76,8 @@ server.kicked.nameInUse = Někdo se stejným jménem\nje aktuálně na serveru.
server.kicked.nameEmpty = Tvé jméno je neplatné. server.kicked.nameEmpty = Tvé jméno je neplatné.
server.kicked.idInUse = Již jsi na tomhle serveru připojen! Připojování se dvěma účty není povoleno. server.kicked.idInUse = Již jsi na tomhle serveru připojen! Připojování se dvěma účty není povoleno.
server.kicked.customClient = Tento server nepodporuje vlastní verze hry. Stáhni si oficiální verzi. server.kicked.customClient = Tento server nepodporuje vlastní verze hry. Stáhni si oficiální verzi.
server.kicked.gameover = Game over! server.kicked.gameover = Konec hry!
server.versions = Your version:[accent] {0}[]\nServer version:[accent] {1}[] server.versions = Verze klienta:[accent] {0}[]\nVerze serveru:[accent] {1}[]
host.info = [accent]hostitel[] hostuje server na portu [scarlet]6567[]. \nKdokoliv na stejné [LIGHT_GRAY]wifi nebo místní síti[] by měl vidět server ve svém listu serverů.\n\nJestli chcete aby se uživatelé připojovali odkudkoliv pomocí IP, [accent]přesměrování portů[] je nutné.\n\n[LIGHT_GRAY]Poznámka: Jestli někdo má problém s připojením ke své LAN hře, ujistěte se že má Mindustry povolený přístup k místní síti v nastavení Firewallu. host.info = [accent]hostitel[] hostuje server na portu [scarlet]6567[]. \nKdokoliv na stejné [LIGHT_GRAY]wifi nebo místní síti[] by měl vidět server ve svém listu serverů.\n\nJestli chcete aby se uživatelé připojovali odkudkoliv pomocí IP, [accent]přesměrování portů[] je nutné.\n\n[LIGHT_GRAY]Poznámka: Jestli někdo má problém s připojením ke své LAN hře, ujistěte se že má Mindustry povolený přístup k místní síti v nastavení Firewallu.
join.info = Tady můžeš vložit [accent]IP serveru[] ke kterému se chceš připojit, nebo objevit [accent]Servery Místní sítě[] ke kterým se chceš připojit.\nLAN i Multiplayer jsou podporovány.\n\n[LIGHT_GRAY]Poznámka: Není žádný globální seznam serverů; Pokud se budeš chtít připojit k někomu pomocí IP, budeš jí muset znát od hostitele. join.info = Tady můžeš vložit [accent]IP serveru[] ke kterému se chceš připojit, nebo objevit [accent]Servery Místní sítě[] ke kterým se chceš připojit.\nLAN i Multiplayer jsou podporovány.\n\n[LIGHT_GRAY]Poznámka: Není žádný globální seznam serverů; Pokud se budeš chtít připojit k někomu pomocí IP, budeš jí muset znát od hostitele.
hostserver = Hostovat hru hostserver = Hostovat hru
@@ -151,30 +151,30 @@ save.wave = Vlna {0}
save.difficulty = Obtížnost: {0} save.difficulty = Obtížnost: {0}
save.date = Naposledy uloženo: {0} save.date = Naposledy uloženo: {0}
save.playtime = Herní čas: {0} save.playtime = Herní čas: {0}
warning = Warning. warning = Varování.
confirm = Potvrdit confirm = Potvrdit
delete = Smazat delete = Smazat
ok = OK ok = OK
open = Otevřít open = Otevřít
customize = Customize customize = Přizpůsobit
cancel = Zrušit cancel = Zrušit
openlink = Otevřít Odkaz openlink = Otevřít Odkaz
copylink = Zkopírovat Odkaz copylink = Zkopírovat Odkaz
back = Zpět back = Zpět
data.export = Export Data data.export = Exportuj Data
data.import = Import Data data.import = Importuj Data
data.exported = Data exported. data.exported = Data exportována.
data.invalid = This isn't valid game data. data.invalid = Neplatná herní data.
data.import.confirm = Importing external data will erase[scarlet] all[] your current game data.\n[accent]This cannot be undone![]\n\nOnce the data is imported, your game will exit immediately. data.import.confirm = Import externích dat smaže[scarlet] všechna[] vaše současná herní data.\n[accent]To nelze vrátit zpět![]\n\nPo importu data se hra ukončí.
classic.export = Export Classic Data classic.export = Exportovat klasická data
classic.export.text = [accent]Mindustry[] has just had a major update.\nClassic (v3.5 build 40) save or map data has been detected. Would you like to export these saves to your phone's home folder, for use in the Mindustry Classic app? classic.export.text = [accent]Mindustry[] has just had a major update.\nClassic (v3.5 build 40) save or map data has been detected. Would you like to export these saves to your phone's home folder, for use in the Mindustry Classic app?
quit.confirm = Jsi si jistý že chceš ukončit ? quit.confirm = Jsi si jistý že chceš ukončit ?
quit.confirm.tutorial = Are you sure you know what you're doing?\nThe tutorial can be re-taken in[accent] Settings->Game->Re-Take Tutorial.[] quit.confirm.tutorial = Jste si vážně jist?\nTutoriál se dá znovu spustit v[accent] Nastavení->Hra->Spusť Tutoriál.[]
loading = [accent]Načítám... loading = [accent]Načítám...
saving = [accent]Ukládám... saving = [accent]Ukládám...
wave = [accent]Vlna {0} wave = [accent]Vlna {0}
wave.waiting = [LIGHT_GRAY]Vlna za {0} wave.waiting = [LIGHT_GRAY]Vlna za {0}
wave.waveInProgress = [LIGHT_GRAY]Wave in progress wave.waveInProgress = [LIGHT_GRAY]Vlna v pohybu
waiting = [LIGHT_GRAY]Čekám... waiting = [LIGHT_GRAY]Čekám...
waiting.players = Čekání na hráče... waiting.players = Čekání na hráče...
wave.enemies = [LIGHT_GRAY]{0} Nepřátel zbývá wave.enemies = [LIGHT_GRAY]{0} Nepřátel zbývá
@@ -186,9 +186,9 @@ custom = Vlastní
builtin = Zabudovaný builtin = Zabudovaný
map.delete.confirm = Jsi si jistý žechceš tuto mapu smazat? tato akce je nevratná! map.delete.confirm = Jsi si jistý žechceš tuto mapu smazat? tato akce je nevratná!
map.random = [accent]Náhodná mapa map.random = [accent]Náhodná mapa
map.nospawn = Tato mapa nemá žádná jádra pro hráče ke spawnutí! přidej[ROYAL] blue[] jádro na tuto mapu v editoru. map.nospawn = Tato mapa nemá žádné jádro pro hráče ke spawnutí! Přidej v editoru do této mapy[ROYAL] modré[] jádro.
map.nospawn.pvp = Tato mapa nemá žádné nepřátelské jádra pro hráče ke spawnutí! přidej[SCARLET] red[] jádro na tuto mapu v editoru. map.nospawn.pvp = Tato mapa nemá žádné nepřátelské jádro pro druhého hráče! Přidej v editoru do této mapy[SCARLET] červené[] jádro.
map.nospawn.attack = This map does not have any enemy cores for player to attack! Add[SCARLET] red[] cores to this map in the editor. map.nospawn.attack = Tato mapa nemá žádná nepřátelská jádra ke zničení! Přidej v editoru do této mapy [SCARLET] červené[] jádro.
map.invalid = Chyba v načítání mapy: poškozený nebo neplatný soubor mapy. map.invalid = Chyba v načítání mapy: poškozený nebo neplatný soubor mapy.
editor.brush = Štětec editor.brush = Štětec
editor.openin = Otevřít v editoru. editor.openin = Otevřít v editoru.
@@ -197,11 +197,11 @@ editor.oregen.info = Generování nerostných zdrojů:
editor.mapinfo = Informace o mapě editor.mapinfo = Informace o mapě
editor.author = Autor: editor.author = Autor:
editor.description = Popis: editor.description = Popis:
editor.waves = Waves: editor.waves = Vln:
editor.rules = Rules: editor.rules = Pravidla:
editor.generation = Generation: editor.generation = Generation:
editor.ingame = Edit In-Game editor.ingame = Edit In-Game
editor.newmap = New Map editor.newmap = Nová mapa
waves.title = Waves waves.title = Waves
waves.remove = Remove waves.remove = Remove
waves.never = <never> waves.never = <never>
@@ -868,7 +868,7 @@ unit.lich.name = Lich
unit.reaper.name = Reaper unit.reaper.name = Reaper
tutorial.next = [lightgray]<Tap to continue> tutorial.next = [lightgray]<Tap to continue>
tutorial.intro = You have entered the[scarlet] Mindustry Tutorial.[]\nBegin by[accent] mining copper[]. Tap a copper ore vein near your core to do this.\n\n[accent]{0}/{1} copper tutorial.intro = You have entered the[scarlet] Mindustry Tutorial.[]\nBegin by[accent] mining copper[]. Tap a copper ore vein near your core to do this.\n\n[accent]{0}/{1} copper
tutorial.drill = Manuální zěžba je neefektivní.\n[accent]Vrty []budou těžit automaticky.\npolož jeden na měděnou rudu. tutorial.drill = Manuální těžba je neefektivní.\n[accent]Vrty []budou těžit automaticky.\npolož jeden na měděnou rudu.
tutorial.drill.mobile = Mining manually is inefficient.\n[accent]Drills []can mine automatically.\nTap the drill tab in the bottom right.\nSelect the[accent] mechanical drill[].\nPlace it on a copper vein by tapping, then press the[accent] checkmark[] below to confirm your selection.\nPress the[accent] X button[] to cancel placement. tutorial.drill.mobile = Mining manually is inefficient.\n[accent]Drills []can mine automatically.\nTap the drill tab in the bottom right.\nSelect the[accent] mechanical drill[].\nPlace it on a copper vein by tapping, then press the[accent] checkmark[] below to confirm your selection.\nPress the[accent] X button[] to cancel placement.
tutorial.blockinfo = Each block has different stats. Each drill can only mine certain ores.\nTo check a block's info and stats,[accent] tap the "?" button while selecting it in the build menu.[]\n\n[accent]Access the Mechanical Drill's stats now.[] tutorial.blockinfo = Each block has different stats. Each drill can only mine certain ores.\nTo check a block's info and stats,[accent] tap the "?" button while selecting it in the build menu.[]\n\n[accent]Access the Mechanical Drill's stats now.[]
tutorial.conveyor = [accent]Dopravníky[] jsou zapotřebí k dopravě materiálu k jádru.\nVytvoř řadu dopravníku od vrtu až k jádru. tutorial.conveyor = [accent]Dopravníky[] jsou zapotřebí k dopravě materiálu k jádru.\nVytvoř řadu dopravníku od vrtu až k jádru.
@@ -959,7 +959,7 @@ block.surge-wall-large.description = Nejsilnější defenzivní blok.\nMá malou
block.door.description = Malé dveře, které se dají otevřít nebo zavřít kliknutím na ně.\nKdyž otevřené nepřátelé mohou střílet a dostat se skrz. block.door.description = Malé dveře, které se dají otevřít nebo zavřít kliknutím na ně.\nKdyž otevřené nepřátelé mohou střílet a dostat se skrz.
block.door-large.description = Velké dveře, které se dají otevřít nebo zavřít kliknutím na ně.\nKdyž otevřené nepřátelé mohou střílet a dostat se skrz.\nZabírá více polí. block.door-large.description = Velké dveře, které se dají otevřít nebo zavřít kliknutím na ně.\nKdyž otevřené nepřátelé mohou střílet a dostat se skrz.\nZabírá více polí.
block.mender.description = Periodically repairs blocks in its vicinity. Keeps defenses repaired in-between waves.\nOptionally uses silicon to boost range and efficiency. block.mender.description = Periodically repairs blocks in its vicinity. Keeps defenses repaired in-between waves.\nOptionally uses silicon to boost range and efficiency.
block.mend-projector.description = Kontinuálně léčí bloky ve poli svého působení. block.mend-projector.description = Kontinuálně léčí bloky v poli svého působení.
block.overdrive-projector.description = Zrychluje funkce blízkých struktůr jako jsou vrty a dopravníky. block.overdrive-projector.description = Zrychluje funkce blízkých struktůr jako jsou vrty a dopravníky.
block.force-projector.description = Vytvoří okolo sebe šestihrané silové pole, chrání jednotky a budovy uvnitř sebe vůči střelám. block.force-projector.description = Vytvoří okolo sebe šestihrané silové pole, chrání jednotky a budovy uvnitř sebe vůči střelám.
block.shock-mine.description = Působí poškození nepřátelským jednotkám při sešlápnutí. Skoro neviditelné nepřáteli. block.shock-mine.description = Působí poškození nepřátelským jednotkám při sešlápnutí. Skoro neviditelné nepřáteli.
@@ -973,7 +973,7 @@ block.router.description = Příijmá předměty z jednoho směru a posílá je
block.distributor.description = Pokročilý směrovač, který z libovolného počtu vstupů vytvoří libovolný počet výstupu a rozdělí přísun předmětů rovnoměrně do každého z nich, obdoba Multiplexeru a Demultiplexeru. block.distributor.description = Pokročilý směrovač, který z libovolného počtu vstupů vytvoří libovolný počet výstupu a rozdělí přísun předmětů rovnoměrně do každého z nich, obdoba Multiplexeru a Demultiplexeru.
block.overflow-gate.description = Kombinace distributoru a děličky která má výstup do leva nebo do prava jen pokud je přední strana zablokovaná. block.overflow-gate.description = Kombinace distributoru a děličky která má výstup do leva nebo do prava jen pokud je přední strana zablokovaná.
block.mass-driver.description = Ultimátní blok přepravy předmětů. Sbírá několik druhů předmětů a vystřelí je k dalšímu hromadnému distributoru přes veliké vzdálenosti. block.mass-driver.description = Ultimátní blok přepravy předmětů. Sbírá několik druhů předmětů a vystřelí je k dalšímu hromadnému distributoru přes veliké vzdálenosti.
block.mechanical-pump.description = Levná pumpa s pomalým tokem, ale nevyžaduje nergii k provozu. block.mechanical-pump.description = Levná pumpa s pomalým tokem, ale nevyžaduje energii k provozu.
block.rotary-pump.description = Pokročilá pumpa která, zdvojnásobuje přísun tekutin za použití energie. block.rotary-pump.description = Pokročilá pumpa která, zdvojnásobuje přísun tekutin za použití energie.
block.thermal-pump.description = Ultimátní pumpa. Trojnásobně rychlejší než mechanická pumpa a jediná pumpa která dokáže pracovat s lávou. block.thermal-pump.description = Ultimátní pumpa. Trojnásobně rychlejší než mechanická pumpa a jediná pumpa která dokáže pracovat s lávou.
block.conduit.description = Základní blok přepravy tekutin. Funguje jako dopravník, ale na tekutiny, chápeš ne ? Užívá se s extraktory, pumpami nebo jiným potrubím. block.conduit.description = Základní blok přepravy tekutin. Funguje jako dopravník, ale na tekutiny, chápeš ne ? Užívá se s extraktory, pumpami nebo jiným potrubím.
@@ -998,7 +998,7 @@ block.solar-panel-large.description = Poskytuje mnohem lepší zdroj energie ne
block.thorium-reactor.description = Generuje obrovské množství energie z radioaktivního thoria. Vyžaduje konstantní chlazení. Způsobí velikou explozi je-li zásobován nedostatečným množstvím chlazení. Výstup energie závisí na plnosti obsahu generátoru, základní generování energie se aktivuje při poloviční kapacitě. block.thorium-reactor.description = Generuje obrovské množství energie z radioaktivního thoria. Vyžaduje konstantní chlazení. Způsobí velikou explozi je-li zásobován nedostatečným množstvím chlazení. Výstup energie závisí na plnosti obsahu generátoru, základní generování energie se aktivuje při poloviční kapacitě.
block.impact-reactor.description = An advanced generator, capable of creating massive amounts of power at peak efficiency. Requires a significant power input to kickstart the process. block.impact-reactor.description = An advanced generator, capable of creating massive amounts of power at peak efficiency. Requires a significant power input to kickstart the process.
block.mechanical-drill.description = Levný vrt. Při položení na vhodné pole, natrvalo a pomalu produkuje materiál na který byl položen. block.mechanical-drill.description = Levný vrt. Při položení na vhodné pole, natrvalo a pomalu produkuje materiál na který byl položen.
block.pneumatic-drill.description = Vylepšený vrt, který je rychlejší a je schopen zpracovat trdší materiály za pomocí tlaku. block.pneumatic-drill.description = Vylepšený vrt, který je rychlejší a je schopen zpracovat tvrdší materiály za pomocí tlaku.
block.laser-drill.description = Dovoluje vrtat ještě rychleji díky laserové technologii, požaduje energii k provozu. Dodatečně, dokáže vrtat žíly radioaktivního thoria. block.laser-drill.description = Dovoluje vrtat ještě rychleji díky laserové technologii, požaduje energii k provozu. Dodatečně, dokáže vrtat žíly radioaktivního thoria.
block.blast-drill.description = Ultimátní vrt, vyžaduje velké množství energie k provozu. block.blast-drill.description = Ultimátní vrt, vyžaduje velké množství energie k provozu.
block.water-extractor.description = Extrahuje vodu ze země. Vhodný k použití když se v oblasti nenachází zdroj vody. block.water-extractor.description = Extrahuje vodu ze země. Vhodný k použití když se v oblasti nenachází zdroj vody.

View File

@@ -866,26 +866,26 @@ unit.chaos-array.name = Chaos Array
unit.eradicator.name = Eradicator unit.eradicator.name = Eradicator
unit.lich.name = Lich unit.lich.name = Lich
unit.reaper.name = Reaper unit.reaper.name = Reaper
tutorial.next = [lightgray]<Tap to continue> tutorial.next = [lightgray]<Tippen um fortzufahren>
tutorial.intro = You have entered the[scarlet] Mindustry Tutorial.[]\nBegin by[accent] mining copper[]. Tap a copper ore vein near your core to do this.\n\n[accent]{0}/{1} copper tutorial.intro = Du befindest dich im[scarlet] Mindustry-Tutorial.[]\nBeginne, indem du[accent] Kupfer abbaust[]. Tippe dazu auf ein Kupfervorkommen in der Nähe deiner Basis.\n\n[accent]{0}/{1} Kupfer
tutorial.drill = Manuelles Abbauen von Ressourcen ist ineffizient.\n[accent]Bohrer[] können automatisch abbauen.\n Platziere einen auf einem Kupfer Vorkommen. tutorial.drill = Manuelles Abbauen ist ineffizient.\n[accent]Bohrer []können automatisch abbauen.\nTippe auf den Bohrer Tab unten rechts.\nWähle den[accent] Mechanischen Bohrer[].\nPlatziere ihn durch Tippen auf ein Kupfervorkommen.\nMit einem [accent]Rechtsklick[] brichst du den Bau ab.
tutorial.drill.mobile = Mining manually is inefficient.\n[accent]Drills []can mine automatically.\nTap the drill tab in the bottom right.\nSelect the[accent] mechanical drill[].\nPlace it on a copper vein by tapping, then press the[accent] checkmark[] below to confirm your selection.\nPress the[accent] X button[] to cancel placement. tutorial.drill.mobile = Manuelles Abbauen ist ineffizient.\n[accent]Bohrer []können automatisch abbauen.\nTippe auf den Bohrer Tab unten rechts.\nWähle den[accent] Mechanischen Bohrer[].\nPlatziere ihn durch Tippen auf ein Kupfervorkommen, dann klicke auf das[accent] Häkchen[] unten um deine Auswahl zu bestätigen.\nKlicke auf den[accent] X-Button[] um den Bau abzubrechen.
tutorial.blockinfo = Each block has different stats. Each drill can only mine certain ores.\nTo check a block's info and stats,[accent] tap the "?" button while selecting it in the build menu.[]\n\n[accent]Access the Mechanical Drill's stats now.[] tutorial.blockinfo = Jeder Block hat unterschiedliche Eigenschaften. Jeder Bohrer kann immer nur ein bestimmtes Material abbauen.\nFür Infos und Stats eines Blocks wähle einen Block im Baumenü aus und [accent] klicke auf den "?"-Button.[]\n\n[accent]Schau dir jetzt die Stats des Mechanischen Bohrers an.[]
tutorial.conveyor = [accent]Transportbänder[] werden dazu benutzt Materialien zum Kern zu transportieren.\n Erstelle eine Reihe von Transportbändern zum Kern. tutorial.conveyor = Mit [accent]Förderbändern[] werden Materialien zum Kern transportiert.\nReihe mehrere Förderbänder aneinander bis zum Kern.
tutorial.conveyor.mobile = [accent]Conveyors[] are used to transport items to the core.\nMake a line of conveyors from the drill to the core.\n[accent] Place in a line by holding down your finger for a few seconds[] and dragging in a direction.\n\n[accent]{0}/{1} conveyors placed in line\n[accent]0/1 items delivered tutorial.conveyor.mobile = Mit [accent]Förderbändern[] werden Materialien zum Kern transportiert.\nReihe mehrere Förderbänder aneinander bis zum Kern.\n[accent] Zum Bau in einer Reihe lasse deinen Finger für einige Sekunden gedrückt[] und ziehe ihn in eine beliebige Richtung.\n\n[accent]{0}/{1} Förderbänder in Reihe erstellt\n[accent]0/1 Ressourcen transportiert.
tutorial.turret = Verteidigungsgebäude müssen gebaut werden um[LIGHT_GRAY] Gegner[] abzuwehren.\nBaue einen Duo Geschützturm in die Nähe deiner Basis. tutorial.turret = Verteidigungsgebäude müssen gebaut werden um[LIGHT_GRAY] Gegner[] abzuwehren.\nBaue einen Duo Geschützturm in die Nähe deiner Basis.
tutorial.drillturret = Duo Geschütztürme benötigen[accent] Kupfermunition, []um schießen zu können.\nPlatziere neben das Geschütz einen Bohrer, um ihn mit Kupfer zu versorgen. tutorial.drillturret = Duo Geschütztürme benötigen[accent] Kupfermunition, []um schießen zu können.\nPlatziere neben das Geschütz einen Bohrer, um ihn mit Kupfer zu versorgen.
tutorial.pause = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press space to pause. tutorial.pause = Du kannst das Spiel jederzeit [accent]pausieren.[]\nIn einer Pause kannst du den Bau weiterer Gebäude in Auftrag geben.\n\n[accent]Drücke die Leertaste um zu pausieren.
tutorial.pause.mobile = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press this button in the top left to pause. tutorial.pause.mobile = Du kannst das Spiel jederzeit [accent]pausieren.[]\nIn einer Pause kannst du den Bau weiterer Gebäude in Auftrag geben.\n\n[accent]Drücke diesen Button oben links um zu pausieren.
tutorial.unpause = Now press space again to unpause. tutorial.unpause = Drücke die Leertaste erneut um das Spiel fortzusetzen.
tutorial.unpause.mobile = Now press it again to unpause. tutorial.unpause.mobile = Drücke ihn erneut um das Spiel fortzusetzen.
tutorial.breaking = Blocks frequently need to be destroyed.\n[accent]Hold down right-click[] to destroy all blocks in a selection.[]\n\n[accent]Destroy all the scrap blocks to the left of your core using area selection. tutorial.breaking = Oft kommt es vor, dass Blöcke zerstört werden müssen.\n[accent]Halte die rechte Maustaste gedrückt[] während du eine Fläche auswählst. Dadurch werden alle Blöcke darin zerstört.[]\n\n[accent]Zerstöre alle Schrott-Blöcke links neben deinem Kern mithilfe der Flächenauswahl.
tutorial.breaking.mobile = Blocks frequently need to be destroyed.\n[accent]Select deconstruction mode[], then tap a block to begin breaking it.\nDestroy an area by holding down your finger for a few seconds[] and dragging in a direction.\nPress the checkmark button to confirm breaking.\n\n[accent]Destroy all the scrap blocks to the left of your core using area selection. tutorial.breaking.mobile = Oft kommt es vor, dass Blöcke zerstört werden müssen.\n[accent]Wähle den Abbau-Modus[], dann wähle einen Block um ihn zu zerstören.\nZerstöre eine Fläche indem du deinen Finger einige Sekunden gedrückt hältst[] und in eine beliebige Richtung ziehst.\nTippe auf das Häkchen um den Rückbau zu bestätigen.\n\n[accent]Zerstöre all Schrott-Blöcke links des Kerns mithilfe der Flächenauswahl.
tutorial.withdraw = In some situations, taking items directly from blocks is necessary.\nTo do this, [accent]tap a block[] with items in it, then [accent]tap the item[] in the inventory.\nMultiple items can be withdrawn by [accent]tapping and holding[].\n\n[accent]Withdraw some copper from the core.[] tutorial.withdraw = Einige Situationen erfordern, dass Materialien direkt aus den Blöcken aufgenommen werden.\nUm dies zu tun, [accent]tippe auf einen Block[] mit Materialien dann [accent]tippe auf das Material[] in diesem Block.\nUm mehrere Materialien zu entnehmen [accent]tippe darauf und halte die Maustaste gedrückt[].\n\n[accent]Entnimm etwas Kupfer vom Kern.[]
tutorial.deposit = Deposit items into blocks by dragging from your ship to the destination block.\n\n[accent]Deposit your copper back into the core.[] tutorial.deposit = Materialien können in Blöcke abgelegt werden, indem du sie dorthin ziehst.\n\n[accent]Lege das Kupfer zurück in den Kern.[]
tutorial.waves = Der [LIGHT_GRAY] Gegner[] greift an.\n\nVerteidige deinen Kern 2 Wellen lang. Bau mehr Türme. tutorial.waves = Der [LIGHT_GRAY]Gegner[] greift an.\n\nVerteidige deinen Kern 2 Wellen lang. Baue mehr Türme.
tutorial.waves.mobile = The[lightgray] enemy[] approaches.\n\nDefend the core for 2 waves. Your ship will automatically fire at enemies.\nBuild more turrets and drills. Mine more copper. tutorial.waves.mobile = Der[lightgray] Gegner[] greift an.\n\nVerteidige deinen Kern 2 Wellen lang. Dein Schiff feuert automatisch auf Gegner.\nBaue mehr Geschütztürme und Bohrer. Baue mehr Kupfer ab.
tutorial.launch = Once you reach a specific wave, you are able to[accent] launch the core[], leaving your defenses behind and[accent] obtaining all the resources in your core.[]\nThese resources can then be used to research new technology.\n\n[accent]Press the launch button. tutorial.launch = Sobald du eine bestimmte Welle erreicht hast, kannst du die [accent]Mission abschließen[]. Dadurch lässt du deine Basis zurück[accent] und überträgst alle Ressourcen in deinen Kern.[]\nDiese Ressourcen können zur Erforschung neuer Technologien eingesetzt werden.\n\n[accent]Drücke nun den Abschluss-Button.
item.copper.description = Ein nützliches Material. Wird in allen Arten von Blöcken verwendet. item.copper.description = Ein nützliches Material. Wird in allen Arten von Blöcken verwendet.
item.lead.description = Ein grundlegendes Material. Häufig in Elektronik und Flüssigkeits-Transport-Blöcken verwendet. item.lead.description = Ein grundlegendes Material. Häufig in Elektronik und Flüssigkeits-Transport-Blöcken verwendet.
item.metaglass.description = Eine extrem harte Glasmischung. Wird zur Verteilung und Lagerung von Flüssigkeiten benutzt. item.metaglass.description = Eine extrem harte Glasmischung. Wird zur Verteilung und Lagerung von Flüssigkeiten benutzt.

View File

@@ -95,6 +95,7 @@ server.versions = Votre version:[accent] {0}[]\nLa version du serveur:[accent] {
host.info = Le bouton [accent]Héberger[] héberge un serveur sur le port [scarlet]6567[]. \nN'importe qui sur le même [lightgray]wifi ou réseau local []devrait voir votre serveur sur leur liste des serveurs.\n\nSi vous voulez que les gens puissent s'y connecter de partout à l'aide de votre IP, [accent]le transfert de port (port forwarding)[] est requis.\n\n[lightgray]Note: Si quelqu'un a des problèmes de connexion à votre partie LAN, vérifiez que vous avez autorisé l'accès à Mindustry sur votre réseau local dans les paramètres de votre pare-feu. host.info = Le bouton [accent]Héberger[] héberge un serveur sur le port [scarlet]6567[]. \nN'importe qui sur le même [lightgray]wifi ou réseau local []devrait voir votre serveur sur leur liste des serveurs.\n\nSi vous voulez que les gens puissent s'y connecter de partout à l'aide de votre IP, [accent]le transfert de port (port forwarding)[] est requis.\n\n[lightgray]Note: Si quelqu'un a des problèmes de connexion à votre partie LAN, vérifiez que vous avez autorisé l'accès à Mindustry sur votre réseau local dans les paramètres de votre pare-feu.
join.info = Ici vous pouvez entrez [accent]l'adresse IP d'un serveur []pour s'y connecter, ou découvrir un serveur en [accent]réseau local[].\nLe multijoueur en LAN ainsi qu'en WAN est supporté.\n\n[lightgray]Note: Il n'y a pas de liste de serveurs globaux automatiques; Si vous voulez vous connectez à quelqu'un par IP, il faudra d'abord demander à l'hébergeur leur IP. join.info = Ici vous pouvez entrez [accent]l'adresse IP d'un serveur []pour s'y connecter, ou découvrir un serveur en [accent]réseau local[].\nLe multijoueur en LAN ainsi qu'en WAN est supporté.\n\n[lightgray]Note: Il n'y a pas de liste de serveurs globaux automatiques; Si vous voulez vous connectez à quelqu'un par IP, il faudra d'abord demander à l'hébergeur leur IP.
hostserver = Héberger une partie hostserver = Héberger une partie
invitefriends = Inviter des Amis
hostserver.mobile = Héberger\nune partie hostserver.mobile = Héberger\nune partie
host = Héberger host = Héberger
hosting = [accent]Préparation du serveur... hosting = [accent]Préparation du serveur...
@@ -124,6 +125,7 @@ server.version = [lightgray]Version: {0} {1}
server.custombuild = [yellow]Version personnalisée server.custombuild = [yellow]Version personnalisée
confirmban = Souhaitez vous vraiment bannir ce joueur? confirmban = Souhaitez vous vraiment bannir ce joueur?
confirmkick = Souhaitez vous vraiment expulser ce joueur? confirmkick = Souhaitez vous vraiment expulser ce joueur?
confirmvotekick = Voulez vous vraiment voter l'expulsion de ce joueur?
confirmunban = Souhaitez vous vraiment réintégrer ce joueur ? confirmunban = Souhaitez vous vraiment réintégrer ce joueur ?
confirmadmin = Souhaitez vous vraiment rendre ce joueur administrateur? confirmadmin = Souhaitez vous vraiment rendre ce joueur administrateur?
confirmunadmin = Souhaitez vous vraiment enlever le statut d'administrateur à ce joueur? confirmunadmin = Souhaitez vous vraiment enlever le statut d'administrateur à ce joueur?
@@ -134,6 +136,7 @@ disconnect.error = Erreur de connexion.
disconnect.closed = Connexion fermée. disconnect.closed = Connexion fermée.
disconnect.timeout = Délai de connexion expiré. disconnect.timeout = Délai de connexion expiré.
disconnect.data = Les données du monde n'ont pas pu être chargées! disconnect.data = Les données du monde n'ont pas pu être chargées!
cantconnect = Impossible de rejoindre ([accent]{0}[]).
connecting = [accent]Connexion... connecting = [accent]Connexion...
connecting.data = [accent]Chargement de la partie... connecting.data = [accent]Chargement de la partie...
server.port = Port: server.port = Port:
@@ -159,6 +162,7 @@ save.rename = Renommer
save.rename.text = Nouveau nom: save.rename.text = Nouveau nom:
selectslot = Choisissez une sauvegarde. selectslot = Choisissez une sauvegarde.
slot = [accent]Emplacement {0} slot = [accent]Emplacement {0}
editmessage = Modifier le Message
save.corrupted = [accent]Sauvegarde corrompue ou invalide!\nSi vous venez de mettre à jour votre jeu, c'est probablement dû à un changement du format de sauvegarde et [scarlet]pas[] à un bug. save.corrupted = [accent]Sauvegarde corrompue ou invalide!\nSi vous venez de mettre à jour votre jeu, c'est probablement dû à un changement du format de sauvegarde et [scarlet]pas[] à un bug.
empty = <vide> empty = <vide>
on = Activé on = Activé
@@ -172,6 +176,7 @@ save.playtime = Temps de jeu: {0}
warning = Avertissement. warning = Avertissement.
confirm = Confirmer confirm = Confirmer
delete = Supprimer delete = Supprimer
view.workshop = Voir dans le Workshop
ok = OK ok = OK
open = Ouverture open = Ouverture
customize = Personaliser customize = Personaliser
@@ -209,6 +214,8 @@ map.nospawn.pvp = Cette carte n'a pas de base ennemies pour qu'un joueur ennemi
map.nospawn.attack = Cette carte n'a aucune base ennemie à attaquer! Veuillez ajouter une base[SCARLET] rouge[] sur cette carte dans l'éditeur. map.nospawn.attack = Cette carte n'a aucune base ennemie à attaquer! Veuillez ajouter une base[SCARLET] rouge[] sur cette carte dans l'éditeur.
map.invalid = Erreur lors du chargement de la carte: carte corrompue ou invalide. map.invalid = Erreur lors du chargement de la carte: carte corrompue ou invalide.
map.publish.error = Erreur de Publication de la Carte: {0} map.publish.error = Erreur de Publication de la Carte: {0}
map.publish.confirm = Êtes-vous sûr de vouloir publier cette carte?\n\n[lightgray]Assurez-vous daccepter dabord les CGU du Workshop, sinon vos cartes ne seront pas affichées!
eula = CGU de Steam
map.publish = Carte publiée. map.publish = Carte publiée.
map.publishing = [accent]Publication de la carte... map.publishing = [accent]Publication de la carte...
editor.brush = Pinceau editor.brush = Pinceau
@@ -218,6 +225,7 @@ editor.oregen.info = Génération de minerais:
editor.mapinfo = Infos Carte editor.mapinfo = Infos Carte
editor.author = Auteur: editor.author = Auteur:
editor.description = Description: editor.description = Description:
editor.nodescription = Une carte doit avoir une description d'au moins 4 caractères pour pouvoir être publiée.
editor.waves = Vagues: editor.waves = Vagues:
editor.rules = Règles: editor.rules = Règles:
editor.generation = Génération: editor.generation = Génération:
@@ -284,6 +292,7 @@ editor.resizemap = Redimensionner\nla carte
editor.mapname = Nom de la carte: editor.mapname = Nom de la carte:
editor.overwrite = [accent]Attention!\nCeci écrase une carte existante. editor.overwrite = [accent]Attention!\nCeci écrase une carte existante.
editor.overwrite.confirm = [scarlet]Attention![] Une carte avec ce nom existe déjà. Êtes-vous sûr de vouloir l'écraser? editor.overwrite.confirm = [scarlet]Attention![] Une carte avec ce nom existe déjà. Êtes-vous sûr de vouloir l'écraser?
editor.exists = Une carte avec ce nom existe déjà.
editor.selectmap = Sélectionnez une carte: editor.selectmap = Sélectionnez une carte:
toolmode.replace = Remplacer toolmode.replace = Remplacer
@@ -478,9 +487,11 @@ bar.drilltierreq = Foreuse Ameliorée Requise
bar.drillspeed = Vitesse de forage: {0}/s bar.drillspeed = Vitesse de forage: {0}/s
bar.efficiency = Efficacité: {0}% bar.efficiency = Efficacité: {0}%
bar.powerbalance = Énergie: {0}/s bar.powerbalance = Énergie: {0}/s
bar.powerstored = Stocké: {0}/{1}
bar.poweramount = Énergie: {0} bar.poweramount = Énergie: {0}
bar.poweroutput = Énergie Produite: {0} bar.poweroutput = Énergie Produite: {0}
bar.items = Objets: {0} bar.items = Objets: {0}
bar.capacity = Capacité: {0}
bar.liquid = Liquide bar.liquid = Liquide
bar.heat = Chaleur bar.heat = Chaleur
bar.power = Énergie bar.power = Énergie
@@ -527,6 +538,7 @@ setting.antialias.name = Antialias[lightgray] (redémarrage du jeu nécéssaire)
setting.indicators.name = Indicateurs Alliés/Ennemis setting.indicators.name = Indicateurs Alliés/Ennemis
setting.autotarget.name = Visée automatique setting.autotarget.name = Visée automatique
setting.keyboard.name = Controles Sourie+Clavier setting.keyboard.name = Controles Sourie+Clavier
setting.touchscreen.name = Commandes d'Écran Tactile
setting.fpscap.name = FPS Max setting.fpscap.name = FPS Max
setting.fpscap.none = Aucun setting.fpscap.none = Aucun
setting.fpscap.text = {0} FPS setting.fpscap.text = {0} FPS
@@ -569,8 +581,8 @@ category.general.name = Général
category.view.name = Voir category.view.name = Voir
category.multiplayer.name = Multijoueur category.multiplayer.name = Multijoueur
command.attack = Attaque command.attack = Attaque
command.rally = Rassembler
command.retreat = Retraite command.retreat = Retraite
command.patrol = Patrouille
keybind.gridMode.name = Sélection des blocs keybind.gridMode.name = Sélection des blocs
keybind.gridModeShift.name = Sélection des catégories keybind.gridModeShift.name = Sélection des catégories
keybind.press = Appuyer sur une touche... keybind.press = Appuyer sur une touche...
@@ -789,10 +801,13 @@ block.hail.name = Grêle
block.lancer.name = Lancier block.lancer.name = Lancier
block.conveyor.name = Convoyeur block.conveyor.name = Convoyeur
block.titanium-conveyor.name = Convoyeur en Titane block.titanium-conveyor.name = Convoyeur en Titane
block.armored-conveyor.name = Convoyeur Cuirassé
block.armored-conveyor.description = Déplace les objets à la même vitesse que les convoyeurs en titane, mais est plus résistant. Seulement d'autres convoyeurs peuvent faire rentrer des ressources par ses cotés.
block.junction.name = Jonction block.junction.name = Jonction
block.router.name = Routeur block.router.name = Routeur
block.distributor.name = Distributeur block.distributor.name = Distributeur
block.sorter.name = Trieur block.sorter.name = Trieur
block.message.name = Message
block.overflow-gate.name = Barrière de Débordement block.overflow-gate.name = Barrière de Débordement
block.silicon-smelter.name = Fonderie de Silicone block.silicon-smelter.name = Fonderie de Silicone
block.phase-weaver.name = Tisseur à Phase block.phase-weaver.name = Tisseur à Phase
@@ -846,6 +861,8 @@ block.solar-panel.name = Panneau Solaire
block.solar-panel-large.name = Grand Panneau Solaire block.solar-panel-large.name = Grand Panneau Solaire
block.oil-extractor.name = Extracteur de Pétrole block.oil-extractor.name = Extracteur de Pétrole
block.command-center.name = Centre de Commandement block.command-center.name = Centre de Commandement
block.rally-point.name = Point de Raliement
block.rally-point.description = Un marqueur pour que les unitées s'y regroupent autour. Nécessite l'émission de la commande 'Rassembler' depuis le centre de commande pour pouvoir l'utiliser.
block.draug-factory.name = Usine de Drones Draug Mineurs block.draug-factory.name = Usine de Drones Draug Mineurs
block.spirit-factory.name = Usine de Drones Spirituels Réparateurs block.spirit-factory.name = Usine de Drones Spirituels Réparateurs
block.phantom-factory.name = Usine de Drones Fantômes Constructeurs block.phantom-factory.name = Usine de Drones Fantômes Constructeurs
@@ -876,7 +893,7 @@ block.surge-wall.name = Mur Superchargé
block.surge-wall-large.name = Grand mur Superchargé block.surge-wall-large.name = Grand mur Superchargé
block.cyclone.name = Cyclone block.cyclone.name = Cyclone
block.fuse.name = Fusible block.fuse.name = Fusible
block.shock-mine.name = Mine Terreur block.shock-mine.name = Mine à Chocs
block.overdrive-projector.name = Projecteur Surmultiplicateur block.overdrive-projector.name = Projecteur Surmultiplicateur
block.force-projector.name = Champ de Force block.force-projector.name = Champ de Force
block.arc.name = Arc block.arc.name = Arc
@@ -887,10 +904,10 @@ block.container.name = Conteneur
block.launch-pad.name = Plateforme de Lancement block.launch-pad.name = Plateforme de Lancement
block.launch-pad-large.name = Grande Plateforme de Lancement block.launch-pad-large.name = Grande Plateforme de Lancement
team.blue.name = bleu team.blue.name = bleu
team.crux.name = red team.crux.name = rouge
team.sharded.name = orange team.sharded.name = éclaté
team.orange.name = orange team.orange.name = orange
team.derelict.name = derelict team.derelict.name = abandonné
team.green.name = vert team.green.name = vert
team.purple.name = violet team.purple.name = violet
unit.spirit.name = Drone Spirituel Réparateur unit.spirit.name = Drone Spirituel Réparateur
@@ -929,7 +946,6 @@ tutorial.waves = L'[lightgray] ennemi[] approche.\n\nDefend le noyau pendant 2 v
tutorial.waves.mobile = L'[lightgray] ennemi[] approche.\n\nDefend le noyau pendant 2 vagues. Votre vaisseau tirera automatiquement sur les ennemis.\nConstruisez plus de tourelles et de foreuses. Minez plus de cuivre. tutorial.waves.mobile = L'[lightgray] ennemi[] approche.\n\nDefend le noyau pendant 2 vagues. Votre vaisseau tirera automatiquement sur les ennemis.\nConstruisez plus de tourelles et de foreuses. Minez plus de cuivre.
tutorial.launch = Une fois que vous aurez atteind une vague spécifique, vous aurez la possibilité de[accent] faire décoler le noyau[], abandonant vos défenses mais en [accent]sécurisant toutes les ressources de votre noyau.[]\nCes ressources peuvent ensuite être utilisées pour rechercher de nouvelles technologies.\n\n[accent]Appuyez sur le bouton de lancement. tutorial.launch = Une fois que vous aurez atteind une vague spécifique, vous aurez la possibilité de[accent] faire décoler le noyau[], abandonant vos défenses mais en [accent]sécurisant toutes les ressources de votre noyau.[]\nCes ressources peuvent ensuite être utilisées pour rechercher de nouvelles technologies.\n\n[accent]Appuyez sur le bouton de lancement.
item.copper.description = Le matériau structurel de base. Utilisé intensivement dans tout les blocs. item.copper.description = Le matériau structurel de base. Utilisé intensivement dans tout les blocs.
item.lead.description = Un matériau de départ. Utilisé intensivement en électronique et dans les blocs de trasports de liquides. item.lead.description = Un matériau de départ. Utilisé intensivement en électronique et dans les blocs de trasports de liquides.
item.metaglass.description = Un composé de vitre super-résistant. Utilisé largement pour le transport et le stockage de liquides. item.metaglass.description = Un composé de vitre super-résistant. Utilisé largement pour le transport et le stockage de liquides.
@@ -969,6 +985,7 @@ unit.eruptor.description = Une unité lourde conçue pour détruire les structur
unit.wraith.description = Une unité d'interception rapide et de frappe. Cible les générateurs d'énergie. unit.wraith.description = Une unité d'interception rapide et de frappe. Cible les générateurs d'énergie.
unit.ghoul.description = Un bombardier lourd de saturation. Déchire a travert les structures ennemies, ciblant les infrastructures critiques. unit.ghoul.description = Un bombardier lourd de saturation. Déchire a travert les structures ennemies, ciblant les infrastructures critiques.
unit.revenant.description = Un arsenal de missiles lourd et planant. unit.revenant.description = Un arsenal de missiles lourd et planant.
block.message.description = Enregistre un message. Utilisé pour la communication entre alliés.
block.graphite-press.description = Compresse des morceaux de charbon en feuilles de graphite pur. block.graphite-press.description = Compresse des morceaux de charbon en feuilles de graphite pur.
block.multi-press.description = Une version améliorée de la presse à graphite. Utilise de l'eau et de l'électricité pour traiter le charbon rapidement et efficacement. block.multi-press.description = Une version améliorée de la presse à graphite. Utilise de l'eau et de l'électricité pour traiter le charbon rapidement et efficacement.
block.silicon-smelter.description = Réduit le sable avec du charbon pur. Produit du silicone. block.silicon-smelter.description = Réduit le sable avec du charbon pur. Produit du silicone.

View File

@@ -32,7 +32,7 @@ level.select = Selezione del livello
level.mode = Modalità di gioco: level.mode = Modalità di gioco:
showagain = non mostrare più showagain = non mostrare più
coreattack = < Il nucleo è sotto attacco! > coreattack = < Il nucleo è sotto attacco! >
nearpoint = [[ [scarlet]LACIA LA ZONA NEMICA IMMEDIATAMENTE[] ]\nautodistruzione imminente nearpoint = [[ [scarlet]LASCIA LA ZONA NEMICA IMMEDIATAMENTE[] ]\nautodistruzione imminente
database = Database nucleo database = Database nucleo
savegame = Salva savegame = Salva
loadgame = Carica loadgame = Carica
@@ -41,7 +41,7 @@ addplayers = Aggiungi/rimuovi giocatori
customgame = Gioco personalizzato customgame = Gioco personalizzato
newgame = Nuova partita newgame = Nuova partita
none = <Niente . . . > none = <Niente . . . >
minimap = Minimapa minimap = Minimappa
close = Chiuso close = Chiuso
website = Website website = Website
quit = Esci quit = Esci
@@ -103,7 +103,7 @@ server.outdated.client = [crimson]Client obsoleto![]
server.version = [lightgray]Versione: {0} server.version = [lightgray]Versione: {0}
server.custombuild = [yellow] Costruzione personalizzata server.custombuild = [yellow] Costruzione personalizzata
confirmban = Sei sicuro di voler bandire questo giocatore? confirmban = Sei sicuro di voler bandire questo giocatore?
confirmkick = Are you sure you want to kick this player? confirmkick = Sei sicuro di voler espellere questo giocatore?
confirmunban = Sei sicuro di voler riammettere questo giocatore? confirmunban = Sei sicuro di voler riammettere questo giocatore?
confirmadmin = Sei sicuro di voler rendere questo giocatore un amministratore? confirmadmin = Sei sicuro di voler rendere questo giocatore un amministratore?
confirmunadmin = Sei sicuro di voler rimuovere lo stato di amministratore da questo giocatore? confirmunadmin = Sei sicuro di voler rimuovere lo stato di amministratore da questo giocatore?
@@ -123,13 +123,16 @@ save.overwrite = Sei sicuro di voler sovrascrivere questo salvataggio?
overwrite = Sovrascrivi overwrite = Sovrascrivi
save.none = Nessun salvataggio trovato! save.none = Nessun salvataggio trovato!
saveload = [Accent]Salvataggio ... saveload = [Accent]Salvataggio ...
savefail = Salvataggio del gioco non riuscito! savefail = [crimson]Salvataggio del gioco NON riuscito!
save.delete.confirm = Sei sicuro di voler eliminare questo salvataggio? save.delete.confirm = Sei sicuro di voler eliminare questo salvataggio?
save.delete = Elimina save.delete = Elimina
save.export = Esporta Salvataggio save.export = Esporta Salvataggio
save.import.invalid = [accent]Questo salvataggio non è valido! save.import.invalid = [accent]Questo salvataggio non è valido!
save.import.fail = [crimson]Impossibile importare salvataggio: [accent]{0} save.import.fail = [crimson]Impossibile importare salvataggio: [accent]{0}
save.export.fail = [crimson]Impossibile esportare il salvataggio: [accent]{0} save.export.fail = [crimson]Impossibile esportare il salvataggio: [accent]{0}
settings.data = Importa/Esporta salvataggio
data.export = Esporta Salvataggio
data.import = Importa Salvataggio
save.import = Importa Salvataggio save.import = Importa Salvataggio
save.newslot = Salva nome: save.newslot = Salva nome:
save.rename = Rinomina save.rename = Rinomina
@@ -146,12 +149,12 @@ save.wave = Ondata: {0}
save.difficulty = Difficoltà: {0} save.difficulty = Difficoltà: {0}
save.date = Ultimo salvataggio: {0} save.date = Ultimo salvataggio: {0}
save.playtime = Tempo di gioco: {0} save.playtime = Tempo di gioco: {0}
warning = Warning. warning = Attenzione
confirm = Conferma confirm = Conferma
delete = Elimina delete = Elimina
ok = OK ok = OK
open = Apri open = Apri
customize = Customize customize = Personalizza
cancel = Annulla cancel = Annulla
openlink = Apri Link openlink = Apri Link
copylink = Copia link copylink = Copia link
@@ -161,9 +164,9 @@ classic.export.text = [accent]Mindustry[] ha appena rilasciato un aggiornamento
quit.confirm = Sei sicuro di voler uscire? quit.confirm = Sei sicuro di voler uscire?
quit.confirm.tutorial = Sei sicuro di sapere cosa stai facendo? Il tutorial può essere ripetuto in[accent] Impostazioni->Gioco->Ripeti il tutorial.[] quit.confirm.tutorial = Sei sicuro di sapere cosa stai facendo? Il tutorial può essere ripetuto in[accent] Impostazioni->Gioco->Ripeti il tutorial.[]
loading = [accent]Caricamento in corso ... loading = [accent]Caricamento in corso ...
saving = [accent]Salvando . . . saving = [accent]Salvando ...
wave = [accent]Ondata {0} wave = [accent]Ondata {0}
wave.waiting = Ondata in {0} wave.waiting = Ondata tra {0}
wave.waveInProgress = [LIGHT_GRAY]Ondata in corso... wave.waveInProgress = [LIGHT_GRAY]Ondata in corso...
waiting = In attesa... waiting = In attesa...
waiting.players = Aspettando giocatori... waiting.players = Aspettando giocatori...
@@ -174,9 +177,9 @@ saveimage = Salva Immagine
unknown = Sconosciuto unknown = Sconosciuto
custom = Personalizzato custom = Personalizzato
builtin = Incluso builtin = Incluso
map.delete.confirm = Sei sicuro di voler eliminare questa mappa? Non potrai tornare indietro! map.delete.confirm = Sei sicuro di voler eliminare questa mappa? L'operazione è irreversibile!
map.random = [accent]Mappa casuale map.random = [accent]Mappa casuale
map.nospawn = Questa mappa non possiede un nucleo dove spawnare! Aggiungine uno nell'editor. map.nospawn = Questa mappa non possiede un nucleo in cui spawnare! Aggiungine uno nell'editor.
map.nospawn.pvp = Questa mappa non ha un nucleo nemico! Aggiungi un [SCARLET]nucleo rosso[] nell'editor per poter giocare. map.nospawn.pvp = Questa mappa non ha un nucleo nemico! Aggiungi un [SCARLET]nucleo rosso[] nell'editor per poter giocare.
map.nospawn.attack = Questa mappa non ha un nucleo nemico! Aggiungi un [SCARLET]nucleo rosso[] nell'editor per poter giocare. map.nospawn.attack = Questa mappa non ha un nucleo nemico! Aggiungi un [SCARLET]nucleo rosso[] nell'editor per poter giocare.
map.invalid = Errore nel caricamento della mappa: file mappa corrotto o non valido. map.invalid = Errore nel caricamento della mappa: file mappa corrotto o non valido.
@@ -194,7 +197,7 @@ editor.ingame = Modifica in gioco
editor.newmap = Nuova mappa editor.newmap = Nuova mappa
waves.title = Ondate waves.title = Ondate
waves.remove = Rimuovi waves.remove = Rimuovi
waves.never = <mai> waves.never = mai
waves.every = sempre waves.every = sempre
waves.waves = ondata/e waves.waves = ondata/e
waves.perspawn = per spawn waves.perspawn = per spawn
@@ -216,7 +219,7 @@ editor.teams = Squadre
editor.errorload = Errore nel caricamento di:\n[accent]{0} editor.errorload = Errore nel caricamento di:\n[accent]{0}
editor.errorsave = Errore nel salvataggio di:\n[accent]{0} editor.errorsave = Errore nel salvataggio di:\n[accent]{0}
editor.errorimage = Quella è un'immagine, non una mappa. Non cambiare estensioni sperando che funzioni.\n\n Se vuoi importare una mappa vecchia clicca su "importa una mappa vecchia" nell'editor. editor.errorimage = Quella è un'immagine, non una mappa. Non cambiare estensioni sperando che funzioni.\n\n Se vuoi importare una mappa vecchia clicca su "importa una mappa vecchia" nell'editor.
editor.errorlegacy = La mappa è troppo vecchia e usa un formato che non è più supportato. editor.errorlegacy = La mappa è troppo vecchia ed usa un formato che non è più supportato.
editor.errorheader = Questo file della mappa è invalido o corrotto. editor.errorheader = Questo file della mappa è invalido o corrotto.
editor.errorname = Questa mappa è senza nome. editor.errorname = Questa mappa è senza nome.
editor.update = Aggiorna editor.update = Aggiorna
@@ -229,7 +232,7 @@ editor.savemap = Salva\nla mappa
editor.saved = Salvato! editor.saved = Salvato!
editor.save.noname = La tua mappa non ha un nome! Impostane uno nelle informazioni della mappa. editor.save.noname = La tua mappa non ha un nome! Impostane uno nelle informazioni della mappa.
editor.save.overwrite = La tua mappa sovrascrive quelle incluse! Imposta un nome diverso nelle informazioni della mappa. editor.save.overwrite = La tua mappa sovrascrive quelle incluse! Imposta un nome diverso nelle informazioni della mappa.
editor.import.exists = [scarlet]Impossibile importare:[] esiste già una mappa chiamata '{0}' che non può essere svrascritta! editor.import.exists = [scarlet]Impossibile importare:[] esiste già una mappa chiamata '{0}' che non può essere sovrascritta!
editor.import = Importando... editor.import = Importando...
editor.importmap = Importa mappa editor.importmap = Importa mappa
editor.importmap.description = Importa mappa preesistente editor.importmap.description = Importa mappa preesistente
@@ -264,7 +267,7 @@ toolmode.fillteams = Riempi squadre
toolmode.fillteams.description = Riempe squadre al posto di blocchi toolmode.fillteams.description = Riempe squadre al posto di blocchi
toolmode.drawteams = Disegna squadre toolmode.drawteams = Disegna squadre
toolmode.drawteams.description = Disegna squadre al posto di blocchi toolmode.drawteams.description = Disegna squadre al posto di blocchi
filters.empty = [LIGHT_GRAY]Nessun filtro! Aggiungi uno cliccando il tasto sotto. filters.empty = [LIGHT_GRAY]Nessun filtro! Aggiungine uno cliccando il tasto sotto.
filter.distort = Modifica filter.distort = Modifica
filter.noise = Interferenza filter.noise = Interferenza
filter.median = Mediana filter.median = Mediana
@@ -273,7 +276,7 @@ filter.blend = Miscela
filter.defaultores = Minerali predefiniti filter.defaultores = Minerali predefiniti
filter.ore = Minerali filter.ore = Minerali
filter.rivernoise = Interferenze a fiume filter.rivernoise = Interferenze a fiume
filter.mirror = Specchia filter.mirror = Rifletti
filter.clear = Resetta il filtro filter.clear = Resetta il filtro
filter.option.ignore = Ignora filter.option.ignore = Ignora
filter.scatter = Dispersione filter.scatter = Dispersione
@@ -322,15 +325,15 @@ bestwave = [LIGHT_GRAY]Migliore: {0}
launch = Decollare launch = Decollare
launch.title = Decollo riuscito! launch.title = Decollo riuscito!
launch.next = [LIGHT_GRAY]Nuova opportunità all'ondata {0} launch.next = [LIGHT_GRAY]Nuova opportunità all'ondata {0}
launch.unable2 = [scarlet]Decollo FALLITO![] launch.unable2 = [scarlet]IMPOSSIBILE DECOLLARE![]
launch.confirm = Questo trasporterà tutte le risorse nel tuo nucleo.\nNon riuscirai a ritornare in questa base. launch.confirm = Questo trasporterà tutte le risorse nel tuo nucleo.\nNon riuscirai a ritornare in questa base.
launch.skip.confirm = Se salti adesso non riuscirai a decollare fino alle onde sucessive launch.skip.confirm = Se salti adesso non riuscirai a decollare fino alle ondate successive
uncover = Svlare uncover = Svelare
configure = Configura l'equipaggio configure = Configura l'equipaggiamento
configure.locked = [LIGHT_GRAY]Arriva all'ondata {0}\nper configurare l'equipaggiamento. configure.locked = [LIGHT_GRAY]Arriva all'ondata {0}\nper configurare l'equipaggiamento.
zone.unlocked = [LIGHT_GRAY]{0} sbloccata. zone.unlocked = [LIGHT_GRAY]{0} sbloccata.
zone.requirement.complete = Ondata {0} raggiunta:\n{1} requisiti di zona soddisfatti. zone.requirement.complete = Ondata {0} raggiunta:\n{1} requisiti di zona soddisfatti.
zone.config.complete = Ondata {0} reached:\nLoadout config unlocked. zone.config.complete = Ondata {0} raggiunta:\nEquipaggiamento personalizzato sbloccato.
zone.resources = Risorse trovate: zone.resources = Risorse trovate:
zone.objective = [lightgray]Obiettivo: [accent]{0} zone.objective = [lightgray]Obiettivo: [accent]{0}
zone.objective.survival = Sopravvivere zone.objective.survival = Sopravvivere
@@ -346,7 +349,7 @@ error.alreadyconnected = Già connesso.
error.mapnotfound = Mappa non trovata error.mapnotfound = Mappa non trovata
error.io = Errore I/O di rete. error.io = Errore I/O di rete.
error.any = Errore di rete sconosciuto. error.any = Errore di rete sconosciuto.
error.bloom = Failed to initialize bloom.\nYour device may not support it. error.bloom = Errore dell'avvio del bloom.\nIl tuo dispositivo potrebbe non supportarlo.
zone.groundZero.name = Terreno Zero zone.groundZero.name = Terreno Zero
zone.desertWastes.name = Rifiuti Desertici zone.desertWastes.name = Rifiuti Desertici
zone.craters.name = Crateri zone.craters.name = Crateri
@@ -362,16 +365,16 @@ zone.impact0078.name = Impatto 0078
zone.crags.name = Dirupi zone.crags.name = Dirupi
zone.fungalPass.name = Passaggio Fungoso zone.fungalPass.name = Passaggio Fungoso
zone.groundZero.description = La posizione ottimale per cominciare. Bassa minaccia nemica. Poche risorse.\nRaccogli quanto più piombo e rame possibile.\nProcedi. zone.groundZero.description = La posizione ottimale per cominciare. Bassa minaccia nemica. Poche risorse.\nRaccogli quanto più piombo e rame possibile.\nProcedi.
zone.frozenForest.description = Anche qui, più vicino alle montagne, le spore si sono diffuse. Le temperature rigide non possono contenerle per sempre.\n Inizia la scoperta dell'energia. Costruisci generatori di combustione. Impara a usare i riparatori. zone.frozenForest.description = Anche qui, più vicino alle montagne, le spore si sono diffuse. Le temperature rigide non possono contenerle per sempre.\n Inizia la scoperta dell'energia. Costruisci generatori a combustione. Impara a usare i riparatori.
zone.desertWastes.description = Questi rifiuti sono vasti, imprevedibili e attraversati da strutture settoriali abbandonate.\n\nIl carbone è presente nella regione. Bruciatelo per ottenere energia o sintetizzate la grafite.\n\n[lightgray]Questa posizione di atterraggio non può essere garantita. zone.desertWastes.description = Questi rifiuti sono vasti, imprevedibili ed attraversati da strutture settoriali abbandonate.\n\nIl carbone è presente nella regione. Bruciatelo per ottenere energia o sintetizzate la grafite.\n\n[lightgray]Questa posizione di atterraggio non può essere garantita.
zone.saltFlats.description = Alle periferie del deserto si trovano le saline. Poche risorse possono essere trovate in questa posizione.\n\nIl nemico ha eretto un complesso di archiviazione delle risorse qui. Sradicare il loro nucleo. Non lasciare nulla in piedi. zone.saltFlats.description = Alle periferie del deserto si trovano le saline. Poche risorse possono essere trovate in questa posizione.\n\nIl nemico ha eretto un complesso di archiviazione delle risorse qui. Sradicare il loro nucleo. Non lasciare nulla in piedi.
zone.craters.description = L'acqua si è accumulata in questo cratere, reliquia delle vecchie guerre. Recupera l'area. Raccogli la sabbia. Fondi il vetro metallico. Pompa l'acqua per raffreddare torrette e trapani. zone.craters.description = L'acqua si è accumulata in questo cratere, reliquia delle vecchie guerre. Recupera l'area. Raccogli la sabbia. Fondi il vetro metallico. Pompa l'acqua per raffreddare torrette e trivelle.
zone.ruinousShores.description = Oltre i rifiuti, c'è il litorale. Una volta, questa posizione ospitava una schiera di difesa costiera. Non rimane molto. Solo le strutture di difesa più elementari sono rimaste incolume, tutto il resto ridotto a rottami.\nContinua l'espansione verso l'esterno. Riscopri la tecnologia. zone.ruinousShores.description = Oltre i rifiuti, c'è il litorale. Una volta, questa posizione ospitava una schiera di difesa costiera. Non rimane molto. Solo le strutture di difesa più elementari sono rimaste incolume, tutto il resto ridotto a rottami.\nContinua l'espansione verso l'esterno. Riscopri la tecnologia.
zone.stainedMountains.description = Più nell'entroterra si trovano le montagne, non ancora contaminate da spore.\nEstrai l'abbondante titanio in questa zona. Scopri come usarlo.\n\nLa presenza del nemico è maggiore qui. Non dare loro il tempo di inviare le loro unità più forti. zone.stainedMountains.description = Più nell'entroterra si trovano le montagne, non ancora contaminate da spore.\nEstrai l'abbondante titanio in questa zona. Scopri come usarlo.\n\nLa presenza del nemico è maggiore qui. Non dare loro il tempo di inviare le loro unità più forti.
zone.overgrowth.description = Quest'area è invasa, più vicina alla fonte delle spore.\nIl nemico ha stabilito qui un avamposto. Costruisci unità col pugnale. Distruggilo. Riprenditi ciò che è stato perso. zone.overgrowth.description = Quest'area è invasa, più vicina alla fonte delle spore.\nIl nemico ha stabilito qui un avamposto. Costruisci unità col pugnale. Distruggilo. Riprenditi ciò che è stato perso.
zone.tarFields.description = La periferia di una zona di produzione di petrolio, tra le montagne e il deserto. Una delle poche aree con riserve di catrame utilizzabili.\nAnche se abbandonata, questa zona ha alcune pericolose forze nemiche nelle vicinanze. Non sottovalutarlo.\n\n[lightgray]Ricerca la tecnologia di lavorazione dell'olio, se possibile. zone.tarFields.description = La periferia di una zona di produzione di petrolio, tra le montagne e il deserto. Una delle poche aree con riserve di catrame utilizzabili.\nAnche se abbandonata, questa zona ha alcune pericolose forze nemiche nelle vicinanze. Non sottovalutarlo.\n\n[lightgray]Ricerca la tecnologia di lavorazione del petrolio, se possibile.
zone.desolateRift.description = Una zona estremamente pericolosa. Risorse abbondanti, ma poco spazio. Alto rischio di distruzione. Lascia il prima possibile. Non lasciarti ingannare dalla lunga distanza tra gli attacchi nemici. zone.desolateRift.description = Una zona estremamente pericolosa. Risorse abbondanti, ma poco spazio. Alto rischio di distruzione. Lascia il prima possibile. Non lasciarti ingannare dalla lunga distanza tra gli attacchi nemici.
zone.nuclearComplex.description = Un ex impianto per la produzione e la lavorazione del torio, ridotto in rovina.\n[lightgray] Ricerca il torio e i suoi numerosi usi.\n\nIl nemico è presente qui in gran numero, alla costante ricerca di aggressori. zone.nuclearComplex.description = Un ex impianto per la produzione e la lavorazione del torio, ridotto in rovina.\n[lightgray] Ricerca il torio ed i suoi numerosi usi.\n\nIl nemico è presente qui in gran numero, alla costante ricerca di aggressori.
zone.fungalPass.description = Un'area di transizione tra alte montagne e terre più basse, piene di spore. Qui si trova una piccola base di ricognizione nemica.\nDistruggila.\nUsa le unità Pugnale e Strisciatore. Elimina i due nuclei. zone.fungalPass.description = Un'area di transizione tra alte montagne e terre più basse, piene di spore. Qui si trova una piccola base di ricognizione nemica.\nDistruggila.\nUsa le unità Pugnale e Strisciatore. Elimina i due nuclei.
zone.impact0078.description = <inserisci descrizione> zone.impact0078.description = <inserisci descrizione>
zone.crags.description = <inserisci descrizione> zone.crags.description = <inserisci descrizione>
@@ -394,6 +397,7 @@ info.title = [accent] Info
error.title = [crimson]Si è verificato un errore error.title = [crimson]Si è verificato un errore
error.crashtitle = Si è verificato un errore error.crashtitle = Si è verificato un errore
attackpvponly = [scarlet]Solo possible nelle modalità Attacco/PvP attackpvponly = [scarlet]Solo possible nelle modalità Attacco/PvP
blocks.buildcost = Costo di Costruzione
blocks.input = Ingresso blocks.input = Ingresso
blocks.output = Uscita blocks.output = Uscita
blocks.booster = Booster blocks.booster = Booster
@@ -413,21 +417,21 @@ blocks.poweruse = Utilizzo energia
blocks.powerdamage = Energia/Danno blocks.powerdamage = Energia/Danno
blocks.itemcapacity = Capacità blocks.itemcapacity = Capacità
blocks.basepowergeneration = Generazione energia di base blocks.basepowergeneration = Generazione energia di base
blocks.productiontime = Tempo produzione blocks.productiontime = Tempo di produzione
blocks.repairtime = Tempo di riparo completo blocks.repairtime = Tempo di riparazione completa
blocks.speedincrease = Aumento Velocità blocks.speedincrease = Aumento Velocità
blocks.range = Raggio blocks.range = Raggio
blocks.drilltier = Scavabili blocks.drilltier = Scavabili
blocks.drillspeed = Velocità scavo stbile blocks.drillspeed = Velocità di scavo stabile
blocks.boosteffect = Effetto boost blocks.boosteffect = Effetto boost
blocks.maxunits = Unità attive max blocks.maxunits = Unità attive max
blocks.health = Salute blocks.health = Salute
blocks.buildtime = Tempo costruzione blocks.buildtime = Tempo di costruzione
blocks.inaccuracy = Inaccuratezza blocks.inaccuracy = Inaccuratezza
blocks.shots = Colpi blocks.shots = Colpi
blocks.reload = Ricarica blocks.reload = Ricarica
blocks.ammo = Munizioni blocks.ammo = Munizioni
bar.drilltierreq = Migliore trapano richiesto bar.drilltierreq = Miglior trivella richiesta
bar.drillspeed = Velocità scavo: {0}/s bar.drillspeed = Velocità scavo: {0}/s
bar.efficiency = Efficienza: {0}% bar.efficiency = Efficienza: {0}%
bar.powerbalance = Energia: {0} bar.powerbalance = Energia: {0}
@@ -443,7 +447,7 @@ bullet.damage = [stat]{0}[lightgray] danno
bullet.splashdamage = [stat]{0}[lightgray] danno ad area ~[stat] {1}[lightgray] blocchi bullet.splashdamage = [stat]{0}[lightgray] danno ad area ~[stat] {1}[lightgray] blocchi
bullet.incendiary = [stat]incendiario bullet.incendiary = [stat]incendiario
bullet.homing = [stat]autoguidato bullet.homing = [stat]autoguidato
bullet.shock = [stat]shock bullet.shock = [stat]stordente
bullet.frag = [stat]frammentazione bullet.frag = [stat]frammentazione
bullet.knockback = [stat]{0}[lightgray] contraccolpo bullet.knockback = [stat]{0}[lightgray] contraccolpo
bullet.freezing = [stat]congelamento bullet.freezing = [stat]congelamento
@@ -510,7 +514,7 @@ setting.crashreport.name = Invia rapporti sugli arresti anomali anonimamente
setting.chatopacity.name = Opacità chat setting.chatopacity.name = Opacità chat
setting.playerchat.name = Mostra Chat in-game setting.playerchat.name = Mostra Chat in-game
uiscale.reset = La scala dell'interfaccia utente è stata modificata.\nPremere "OK" per confermare questa scala.\n[scarlet] Ripristina ed esci dalle impostazioni [accent] {0}[] impostazioni... uiscale.reset = La scala dell'interfaccia utente è stata modificata.\nPremere "OK" per confermare questa scala.\n[scarlet] Ripristina ed esci dalle impostazioni [accent] {0}[] impostazioni...
uiscale.cancel = Annulla e esci uiscale.cancel = Annulla ed esci
setting.bloom.name = Shaders setting.bloom.name = Shaders
keybind.title = Configurazione Tasti keybind.title = Configurazione Tasti
keybinds.mobile = [scarlet]La maggior parte dei keybind qui non sono funzionali sui dispositivi mobili. È supportato solo il movimento di base. keybinds.mobile = [scarlet]La maggior parte dei keybind qui non sono funzionali sui dispositivi mobili. È supportato solo il movimento di base.
@@ -518,7 +522,7 @@ category.general.name = Generale
category.view.name = Visualizzazione category.view.name = Visualizzazione
category.multiplayer.name = Multigiocatore category.multiplayer.name = Multigiocatore
command.attack = Attacca command.attack = Attacca
command.retreat = Ritorna indietro command.retreat = Torna indietro
command.patrol = Guardia command.patrol = Guardia
keybind.gridMode.name = Seleziona blocco keybind.gridMode.name = Seleziona blocco
keybind.gridModeShift.name = Seleziona categoria keybind.gridModeShift.name = Seleziona categoria
@@ -533,8 +537,8 @@ keybind.pick.name = Scegli Blocco
keybind.break_block.name = Rompi blocco keybind.break_block.name = Rompi blocco
keybind.deselect.name = Deseleziona keybind.deselect.name = Deseleziona
keybind.shoot.name = spara keybind.shoot.name = spara
keybind.zoom_hold.name = zoomma keybind.zoom_hold.name = attiva zoom
keybind.zoom.name = zoom keybind.zoom.name = esegui zoom
keybind.menu.name = menu keybind.menu.name = menu
keybind.pause.name = pausa keybind.pause.name = pausa
keybind.minimap.name = Minimappa keybind.minimap.name = Minimappa
@@ -547,18 +551,18 @@ keybind.toggle_menus.name = Abilita menù
keybind.chat_history_prev.name = Scorri chat vero l'alto keybind.chat_history_prev.name = Scorri chat vero l'alto
keybind.chat_history_next.name = Scorri chatt verso il basso keybind.chat_history_next.name = Scorri chatt verso il basso
keybind.chat_scroll.name = Scorri chat keybind.chat_scroll.name = Scorri chat
keybind.drop_unit.name = droppa materiali keybind.drop_unit.name = Lascia materiali
keybind.zoom_minimap.name = Zomma minimappa keybind.zoom_minimap.name = Esegui Zoom minimappa
mode.help.title = Descrizione delle modalità mode.help.title = Descrizione delle modalità
mode.survival.name = Sopravvivenza mode.survival.name = Sopravvivenza
mode.survival.description = La modalità normale. Risorse limitate e ondate in entrata automatiche. mode.survival.description = La modalità normale. Risorse limitate ed ondate in entrata automatiche.
mode.sandbox.name = Sandbox mode.sandbox.name = Creativa
mode.sandbox.description = risorse infinite e nessun timer per le ondate. mode.sandbox.description = Risorse infinite e nessun timer per le ondate.
mode.pvp.name = PvP mode.pvp.name = PvP
mode.pvp.description = Lotta contro altri giocatori mode.pvp.description = Lotta contro altri giocatori.
mode.attack.name = Attacco mode.attack.name = Attacco
mode.attack.description = Obiettivo: Distruggere la base nemica, non ci sono ondate mode.attack.description = Obiettivo: Distruggere la base nemica, non ci sono ondate
mode.custom = Regole customizzabili mode.custom = Regole personalizzate
rules.infiniteresources = Risorse infinite rules.infiniteresources = Risorse infinite
rules.wavetimer = Timer ondate rules.wavetimer = Timer ondate
rules.waves = Ondate rules.waves = Ondate
@@ -600,14 +604,14 @@ item.silicon.name = Silicio
item.plastanium.name = Plastanio item.plastanium.name = Plastanio
item.phase-fabric.name = Tessuto di Fase item.phase-fabric.name = Tessuto di Fase
item.surge-alloy.name = Lega di Sovratensione item.surge-alloy.name = Lega di Sovratensione
item.spore-pod.name = Piattaforma di Spore item.spore-pod.name = Baccello di Spore
item.sand.name = Sabbia item.sand.name = Sabbia
item.blast-compound.name = Polvere esplosiva item.blast-compound.name = Composto Esplosivo
item.pyratite.name = Pirite item.pyratite.name = Pirite
item.metaglass.name = Vetro Metallico item.metaglass.name = Vetro Metallico
item.scrap.name = Rottame item.scrap.name = Rottame
liquid.water.name = Acqua liquid.water.name = Acqua
liquid.slag.name = Scorie liquid.slag.name = Scoria
liquid.oil.name = Petrolio liquid.oil.name = Petrolio
liquid.cryofluid.name = Criofluido liquid.cryofluid.name = Criofluido
mech.alpha-mech.name = Alpha mech.alpha-mech.name = Alpha
@@ -618,11 +622,11 @@ mech.delta-mech.weapon = Generatore di fulmini
mech.delta-mech.ability = Scarica mech.delta-mech.ability = Scarica
mech.tau-mech.name = Tau mech.tau-mech.name = Tau
mech.tau-mech.weapon = Laser ricostruttore mech.tau-mech.weapon = Laser ricostruttore
mech.tau-mech.ability = Ripara esplosioni mech.tau-mech.ability = Impulso riparatore
mech.omega-mech.name = Omega mech.omega-mech.name = Omega
mech.omega-mech.weapon = Sciame di missili mech.omega-mech.weapon = Sciame di missili
mech.omega-mech.ability = Configurazione armata mech.omega-mech.ability = Configurazione armata
mech.dart-ship.name = Dart mech.dart-ship.name = Dardo
mech.dart-ship.weapon = Ripetitore mech.dart-ship.weapon = Ripetitore
mech.javelin-ship.name = Giavellotto mech.javelin-ship.name = Giavellotto
mech.javelin-ship.weapon = Missili esplosivi mech.javelin-ship.weapon = Missili esplosivi
@@ -634,10 +638,10 @@ mech.glaive-ship.weapon = Ripetitore di fiamma
item.explosiveness = [LIGHT_GRAY]Esplosività: {0} item.explosiveness = [LIGHT_GRAY]Esplosività: {0}
item.flammability = [LIGHT_GRAY]Infiammabilità: {0} item.flammability = [LIGHT_GRAY]Infiammabilità: {0}
item.radioactivity = [LIGHT_GRAY]Radioattività: {0} item.radioactivity = [LIGHT_GRAY]Radioattività: {0}
unit.health = [LIGHT_GRAY]Vita: {0} unit.health = [LIGHT_GRAY]Salute: {0}
unit.speed = [LIGHT_GRAY]Velocità: {0} unit.speed = [LIGHT_GRAY]Velocità: {0}
mech.weapon = [LIGHT_GRAY]Armi: {0} mech.weapon = [LIGHT_GRAY]Armi: {0}
mech.health = [LIGHT_GRAY]Vita: {0} mech.health = [LIGHT_GRAY]Salute: {0}
mech.itemcapacity = [LIGHT_GRAY]Capacità oggetti: {0} mech.itemcapacity = [LIGHT_GRAY]Capacità oggetti: {0}
mech.minespeed = [LIGHT_GRAY]Velocità di scavo: {0} mech.minespeed = [LIGHT_GRAY]Velocità di scavo: {0}
mech.minepower = [LIGHT_GRAY]Potenza di scavo: {0} mech.minepower = [LIGHT_GRAY]Potenza di scavo: {0}
@@ -662,18 +666,18 @@ block.shale.name = Scisto
block.shale-boulder.name = Masso di scisto block.shale-boulder.name = Masso di scisto
block.moss.name = Muschio block.moss.name = Muschio
block.shrubs.name = Arbusti block.shrubs.name = Arbusti
block.spore-moss.name = Spore di Muschio block.spore-moss.name = Muschio di spore
block.shalerocks.name = Roccie di scisto block.shalerocks.name = Rocce di scisto
block.scrap-wall.name = Muro di Rottami block.scrap-wall.name = Muro di Rottami
block.scrap-wall-large.name = Muro di rottami grande block.scrap-wall-large.name = Muro di Rottami grande
block.scrap-wall-huge.name = Muro di rottami enorme block.scrap-wall-huge.name = Muro di Rottami enorme
block.scrap-wall-gigantic.name = Muro di Rottami Gigante block.scrap-wall-gigantic.name = Muro di Rottami gigante
block.thruster.name = Propulsore block.thruster.name = Propulsore
block.kiln.name = Forno block.kiln.name = Forno
block.graphite-press.name = Pressa per grafite block.graphite-press.name = Pressa per grafite
block.multi-press.name = Multi Pressa block.multi-press.name = Multi Pressa
block.constructing = {0}\n[LIGHT_GRAY](In costruzione) block.constructing = {0}\n[LIGHT_GRAY](In costruzione)
block.spawn.name = Spawning nemico block.spawn.name = Spawn nemico
block.core-shard.name = Nucleo: Frammento block.core-shard.name = Nucleo: Frammento
block.core-foundation.name = Nucleo: Fondamento block.core-foundation.name = Nucleo: Fondamento
block.core-nucleus.name = Nucleo: Kernel block.core-nucleus.name = Nucleo: Kernel
@@ -688,12 +692,12 @@ block.darksand.name = Sabbia Scura
block.ice.name = Ghiaccio block.ice.name = Ghiaccio
block.snow.name = Neve block.snow.name = Neve
block.craters.name = Crateri block.craters.name = Crateri
block.sand-water.name = Acqua Sabbiosa block.sand-water.name = Acqua sabbiosa
block.darksand-water.name = Acqua sabbiosa scura block.darksand-water.name = Acqua sabbiosa scura
block.char.name = Carbone block.char.name = Carbone
block.holostone.name = Pietra di holo block.holostone.name = Pietra Holo
block.ice-snow.name = Neve ghiacciata block.ice-snow.name = Neve ghiacciata
block.rocks.name = Roccie block.rocks.name = Rocce
block.icerocks.name = Rocce ghiacciate block.icerocks.name = Rocce ghiacciate
block.snowrocks.name = Rocce innevate block.snowrocks.name = Rocce innevate
block.dunerocks.name = Rocce delle dune block.dunerocks.name = Rocce delle dune
@@ -725,92 +729,92 @@ block.phase-wall.name = Muro di fase
block.phase-wall-large.name = Muro grande di fase block.phase-wall-large.name = Muro grande di fase
block.thorium-wall.name = Muro di torio block.thorium-wall.name = Muro di torio
block.thorium-wall-large.name = Muro grande di torio block.thorium-wall-large.name = Muro grande di torio
block.door.name = porta block.door.name = Porta
block.door-large.name = Porta grande block.door-large.name = Porta grande
block.duo.name = Torretta a due block.duo.name = Torretta Duo
block.scorch.name = Bruciatore block.scorch.name = Bruciatore
block.scatter.name = Spargimento block.scatter.name = Cannone a dispersione
block.hail.name = Bombardiere block.hail.name = Bombardiere
block.lancer.name = Idrogetto block.lancer.name = Lanciere
block.conveyor.name = trasportatore block.conveyor.name = Nastro trasportatore
block.titanium-conveyor.name = Nastro trasportatore potenziato block.titanium-conveyor.name = Nastro trasportatore avanzato
block.junction.name = Incrocio block.junction.name = Incrocio
block.router.name = Distributore block.router.name = Distributore
block.distributor.name = Mega Separatore block.distributor.name = Distributore Grande
block.sorter.name = Filtro block.sorter.name = Filtro
block.overflow-gate.name = Separatore per eccesso block.overflow-gate.name = Separatore per eccesso
block.silicon-smelter.name = Fonderia per silicio block.silicon-smelter.name = Fonderia
block.phase-weaver.name = Tessitore di fase block.phase-weaver.name = Tessitore di fase
block.pulverizer.name = Polverizzatore block.pulverizer.name = Polverizzatore
block.cryofluidmixer.name = Miscelatore liquidi block.cryofluidmixer.name = Miscelatore di liquidi
block.melter.name = Fonditore block.melter.name = Fonditore
block.incinerator.name = Inceneritore block.incinerator.name = Inceneritore
block.spore-press.name = Pressa di Spore block.spore-press.name = Pressa di Spore
block.separator.name = Separatore block.separator.name = Separatore
block.coal-centrifuge.name = Centrifuga di Carbone block.coal-centrifuge.name = Centrifuga di Carbone
block.power-node.name = Snodo energetico block.power-node.name = Nodo energetico
block.power-node-large.name = Snodo energetico grande block.power-node-large.name = Nodo energetico grande
block.surge-tower.name = Torre di Sovratensione block.surge-tower.name = Torre di Sovratensione
block.battery.name = Batteria block.battery.name = Batteria
block.battery-large.name = Batteria grossa block.battery-large.name = Batteria grande
block.combustion-generator.name = Generatore a carbone block.combustion-generator.name = Generatore a combustibile
block.turbine-generator.name = Turbina block.turbine-generator.name = Turbina a vapore
block.differential-generator.name = Generatore differenziale block.differential-generator.name = Generatore differenziale
block.impact-reactor.name = Reattore ad Impatto block.impact-reactor.name = Reattore ad Impatto
block.mechanical-drill.name = Trapano meccanico block.mechanical-drill.name = Trivella meccanica
block.pneumatic-drill.name = Trapano pneumatico block.pneumatic-drill.name = Trivella pneumatica
block.laser-drill.name = Estrattore laser block.laser-drill.name = Trivella laser
block.water-extractor.name = Estrattore d'acqua block.water-extractor.name = Estrattore d'acqua
block.cultivator.name = Coltivatore block.cultivator.name = Coltivatore
block.dart-mech-pad.name = Blocco del Mech Dardo block.dart-mech-pad.name = Piattaforma del Mech Dardo
block.delta-mech-pad.name = Blocco del Mech Delta block.delta-mech-pad.name = Piattaforma del Mech Delta
block.javelin-ship-pad.name = Blocco della Nave Giavellotto block.javelin-ship-pad.name = Piattaforma della Nave Giavellotto
block.trident-ship-pad.name = Blocco della Nave Tridente block.trident-ship-pad.name = Piattaforma della Nave Tridente
block.glaive-ship-pad.name = Blocco della Nave Glaive block.glaive-ship-pad.name = Piattaforma della Nave Glaive
block.omega-mech-pad.name = Blocco della Nave Omega block.omega-mech-pad.name = Piattaforma della Nave Omega
block.tau-mech-pad.name = Blocco della Nave Tau block.tau-mech-pad.name = Piattaforma della Nave Tau
block.conduit.name = Condotto block.conduit.name = Condotta
block.mechanical-pump.name = Pompa meccanica block.mechanical-pump.name = Pompa meccanica
block.item-source.name = Sorgente oggetti block.item-source.name = Fonte infinita (oggetti)
block.item-void.name = Vuoto oggetti block.item-void.name = Cestino (oggetti)
block.liquid-source.name = Sorgente liquida block.liquid-source.name = Fonte infinita (liquidi)
block.power-void.name = Nullità Energetica block.power-void.name = Cestino (energia)
block.power-source.name = Energia infinita block.power-source.name = Fonte infinita (energia)
block.unloader.name = Scaricatore block.unloader.name = Scaricatore
block.vault.name = Deposito block.vault.name = Deposito
block.wave.name = Idrogetto block.wave.name = Idrogetto
block.swarmer.name = Sciamatore block.swarmer.name = Sciamatore
block.salvo.name = Cannoncino block.salvo.name = Cannone Leggero
block.ripple.name = Cannone block.ripple.name = Cannone Pesante
block.phase-conveyor.name = Nastro trasportatore ad alta velocità block.phase-conveyor.name = Nastro di fase
block.bridge-conveyor.name = Nastro trasportatore sopraelevato block.bridge-conveyor.name = Nastro trasportatore sopraelevato
block.plastanium-compressor.name = Compressore al plastanio block.plastanium-compressor.name = Compressore al plastanio
block.pyratite-mixer.name = Miscelatore di pirite block.pyratite-mixer.name = Miscelatore di pirite
block.blast-mixer.name = Miscelatore poleri block.blast-mixer.name = Miscelatore di esplosivi
block.solar-panel.name = Pannello solare block.solar-panel.name = Pannello solare
block.solar-panel-large.name = Pannrllo solare 3x3 block.solar-panel-large.name = Pannello solare 3x3
block.oil-extractor.name = Estrattore petrolio block.oil-extractor.name = Estrattore di petrolio
block.draug-factory.name = Fabbrica Droni Minatori block.draug-factory.name = Fabbrica Droni Minatori
block.spirit-factory.name = Fabbrica Droni Riparatori block.spirit-factory.name = Fabbrica Droni Riparatori
block.phantom-factory.name = Fabbrica Droni Fantasma block.phantom-factory.name = Fabbrica Droni Fantasma
block.wraith-factory.name = Fabbrica Combattenti Spettro block.wraith-factory.name = Fabbrica Combattenti Spettro
block.ghoul-factory.name = Fabbrica Bombardieri Demoniaci block.ghoul-factory.name = Fabbrica Bombardieri Demoniaci
block.dagger-factory.name = Fabbrica Mech col Pugnale block.dagger-factory.name = Fabbrica Droni Pugnalatori
block.crawler-factory.name = Fabbrica Mech Strisciatore block.crawler-factory.name = Fabbrica Mech Strisciatore
block.titan-factory.name = Fabbrica Mech Titano block.titan-factory.name = Fabbrica Mech Titano
block.fortress-factory.name = Fabbrica Mech Fortezza block.fortress-factory.name = Fabbrica Mech Fortezza
block.revenant-factory.name = Fabbrica Combattenti Superstiti block.revenant-factory.name = Fabbrica Combattenti Superstiti
block.repair-point.name = Punto di riparazione block.repair-point.name = Punto di riparazione
block.pulse-conduit.name = Condotta attiva block.pulse-conduit.name = Condotta attiva
block.phase-conduit.name = Condotto ad alta velocità block.phase-conduit.name = Condotta di fase
block.liquid-router.name = Distributore di liquidi block.liquid-router.name = Distributore di liquidi
block.liquid-tank.name = Tanica d'acqua block.liquid-tank.name = Serbatoio
block.liquid-junction.name = Giunzione liquida block.liquid-junction.name = Giunzione liquida
block.bridge-conduit.name = Condotta sopraelevata block.bridge-conduit.name = Condotta sopraelevata
block.rotary-pump.name = Pompa a turbina block.rotary-pump.name = Pompa a turbina
block.thorium-reactor.name = Reattore al torio block.thorium-reactor.name = Reattore al torio
block.mass-driver.name = Lancia Materiali block.mass-driver.name = Lancia Materiali
block.blast-drill.name = Trapano Esplosivo block.blast-drill.name = Trivella ad impulsi
block.thermal-pump.name = Pompa termica block.thermal-pump.name = Pompa termica
block.thermal-generator.name = Generatore termico block.thermal-generator.name = Generatore termico
block.alloy-smelter.name = Altoforno block.alloy-smelter.name = Altoforno
@@ -819,17 +823,18 @@ block.mend-projector.name = Riparatore Grande
block.surge-wall.name = Muro di Sovratensione block.surge-wall.name = Muro di Sovratensione
block.surge-wall-large.name = Muro di Sovratensione Grande block.surge-wall-large.name = Muro di Sovratensione Grande
block.cyclone.name = Ciclone block.cyclone.name = Ciclone
block.fuse.name = Fusibile block.fuse.name = Frantume
block.shock-mine.name = Mina Scioccante block.shock-mine.name = Mina Stordente
block.overdrive-projector.name = Proiettore ad Attività Frenetica block.overdrive-projector.name = Generatore di Campo di Overclock
block.force-projector.name = Proiettore della Forza block.force-projector.name = Generatore di Campo di Forza
block.arc.name = Arco block.arc.name = Arco Elettrico
block.rtg-generator.name = Generatore Termico ai Radioisotopi block.rtg-generator.name = Generatore Termico ai Radioisotopi
block.spectre.name = Spettro block.spectre.name = Spettro
block.meltdown.name = Fusione block.meltdown.name = Fusione
block.container.name = Contenitore block.container.name = Contenitore
block.launch-pad.name = Trampolino di Lancio block.launch-pad.name = Ascensore Spaziale
block.launch-pad-large.name = Trampolino di Lancio Grande block.launch-pad-large.name = Ascensore Spaziale Avanzato
block.command-center.name = Centro di Comando
team.blue.name = blu team.blue.name = blu
team.crux.name = rosso team.crux.name = rosso
team.sharded.name = arancione team.sharded.name = arancione
@@ -847,22 +852,22 @@ unit.ghoul.name = Bombardiere Demoniaco
unit.wraith.name = Combattente Spettro unit.wraith.name = Combattente Spettro
unit.fortress.name = Fortezza unit.fortress.name = Fortezza
unit.revenant.name = Superstite unit.revenant.name = Superstite
unit.eruptor.name = Eruttore unit.eruptor.name = Incandescente
unit.chaos-array.name = Schieramento di Chaos unit.chaos-array.name = Matrice del Caos
unit.eradicator.name = Eradicatore unit.eradicator.name = Estirpatore
unit.lich.name = Lich unit.lich.name = Lich
unit.reaper.name = Mietitore unit.reaper.name = Mietitore
tutorial.next = [lightgray]<Clicca per continuare> tutorial.next = [lightgray]<Clicca per continuare>
tutorial.intro = Sei entrato nel[scarlet] Tutorial di Mindustry.[]\nInizia [accent] scavando rame[]. Clicca un minerale di rame vicino al tuo nucleo per farlo.\n\n[accent]{0}/{1} rame tutorial.intro = Sei entrato nel[scarlet] Tutorial di Mindustry.[]\nInizia [accent] scavando rame[]. Clicca un minerale di rame vicino al tuo nucleo per farlo.\n\n[accent]{0}/{1} rame
tutorial.drill = Minare manualmente.\n[accent]Trapani []possono scavare automaticamente\nPiazzane uno su un minerale di rame tutorial.drill = Minare manualmente.\n[accent]Le trivelle []possono scavare automaticamente\nPiazzane una su un minerale di rame.
tutorial.drill.mobile = L'estrazione manuale è inefficiente. \n[accent] I trapani [] possono estrarre automaticamente. \n Toccare la scheda del trapano in basso a destra. \n Selezionare il trapano meccanico [accent] []. \n Posizionarlo su una vena di rame toccando, quindi premere il segno di spunta [accent] [] in basso per confermare la selezione. \n Premere il tasto X [accent] [] per annullare il posizionamento. tutorial.drill.mobile = L'estrazione manuale è inefficiente. \n[accent] Le trivelle [] possono estrarre automaticamente. \n Toccare la scheda della trivella in basso a destra. \n Selezionare la trivella meccanica [accent] []. \n Posizionarlo su una vena di rame toccando, quindi premere il segno di spunta [accent] [] in basso per confermare la selezione. \n Premere il tasto X [accent] [] per annullare il posizionamento.
tutorial.blockinfo = Ogni blocco ha statistiche diverse. Ogni trapano può estrarre solo determinati minerali. \n Per controllare le informazioni e le statistiche di un blocco, [accent] tocca "?" mentre lo selezioni nel menu di creazione. []\n\n[accent] Accedi ora alle statistiche del trapano meccanico. [] tutorial.blockinfo = Ogni blocco ha statistiche diverse. Ogni trivella può estrarre solo determinati minerali. \n Per controllare le informazioni e le statistiche di un blocco, [accent] tocca "?" mentre lo selezioni nel menu di creazione. []\n\n[accent] Accedi ora alle statistiche della trivella meccanica. []
tutorial.conveyor = [accent] I nastri trasportatori [] sono usati per trasportare oggetti al nocciolo. \n Crea una linea di nastri dal trapano al nocciolo. tutorial.conveyor = [accent] I nastri trasportatori [] sono usati per trasportare oggetti al nocciolo. \n Crea una linea di nastri dalla trivella al nocciolo.
tutorial.conveyor.mobile = [accent] I nastri trasportatori [] sono usati per trasportare oggetti nel nocciolo. \nFai una linea di nastri trasportatori dal trapano al nocciolo. \n[accent] Posizionati in una linea tenendo premuto il dito per alcuni secondi [] e trascinando in una direzione. \n\n [accent] {0} / {1} nastri trasportatori disposti in linea \n [accent] 0/1 oggetti consegnati tutorial.conveyor.mobile = [accent] I nastri trasportatori [] sono usati per trasportare oggetti nel nocciolo. \nCrea una linea di nastri trasportatori dalla trivella al nocciolo. \n[accent] Posizionati in una linea tenendo premuto il dito per alcuni secondi [] e trascinando in una direzione. \n\n [accent] {0} / {1} nastri trasportatori disposti in linea \n [accent] 0/1 oggetti consegnati
tutorial.turret = Strutture difensive devono essere costruite per respingere il nemico [LIGHT_GRAY] []. \nCostruisci una torretta a due vicino alla tua base. tutorial.turret = Strutture difensive devono essere costruite per respingere il nemico [LIGHT_GRAY] []. \nCostruisci una torretta a due vicino alla tua base.
tutorial.drillturret = Torrette a due richiedono[accent] munizioni di rame[] per sparare.\n Duo turrets require[accent] copper ammo []to shoot.\nPosiziona un trapano vicino alla torretta per rifornirlo di rame estratto. tutorial.drillturret = Torrette a due richiedono[accent] munizioni di rame[] per sparare.\n Duo turrets require[accent] copper ammo []to shoot.\nPosiziona una trivella vicino alla torretta per rifornirlo di rame estratto.
tutorial.pause = Durante la battaglia, puoi mettere in pausa il gioco [accent]. []\nPuoi mettere in fila gli edifici mentre sei in pausa. \n\n[accent] Premi spazio per mettere in pausa. tutorial.pause = Durante la battaglia, puoi mettere in pausa il gioco [accent]. []\nPuoi disporre gli edifici mentre sei in pausa. \n\n[accent] Premi spazio per mettere in pausa.
tutorial.pause.mobile = Durante la battaglia, puoi mettere in pausa il gioco [accent]. []\nPuoi mettere in fila gli edifici mentre sei in pausa. \n\n[accent] Premi questo pulsante in alto a sinistra per mettere in pausa. tutorial.pause.mobile = Durante la battaglia, puoi mettere in pausa il gioco [accent]. []\nPuoi disporre gli edifici mentre sei in pausa. \n\n[accent] Premi questo pulsante in alto a sinistra per mettere in pausa.
tutorial.unpause = Ora premi di nuovo spazio per annullare la pausa. tutorial.unpause = Ora premi di nuovo spazio per annullare la pausa.
tutorial.unpause.mobile = Ora premilo di nuovo per annullare la pausa. tutorial.unpause.mobile = Ora premilo di nuovo per annullare la pausa.
tutorial.breaking = I blocchi spesso devono essere distrutti. \n [accent] Tieni premuto il tasto destro del mouse [] per distruggere tutti i blocchi in una selezione. []\n\n[accent] Distruggi tutti i blocchi di scarto a sinistra del tuo core usando la selezione dell'area . tutorial.breaking = I blocchi spesso devono essere distrutti. \n [accent] Tieni premuto il tasto destro del mouse [] per distruggere tutti i blocchi in una selezione. []\n\n[accent] Distruggi tutti i blocchi di scarto a sinistra del tuo core usando la selezione dell'area .
@@ -870,33 +875,33 @@ tutorial.breaking.mobile = I blocchi spesso devono essere distrutti. \n [accent]
tutorial.withdraw = In alcune situazioni, è necessario prendere gli oggetti direttamente dai blocchi. \n Per fare ciò, [accent] tocca un blocco [] con oggetti al suo interno, quindi [accent] tocca l'oggetto [] nell'inventario. \nPosti multipli possono essere ritirati da [accent] toccando e tenendo premuto []. \n\n[accent] Prelevare un po' di rame dal nucleo. [] tutorial.withdraw = In alcune situazioni, è necessario prendere gli oggetti direttamente dai blocchi. \n Per fare ciò, [accent] tocca un blocco [] con oggetti al suo interno, quindi [accent] tocca l'oggetto [] nell'inventario. \nPosti multipli possono essere ritirati da [accent] toccando e tenendo premuto []. \n\n[accent] Prelevare un po' di rame dal nucleo. []
tutorial.deposit = Deposita gli oggetti in blocchi trascinandoli dalla tua nave al blocco di destinazione. \n\n[accent] Riporta il rame nel nucleo. [] tutorial.deposit = Deposita gli oggetti in blocchi trascinandoli dalla tua nave al blocco di destinazione. \n\n[accent] Riporta il rame nel nucleo. []
tutorial.waves = Il nemico [LIGHT_GRAY] si avvicina. \n\n Difendi il tuo nucleo per 2 ondate. Costruisci più torrette. tutorial.waves = Il nemico [LIGHT_GRAY] si avvicina. \n\n Difendi il tuo nucleo per 2 ondate. Costruisci più torrette.
tutorial.waves.mobile = Il [lightgray] nemico si avvicina.\n\n Difendi il nucleo per due ondate. La tua nave sparerà automaticamente contro i nemici.\nCostruisci più torrette e trapani. Scava più rame tutorial.waves.mobile = Il [lightgray] nemico si avvicina.\n\n Difendi il nucleo per due ondate. La tua nave sparerà automaticamente contro i nemici.\nCostruisci più torrette e trivelle. Scava più rame
tutorial.launch = Una volta raggiunta un'onda specifica, sei in grado di [accent] decollare con il nucleo [], lasciando indietro le tue difese e [accent] ottenendo tutte le risorse nel tuo nucleo. [] \n Queste risorse possono quindi essere utilizzate per ricercare nuove tecnologie.\n\n [accent] Premi il pulsante di avvio. tutorial.launch = Una volta raggiunta un'onda specifica, sei in grado di [accent] decollare con il nucleo [], lasciando indietro le tue difese ed [accent] ottenendo tutte le risorse nel tuo nucleo. [] \n Queste risorse possono quindi essere utilizzate per ricercare nuove tecnologie.\n\n [accent] Premi il pulsante di avvio.
item.copper.description = Un utile materiale, usato dappertutto item.copper.description = Un utile materiale, usato dappertutto
item.lead.description = Un materiale di base, molto usato nei blocchi di trasporto. item.lead.description = Un materiale di base, molto usato nei blocchi di trasporto.
item.metaglass.description = Un durissimo composto di vetro. Estensivamente usato per trasporto di liquidi e immagazzinamento. item.metaglass.description = Un durissimo composto di vetro. Estensivamente usato per trasporto di liquidi ed immagazzinamento.
item.graphite.description = Carbone mineralizzato, utilizzato per munizioni e insulazione elettrica. item.graphite.description = Carbone mineralizzato, utilizzato per munizioni ed isolamento elettrico.
item.sand.description = Un materiale di base che viene usato molto nei processi di fusione, sia come lega che come lubrificante. item.sand.description = Un materiale di base che viene usato molto nei processi di fusione, sia come lega che come reagente.
item.coal.description = Un carburante comune e facilmente ottenibile. item.coal.description = Un combustibile comune facilmente ottenibile.
item.titanium.description = Un raro metallo super leggero usato ampiamente nel trasporto di liquidi, trapani e navi. item.titanium.description = Un raro metallo incredibilmente leggero usato ampiamente nella costruzione di trasporti, trivelle e navi.
item.thorium.description = Un materiale denso e radioattivo, utilizzato nella costruzione di strutture e come carburante del reattore nucleare. item.thorium.description = Un materiale denso e radioattivo, utilizzato nella costruzione di strutture e come carburante del reattore nucleare.
item.scrap.description = Resti rimanenti di vecchie strutture e unità. Contiene tracce di molti metalli diversi. item.scrap.description = Resti rimanenti di vecchie strutture ed unità. Contiene tracce di molti metalli diversi.
item.silicon.description = Un semiconduttore molto utile che viene utilizzato nei pannelli solari e nei macchinari elettronici. item.silicon.description = Un semiconduttore molto utile che viene utilizzato nei pannelli solari e nei macchinari elettronici.
item.plastanium.description = Un materiale leggero e duttile, utilizzato nelle navi avanzate e come munizione. item.plastanium.description = Un materiale leggero e duttile, utilizzato nelle navi avanzate e come munizione.
item.phase-fabric.description = Una sostanza quasi senza peso utilizzata nell'elettronica avanzata e nella tecnologia autoriparante. item.phase-fabric.description = Una sostanza quasi senza peso utilizzata nell'elettronica avanzata e nella tecnologia autoriparante.
item.surge-alloy.description = Una lega avanzata con proprietà elettriche uniche. item.surge-alloy.description = Una lega avanzata con proprietà elettriche uniche.
item.spore-pod.description = Utilizzato per la conversione in petrolio, esplosivi e carburante. item.spore-pod.description = Utilizzato per la conversione in petrolio, esplosivi e carburante.
item.blast-compound.description = Un composto altamente volatile, utilizzato nella produzione di bombe ed esplosivi. Può essere utilizzato come combustibile anche se non è consigliato. item.blast-compound.description = Un composto altamente volatile, utilizzato nella produzione di bombe ed esplosivi. Può essere utilizzato come combustibile anche se non è consigliabile.
item.pyratite.description = Una sostanza molto infiammabile che viene utilizzata nelle armi a fuoco. item.pyratite.description = Una sostanza molto infiammabile che viene utilizzata nelle armi da fuoco.
liquid.water.description = comunemente usato per macchine di raffreddamento e trattamento dei rifiuti. liquid.water.description = Il liquido più utile. Comunemente usato per il raffreddamento di macchinari ed il trattamento dei rifiuti.
liquid.slag.description = Vari tipi diversi di metallo fuso mescolati insieme. Può essere separato nei suoi minerali costituenti o spruzzato sulle unità nemiche come un'arma. liquid.slag.description = Diversi tipi di metalli fusi, mescolati insieme. Può essere separato nei suoi minerali costituenti o spruzzato sulle unità nemiche come un'arma.
liquid.oil.description = Può essere bruciato, esploso o usato come refrigerante. liquid.oil.description = Un liquido usato nella produzione avanzata.\nPuò essere convertito in carbone per uso combustibile o spruzzato ed incendiato come arma.
liquid.cryofluid.description = Il liquido più efficiente per il raffreddamento. liquid.cryofluid.description = Un liquido inerte e non corrosivo creato da acqua e titanio.\nIl liquido più efficiente per il raffreddamento.
mech.alpha-mech.description = Il mech standard. È abbastanza veloce e produce abbastanza danni, può anche generare 3 droni per aumentare il suo danno complessivo. mech.alpha-mech.description = Il mech standard. È abbastanza veloce e produce abbastanza danni, può anche generare 3 droni per aumentare il suo danno complessivo.
mech.delta-mech.description = Un mech veloce, poco armato fatto per giocare a tocca e fuga con il nemico. Fa poco danno alle strutture, ma può uccidere un gran nummero di nemici grazie alle sue armi ad alto voltaggio. mech.delta-mech.description = Un mech veloce, poco armato fatto per giocare a tocca e fuga con il nemico. Fa poco danno alle strutture, ma può uccidere un gran nummero di nemici grazie alle sue armi ad alto voltaggio.
mech.tau-mech.description = Un mech di supporto. Cura i blocchi danneggiati sparandogli contro. Può spegnere fuochi e curare i compagni di squadra. mech.tau-mech.description = Un mech di supporto. Cura i blocchi danneggiati sparandogli contro. Può spegnere fuochi e curare i compagni di squadra.
mech.omega-mech.description = Un mech ingombrante e ben armato, fatto per stare in prima linea. La sue difese possono bloccare fino al 90% dei danni. mech.omega-mech.description = Un mech ingombrante e ben armato, fatto per stare in prima linea. La sue difese possono bloccare fino al 90% dei danni.
mech.dart-ship.description = Una navicella standard. Molto veloce e leggera, ma può minare pochi blocchi e ha scarse potenzialità nella difesa. mech.dart-ship.description = Una navicella standard. Molto veloce e leggera, ma può minare pochi blocchi ed ha scarse potenzialità nella difesa.
mech.javelin-ship.description = Una navetta da tocca e fuga. Anche se inizialmente lenta, può accelerare ad alte velocità e volare sopra gli avamposti dei nemici, e provocare molti danni ai nemici tramite l'utilizzo di fulmini o missili. mech.javelin-ship.description = Una navetta da tocca e fuga. Anche se inizialmente lenta, può accelerare ad alte velocità e volare sopra gli avamposti dei nemici, e provocare molti danni ai nemici tramite l'utilizzo di fulmini o missili.
mech.trident-ship.description = Un bombardiere pesante. Molto ben protetto. mech.trident-ship.description = Un bombardiere pesante. Molto ben protetto.
mech.glaive-ship.description = Una grande e ben armata macchina da guerra. Equipaggiata con lanciafamme e con accelerazione veloce. mech.glaive-ship.description = Una grande e ben armata macchina da guerra. Equipaggiata con lanciafamme e con accelerazione veloce.
@@ -904,129 +909,134 @@ unit.draug.description = Un drone minerario primitivo. Economico da produrre. Sa
unit.spirit.description = L'unità drone di partenza. Si genera nel nucleo per impostazione predefinita. Scava automaticamente, raccoglie oggetti e ripara blocchi. unit.spirit.description = L'unità drone di partenza. Si genera nel nucleo per impostazione predefinita. Scava automaticamente, raccoglie oggetti e ripara blocchi.
unit.phantom.description = Un'unità drone avanzata. Scava automaticamente, raccoglie oggetti e ripara blocchi. Significativamente più efficace del drone di partenza. unit.phantom.description = Un'unità drone avanzata. Scava automaticamente, raccoglie oggetti e ripara blocchi. Significativamente più efficace del drone di partenza.
unit.dagger.description = Un unità terrena base, molto più efficiente se in branco. unit.dagger.description = Un unità terrena base, molto più efficiente se in branco.
unit.crawler.description = Un'unità di terra costituita da un telaio abbattuto con alti esplosivi legati sulla parte superiore. Non particolarmente resistente. Esplode a contatto con i nemici. unit.crawler.description = Un'unità di terra costituita da un telaio essenziale con potenti esplosivi legati sulla parte superiore. Non particolarmente resistente. Esplode a contatto con i nemici.
unit.titan.description = Un'unità di terra corazzata avanzata. Utilizza carburo come munizione. Attacca sia bersagli terrestri che aerei. unit.titan.description = Un'unità di terra corazzata avanzata equipaggiata con due piccoli lanciafiamme. Attacca sia bersagli terrestri che aerei.
unit.fortress.description = Un'unità di terra di artiglieria pesante. unit.fortress.description = Un'unità di terra di artiglieria pesante.
unit.eruptor.description = Un mech pesante progettato per abbattere le strutture. Spara un flusso di scorie contro le fortificazioni nemiche, sciogliendole e dando fuoco ai gas. unit.eruptor.description = Un mech pesante progettato per abbattere le strutture. Spara un flusso di scoria contro le fortificazioni nemiche, sciogliendole e dando fuoco a tutto.
unit.wraith.description = Un'unità d'intercezione rapida ed efficiente. unit.wraith.description = Un'unità d'intercezione rapida ed efficiente.
unit.ghoul.description = Un bombardiere pesante. Utilizza composti esplosivi o piratite come munizioni. unit.ghoul.description = Un bombardiere pesante. Utilizza composti esplosivi o pirite come munizioni.
unit.revenant.description = Una serie di missili pesante volante. unit.revenant.description = Un pesante lanciamissili volante.
unit.chaos-array.description = Ignoto
unit.eradicator.description = Ignoto
unit.lich.description = Ignoto
unit.reaper.description = Ignoto
block.command-center.description = Da istruzioni alle unità alleate nella mappa. Comanda la ricongizione, l'attacco del nucleo nemico o la ritirata verso il proprio nucleo o fabbrica.\nQuando non è presente un nucleo nemico, le unità pattuglieranno anche se viene ordinato un attacco.
block.graphite-press.description = Comprime pezzi di carbone in fogli di grafite puri. block.graphite-press.description = Comprime pezzi di carbone in fogli di grafite puri.
block.multi-press.description = Una versione aggiornata della pressa per grafite. Impiega acqua e energia per elaborare il carbone in modo rapido ed efficiente. block.multi-press.description = Una versione aggiornata della pressa per grafite. Impiega acqua ed energia per elaborare il carbone in modo rapido ed efficiente.
block.silicon-smelter.description = Mescola sabbia con carbone riscaldato in assenza d'aria. block.silicon-smelter.description = Fonde sabbia e carbone riscaldati per ottenere silicio.
block.kiln.description = Fonde la sabbia e il piombo in vetro metallico. Richiede piccole quantità di energia. block.kiln.description = Fonde la sabbia ed il piombo in vetro metallico. Richiede piccole quantità di energia.
block.plastanium-compressor.description = Produce plastanio da olio e titanio. block.plastanium-compressor.description = Produce plastanio da petrolio e titanio.
block.phase-weaver.description = Produce tessuto di fase da torio radioattivo e elevate quantità di sabbia. block.phase-weaver.description = Produce tessuto di fase da torio radioattivo ed elevate quantità di sabbia.
block.alloy-smelter.description = Produce leghe di sovratensione da titanio, piombo, silicio e rame. block.alloy-smelter.description = Produce leghe di sovratensione da titanio, piombo, silicio e rame.
block.cryofluidmixer.description = Combina acqua e titanio in criofluido che è molto più efficiente per il raffreddamento. block.cryofluidmixer.description = Combina acqua e titanio in criofluido che è molto più efficiente per il raffreddamento.
block.blast-mixer.description = Utilizza olio per trasformare la piratite nel composto esplosivo, meno infiammabile ma più esplosivo. block.blast-mixer.description = Frantuma e mescola le spore con la pirite per produrre Composto Esplosivo.
block.pyratite-mixer.description = Mescola carbone, piombo e sabbia in piratite altamente infiammabile. block.pyratite-mixer.description = Mescola carbone, piombo e sabbia in pirite altamente infiammabile.
block.melter.description = Riscalda la pietra a temperature molto elevate per ottenere lava. block.melter.description = Riscalda la pietra a temperature molto elevate per ottenere scoria liquida.
block.separator.description = Espone la pietra alla pressione dell'acqua per ottenere vari minerali contenuti nella pietra. block.separator.description = Sottopone le scoria a centrifugazione per ottenere i vari minerali contenuti.
block.spore-press.description = Comprime baccelli di spore in olio. block.spore-press.description = Comprime le spore in petrolio.
block.pulverizer.description = Schiaccia la pietra nella sabbia. Utile quando manca la sabbia naturale. block.pulverizer.description = Polverizza la pietra.\nUtile quando manca la sabbia naturale.
block.coal-centrifuge.description = Solidifica l'olio in pezzi di carbone. block.coal-centrifuge.description = Solidifica il petrolio in pezzi di carbone.
block.incinerator.description = Elimina qualsiasi oggetto in eccesso o liquido. block.incinerator.description = Elimina qualsiasi oggetto o liquido in eccesso.
block.power-void.description = Elimina tutta l'energia messa al suo interno, esiste solo nella sabbiera. block.power-void.description = Elimina tutta l'energia che riceve, esiste solo nella modalità creativa.
block.power-source.description = Produce energia infinita, esiste solo nella sabbiera. block.power-source.description = Produce energia infinita, esiste solo nella modalità creativa.
block.item-source.description = Produce oggetti infiniti, esiste solo nella sabbiera. block.item-source.description = Produce oggetti infiniti, esiste solo nella modalità creativa.
block.item-void.description = Elimina gli oggetti che ci entrano dentro senza energia, esiste solo nella sabbiera. block.item-void.description = Elimina gli oggetti che vi entrano senza bisogno di energia, esiste solo nella modalità creativa.
block.liquid-source.description = Emette continuamente liquidi. Esiste solo nella sabbiera. block.liquid-source.description = Emette continuamente liquidi. Esiste solo nella modalità creativa.
block.copper-wall.description = Un blocco difensivo economico. \n Utile per proteggere il nucleo e le torrette nelle prime ondate. block.copper-wall.description = Un blocco difensivo economico.\nUtile per proteggere il nucleo e le torrette nelle prime ondate.
block.copper-wall-large.description = Un blocco difensivo economico. \n Utile per proteggere il nucleo e le torrette nelle prime ondate. \nOccupa più blocchi block.copper-wall-large.description = Un blocco difensivo economico.\nUtile per proteggere il nucleo e le torrette nelle prime ondate. \nOccupa più blocchi
block.titanium-wall.description =Un blocco difensivo moderatamente forte.\nFornisce una protezione moderata dai nemici. block.titanium-wall.description =Un blocco difensivo moderatamente forte.\nFornisce una protezione moderata dai nemici.
block.titanium-wall-large.description = Un blocco difensivo moderatamente forte. \n Fornisce una protezione moderata dai nemici. \nOccupa più blocchi block.titanium-wall-large.description = Un blocco difensivo moderatamente forte.\nFornisce una protezione moderata dai nemici. \nOccupa più blocchi
block.thorium-wall.description = Un forte blocco difensivo.\nBuona protezione dai nemici. block.thorium-wall.description = Un forte blocco difensivo.\nBuona protezione dai nemici.
block.thorium-wall-large.description = Un forte blocco difensivo.\nBuona protezione dai nemici.\nOccupa più blocchi block.thorium-wall-large.description = Un forte blocco difensivo.\nBuona protezione dai nemici.\nOccupa più blocchi
block.phase-wall.description = Non è forte come un muro di torio, ma devia i proiettili a meno che non siano troppo potenti. block.phase-wall.description = Non è forte come un muro di torio, ma devia i proiettili a meno che non siano troppo potenti.
block.phase-wall-large.description = Non è forte come un muro di torio, ma devia i proiettili a meno che non siano troppo potenti.\nOccupa più blocchi block.phase-wall-large.description = Non è forte come un muro di torio, ma devia i proiettili a meno che non siano troppo potenti.\nOccupa più blocchi
block.surge-wall.description = Il blocco difensivo più forte. \nHa una piccola possibilità di innescare un fulmine verso l'attaccante. block.surge-wall.description = Il blocco difensivo più forte. \nHa una piccola possibilità di innescare un fulmine verso l'attaccante.
block.surge-wall-large.description = Il blocco difensivo più forte. \n Ha una piccola possibilità di innescare un fulmine verso l'attaccante.\nOccupa più blocchi block.surge-wall-large.description = Il blocco difensivo più forte. \n Ha una piccola possibilità di innescare un fulmine verso l'attaccante.\nOccupa più blocchi
block.door.description = Una piccola porta che può essere aperta e chiusa toccandola. \nSe aperta, i nemici possono sparare e attraversare. block.door.description = Una piccola porta che può essere aperta e chiusa toccandola. \nSe aperta, i nemici possono sparare ed attraversare.
block.door-large.description = Una grande porta che può essere aperta e chiusa toccandola. \nSe aperta, i nemici possono sparare e attraversare. \nOccupa più blocchi block.door-large.description = Una grande porta che può essere aperta e chiusa toccandola. \nSe aperta, i nemici possono sparare ed attraversare. \nOccupa più blocchi
block.mender.description = Ripara periodicamente blocchi nelle vicinanze. Mantiene le difese riparate tra le ondate.\nPuò usare del silicio per aumentare la portata e l'efficienza. block.mender.description = Ripara periodicamente blocchi nelle vicinanze.\nUtilizza del silicio per aumentarne portata ed efficienza.
block.mend-projector.description = Cura periodicamente gli edifici nelle vicinanze. block.mend-projector.description = Ripara periodicamente blocchi nelle vicinanze.\nUtilizza del tessuto di fase per aumentarne portata ed efficienza.
block.overdrive-projector.description = Aumenta la velocità di edifici vicini come trapani e nastri trasportatori. block.overdrive-projector.description = Aumenta la velocità di edifici vicini come trivelle e nastri trasportatori.
block.force-projector.description = Crea un campo di forza esagonale attorno a sé, proteggendo gli edifici e le unità all'interno da danni causati da proiettili block.force-projector.description = Crea un campo di forza esagonale attorno a sé, proteggendo gli edifici e le unità all'interno da danni causati da proiettili
block.shock-mine.description = Danneggia i nemici che la calpestano. Quasi invisibile al nemico. block.shock-mine.description = Danneggia i nemici che la calpestano. Quasi invisibile al nemico.
block.conveyor.description = Blocco di trasporto oggetti di base. Sposta gli oggetti in avanti e li deposita automaticamente in altri blocchi. Ruotabile. block.conveyor.description = Nastro di base. Sposta gli oggetti in avanti e li deposita automaticamente in altri blocchi. Ruotabile.
block.titanium-conveyor.description = Blocco trasporto oggetti avanzato. Sposta gli oggetti più velocemente dei trasportatori standard. block.titanium-conveyor.description = Nastro avanzato. Sposta gli oggetti più velocemente dei nastri standard.
block.junction.description = Funziona come un ponte per due nastri trasportatori incrociati. Utile in situazioni con due diversi nastri trasportatori che trasportano materiali diversi in posizioni diverse. block.junction.description = Permette di incrociare nastri che trasportano materiali diversi in posizioni diverse.
block.bridge-conveyor.description = Blocco trasporto oggetti avanzato. Consente il trasporto di oggetti fino a 3 tessere di qualsiasi terreno o edificio. block.bridge-conveyor.description = Consente il trasporto di oggetti fino a 3 tessere ad un altro nastro sopraelevato.\nPuò passare sopra ad altri blocchi od edifici.
block.phase-conveyor.description = Blocco trasporto oggetti avanzato. Utilizza la potenza per teletrasportare gli oggetti su un trasportatore di fase collegato su più piastrelle. block.phase-conveyor.description = Nastro avanzato. Consuma energia per teletrasportare gli oggetti su un altro nastro di fase collegato.
block.sorter.description = Divide gli oggetti. Se l'oggetto corrisponde a quello selezionato, Può passare. Altrimenti viene espulso sui lati. block.sorter.description = Divide gli oggetti. Se l'oggetto corrisponde a quello selezionato, Può passare. Altrimenti viene espulso sui lati.
block.router.description = Accetta gli elementi da una direzione e li emette fino a 3 altre direzioni allo stesso modo. Utile per suddividere i materiali da una fonte a più destinazioni. block.router.description = Accetta gli elementi da una direzione e li emette fino a 3 altre direzioni allo stesso modo. Utile per suddividere i materiali da una fonte a più destinazioni.
block.distributor.description = Un distributore avanzato che divide gli oggetti in altre 7 direzioni allo stesso modo. block.distributor.description = Un distributore avanzato che divide gli oggetti in altre 7 direzioni allo stesso modo.
block.overflow-gate.description = Una combinazione di un divisore e di un router , che distribuisce sui suoi lati se la via centrale è bloccata. block.overflow-gate.description = Una combinazione di un incrocio e di un distributore , che distribuisce sui suoi lati se in nastro difronte si satura.
block.mass-driver.description = Ultimo blocco di trasporto di oggetti. Raccoglie diversi oggetti e poi li spara su un'altra Lancia Materiali a lungo raggio. block.mass-driver.description = Ultimo blocco di trasporto di oggetti. Raccoglie diversi oggetti e poi li spara su un'altra Lancia Materiali a lungo raggio.
block.mechanical-pump.description = Una pompa economica con potenza lenta, ma nessun consumo di energia. block.mechanical-pump.description = Una pompa economica con potenza lenta, ma nessun consumo di energia.
block.rotary-pump.description = Una pompa avanzata che raddoppia la velocità sfruttando la potenza. block.rotary-pump.description = Una pompa avanzata che raddoppia la velocità consumando energia.
block.thermal-pump.description = La pompa migliore. Tre volte più veloce di una pompa meccanica e l'unica pompa in grado di recuperare la lava. block.thermal-pump.description = La pompa migliore. Tre volte più veloce di una pompa meccanica e l'unica pompa in grado di recuperare la lava.
block.conduit.description = Blocco di trasporto del liquido di base. Funziona come un nastro trasportatore, ma con liquidi. Ideale per estrattori, pompe o altri condotti. block.conduit.description = Condotta di base. Funziona come un nastro trasportatore, ma per i liquidi. Ideale per estrattori, pompe o altre condotte.
block.pulse-conduit.description = Blocco trasporto liquidi avanzato. Trasporta i liquidi più velocemente e immagazzina più dei condotti standard. block.pulse-conduit.description = Condotta avanzata. Trasporta più liquido e più velocemente delle condotte standard.
block.liquid-router.description = Accetta i liquidi da una direzione e li emette fino a 3 altre direzioni allo stesso modo. Può anche immagazzinare una certa quantità di liquido. Utile per suddividere i liquidi da una fonte a più bersagli. block.liquid-router.description = Accetta i liquidi da una direzione e li emette fino a 3 altre direzioni allo stesso modo. Può anche immagazzinare una certa quantità di liquido. Utile per suddividere i liquidi da una fonte verso più destinazioni.
block.liquid-tank.description = Conserva una grande quantità di liquidi. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali o come protezione per il raffreddamento di blocchi vitali. block.liquid-tank.description = Conserva una grande quantità di liquidi. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali o come protezione per il raffreddamento di blocchi vitali.
block.liquid-junction.description = Funziona come un ponte per due condotti di attraversamento. Utile in situazioni con due condotti diversi che trasportano liquidi diversi in luoghi diversi. block.liquid-junction.description = Permette di incrociare condotte che trasportano liquidi diversi in posizioni diverse.
block.bridge-conduit.description = Blocco trasporto liquidi avanzato. Consente il trasporto di liquidi fino a 3 piastrelle di qualsiasi terreno o edificio. block.bridge-conduit.description = Consente il trasporto di liquidi fino a 3 tessere da un altra condotta sopraelevata.\nPuò passare sopra ad altri blocchi od edifici.
block.phase-conduit.description = Blocco trasporto liquidi avanzato. Utilizza la potenza per teletrasportare i liquidi in un condotto di fase collegato su più piastrelle. block.phase-conduit.description = Condotta avanzata. Consuma energia per teletrasportare i liquidi in un altra condotta di fase collegata.
block.power-node.description = Trasmette energia ai nodi collegati. È possibile collegare fino a quattro fonti di alimentazione, eliminatori di energia o nodi. Il nodo riceverà energia o fornirà energia a tutti i blocchi adiacenti. block.power-node.description = Trasmette energia tra i nodi collegati. È possibile creare fino a quattro collegamenti.\nClicca sul nodo per configurare i collegamenti.
block.power-node-large.description = Ha un raggio maggiore rispetto al nodo di alimentazione e si collega a un massimo di sei fonti di alimentazione, eliminatori di energia o nodi. block.power-node-large.description = Ha un raggio maggiore rispetto al nodo energetico e si possono creare un massimo di sei collegamenti.\nClicca sul nodo per configurare i collegamenti.
block.surge-tower.description = Un nodo di alimentazione a lungo raggio con meno connessioni disponibili. block.surge-tower.description = Un nodo di alimentazione a lungo raggio solo due connessioni disponibili.\nClicca sul nodo per configurare i collegamenti.
block.battery.description = Accumula energia ogni volta che c'è abbondanza e fornisce energia ogni volta che c'è carenza, purché rimanga capacità. block.battery.description = Accumula energia ogni volta che c'è abbondanza e fornisce energia ogni volta che c'è carenza, purché rimanga carica.
block.battery-large.description = Immagazzina molta più energia di una normale batteria. block.battery-large.description = Immagazzina molta più energia di una normale batteria.
block.combustion-generator.description = Genera energia bruciando olio o materiali infiammabili. block.combustion-generator.description = Genera energia bruciando combustibile.
block.thermal-generator.description = Genera una grande quantità di energia dalla lava. block.thermal-generator.description = Genera una grande quantità di energia dalla lava.
block.turbine-generator.description = Più efficiente di un generatore di combustione, ma richiede acqua aggiuntiva. block.turbine-generator.description = Più efficiente di un generatore a combustione, ma richiede l'aggiunta di acqua.
block.differential-generator.description = Genera grandi quantità di energia. Utilizza la differenza di temperatura tra criofluido e piratite in fiamme. block.differential-generator.description = Genera grandi quantità di energia. Utilizza la differenza di temperatura tra criofluido e pirite in combustione.
block.rtg-generator.description = Un generatore termoelettrico radioisotopico che non richiede raffreddamento ma fornisce meno energia di un reattore al torio. block.rtg-generator.description = Un generatore che sfrutta il calore del decadimento di materiale radioattivo per produrre energia.\nNon richiede raffreddamento ma fornisce meno energia di un reattore al torio.
block.solar-panel.description = Fornisce una piccola quantità di energia dal sole. block.solar-panel.description = Fornisce una piccola quantità di energia dal sole.
block.solar-panel-large.description = Fornisce un'alimentazione molto migliore rispetto a un pannello solare standard, ma è anche molto più costoso da costruire. block.solar-panel-large.description = Fornisce un'alimentazione molto migliore rispetto a un pannello solare standard, ma è anche molto più costoso da costruire.
block.thorium-reactor.description = Genera enormi quantità di energia dal torio altamente radioattivo. Richiede un raffreddamento costante. Esploderà violentemente se vengono fornite quantità insufficienti di refrigerante. block.thorium-reactor.description = Genera enormi quantità di energia dal torio altamente radioattivo. Richiede un raffreddamento costante. Esploderà violentemente se vengono fornite quantità insufficienti di refrigerante.
block.impact-reactor.description = Un generatore avanzato, in grado di creare enormi quantità di energia alla massima efficienza. Richiede un significativo apporto di energia per avviare il processo. block.impact-reactor.description = Un generatore avanzato, in grado di creare enormi quantità di energia alla massima efficienza. Richiede un significativo apporto di energia per avviare il processo.
block.mechanical-drill.description = Un trapano economico. Se posizionato su riquadri appropriati, genera gli oggetti a un ritmo lento indefinitamente. block.mechanical-drill.description = Una trivella economica. Se posizionato su riquadri appropriati, estrae minerali a un ritmo lento e costante.
block.pneumatic-drill.description = Un trapano migliorato che è più veloce e in grado di elaborare materiali più duri sfruttando la pressione dell'aria. block.pneumatic-drill.description = Una trivella migliorata più veloce ed in grado di elaborare materiali più duri sfruttando la pressione dell'aria.
block.laser-drill.description = Consente di perforare ancora più velocemente attraverso la tecnologia laser, ma richiede potenza. Inoltre, con questo trapano è possibile recuperare il torio radioattivo. block.laser-drill.description = Consente di perforare ancora più velocemente attraverso la tecnologia laser, ma richiede energia. Inoltre, con questa trivella è possibile recuperare il torio radioattivo.
block.blast-drill.description = Il trapano migliore. Richiede grandi quantità di energia. block.blast-drill.description = La trivella migliore. Richiede grandi quantità di energia.
block.water-extractor.description = Estrae l'acqua dal terreno. Usalo quando non c'è nessun lago nelle vicinanze. block.water-extractor.description = Estrae l'acqua dal terreno. Usalo quando non c'è nessun lago nelle vicinanze.
block.cultivator.description = Coltiva il terreno con acqua per ottenere materia organica. block.cultivator.description = Coltiva il terreno con acqua per ottenere materia organica.
block.oil-extractor.description = Utilizza grandi quantità di energia per estrarre olio dalla sabbia. Usalo quando non c'è una fonte diretta di petrolio nelle vicinanze. block.oil-extractor.description = Utilizza grandi quantità di energia per estrarre petrolio dalla sabbia. Usalo quando non c'è una fonte diretta di petrolio nelle vicinanze.
block.core-shard.description = La prima iterazione del nucleo. Una volta distrutto, tutti i contatti con la regione vengono persi. Non lasciare che questo accada. block.core-shard.description = La prima iterazione del nucleo. Una volta distrutto, tutti i contatti con la regione vengono persi. Non lasciare che questo accada.
block.core-foundation.description = La seconda versione del nucleo. Meglio corazzato. Immagazzina più risorse. block.core-foundation.description = La seconda versione del nucleo. Meglio corazzato. Immagazzina più risorse.
block.core-nucleus.description = La terza e ultima versione del nucleo. Estremamente ben corazzato. Immagazzina enormi quantità di risorse. block.core-nucleus.description = La terza ed ultima versione del nucleo. Estremamente ben corazzato. Immagazzina enormi quantità di risorse.
block.vault.description = Immagazzina una grande quantità di oggetti. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali. Uno [LIGHT_GRAY]scaricatore[] può essere utilizzato per recuperare elementi dal deposito. block.vault.description = Immagazzina una grande quantità di oggetti. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali. Uno [LIGHT_GRAY]scaricatore[] può essere utilizzato per recuperare elementi dal deposito.
block.container.description = Memorizza una piccola quantità di oggetti. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali. Uno [LIGHT_GRAY]scaricatore[] può essere utilizzato per recuperare elementi dal contenitore. block.container.description = Immagazzina una piccola quantità di oggetti. Usalo per creare zone cuscinetto quando c'è una domanda non costante di materiali. Uno [LIGHT_GRAY]scaricatore[] può essere utilizzato per recuperare elementi dal contenitore.
block.unloader.description = Scarica gli oggetti da un contenitore, caveau o nucleo su un trasportatore o direttamente in un blocco adiacente. Il tipo di articolo da scaricare può essere modificato toccando lo scaricatore. block.unloader.description = Scarica gli oggetti da un contenitore, caveau o nucleo su un trasportatore o direttamente in un blocco adiacente. L'oggetto da scaricare può essere scelto toccando lo scaricatore.
block.launch-pad.description = Lancia oggetti senza necessità di un lancio di base. Incompiuto. block.launch-pad.description = Lancia oggetti nel tuo nucleo senza necessità di un lasciare la zona.
block.launch-pad-large.description = Una versione migliore della piattaforma di lancio, immagazzina più oggetti. Lancia oggetti più frequentemente. block.launch-pad-large.description = Una versione migliore dell'Ascensore Spaziale, immagazzina più oggetti. Lancia oggetti più frequentemente.
block.duo.description = Una torretta piccola ed economica. block.duo.description = Una torretta piccola ed economica.
block.scatter.description = Una torretta anti-aria di medie dimensioni. Spruzza grumi di piombo o frammenti di scorie sulle unità nemiche. block.scatter.description = Una torretta antiaerea di medie dimensioni. Spara schegge di piombo o frammenti di rottami sulle unità nemiche.
block.scorch.description = Brucia qualsiasi nemico di terra vicino ad esso. Molto efficace a distanza ravvicinata. block.scorch.description = Brucia qualsiasi nemico di terra vicino ad esso. Molto efficace a distanza ravvicinata.
block.hail.description = Una piccola torretta di artiglieria. block.hail.description = Una piccola torretta di artiglieria.
block.wave.description = Una torretta a fuoco rapido di medie dimensioni che spara bolle liquide. block.wave.description = Una torretta a fuoco rapido di medie dimensioni che spara liquidi.
block.lancer.description = Una torretta di medie dimensioni che spara fasci di elettricità caricati. block.lancer.description = Una torretta di medie dimensioni che dopo un breve caricamento spara potenti fasci elettrici.
block.arc.description = Una piccola torretta che spara elettricità in un arco casuale verso il nemico. block.arc.description = Una piccola torretta che spara elettricità in un arco casuale verso il nemico.
block.swarmer.description = Una torretta di medie dimensioni che spara missili esplosivi. block.swarmer.description = Una torretta di medie dimensioni che spara missili esplosivi.
block.salvo.description = Una torretta di medie dimensioni che spara colpi in salve. block.salvo.description = Una torretta di medie dimensioni che spara colpi in salve.
block.fuse.description = Una grande torretta che spara potenti raggi a corto raggio. block.fuse.description = Una grande torretta a corto raggio che spara tre potenti schegge perforanti.
block.ripple.description = Una grande torretta di artiglieria che spara più colpi contemporaneamente. block.ripple.description = Una grande torretta di artiglieria che spara più colpi contemporaneamente.
block.cyclone.description = Una grande torretta a fuoco rapido. block.cyclone.description = Una grande torretta a fuoco rapido.
block.spectre.description = Una grande torretta che spara due potenti proiettili contemporaneamente. block.spectre.description = Una grande torretta che spara due potenti proiettili contemporaneamente.
block.meltdown.description = Una grande torretta che spara potenti raggi a lungo raggio. block.meltdown.description = Una grande torretta che spara un potente laser a lungo raggio.
block.draug-factory.description = Produce droni minerari block.draug-factory.description = Produce droni per la raccolta mineraria.
block.spirit-factory.description = Produce droni che riparano blocchi. block.spirit-factory.description = Produce droni che riparano blocchi.
block.phantom-factory.description = Produce unità drone avanzate che sono significativamente più efficaci di un drone riparatore. block.phantom-factory.description = Produce droni avanzati che seguono il giocatore e lo assistono nella costruzione.
block.wraith-factory.description = Produce unità intercettatrici veloci e veloci. block.wraith-factory.description = Produce unità intercettatrici veloci.
block.ghoul-factory.description = Produce bombardieri pesanti. block.ghoul-factory.description = Produce bombardieri pesanti.
block.revenant-factory.description = Produce unità laser di terra pesanti. block.revenant-factory.description = Produce unità laser di terra pesanti.
block.dagger-factory.description = Produce unità di base di terra. block.dagger-factory.description = Produce unità di base corpo a corpo di terra.
block.crawler-factory.description = Produce unità di sciame veloci autodistruggenti. block.crawler-factory.description = Produce unità di sciame veloci ed autodistruggenti.
block.titan-factory.description = Produce unità terrestri avanzate e corazzate. block.titan-factory.description = Produce unità terrestri avanzate e corazzate.
block.fortress-factory.description = Produce unità di terra di artiglieria pesante. block.fortress-factory.description = Produce unità di terra di artiglieria pesante.
block.repair-point.description = Cura continuamente l'unità danneggiata più vicina block.repair-point.description = Cura continuamente l'unità danneggiata più vicina.
block.dart-mech-pad.description = Fornisce la trasformazione in un mech di attacco di base. \nUtilizzare toccando stando in piedi su di esso. block.dart-mech-pad.description = Trasforma la tua nave in un mech di attacco di base. \nUsa il blocco toccando due volte mentre ti trovi su di esso.
block.delta-mech-pad.description = Lascia la tua attuale nave e trasformala in un mech veloce e leggermente corazzato fatto per gli attacchi di tipo "colpisci e scappa". \nUsa il blocco toccando due volte mentre ti ci trovi sopra. block.delta-mech-pad.description = Trasforma la tua nave in un mech veloce e leggermente corazzato, ideale per colpire e scappare. \nUsa il blocco toccando due volte mentre ti ci trovi sopra.
block.tau-mech-pad.description = Lascia la tua attuale nave e trasformala in un mech di supporto in grado di curare edifici e unità amichevoli. \n Usa il blocco toccando due volte mentre sei in piedi su di esso. block.tau-mech-pad.description = Trasforma la tua nave in un mech di supporto in grado di curare edifici ed unità alleate. \n Usa il blocco toccando due volte mentre sei in piedi su di esso.
block.omega-mech-pad.description = Lascia la tua attuale nave e trasformala in un mech voluminoso e ben corazzato, creato per gli assalti in prima linea. \nUsa il blocco toccando due volte mentre sei in piedi su di esso. block.omega-mech-pad.description = Trasforma la tua nave in un mech voluminoso e ben corazzato, creato per gli assalti in prima linea. \nUsa il blocco toccando due volte mentre sei in piedi su di esso.
block.javelin-ship-pad.description = Lascia la tua attuale nave e trasformala in un intercettore forte e veloce con armi elettriche.\nUsa il blocco toccando due volte mentre ti trovi su di esso. block.javelin-ship-pad.description = Trasforma la tua nave in un intercettore forte e veloce con armi elettriche.\nUsa il blocco toccando due volte mentre ti trovi su di esso.
block.trident-ship-pad.description = Lascia la tua attuale nave e trasformala in un bombardiere pesantemente ben corazzato. \nUsa il blocco toccando due volte mentre ti trovi su di esso. block.trident-ship-pad.description = Trasforma la tua nave in un bombardiere pesante e ben corazzato. \nUsa il blocco toccando due volte mentre ti trovi su di esso.
block.glaive-ship-pad.description = Lascia la tua attuale nave e trasformati in una grande nave ben corazzata. \n Usa il blocco toccando due volte mentre ti trovi su di esso. block.glaive-ship-pad.description = Trasforma la tua nave in una nave grande e ben corazzata. \nUsa il blocco toccando due volte mentre ti trovi su di esso.

File diff suppressed because it is too large Load Diff

View File

@@ -1,28 +1,28 @@
credits.text = Created by [ROYAL]Anuken[] - [SKY]anukendev@gmail.com[]\n\n[GRAY](In case you can't tell, this text is currently unfinished.\nTranslators, don't edit it yet!) credits.text = Created by [ROYAL]Anuken[] - [SKY]anukendev@gmail.com[]
credits = Creditos credits = Créditos
contributors = Tradutores e contribuidores contributors = Tradutores e contribuidores
discord = Junte-se ao Discord do Mindustry! (Lá nós falamos em inglês) discord = Junte-se ao Discord do Mindustry! (Lá nós falamos em inglês)
link.discord.description = O discord oficial do Mindustry link.discord.description = O discord oficial do Mindustry
link.github.description = Codigo fonte do jogo. link.github.description = Código fonte do jogo.
link.changelog.description = List of update changes link.changelog.description = List of update changes
link.dev-builds.description = Desenvolvimentos Instaveis link.dev-builds.description = Desenvolvimentos Instáveis
link.trello.description = Trello Oficial para Updates Planejados link.trello.description = Trello Oficial para Updates Planejados
link.itch.io.description = Pagina da Itch.io com os Downloads link.itch.io.description = Pagina da Itch.io com os Downloads
link.google-play.description = Listamento do google play store link.google-play.description = Listamento do google play store
link.wiki.description = Wiki oficial do Mindustry link.wiki.description = Wiki oficial do Mindustry
linkfail = Falha ao abrir o link\nO Url foi copiado linkfail = Falha ao abrir o link\nO Url foi copiado
screenshot = Screenshot salvo para {0} screenshot = Screenshot salvo para {0}
screenshot.invalid = Mapa grande demais, Potencialmente sem memoria suficiente para captura. screenshot.invalid = Mapa grande demais, Potencialmente sem memória suficiente para captura.
gameover = O núcleo foi destruído. gameover = O núcleo foi destruído.
gameover.pvp = O time[accent] {0}[] É vitorioso! gameover.pvp = O time[accent] {0}[] É vitorioso!
highscore = [YELLOW]Novo recorde! highscore = [YELLOW]Novo recorde!
load.sound = Sounds load.sound = Sons
load.map = Maps load.map = Mapas
load.image = Images load.image = Imagens
load.content = Content load.content = Conteúdo
load.system = System load.system = Sistema
stat.wave = Hordas derrotadas:[accent] {0} stat.wave = Hordas derrotadas:[accent] {0}
stat.enemiesDestroyed = Enimigos Destruídos:[accent] {0} stat.enemiesDestroyed = Inimigos Destruídos:[accent] {0}
stat.built = Construções construídas:[accent] {0} stat.built = Construções construídas:[accent] {0}
stat.destroyed = Construções destruídas:[accent] {0} stat.destroyed = Construções destruídas:[accent] {0}
stat.deconstructed = Construções desconstruídas:[accent] {0} stat.deconstructed = Construções desconstruídas:[accent] {0}
@@ -66,18 +66,18 @@ players.single = {0} Jogador Ativo
server.closing = [accent]Fechando servidor... server.closing = [accent]Fechando servidor...
server.kicked.kick = Voce foi expulso do servidor! server.kicked.kick = Voce foi expulso do servidor!
server.kicked.serverClose = Servidor Fechado. server.kicked.serverClose = Servidor Fechado.
server.kicked.vote = You have been vote-kicked. Goodbye. server.kicked.vote = Você foi expulso desse servidor. Tchau.
server.kicked.clientOutdated = Cliente desatualizado! Atualize seu jogo! server.kicked.clientOutdated = Cliente desatualizado! Atualize seu jogo!
server.kicked.serverOutdated = Servidor desatualiado! Peca ao dono para atualizar! server.kicked.serverOutdated = Servidor desatualiado! Peça ao dono para atualizar!
server.kicked.banned = Voce foi banido do servidor. server.kicked.banned = Você foi banido do servidor.
server.kicked.typeMismatch = This server is not compatible with your build type. server.kicked.typeMismatch = Este servidor não é compatível com a sua versão.
server.kicked.recentKick = Voce foi banido recentemente.\nEspere para conectar de novo. server.kicked.recentKick = Voce foi banido recentemente.\nEspere para conectar de novo.
server.kicked.nameInUse = Este nome ja esta sendo usado\nneste servidor. server.kicked.nameInUse = Este nome já esta sendo usado\nneste servidor.
server.kicked.nameEmpty = Voce deve ter pelo menos uma letra ou numero. server.kicked.nameEmpty = Voce deve ter pelo menos uma letra ou número.
server.kicked.idInUse = Voce ja esta neste servidor! Conectar com duas contas não é permitido. server.kicked.idInUse = Voce ja está neste servidor! Conectar com duas contas não é permitido.
server.kicked.customClient = Este servidor não suporta construções customizadas. Baixe a versão original. server.kicked.customClient = Este servidor não suporta construções customizadas. Baixe a versão original.
server.kicked.gameover = Fim de jogo! server.kicked.gameover = Fim de jogo!
server.versions = Your version:[accent] {0}[]\nServer version:[accent] {1}[] server.versions = Sua versão:[accent] {0}[]\nVersão do servidor:[accent] {1}[]
host.info = The [accent]Hospedar[]Botão Hopeda um servidor no Host[scarlet]6567[] e [scarlet]6568.[]\nQualquer um no [LIGHT_GRAY]Wi-fi Ou Internet local[] Pode ver este servidor na lista de servidores.\n\nSe voce quer poder entrar em qualquer servidor em seu ip, [accent]port forwarding[] é requerido.\n\n[LIGHT_GRAY]Note: Se alguem esta com problemas em conectar no seu servidor lan, Tenha certeza que deixou mindustry Acessar sua internet local nas configurações de firewall host.info = The [accent]Hospedar[]Botão Hopeda um servidor no Host[scarlet]6567[] e [scarlet]6568.[]\nQualquer um no [LIGHT_GRAY]Wi-fi Ou Internet local[] Pode ver este servidor na lista de servidores.\n\nSe voce quer poder entrar em qualquer servidor em seu ip, [accent]port forwarding[] é requerido.\n\n[LIGHT_GRAY]Note: Se alguem esta com problemas em conectar no seu servidor lan, Tenha certeza que deixou mindustry Acessar sua internet local nas configurações de firewall
join.info = Aqui, Você pode entar em um [accent]IP De servidor[] Para conectar, Ou descobrir [accent]Servidores[] Da rede local.\nAmbos os servidores LAN e WAN São suportados.\n\n[LIGHT_GRAY]Note: Não tem uma lista de servidores automaticos; Se você quer conectar ao IP de alguem, Você precisa pedir o IP Ao Rosteador. join.info = Aqui, Você pode entar em um [accent]IP De servidor[] Para conectar, Ou descobrir [accent]Servidores[] Da rede local.\nAmbos os servidores LAN e WAN São suportados.\n\n[LIGHT_GRAY]Note: Não tem uma lista de servidores automaticos; Se você quer conectar ao IP de alguem, Você precisa pedir o IP Ao Rosteador.
hostserver = Hospedar servidor hostserver = Hospedar servidor
@@ -115,12 +115,12 @@ confirmunadmin = Certeza que quer remover o estatus de adminstrador deste jogado
joingame.title = Entrar no jogo joingame.title = Entrar no jogo
joingame.ip = IP: joingame.ip = IP:
disconnect = Desconectado. disconnect = Desconectado.
disconnect.data = Falha ao abrir a data do mundo! disconnect.data = Falha ao abrir os dados do mundo!
connecting = [accent]Conectando... connecting = [accent]Conectando...
connecting.data = [accent]Carregando data do mundo... connecting.data = [accent]Carregando dados do mundo...
server.port = Porte: server.port = Porte:
server.addressinuse = Senha em uso! server.addressinuse = Senha em uso!
server.invalidport = Numero de port invalido! server.invalidport = Numero de porta invalido!
server.error = [crimson]Erro ao hospedar o servidor: [accent]{0} server.error = [crimson]Erro ao hospedar o servidor: [accent]{0}
save.old = Este save é para uma versão antiga do jogo, E não pode ser usado.\n\n[LIGHT_GRAY]Salvar Versões antigas vai ser Implementado Na versão 4.0 completa save.old = Este save é para uma versão antiga do jogo, E não pode ser usado.\n\n[LIGHT_GRAY]Salvar Versões antigas vai ser Implementado Na versão 4.0 completa
save.new = Novo Save save.new = Novo Save
@@ -161,15 +161,15 @@ cancel = Cancelar
openlink = Abrir Link openlink = Abrir Link
copylink = Copiar link copylink = Copiar link
back = Voltar back = Voltar
data.export = Export Data data.export = Exportar Data
data.import = Import Data data.import = Importar Data
data.exported = Data exported. data.exported = Data exportada.
data.invalid = This isn't valid game data. data.invalid = Isso não é daa de jogo válida.
data.import.confirm = Importing external data will erase[scarlet] all[] your current game data.\n[accent]This cannot be undone![]\n\nOnce the data is imported, your game will exit immediately. data.import.confirm = Importal data externa irá deletar[scarlet] toda[] sua data atual.\n[accent]Isso não pode ser desfeito![]\n\nQuando sua data é importada, seu jogo ira sair imediatamente.
classic.export = Export Classic Data classic.export = Exportar data classica
classic.export.text = [accent]Mindustry[] has just had a major update.\nClassic (v3.5 build 40) save or map data has been detected. Would you like to export these saves to your phone's home folder, for use in the Mindustry Classic app? classic.export.text = [accent]Mindustry[] has just had a major update.\nClassic (v3.5 build 40) save or map data has been detected. Would you like to export these saves to your phone's home folder, for use in the Mindustry Classic app?
quit.confirm = Você tem certeza que quer sair? quit.confirm = Você tem certeza que quer sair?
quit.confirm.tutorial = Are you sure you know what you're doing?\nThe tutorial can be re-taken in[accent] Settings->Game->Re-Take Tutorial.[] quit.confirm.tutorial = Você tem certeza você sabe oque Você esta fazendo?\nO tutorial pode ser refeito nas [accent] Configurações->Jogo->Refazer Tutorial.[]
loading = [accent]Carregando... loading = [accent]Carregando...
saving = [accent]Salvando... saving = [accent]Salvando...
wave = [accent]Horda {0} wave = [accent]Horda {0}
@@ -188,7 +188,7 @@ map.delete.confirm = Certeza que quer deletar este mapa? Isto não pode ser desf
map.random = [accent]Mapa aleatório map.random = [accent]Mapa aleatório
map.nospawn = Esse mapa não contém um [yellow]núcleo[] para o jogador Nascer! [ROYAL]blue[] Coloque um [yellow]núcleo[] no editor de mapa. map.nospawn = Esse mapa não contém um [yellow]núcleo[] para o jogador Nascer! [ROYAL]blue[] Coloque um [yellow]núcleo[] no editor de mapa.
map.nospawn.pvp = Esse mapa não tem núcleos inimigos para os jogadores nascerem! Adicione[SCARLET] Núcleos vermelhos[] no mapa no editor. map.nospawn.pvp = Esse mapa não tem núcleos inimigos para os jogadores nascerem! Adicione[SCARLET] Núcleos vermelhos[] no mapa no editor.
map.nospawn.attack = This map does not have any enemy cores for player to attack! Add[SCARLET] red[] cores to this map in the editor. map.nospawn.attack = Esse mapa não tem nenhum núcleos enimigos para o jogador atacar! coloque[SCARLET] Núcleos[] vermelhos no editor.
map.invalid = Erro ao carregar o mapa: Arquivo de mapa invalido ou corrupto. map.invalid = Erro ao carregar o mapa: Arquivo de mapa invalido ou corrupto.
editor.brush = Pincel editor.brush = Pincel
editor.openin = Abrir no Editor editor.openin = Abrir no Editor
@@ -200,8 +200,8 @@ editor.description = Descrição:
editor.waves = Ondas: editor.waves = Ondas:
editor.rules = Regras: editor.rules = Regras:
editor.generation = Generation: editor.generation = Generation:
editor.ingame = Editar em-jogo editor.ingame = Editar em jogo
editor.newmap = New Map editor.newmap = Novo mapa
waves.title = Hordas waves.title = Hordas
waves.remove = Remover waves.remove = Remover
waves.never = <nunca> waves.never = <nunca>
@@ -227,7 +227,7 @@ editor.errorload = Erro carregando arquivo:\n[accent]{0}
editor.errorsave = Erro salvando arquivo:\n[accent]{0} editor.errorsave = Erro salvando arquivo:\n[accent]{0}
editor.errorimage = Isso é uma imagem, Não um mapa. Não vá por aí mudando extensões esperando que funcione.\n\nSe você quer importar um mapa legacy, Use o botão 'Importar mapa legacy'no editor. editor.errorimage = Isso é uma imagem, Não um mapa. Não vá por aí mudando extensões esperando que funcione.\n\nSe você quer importar um mapa legacy, Use o botão 'Importar mapa legacy'no editor.
editor.errorlegacy = Esse mapa é velho demais, E usa um formato de mapa legacy que não é mais suportado. editor.errorlegacy = Esse mapa é velho demais, E usa um formato de mapa legacy que não é mais suportado.
editor.errorheader = Este arquivo de mapa não é mais valido, Ou esta corrompido. editor.errorheader = Este arquivo de mapa não é mais válido ou está corrompido.
editor.errorname = Mapa não tem nome definido. editor.errorname = Mapa não tem nome definido.
editor.update = atualizar editor.update = atualizar
editor.randomize = Randomizar editor.randomize = Randomizar
@@ -240,14 +240,14 @@ editor.saved = Salvo!
editor.save.noname = Seu mapa não tem um nome! Coloque um no menu de "Informação do mapa" editor.save.noname = Seu mapa não tem um nome! Coloque um no menu de "Informação do mapa"
editor.save.overwrite = O seu mapa Substitui um mapa já construído! Coloque um nome diferente no menu "Informação do mapa" editor.save.overwrite = O seu mapa Substitui um mapa já construído! Coloque um nome diferente no menu "Informação do mapa"
editor.import.exists = [scarlet]Não foi possivel importar:[] Um mapa Construído chamado '{0}' Já existe! editor.import.exists = [scarlet]Não foi possivel importar:[] Um mapa Construído chamado '{0}' Já existe!
editor.import = Importando... editor.import = Importar...
editor.importmap = Importar Mapa editor.importmap = Importar Mapa
editor.importmap.description = Importar um mapa existente editor.importmap.description = Importar um mapa existente
editor.importfile = Importar arquivo editor.importfile = Importar arquivo
editor.importfile.description = Importar um arquivo externo editor.importfile.description = Importar um arquivo externo
editor.importimage = Importar imagem do terreno editor.importimage = Importar imagem do terreno
editor.importimage.description = Importar uma imagem de terreno externa editor.importimage.description = Importar uma imagem de terreno externa
editor.export = Exportando... editor.export = Exportar...
editor.exportfile = Exportar arquivo editor.exportfile = Exportar arquivo
editor.exportfile.description = Exportar um arquivo de mapa editor.exportfile.description = Exportar um arquivo de mapa
editor.exportimage = Exportar imagem de terreno editor.exportimage = Exportar imagem de terreno
@@ -260,16 +260,16 @@ editor.mapname = Nome do Mapa:
editor.overwrite = [accent]Aviso!\nIsso Subistitui um mapa existente. editor.overwrite = [accent]Aviso!\nIsso Subistitui um mapa existente.
editor.overwrite.confirm = [scarlet]Aviso![] Um mapa com esse nome já existe. Tem certeza que deseja substituir? editor.overwrite.confirm = [scarlet]Aviso![] Um mapa com esse nome já existe. Tem certeza que deseja substituir?
editor.selectmap = Selecione uma mapa para carregar: editor.selectmap = Selecione uma mapa para carregar:
toolmode.replace = Replace toolmode.replace = Substituir
toolmode.replace.description = Draws only on solid blocks. toolmode.replace.description = Draws only on solid blocks.
toolmode.replaceall = Replace All toolmode.replaceall = Substituir tudo
toolmode.replaceall.description = Replace all blocks in map. toolmode.replaceall.description = Substitui todos os blocos no mapa
toolmode.orthogonal = Orthogonal toolmode.orthogonal = Orthogonal
toolmode.orthogonal.description = Draws only orthogonal lines. toolmode.orthogonal.description = Draws only orthogonal lines.
toolmode.square = Square toolmode.square = Square
toolmode.square.description = Square brush. toolmode.square.description = Square brush.
toolmode.eraseores = Erase Ores toolmode.eraseores = Apagar minérios
toolmode.eraseores.description = Erase only ores. toolmode.eraseores.description = Apaga apenas minérios.
toolmode.fillteams = Fill Teams toolmode.fillteams = Fill Teams
toolmode.fillteams.description = Fill teams instead of blocks. toolmode.fillteams.description = Fill teams instead of blocks.
toolmode.drawteams = Draw Teams toolmode.drawteams = Draw Teams
@@ -309,7 +309,7 @@ width = Largura:
height = Altura: height = Altura:
menu = Menu menu = Menu
play = Jogar play = Jogar
campaign = Campaign campaign = Campanha
load = Carregar load = Carregar
save = Salvar save = Salvar
fps = FPS: {0} fps = FPS: {0}
@@ -318,14 +318,14 @@ ping = Ping: {0}ms
language.restart = Por favor Reinicie seu jogo para a tradução tomar efeito. language.restart = Por favor Reinicie seu jogo para a tradução tomar efeito.
settings = Configurações settings = Configurações
tutorial = Tutorial tutorial = Tutorial
tutorial.retake = Re-Take Tutorial tutorial.retake = Refazer Tutorial
editor = Editor editor = Editor
mapeditor = Editor de mapa mapeditor = Editor de mapa
donate = Doar donate = Doar
abandon = Abandonar abandon = Abandonar
abandon.text = Esta zona e todos os seus recursos serão perdidos para o enimigo. abandon.text = Esta zona e todos os seus recursos serão perdidos para o inimigo.
locked = Trancado locked = Trancado
complete = [LIGHT_GRAY]Complete: complete = [LIGHT_GRAY]Completo:
zone.requirement = Onda {0} Na zona {1} zone.requirement = Onda {0} Na zona {1}
resume = Resumir Zona:\n[LIGHT_GRAY]{0} resume = Resumir Zona:\n[LIGHT_GRAY]{0}
bestwave = [LIGHT_GRAY]Melhor: {0} bestwave = [LIGHT_GRAY]Melhor: {0}
@@ -334,7 +334,7 @@ launch.title = Lançamento feito com sucesso
launch.next = [LIGHT_GRAY]próxima oportunidade na onda {0} launch.next = [LIGHT_GRAY]próxima oportunidade na onda {0}
launch.unable2 = [scarlet]Unable to LAUNCH.[] launch.unable2 = [scarlet]Unable to LAUNCH.[]
launch.confirm = Isto vai lançar todos os seus recursos no seu núcleo.\nVoce não será capaz de retornar para esta base. launch.confirm = Isto vai lançar todos os seus recursos no seu núcleo.\nVoce não será capaz de retornar para esta base.
launch.skip.confirm = If you skip now, you will not be able to launch until later waves. launch.skip.confirm = Se você pular a onda agora, você não será capaz de lançar até ondas mais avançadas.
uncover = Descobrir uncover = Descobrir
configure = Configurar carregamento configure = Configurar carregamento
configure.locked = [LIGHT_GRAY]Alcançe a onda {0}\npara Configurar o Loadout. configure.locked = [LIGHT_GRAY]Alcançe a onda {0}\npara Configurar o Loadout.
@@ -342,9 +342,9 @@ zone.unlocked = [LIGHT_GRAY]{0} Desbloqueado.
zone.requirement.complete = Onda {0} alcançada:\n{1} Requerimentos da zona alcançada. zone.requirement.complete = Onda {0} alcançada:\n{1} Requerimentos da zona alcançada.
zone.config.complete = Onda {0} Alcançada:\nLoadout config desbloqueado. zone.config.complete = Onda {0} Alcançada:\nLoadout config desbloqueado.
zone.resources = Recursos detectados: zone.resources = Recursos detectados:
zone.objective = [lightgray]Objective: [accent]{0} zone.objective = [lightgray]Objetivo: [accent]{0}
zone.objective.survival = Survive zone.objective.survival = Sobreviver
zone.objective.attack = Destroy Enemy Core zone.objective.attack = Destruir o núcleo inimigo
add = Adicionar... add = Adicionar...
boss.health = Saúde do chefe boss.health = Saúde do chefe
connectfail = [crimson]Falha ao entrar no servidor: [accent]{0} connectfail = [crimson]Falha ao entrar no servidor: [accent]{0}
@@ -371,8 +371,8 @@ zone.saltFlats.name = Salt Flats
zone.impact0078.name = Impact 0078 zone.impact0078.name = Impact 0078
zone.crags.name = Crags zone.crags.name = Crags
zone.fungalPass.name = Fungal Pass zone.fungalPass.name = Fungal Pass
zone.groundZero.description = The optimal location to begin once more. Low enemy threat. Few resources.\nGather as much lead and copper as possible.\nMove on. zone.groundZero.description = Uma ótima localização para começar de novo. Baixa ameaça inimiga. Poucos recursos.\nColete o máximo de chumbo e cobre possível.\nBora!
zone.frozenForest.description = Even here, closer to mountains, the spores have spread. The fridgid temperatures cannot contain them forever.\n\nBegin the venture into power. Build combustion generators. Learn to use menders. zone.frozenForest.description = Até aqui, perto das montanhas, os esporos se espalharam. As baixas temperaturas não podem contê-los para sempre.\n\nComeçe a busca por energia. Construa geradores à combustão. Aprenda a usar os reparadores (menders).
zone.desertWastes.description = These wastes are vast, unpredictable, and criss-crossed with derelict sector structures.\nCoal is present in the region. Burn it for power, or synthesize graphite.\n\n[lightgray]This landing location cannot be guaranteed. zone.desertWastes.description = These wastes are vast, unpredictable, and criss-crossed with derelict sector structures.\nCoal is present in the region. Burn it for power, or synthesize graphite.\n\n[lightgray]This landing location cannot be guaranteed.
zone.saltFlats.description = On the outskirts of the desert lie the Salt Flats. Few resources can be found in this location.\n\nThe enemy has erected a resource storage complex here. Eradicate their core. Leave nothing standing. zone.saltFlats.description = On the outskirts of the desert lie the Salt Flats. Few resources can be found in this location.\n\nThe enemy has erected a resource storage complex here. Eradicate their core. Leave nothing standing.
zone.craters.description = Water has accumulated in this crater, relic of the old wars. Reclaim the area. Collect sand. Smelt metaglass. Pump water to cool turrets and drills. zone.craters.description = Water has accumulated in this crater, relic of the old wars. Reclaim the area. Collect sand. Smelt metaglass. Pump water to cool turrets and drills.
@@ -393,8 +393,8 @@ settings.controls = Controles
settings.game = Jogo settings.game = Jogo
settings.sound = Som settings.sound = Som
settings.graphics = Gráficos settings.graphics = Gráficos
settings.cleardata = Data do jogo limpa... settings.cleardata = Apagar dados...
settings.clear.confirm = Certeza que quer limpar a data?\nOque é feito não pode ser desfeito! settings.clear.confirm = Certeza que quer limpar a os dados?\nOque é feito não pode ser desfeito!
settings.clearall.confirm = [scarlet]Aviso![]\nIsso vai limpar toda a data, Incluindo saves, mapas, Keybinds e desbloqueados.\nQuando apertar 'ok' Vai apagar toda a data e sair automaticamente. settings.clearall.confirm = [scarlet]Aviso![]\nIsso vai limpar toda a data, Incluindo saves, mapas, Keybinds e desbloqueados.\nQuando apertar 'ok' Vai apagar toda a data e sair automaticamente.
settings.clearunlocks = Limpar liberados settings.clearunlocks = Limpar liberados
settings.clearall = Limpar tudo settings.clearall = Limpar tudo
@@ -411,7 +411,7 @@ blocks.booster = Booster
block.unknown = [LIGHT_GRAY]??? block.unknown = [LIGHT_GRAY]???
blocks.powercapacity = Capacidade de Energia blocks.powercapacity = Capacidade de Energia
blocks.powershot = Energia/tiro blocks.powershot = Energia/tiro
blocks.damage = Damage blocks.damage = Dano
blocks.targetsair = Mirar no ar blocks.targetsair = Mirar no ar
blocks.targetsground = Mirar no chão blocks.targetsground = Mirar no chão
blocks.itemsmoved = Velocidade de movimento blocks.itemsmoved = Velocidade de movimento
@@ -429,7 +429,7 @@ blocks.repairtime = Tempo de reparo total do bloco
blocks.speedincrease = Aumento de velocidade blocks.speedincrease = Aumento de velocidade
blocks.range = Distancia blocks.range = Distancia
blocks.drilltier = Furaveis blocks.drilltier = Furaveis
blocks.drillspeed = Velocidade da furadeira base blocks.drillspeed = Velocidade da broca base
blocks.boosteffect = Efeito do Boost blocks.boosteffect = Efeito do Boost
blocks.maxunits = Maximo de unidades ativas blocks.maxunits = Maximo de unidades ativas
blocks.health = Saúde blocks.health = Saúde
@@ -438,8 +438,8 @@ blocks.inaccuracy = Imprecisão
blocks.shots = Tiros blocks.shots = Tiros
blocks.reload = Recarregar blocks.reload = Recarregar
blocks.ammo = Munição blocks.ammo = Munição
bar.drilltierreq = Better Drill Required bar.drilltierreq = Broca melhor requerida.
bar.drillspeed = Velocidade da furadeira: {0}/s bar.drillspeed = Velocidade da broca: {0}/s
bar.efficiency = Eficiencia: {0}% bar.efficiency = Eficiencia: {0}%
bar.powerbalance = Energia: {0} bar.powerbalance = Energia: {0}
bar.poweramount = Energia: {0} bar.poweramount = Energia: {0}
@@ -513,15 +513,15 @@ setting.lasers.name = Mostrar lasers
setting.pixelate.name = Pixelizado [LIGHT_GRAY](Pode diminuir a performace) setting.pixelate.name = Pixelizado [LIGHT_GRAY](Pode diminuir a performace)
setting.minimap.name = Mostrar minimapa setting.minimap.name = Mostrar minimapa
setting.musicvol.name = Volume da Música setting.musicvol.name = Volume da Música
setting.ambientvol.name = Ambient Volume setting.ambientvol.name = Volume do ambiente
setting.mutemusic.name = Desligar Música setting.mutemusic.name = Desligar Música
setting.sfxvol.name = Volume de Efeitos setting.sfxvol.name = Volume de Efeitos
setting.mutesound.name = Desligar Som setting.mutesound.name = Desligar Som
setting.crashreport.name = Enviar denuncias de crash anonimas setting.crashreport.name = Enviar denuncias de crash anonimas
setting.savecreate.name = Auto-Create Saves setting.savecreate.name = Auto-Create Saves
setting.chatopacity.name = Opacidade do chat setting.chatopacity.name = Opacidade do chat
setting.playerchat.name = Mostrar chat em-jogo setting.playerchat.name = Mostrar chat em jogo
uiscale.reset = UI scale has been changed.\nPress "OK" to confirm this scale.\n[scarlet]Reverting and exiting in[accent] {0}[] settings... uiscale.reset = A escala da interface do usuário foi mudada.\nPressione "OK" para confirmar esta escala.\n[scarlet]Revertendo e saindo em[accent] {0}[] settings...
uiscale.cancel = Cancel & Exit uiscale.cancel = Cancel & Exit
setting.bloom.name = Bloom setting.bloom.name = Bloom
keybind.title = Refazer teclas keybind.title = Refazer teclas
@@ -687,9 +687,9 @@ block.graphite-press.name = Prensa de grafite
block.multi-press.name = Multi-Prensa block.multi-press.name = Multi-Prensa
block.constructing = {0}\n[LIGHT_GRAY](Construindo) block.constructing = {0}\n[LIGHT_GRAY](Construindo)
block.spawn.name = Spawn dos inimigos block.spawn.name = Spawn dos inimigos
block.core-shard.name = Core: Fragmento block.core-shard.name = Fragmento do núcleo
block.core-foundation.name = Core: Fundação block.core-foundation.name = Fundação do núcleo
block.core-nucleus.name = Core: Nucleus block.core-nucleus.name = Núcleo do núcleo
block.deepwater.name = água funda block.deepwater.name = água funda
block.water.name = Água block.water.name = Água
block.tainted-water.name = Água contaminada block.tainted-water.name = Água contaminada
@@ -770,8 +770,8 @@ block.combustion-generator.name = Gerador de combustão
block.turbine-generator.name = Gerador de Turbina block.turbine-generator.name = Gerador de Turbina
block.differential-generator.name = Gerador diferencial block.differential-generator.name = Gerador diferencial
block.impact-reactor.name = Reator De Impacto block.impact-reactor.name = Reator De Impacto
block.mechanical-drill.name = Furadera Mecânica block.mechanical-drill.name = Broca Mecânica
block.pneumatic-drill.name = Mineradora Pneumatica block.pneumatic-drill.name = Broca Pneumática
block.laser-drill.name = Broca a Laser block.laser-drill.name = Broca a Laser
block.water-extractor.name = Extrator de Agua block.water-extractor.name = Extrator de Agua
block.cultivator.name = Cultivador block.cultivator.name = Cultivador
@@ -824,7 +824,7 @@ block.bridge-conduit.name = Conduto-Ponte
block.rotary-pump.name = Bomba Rotatoria block.rotary-pump.name = Bomba Rotatoria
block.thorium-reactor.name = Reator Torio block.thorium-reactor.name = Reator Torio
block.mass-driver.name = Drive de Massa block.mass-driver.name = Drive de Massa
block.blast-drill.name = Mineradora de Explosão block.blast-drill.name = Broca de Explosão
block.thermal-pump.name = Cano termico block.thermal-pump.name = Cano termico
block.thermal-generator.name = Gerador Térmico block.thermal-generator.name = Gerador Térmico
block.alloy-smelter.name = Fundidora de Liga block.alloy-smelter.name = Fundidora de Liga
@@ -868,13 +868,13 @@ unit.lich.name = Lich
unit.reaper.name = Ceifador unit.reaper.name = Ceifador
tutorial.next = [lightgray]<Tap to continue> tutorial.next = [lightgray]<Tap to continue>
tutorial.intro = You have entered the[scarlet] Mindustry Tutorial.[]\nBegin by[accent] mining copper[]. Tap a copper ore vein near your core to do this.\n\n[accent]{0}/{1} copper tutorial.intro = You have entered the[scarlet] Mindustry Tutorial.[]\nBegin by[accent] mining copper[]. Tap a copper ore vein near your core to do this.\n\n[accent]{0}/{1} copper
tutorial.drill = Minerar manualmente é ineficiente.\n[accent]Mineradoras []podem minerar automaticamente.\nColoque uma numa veia de cobre. tutorial.drill = Minerar manualmente é ineficiente.\n[accent]Brocas []podem minerar automaticamente.\nColoque uma numa veia de cobre.
tutorial.drill.mobile = Mining manually is inefficient.\n[accent]Drills []can mine automatically.\nTap the drill tab in the bottom right.\nSelect the[accent] mechanical drill[].\nPlace it on a copper vein by tapping, then press the[accent] checkmark[] below to confirm your selection.\nPress the[accent] X button[] to cancel placement. tutorial.drill.mobile = Minerar manualmente é ineficiente.\n[accent]Brocas []podem minerar automaticamente.\nToque na aba de brocas no canto inferior direito.\nSelecione a[accent] broca mecânica[].\nToque em um veio de cobre para colocá-la, então pressione a[accent] marca de verificação[] abaixo para confirmar sua seleção.\nPressione o[accent] botão "X"[] para cancelar o posicionamento.
tutorial.blockinfo = Each block has different stats. Each drill can only mine certain ores.\nTo check a block's info and stats,[accent] tap the "?" button while selecting it in the build menu.[]\n\n[accent]Access the Mechanical Drill's stats now.[] tutorial.blockinfo = Cada bloco tem diferentes status. Cada broca pode extrair certos minérios.\nPara checar as informações e os status de um bloco,[accent] toque o botão "?" enquanto o seleciona no menu de construção.[]\n\n[accent]Acesse os status da broca mecânica agora.[]
tutorial.conveyor = [accent]Esteiras[] São usadas para transportar itens até o core.\nFaça uma linha de Esteiras da mineradora até o core. tutorial.conveyor = [accent]Esteiras[] São usadas para transportar itens até o núcleo.\nFaça uma linha de Esteiras da mineradora até o núcleo.
tutorial.conveyor.mobile = [accent]Conveyors[] are used to transport items to the core.\nMake a line of conveyors from the drill to the core.\n[accent] Place in a line by holding down your finger for a few seconds[] and dragging in a direction.\n\n[accent]{0}/{1} conveyors placed in line\n[accent]0/1 items delivered tutorial.conveyor.mobile = [accent]Esteiras[] são usadas para transportar itens até o núcleo.\nFaça uma linha de esteiras da broca até o núcleo.\n[accent] Coloque uma linha segurando por alguns segundos[] e arrastando em uma direção.\n\n[accent]{0}/{1} conveyors placed in line\n[accent]0/1 items delivered
tutorial.turret = Estruturas defensivas devem ser construidas para repelir[LIGHT_GRAY] O inimigo[].\nConstrua uma torre dupla perto de sua base. tutorial.turret = Estruturas defensivas devem ser construidas para repelir[LIGHT_GRAY] O inimigo[].\nConstrua uma torre dupla perto de sua base.
tutorial.drillturret = Torres duplas precisam de[accent] Cobre como munição []Para atirar.\nColoque uma mineradoura Proxima a torre Para carregar ela com cobre minerado. tutorial.drillturret = Torres duplas precisam de[accent] Cobre como munição []Para atirar.\nColoque uma broca próxima à torre para carregá-la com o cobre minerado.
tutorial.pause = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press space to pause. tutorial.pause = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press space to pause.
tutorial.pause.mobile = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press this button in the top left to pause. tutorial.pause.mobile = During battle, you are able to[accent] pause the game.[]\nYou may queue buildings while paused.\n\n[accent]Press this button in the top left to pause.
tutorial.unpause = Now press space again to unpause. tutorial.unpause = Now press space again to unpause.
@@ -883,7 +883,7 @@ tutorial.breaking = Blocks frequently need to be destroyed.\n[accent]Hold down r
tutorial.breaking.mobile = Blocks frequently need to be destroyed.\n[accent]Select deconstruction mode[], then tap a block to begin breaking it.\nDestroy an area by holding down your finger for a few seconds[] and dragging in a direction.\nPress the checkmark button to confirm breaking.\n\n[accent]Destroy all the scrap blocks to the left of your core using area selection. tutorial.breaking.mobile = Blocks frequently need to be destroyed.\n[accent]Select deconstruction mode[], then tap a block to begin breaking it.\nDestroy an area by holding down your finger for a few seconds[] and dragging in a direction.\nPress the checkmark button to confirm breaking.\n\n[accent]Destroy all the scrap blocks to the left of your core using area selection.
tutorial.withdraw = In some situations, taking items directly from blocks is necessary.\nTo do this, [accent]tap a block[] with items in it, then [accent]tap the item[] in the inventory.\nMultiple items can be withdrawn by [accent]tapping and holding[].\n\n[accent]Withdraw some copper from the core.[] tutorial.withdraw = In some situations, taking items directly from blocks is necessary.\nTo do this, [accent]tap a block[] with items in it, then [accent]tap the item[] in the inventory.\nMultiple items can be withdrawn by [accent]tapping and holding[].\n\n[accent]Withdraw some copper from the core.[]
tutorial.deposit = Deposit items into blocks by dragging from your ship to the destination block.\n\n[accent]Deposit your copper back into the core.[] tutorial.deposit = Deposit items into blocks by dragging from your ship to the destination block.\n\n[accent]Deposit your copper back into the core.[]
tutorial.waves = O[LIGHT_GRAY] Inimigo[] se aproxima.\n\nDefenda seu core por 2 ondas. Construa mais torres. tutorial.waves = O[LIGHT_GRAY] Inimigo[] se aproxima.\n\nDefenda seu núcleo por 2 ondas. Construa mais torres.
tutorial.waves.mobile = The[lightgray] enemy[] approaches.\n\nDefend the core for 2 waves. Your ship will automatically fire at enemies.\nBuild more turrets and drills. Mine more copper. tutorial.waves.mobile = The[lightgray] enemy[] approaches.\n\nDefend the core for 2 waves. Your ship will automatically fire at enemies.\nBuild more turrets and drills. Mine more copper.
tutorial.launch = Once you reach a specific wave, you are able to[accent] launch the core[], leaving your defenses behind and[accent] obtaining all the resources in your core.[]\nThese resources can then be used to research new technology.\n\n[accent]Press the launch button. tutorial.launch = Once you reach a specific wave, you are able to[accent] launch the core[], leaving your defenses behind and[accent] obtaining all the resources in your core.[]\nThese resources can then be used to research new technology.\n\n[accent]Press the launch button.
item.copper.description = Um material de estrutura util. Usado extensivamente em Maioria dos blocos. item.copper.description = Um material de estrutura util. Usado extensivamente em Maioria dos blocos.
@@ -915,7 +915,7 @@ mech.javelin-ship.description = Uma nave de espinhos de atacar e correr. Quando
mech.trident-ship.description = Um bombardeiro pesado. Consideravelmente bem armadurado. mech.trident-ship.description = Um bombardeiro pesado. Consideravelmente bem armadurado.
mech.glaive-ship.description = Uma nave armada, bem armadurada. Com um repetidor incendario equipado. Boa aceleração e maxima velocidade. mech.glaive-ship.description = Uma nave armada, bem armadurada. Com um repetidor incendario equipado. Boa aceleração e maxima velocidade.
unit.draug.description = A primitive mining drone. Cheap to produce. Expendable. Automatically mines copper and lead in the vicinity. Delivers mined resources to the closest core. unit.draug.description = A primitive mining drone. Cheap to produce. Expendable. Automatically mines copper and lead in the vicinity. Delivers mined resources to the closest core.
unit.spirit.description = A unidade de drone inicial. Ele nasce no core por padrão. Minera minérios automaticamente, Coleta itens e repara blocos. unit.spirit.description = A unidade de drone inicial. Ele nasce no núcleo por padrão. Minera minérios automaticamente, Coleta itens e repara blocos.
unit.phantom.description = Uma unidade de drone avançada. Minera minérios automaticamente, Coleta itens e repara blocos automaticamente. Significantemente mais efetiva. unit.phantom.description = Uma unidade de drone avançada. Minera minérios automaticamente, Coleta itens e repara blocos automaticamente. Significantemente mais efetiva.
unit.dagger.description = Unidade terrestre basica, Forte em grupos. unit.dagger.description = Unidade terrestre basica, Forte em grupos.
unit.crawler.description = A ground unit consisting of a stripped-down frame with high explosives strapped on top. Not particular durable. Explodes on contact with enemies. unit.crawler.description = A ground unit consisting of a stripped-down frame with high explosives strapped on top. Not particular durable. Explodes on contact with enemies.
@@ -946,8 +946,8 @@ block.power-source.description = Infinitivamente da energia. Apenas caixa de are
block.item-source.description = Infinivamente da itens. Apenas caixa de areia. block.item-source.description = Infinivamente da itens. Apenas caixa de areia.
block.item-void.description = Destroi qualquer item que entre sem requerir energia. Apenas caixa de areia. block.item-void.description = Destroi qualquer item que entre sem requerir energia. Apenas caixa de areia.
block.liquid-source.description = Infinitivamente da Liquidos. Apenas caixa de areia. block.liquid-source.description = Infinitivamente da Liquidos. Apenas caixa de areia.
block.copper-wall.description = Um bloco defensivo e barato.\nUtil para proteger o core e torres no começo. block.copper-wall.description = Um bloco defensivo e barato.\nUtil para proteger o núcleo e torres no começo.
block.copper-wall-large.description = Um bloco defensivo e barato.\nUtil para proteger o core e torres no começo.\nOcupa multiplos espaços. block.copper-wall-large.description = Um bloco defensivo e barato.\nUtil para proteger o núcleo e torres no começo.\nOcupa multiplos espaços.
block.titanium-wall.description = A moderately strong defensive block.\nProvides moderate protection from enemies. block.titanium-wall.description = A moderately strong defensive block.\nProvides moderate protection from enemies.
block.titanium-wall-large.description = A moderately strong defensive block.\nProvides moderate protection from enemies.\nSpans multiple tiles. block.titanium-wall-large.description = A moderately strong defensive block.\nProvides moderate protection from enemies.\nSpans multiple tiles.
block.thorium-wall.description = A strong defensive block.\nBoa proteção contra inimigos. block.thorium-wall.description = A strong defensive block.\nBoa proteção contra inimigos.

View File

@@ -10,17 +10,19 @@ link.trello.description = Trello board 上的官方计划表
link.itch.io.description = PC版下载和网页版(itch.io) link.itch.io.description = PC版下载和网页版(itch.io)
link.google-play.description = 从谷歌商店获取安卓版 link.google-play.description = 从谷歌商店获取安卓版
link.wiki.description = 官方 Mindustry 维基 link.wiki.description = 官方 Mindustry 维基
linkfail = 打开链接失败!\nURL 已经复制到剪贴板。 linkfail = 打开链接失败!\n网址已经复制到剪贴板。
screenshot = 幕截图已放在 {0} screenshot = 幕截图已放在 {0}
screenshot.invalid = 地图太大,可能没有足够的内存用于截图。 screenshot.invalid = 地图太大,可能没有足够的内存用于截图。
gameover = 你的核心被摧毁了! gameover = 你的核心被摧毁了!
gameover.pvp = [accent] {0}[] 队获胜! gameover.pvp = [accent] {0}[]队获胜!
highscore = [accent]新纪录! highscore = [accent]新纪录!
load.sound = 音乐加载中 load.sound = 音乐加载中
load.map = 地图加载中 load.map = 地图加载中
load.image = 图片加载中 load.image = 图片加载中
load.content = 内容加载中 load.content = 内容加载中
load.system = 系统加载中 load.system = 系统加载中
stat.wave = 战胜的波数:[accent]{0} stat.wave = 战胜的波数:[accent]{0}
stat.enemiesDestroyed = 消灭的敌人:[accent]{0} stat.enemiesDestroyed = 消灭的敌人:[accent]{0}
stat.built = 建造的建筑:[accent]{0} stat.built = 建造的建筑:[accent]{0}
@@ -28,6 +30,7 @@ stat.destroyed = 摧毁的建筑:[accent]{0}
stat.deconstructed = 拆除的建筑:[accent]{0} stat.deconstructed = 拆除的建筑:[accent]{0}
stat.delivered = 发射的资源: stat.delivered = 发射的资源:
stat.rank = 最终等级:[accent]{0} stat.rank = 最终等级:[accent]{0}
launcheditems = [accent]发射的资源 launcheditems = [accent]发射的资源
map.delete = 确定要删除 "[accent]{0}[]" 地图吗? map.delete = 确定要删除 "[accent]{0}[]" 地图吗?
level.highscore = 最高分:[accent]{0} level.highscore = 最高分:[accent]{0}
@@ -49,8 +52,17 @@ close = 关闭
website = 官网 website = 官网
quit = 退出 quit = 退出
maps = 地图 maps = 地图
maps.browse = 浏览地图
continue = 继续 continue = 继续
maps.none = [LIGHT_GRAY]没有找到地图! maps.none = [LIGHT_GRAY]没有找到地图!
invalid = 无效
preparingconfig = 正在准备配置
preparingcontent = 正在准备内容
uploadingcontent = 正在上传内容
uploadingpreviewfile = 正在上传预览文件
committingchanges = 提交更改
done = 已完成
about.button = 关于 about.button = 关于
name = 名字: name = 名字:
noname = 先取一个[accent]玩家名[]。 noname = 先取一个[accent]玩家名[]。
@@ -71,32 +83,35 @@ server.kicked.vote = 你被投票踢出了服务器。永别了。
server.kicked.clientOutdated = 客户端过旧,请更新你的游戏。 server.kicked.clientOutdated = 客户端过旧,请更新你的游戏。
server.kicked.serverOutdated = 服务器过旧,请联系房主升级服务器。 server.kicked.serverOutdated = 服务器过旧,请联系房主升级服务器。
server.kicked.banned = 你在这个服务器上被拉入黑名单了。 server.kicked.banned = 你在这个服务器上被拉入黑名单了。
server.kicked.typeMismatch = 此服务器与的不稳定测试版不兼容。 server.kicked.typeMismatch = 此服务器与的不稳定测试版不兼容。
server.kicked.playerLimit = 服务器已满,请等待一个空位。
server.kicked.recentKick = 你刚刚被踢出服务器。\n请稍后重新连接 server.kicked.recentKick = 你刚刚被踢出服务器。\n请稍后重新连接
server.kicked.nameInUse = 你的名字与服务器中的一个人重复了。 server.kicked.nameInUse = 你的名字与服务器中的一个人重复了。
server.kicked.nameEmpty = 无效的名字! server.kicked.nameEmpty = 无效的名字!
server.kicked.idInUse = 你已在这个服务器上!不允许用两个账号连接。 server.kicked.idInUse = 你已在这个服务器上!不允许用两个账号连接。
server.kicked.customClient = 这个服务器不支持定制版本。下载官方版本。 server.kicked.customClient = 这个服务器不支持自定义版本。下载官方版本。
server.kicked.gameover = 游戏结束! server.kicked.gameover = 游戏结束!
server.versions = 客户端版本:[accent] {0}[]\n服务器版本[accent] {1}[] server.versions = 客户端版本:[accent] {0}[]\n服务器版本[accent] {1}[]
host.info = [accent]创建局域网游戏[]按钮会在[scarlet]6567[]端口运行一个服务器。[]\n任何在同一个[LIGHT_GRAY]wifi或本地网络[]下的人应该可以在服务器列表中看到你的服务器。\n\n如果你想让别人在任何地方都能通过IP地址连接你需要设定[accent]端口转发[]。\n\n[LIGHT_GRAY]注意如果某人无法连接到你的局域网游戏请确保你在防火墙设置里允许了Mindustry访问本地网络。 host.info = [accent]创建局域网游戏[]按钮会在[scarlet] 6567 []端口运行一个服务器。[]\n任何在同一个[LIGHT_GRAY] Wi-Fi 或本地网络[]下的人应该可以在服务器列表中看到你的服务器。\n\n如果你想让别人在任何地方都能通过 IP 地址连接,你需要设定[accent]端口转发[]。\n\n[LIGHT_GRAY]注意:如果某人无法连接到你的局域网游戏,请确保你在防火墙设置里允许了 Mindustry 访问本地网络。
join.info = 此时,可以输入[accent]服务器的IP地址[]来连接,或寻找[accent]本地网络[]中的服务器来连接。\n局域网或广域网多人游戏都支持。\n\n[LIGHT_GRAY]注意没有全球服务器列表如果你想通过IP地址连接某个服务器你需要向房主询问IP地址。 join.info = 此时,可以输入[accent]服务器的 IP 地址[]来连接,或寻找[accent]本地网络[]中的服务器来连接。\n局域网或广域网多人游戏都支持。\n\n[LIGHT_GRAY]注意:没有全球服务器列表;如果你想通过 IP 地址连接某个服务器,你需要向房主询问 IP 地址。
hostserver = 创建服务器 hostserver = 创建服务器
invitefriends = 邀请朋友
hostserver.mobile = 创建\n服务器 hostserver.mobile = 创建\n服务器
host = 创建 host = 创建
hosting = [accent]正在打开服务器…… hosting = [accent]正在打开服务器……
hosts.refresh = 刷新 hosts.refresh = 刷新
hosts.discovering = 正在搜索局域网服务器 hosts.discovering = 正在搜索局域网服务器
hosts.discovering.any = 正在搜索服务器
server.refreshing = 正在刷新服务器 server.refreshing = 正在刷新服务器
hosts.none = [lightgray]未发现局域网游戏! hosts.none = [lightgray]未发现局域网游戏!
host.invalid = [scarlet]无法连接服务器。 host.invalid = [scarlet]无法连接服务器。
trace = 跟踪玩家 trace = 跟踪玩家
trace.playername = 玩家名称:[accent]{0} trace.playername = 玩家名称:[accent]{0}
trace.ip = IP地址[accent]{0} trace.ip = IP 地址:[accent]{0}
trace.id = 唯一的ID[accent]{0} trace.id = 唯一的 ID[accent]{0}
trace.mobile = 移动客户端:[accent]{0} trace.mobile = 移动客户端:[accent]{0}
trace.modclient = 定制版客户端:[accent]{0} trace.modclient = 自定义客户端:[accent]{0}
invalidid = 无效的客户端ID提交一个错误报告。 invalidid = 无效的客户端 ID提交一个错误报告。
server.bans = 黑名单 server.bans = 黑名单
server.bans.none = 没有被拉黑的玩家! server.bans.none = 没有被拉黑的玩家!
server.admins = 管理员 server.admins = 管理员
@@ -107,16 +122,21 @@ server.edit = 编辑服务器
server.outdated = [crimson]服务器过旧![] server.outdated = [crimson]服务器过旧![]
server.outdated.client = [crimson]客户端过旧![] server.outdated.client = [crimson]客户端过旧![]
server.version = [lightgray]版本:{0} {1} server.version = [lightgray]版本:{0} {1}
server.custombuild = [yellow]定制版 server.custombuild = [yellow]自定义
confirmban = 确认拉黑这名玩家? confirmban = 确认拉黑这名玩家?
confirmkick = 确定踢这名玩家? confirmkick = 确定踢这名玩家?
confirmvotekick = 确定投票踢出这名玩家?
confirmunban = 确定取消拉黑这名玩家? confirmunban = 确定取消拉黑这名玩家?
confirmadmin = 确定给予这名玩家管理员权限? confirmadmin = 确定给予这名玩家管理员权限?
confirmunadmin = 确定取消这名玩家的管理员权限? confirmunadmin = 确定取消这名玩家的管理员权限?
joingame.title = 加入游戏 joingame.title = 加入游戏
joingame.ip = 地址: joingame.ip = 地址:
disconnect = 已断开 disconnect = 已断开
disconnect.data = 读取世界数据失败! disconnect.error = 连接错误。
disconnect.closed = 连接关闭。
disconnect.timeout = 连接超时。
disconnect.data = 读取服务器数据失败!
cantconnect = 无法加入([accent]{0}[])。
connecting = [accent]连接中…… connecting = [accent]连接中……
connecting.data = [accent]加载中…… connecting.data = [accent]加载中……
server.port = 端口: server.port = 端口:
@@ -142,22 +162,24 @@ save.rename = 重命名
save.rename.text = 新名称: save.rename.text = 新名称:
selectslot = 选择一个存档。 selectslot = 选择一个存档。
slot = [accent]存档位 {0} slot = [accent]存档位 {0}
save.corrupted = [accent]存档损坏或无效!\n如果你刚刚升级了游戏那么这可能是因为存档格式改变了而[scarlet]不是[]bug 。 save.corrupted = [accent]存档损坏或无效!\n如果你刚刚升级了游戏那么这可能是因为存档格式改变了而[scarlet]不是[] bug 。
empty = <> empty = <>
on = on =
off = off =
save.autosave = 自动保存:{0} save.autosave = 自动保存:{0}
save.map = 地图:{0} save.map = 地图:{0}
save.wave = 波次 {0} save.wave = 波次{0}
save.mode = 模式:{0}
save.difficulty = 难度:{0} save.difficulty = 难度:{0}
save.date = 最后保存:{0} save.date = 最后保存:{0}
save.playtime = 游戏时间:{0} save.playtime = 游戏时间:{0}
warning = 警告! warning = 警告!
confirm = 确认 confirm = 确认
delete = 删除 delete = 删除
view.workshop = 浏览创意工坊
ok = 确定 ok = 确定
open = 打开 open = 打开
customize = 定制 customize = 自定义
cancel = 取消 cancel = 取消
openlink = 打开链接 openlink = 打开链接
copylink = 复制链接 copylink = 复制链接
@@ -166,14 +188,14 @@ data.export = 导出数据
data.import = 导入数据 data.import = 导入数据
data.exported = 数据已导入。 data.exported = 数据已导入。
data.invalid = 非有效游戏数据。 data.invalid = 非有效游戏数据。
data.import.confirm = 导入外部游戏数据覆盖本地[scarlet]全部[]游戏数据。\n[accent]此操作无法撤销![]\n\n数据导入后将自动退出游戏。 data.import.confirm = 导入外部游戏数据覆盖本地[scarlet]全部[]游戏数据。\n[accent]此操作无法撤销![]\n\n数据导入后将自动退出游戏。
classic.export = 导出老版本数据 classic.export = 导出老版本数据
classic.export.text = [accent]Mindustry []有了一个重要的更新。\n检测到此为老版本(v3.5 build 40)的存档或地图。是否要将这些保存导出到手机的主文件夹中,以便在 Mindustry 老版本应用程序中使用? classic.export.text = [accent]Mindustry []已经有了一个重要的更新。\n检测到此为老版本(v3.5 build 40)的存档或地图。是否要将这些保存导出到手机的主文件夹中,以便在 Mindustry 老版本应用程序中使用?
quit.confirm = 确定退出? quit.confirm = 确定退出?
quit.confirm.tutorial = 你确定不玩教程就开始游戏\n教程可以通过[accent]设置->游戏->重新游玩教程[]来再次游玩。 quit.confirm.tutorial = 你确定要跳过教程\n教程可以通过[accent]设置->游戏->重新游玩教程[]来再次游玩。
loading = [accent]老滑稽祈祷中…… loading = [accent]加载中……
saving = [accent]保存中…… saving = [accent]保存中……
wave = [accent]波次 {0} wave = [accent]波次{0}
wave.waiting = [LIGHT_GRAY]下一波将在{0}秒后到来 wave.waiting = [LIGHT_GRAY]下一波将在{0}秒后到来
wave.waveInProgress = [LIGHT_GRAY]波次进行中 wave.waveInProgress = [LIGHT_GRAY]波次进行中
waiting = [LIGHT_GRAY]等待中…… waiting = [LIGHT_GRAY]等待中……
@@ -187,10 +209,15 @@ custom = 自定义
builtin = 内建的 builtin = 内建的
map.delete.confirm = 你确定你想要删除这张地图吗?这个操作无法撤销! map.delete.confirm = 你确定你想要删除这张地图吗?这个操作无法撤销!
map.random = [accent]随机地图 map.random = [accent]随机地图
map.nospawn = 这个地图没有核心!请在编辑器中添加一个[ROYAL]蓝色[]的核心。 map.nospawn = 这个地图没有核心!请在编辑器中添加一个[ROYAL]己方[]的核心。
map.nospawn.pvp = 这个地图没有敌人的核心!请在编辑器中添加一个[ROYAL]红色[]的核心。 map.nospawn.pvp = 这个地图没有敌人的核心!请在编辑器中添加一个[ROYAL]敌方[]的核心。
map.nospawn.attack = 这个地图没有敌人的核心!请在编辑中向地图添加一个[SCARLET]红色[]的核心。 map.nospawn.attack = 这个地图没有敌人的核心!请在编辑中向地图添加一个[SCARLET]敌方[]的核心。
map.invalid = 地图载入错误:地图文件可能已经损坏。 map.invalid = 地图载入错误:地图文件可能已经损坏。
map.publish.error = 地图上传错误:{0}
map.publish.confirm = 确定上传此地图?\n\n[lightgray]确定你同意 Steam 创意工坊的最终用户许可协议,否则你的地图将不会被展示!
eula = Steam 最终用户许可协议
map.publish = 地图已上传。
map.publishing = [accent]地图上传中……
editor.brush = 笔刷 editor.brush = 笔刷
editor.openin = 在编辑器中打开 editor.openin = 在编辑器中打开
editor.oregen = 矿石的生成 editor.oregen = 矿石的生成
@@ -198,14 +225,17 @@ editor.oregen.info = 矿石的生成:
editor.mapinfo = 地图信息 editor.mapinfo = 地图信息
editor.author = 作者: editor.author = 作者:
editor.description = 描述: editor.description = 描述:
editor.nodescription = 地图必须要有不少于4个字符的描述才能上传。
editor.waves = 波数: editor.waves = 波数:
editor.rules = 规则: editor.rules = 规则:
editor.generation = 筛选器: editor.generation = 筛选器:
editor.ingame = 游戏内编辑 editor.ingame = 游戏内编辑
editor.publish.workshop = 上传到创意工坊
editor.newmap = 新地图 editor.newmap = 新地图
workshop = 创意工坊
waves.title = 波数 waves.title = 波数
waves.remove = 移除 waves.remove = 移除
waves.never = <永不> waves.never = < 无限 >
waves.every = waves.every =
waves.waves = waves.waves =
waves.perspawn = 每次生成 waves.perspawn = 每次生成
@@ -219,6 +249,7 @@ waves.invalid = 剪贴板中无效的波次信息。
waves.copied = 波次信息已复制。 waves.copied = 波次信息已复制。
waves.none = 无自定义敌人。\n请注意空布局将自动替换为默认布局。 waves.none = 无自定义敌人。\n请注意空布局将自动替换为默认布局。
editor.default = [LIGHT_GRAY]<默认> editor.default = [LIGHT_GRAY]<默认>
details = 详情……
edit = 编辑…… edit = 编辑……
editor.name = 名称: editor.name = 名称:
editor.spawn = 生成单位 editor.spawn = 生成单位
@@ -228,8 +259,9 @@ editor.errorload = 读取文件时出现错误:\n[accent]{0}
editor.errorsave = 保存文件时出现错误:\n[accent]{0} editor.errorsave = 保存文件时出现错误:\n[accent]{0}
editor.errorimage = 这是一幅画,不是地图。不要更改文件的扩展名来让他工作。\n\n如果你想导入地图请在编辑器中使用“导入地图”这一按钮。 editor.errorimage = 这是一幅画,不是地图。不要更改文件的扩展名来让他工作。\n\n如果你想导入地图请在编辑器中使用“导入地图”这一按钮。
editor.errorlegacy = 此地图太旧,而旧的地图格式不再受支持了。 editor.errorlegacy = 此地图太旧,而旧的地图格式不再受支持了。
editor.errornot = 这不是地图文件。
editor.errorheader = 此地图文件已失效或损坏。 editor.errorheader = 此地图文件已失效或损坏。
editor.errorname = 地图没有被定义的名称。 editor.errorname = 地图没有被定义的名称。你是否在尝试加载存档文件?
editor.update = 更新 editor.update = 更新
editor.randomize = 随机化 editor.randomize = 随机化
editor.apply = 应用 editor.apply = 应用
@@ -260,7 +292,9 @@ editor.resizemap = 调整地图大小
editor.mapname = 地图名称: editor.mapname = 地图名称:
editor.overwrite = [accent]警告!\n这将会覆盖一个已经存在的地图。 editor.overwrite = [accent]警告!\n这将会覆盖一个已经存在的地图。
editor.overwrite.confirm = [scarlet]警告![]存在同名地图。你确定你想要覆盖? editor.overwrite.confirm = [scarlet]警告![]存在同名地图。你确定你想要覆盖?
editor.exists = 已经存在同名地图。
editor.selectmap = 选择一个地图加载: editor.selectmap = 选择一个地图加载:
toolmode.replace = 替换 toolmode.replace = 替换
toolmode.replace.description = 仅在实心块上绘制。 toolmode.replace.description = 仅在实心块上绘制。
toolmode.replaceall = 全部替换 toolmode.replaceall = 全部替换
@@ -275,37 +309,39 @@ toolmode.fillteams = 填充团队
toolmode.fillteams.description = 填充团队而不是方块。 toolmode.fillteams.description = 填充团队而不是方块。
toolmode.drawteams = 绘制团队 toolmode.drawteams = 绘制团队
toolmode.drawteams.description = 绘制团队而不是方块。 toolmode.drawteams.description = 绘制团队而不是方块。
filters.empty = [LIGHT_GRAY]没有筛选器!用下方的按钮添加一个。 filters.empty = [LIGHT_GRAY]没有筛选器!用下方的按钮添加一个。
filter.distort = Distort filter.distort = 扭曲程度
filter.noise = Noise filter.noise = 波动程度
filter.median = Median filter.median = 平均数
filter.oremedian = Ore Median filter.oremedian = 矿石平均数
filter.blend = Blend filter.blend = 混合程度
filter.defaultores = Default Ores filter.defaultores = 默认矿石
filter.ore = Ore filter.ore = 矿石
filter.rivernoise = River Noise filter.rivernoise = 河流波动程度
filter.mirror = Mirror filter.mirror = 镜像
filter.clear = Clear filter.clear = 清理
filter.option.ignore = Ignore filter.option.ignore = 忽略
filter.scatter = Scatter filter.scatter = 分散程度
filter.terrain = Terrain filter.terrain = 地形
filter.option.scale = Scale filter.option.scale = 规模大小
filter.option.chance = Chance filter.option.chance = 几率大小
filter.option.mag = Magnitude filter.option.mag = 巨大程度
filter.option.threshold = Threshold filter.option.threshold = 最大阈值
filter.option.circle-scale = Circle Scale filter.option.circle-scale = 圆规模
filter.option.octaves = Octaves filter.option.octaves = 递增
filter.option.falloff = Falloff filter.option.falloff = 递减
filter.option.angle = Angle filter.option.angle = 角度大小
filter.option.block = Block filter.option.block = 方块
filter.option.floor = Floor filter.option.floor = 地面
filter.option.flooronto = Target Floor filter.option.flooronto = 地面目标
filter.option.wall = Wall filter.option.wall =
filter.option.ore = Ore filter.option.ore = 矿石
filter.option.floor2 = Secondary Floor filter.option.floor2 = 二重地面
filter.option.threshold2 = Secondary Threshold filter.option.threshold2 = 二重阈值
filter.option.radius = Radius filter.option.radius = 半径大小
filter.option.percentile = Percentile filter.option.percentile = 百分比
width = 宽度: width = 宽度:
height = 高度: height = 高度:
menu = 菜单 menu = 菜单
@@ -323,9 +359,10 @@ tutorial.retake = 重新游玩教程
editor = 编辑器 editor = 编辑器
mapeditor = 地图编辑器 mapeditor = 地图编辑器
donate = 打赏 donate = 打赏
abandon = 放弃 abandon = 放弃
abandon.text = 这个区域和它的所有资源会被敌人重置。 abandon.text = 这个区域及其资源会被敌人重置。
locked = 锁定 locked = 已锁定
complete = [LIGHT_GRAY]完成: complete = [LIGHT_GRAY]完成:
zone.requirement = 在{1}中达到{0}波 zone.requirement = 在{1}中达到{0}波
resume = 暂停:\n[LIGHT_GRAY]{0} resume = 暂停:\n[LIGHT_GRAY]{0}
@@ -339,6 +376,7 @@ launch.skip.confirm = 如果你现在跳过,在后来的波次前你将无法
uncover = 解锁 uncover = 解锁
configure = 设定发射资源数量 configure = 设定发射资源数量
configure.locked = [LIGHT_GRAY]到达第 {0} 波\n才能设定发射资源。 configure.locked = [LIGHT_GRAY]到达第 {0} 波\n才能设定发射资源。
configure.invalid = 数量必须是0到{0}之间的数字。
zone.unlocked = [LIGHT_GRAY]{0} 已解锁。 zone.unlocked = [LIGHT_GRAY]{0} 已解锁。
zone.requirement.complete = 已达到第{0}波。\n达到解锁{1}的需求。 zone.requirement.complete = 已达到第{0}波。\n达到解锁{1}的需求。
zone.config.complete = 已达到第{0}波。\n允许携带发射的资源进入此地区。 zone.config.complete = 已达到第{0}波。\n允许携带发射的资源进入此地区。
@@ -348,6 +386,7 @@ zone.objective.survival = 生存
zone.objective.attack = 摧毁敌方核心 zone.objective.attack = 摧毁敌方核心
add = 添加…… add = 添加……
boss.health = BOSS 生命值 boss.health = BOSS 生命值
connectfail = [crimson]服务器连接失败:[accent]{0} connectfail = [crimson]服务器连接失败:[accent]{0}
error.unreachable = 服务器无法访问。 error.unreachable = 服务器无法访问。
error.invalidaddress = 地址无效。 error.invalidaddress = 地址无效。
@@ -358,6 +397,7 @@ error.mapnotfound = 找不到地图文件!
error.io = 网络 I/O 错误。 error.io = 网络 I/O 错误。
error.any = 未知网络错误。 error.any = 未知网络错误。
error.bloom = 未能初始化特效。\n您的设备可能不支持它。 error.bloom = 未能初始化特效。\n您的设备可能不支持它。
zone.groundZero.name = 零号地区 zone.groundZero.name = 零号地区
zone.desertWastes.name = 荒芜沙漠 zone.desertWastes.name = 荒芜沙漠
zone.craters.name = 陨石带 zone.craters.name = 陨石带
@@ -372,20 +412,22 @@ zone.saltFlats.name = 盐碱荒滩
zone.impact0078.name = 0078号冲击 zone.impact0078.name = 0078号冲击
zone.crags.name = 悬崖 zone.crags.name = 悬崖
zone.fungalPass.name = 真菌通道 zone.fungalPass.name = 真菌通道
zone.groundZero.description = 重新开始的最佳位置。敌人威胁很小,资源少。\n尽可能收集多的铅和铜。\n行动。
zone.groundZero.description = 重新开始的最佳位置。这儿敌人威胁很小,资源少。\n尽可能收集多的铅和铜。\n行动。
zone.frozenForest.description = 即使在这里,靠近山脉的地方,孢子也已经扩散。寒冷的温度不可能永远容纳它们。\n\n此行动须投入电力。建造燃烧发电机并学会使用修理者。 zone.frozenForest.description = 即使在这里,靠近山脉的地方,孢子也已经扩散。寒冷的温度不可能永远容纳它们。\n\n此行动须投入电力。建造燃烧发电机并学会使用修理者。
zone.desertWastes.description = 这些废物是巨大的,不可预测,并且与废弃的结构交错在一起。燃烧它以获取动力或合成石墨。\n\n[lightgray]无法保证此着陆位置。 zone.desertWastes.description = 这些废料规模巨大,难以预测,并且与废弃的结构交错在一起。\n此地区有煤矿存在燃烧它以获取动力或合成石墨。\n\n[lightgray]无法保证此着陆位置。
zone.saltFlats.description = 在沙漠的郊区有盐滩。在这个地方几乎找不到资源。\n\n敌人在这里建立了一个资源存储区。根除他们的核心。不要留下任何东西。 zone.saltFlats.description = 在沙漠的郊区有盐滩。在这个地方几乎找不到资源。\n\n敌人在这里建立了一个资源存储区。摧毁他们的核心。不要留下任何东西。
zone.craters.description = 水在这个火山口积聚,这是旧战争的遗迹。夺下该区域。收集沙子来冶炼玻璃。用水泵抽水冷却炮塔和钻头。 zone.craters.description = 水在这个火山口积聚,这是旧战争的遗迹。夺下该区域。收集沙子来冶炼玻璃。用水泵抽水来加速炮塔和钻头。
zone.ruinousShores.description = 穿过荒地,就是海岸线。曾经这个地方安置了一个海岸防御阵列。现在剩下的不多了,只有最基本的防御结构仍然毫发无损,其他一切都被毁了。\n继续向外扩展。继续研究科技。 zone.ruinousShores.description = 穿过荒地,就是海岸线。这个地方曾经建造了一个海岸防御线。但现在所剩无几,只有最基本的防御结构仍然毫发无损,其他一切都被毁了。\n继续向外扩展。继续研究科技。
zone.stainedMountains.description = 在更远的内陆地区是山脉,但没有被孢子污染。\n在这一地区分布着丰富的钛学习如何使用它。\n\n这里敌人的存在更大。不要给他们时间派出最强的部队。 zone.stainedMountains.description = 在更远的内陆地区是山脉,但这里没有被孢子污染。\n在这一地区分布着丰富的钛学习如何使用它。\n\n这里敌人的存在更大。不要给他们时间派出最强的部队。
zone.overgrowth.description = 这个地区靠近孢子的来源,生长过度。\n敌人在这里建立了一个前哨站。建造尖刀单位来摧毁它并找回丢失的东西。 zone.overgrowth.description = 这个地区靠近孢子的来源,因此生长过度。\n敌人在这里建立了一个前哨站。建造尖刀单位来摧毁它并找回丢失的东西。
zone.tarFields.description = 位于山脉和沙漠之间的产油区的郊区是少数几个有可用油储量的地区之一。\n尽管被废弃但附近仍有一些危险的敌军。不要低估它们。\n\n[lightgray]如果可能,研究石油加工技术。 zone.tarFields.description = 位于山脉和沙漠之间的产油区的郊区是少数几个有可用油储量的地区之一。\n尽管被废弃但附近仍有一些危险的敌军。不要低估它们。\n\n[lightgray]如果可能,研究石油加工技术。
zone.desolateRift.description = 非常危险的区域。资源丰富但空间小。破坏风险高。尽快离开,不要被敌人的攻击间隔太长所愚弄。 zone.desolateRift.description = 非常危险的区域。这儿资源丰富但空间小。敌人十分危险。尽快离开,不要被敌人的攻击间隔太长所愚弄。
zone.nuclearComplex.description = 以前生产和加工钍的设施已变成废墟。\n[lightgray]研究钍及其多种用途。\n\n敌人在这里大量存在不断侦察入侵者。 zone.nuclearComplex.description = 以前生产和加工钍的设施已变成废墟。\n[lightgray]研究钍及其多种用途。\n\n敌人在这里大量存在不断消灭入侵者。
zone.fungalPass.description = 介于高山和低矮孢子丛生的土地之间的过渡地带。这里有一个小型的敌方侦察基地。\n侦察它。\n使用尖刀和爬行者单位来消灭两个核心。 zone.fungalPass.description = 介于高山和低矮孢子丛生的土地之间的过渡地带。这里有一个小型的敌方侦察基地。\n侦察它。\n使用尖刀和爬行者单位来摧毁两个核心。
zone.impact0078.description = <在此处插入说明> zone.impact0078.description = <在此处插入说明>
zone.crags.description = <在此处插入说明> zone.crags.description = <在此处插入说明>
settings.language = 语言 settings.language = 语言
settings.data = 游戏数据 settings.data = 游戏数据
settings.reset = 恢复默认 settings.reset = 恢复默认
@@ -435,22 +477,27 @@ blocks.boosteffect = 加成影响
blocks.maxunits = 最大单位数量 blocks.maxunits = 最大单位数量
blocks.health = 生命值 blocks.health = 生命值
blocks.buildtime = 建造时间 blocks.buildtime = 建造时间
blocks.buildcost = 建造花费
blocks.inaccuracy = 误差 blocks.inaccuracy = 误差
blocks.shots = 每秒发射数 blocks.shots = 每秒发射数
blocks.reload = 重新装弹 blocks.reload = 重新装弹
blocks.ammo = 子弹 blocks.ammo = 子弹
bar.drilltierreq = 需要更好的钻头 bar.drilltierreq = 需要更好的钻头
bar.drillspeed = 挖掘速度:{0}/s bar.drillspeed = 挖掘速度:{0}/s
bar.efficiency = 效率:{0}% bar.efficiency = 效率:{0}%
bar.powerbalance = 能量:{0} bar.powerbalance = 能量:{0}/秒
bar.powerstored = 储能:{0}/{1}
bar.poweramount = 能量:{0} bar.poweramount = 能量:{0}
bar.poweroutput = 能量输出:{0} bar.poweroutput = 能量输出:{0}
bar.items = 物体:{0} bar.items = 物体:{0}
bar.capacity = 容量:{0}
bar.liquid = 液体 bar.liquid = 液体
bar.heat = 热量 bar.heat = 热量
bar.power = 电力 bar.power = 电力
bar.progress = 制造进度 bar.progress = 制造进度
bar.spawned = 单位数量:{0}/{1} bar.spawned = 单位数量:{0}/{1}
bullet.damage = [stat]{0}[lightgray] 伤害 bullet.damage = [stat]{0}[lightgray] 伤害
bullet.splashdamage = [stat]{0}[lightgray] 范围伤害 ~[stat] {1}[lightgray] 格 bullet.splashdamage = [stat]{0}[lightgray] 范围伤害 ~[stat] {1}[lightgray] 格
bullet.incendiary = [stat] 燃烧 bullet.incendiary = [stat] 燃烧
@@ -462,6 +509,7 @@ bullet.freezing = [stat] 冰冻
bullet.tarred = [stat] 减速 bullet.tarred = [stat] 减速
bullet.multiplier = [stat]{0}[lightgray]x 子弹数量 bullet.multiplier = [stat]{0}[lightgray]x 子弹数量
bullet.reload = [stat]{0}[lightgray]x 装弹 bullet.reload = [stat]{0}[lightgray]x 装弹
unit.blocks = 方块 unit.blocks = 方块
unit.powersecond = 能量单位/秒 unit.powersecond = 能量单位/秒
unit.liquidsecond = 液体单位/秒 unit.liquidsecond = 液体单位/秒
@@ -483,13 +531,14 @@ category.shooting = 发射
category.optional = 可选的增强物品 category.optional = 可选的增强物品
setting.landscape.name = 锁定横屏 setting.landscape.name = 锁定横屏
setting.shadows.name = 影子 setting.shadows.name = 影子
setting.linear.name = 光滑贴图 setting.linear.name = 抗锯齿
setting.animatedwater.name = 流动的水 setting.animatedwater.name = 流动的水
setting.animatedshields.name = 动态画面 setting.animatedshields.name = 动态画面
setting.antialias.name = 抗锯齿[LIGHT_GRAY](需要重新启动)[] setting.antialias.name = 抗锯齿[LIGHT_GRAY](需要重新启动)[]
setting.indicators.name = 队友指示器 setting.indicators.name = 队友指示器
setting.autotarget.name = 自动射击 setting.autotarget.name = 自动射击
setting.keyboard.name = 鼠标+键盘操控 setting.keyboard.name = 鼠标+键盘操控
setting.touchscreen.name = 触屏操控
setting.fpscap.name = 最大FPS setting.fpscap.name = 最大FPS
setting.fpscap.none = setting.fpscap.none =
setting.fpscap.text = {0} FPS setting.fpscap.text = {0} FPS
@@ -520,6 +569,7 @@ setting.sfxvol.name = 音效音量
setting.mutesound.name = 静音 setting.mutesound.name = 静音
setting.crashreport.name = 发送匿名崩溃报告 setting.crashreport.name = 发送匿名崩溃报告
setting.savecreate.name = 自动创建存档 setting.savecreate.name = 自动创建存档
setting.publichost.name = 公共游戏旁观
setting.chatopacity.name = 聊天界面透明度 setting.chatopacity.name = 聊天界面透明度
setting.playerchat.name = 显示游戏内聊天界面 setting.playerchat.name = 显示游戏内聊天界面
uiscale.reset = UI缩放比例已经改变。\n按下“确定”来确定缩放比例\n[accent]{0}[]秒后[scarlet]退出并恢复设定。 uiscale.reset = UI缩放比例已经改变。\n按下“确定”来确定缩放比例\n[accent]{0}[]秒后[scarlet]退出并恢复设定。
@@ -573,6 +623,7 @@ mode.pvp.description = 和本地玩家对战。
mode.attack.name = 攻击 mode.attack.name = 攻击
mode.attack.description = 没有波数,但是有摧毁敌人基地的任务。 mode.attack.description = 没有波数,但是有摧毁敌人基地的任务。
mode.custom = 自定义模式 mode.custom = 自定义模式
rules.infiniteresources = 无限资源 rules.infiniteresources = 无限资源
rules.wavetimer = 波次计时器 rules.wavetimer = 波次计时器
rules.waves = 波次 rules.waves = 波次
@@ -590,7 +641,7 @@ rules.wavespacing = 波次间隔时间:[LIGHT_GRAY](秒)
rules.buildcostmultiplier = 建设花费倍数 rules.buildcostmultiplier = 建设花费倍数
rules.buildspeedmultiplier = 建设时间倍数 rules.buildspeedmultiplier = 建设时间倍数
rules.waitForWaveToEnd = 等待敌人时间 rules.waitForWaveToEnd = 等待敌人时间
rules.dropzoneradius = 敌人出生点毁灭大小:[LIGHT_GRAY](格) rules.dropzoneradius = 敌人出生点毁灭大小[LIGHT_GRAY](格)
rules.respawns = 每波最大重生次数 rules.respawns = 每波最大重生次数
rules.limitedRespawns = 重生限制次数 rules.limitedRespawns = 重生限制次数
rules.title.waves = 波次 rules.title.waves = 波次
@@ -599,6 +650,7 @@ rules.title.resourcesbuilding = 资源和建造
rules.title.player = 玩家 rules.title.player = 玩家
rules.title.enemy = 敌人 rules.title.enemy = 敌人
rules.title.unit = 单位 rules.title.unit = 单位
content.item.name = 物品 content.item.name = 物品
content.liquid.name = 液体 content.liquid.name = 液体
content.unit.name = 部队 content.unit.name = 部队
@@ -651,7 +703,7 @@ item.radioactivity = [LIGHT_GRAY]放射性:{0}
unit.health = [LIGHT_GRAY]生命值:{0} unit.health = [LIGHT_GRAY]生命值:{0}
unit.speed = [LIGHT_GRAY]速度:{0} unit.speed = [LIGHT_GRAY]速度:{0}
mech.weapon = [LIGHT_GRAY]武器:{0} mech.weapon = [LIGHT_GRAY]武器:{0}
mech.health = [LIGHT_GRAY]生命值: {0} mech.health = [LIGHT_GRAY]生命值:{0}
mech.itemcapacity = [LIGHT_GRAY]物品容量:{0} mech.itemcapacity = [LIGHT_GRAY]物品容量:{0}
mech.minespeed = [LIGHT_GRAY]采矿速度:{0} mech.minespeed = [LIGHT_GRAY]采矿速度:{0}
mech.minepower = [LIGHT_GRAY]采矿力量:{0} mech.minepower = [LIGHT_GRAY]采矿力量:{0}
@@ -660,6 +712,7 @@ mech.buildspeed = [LIGHT_GRAY]建造速度:{0}%
liquid.heatcapacity = [LIGHT_GRAY]热容量:{0} liquid.heatcapacity = [LIGHT_GRAY]热容量:{0}
liquid.viscosity = [LIGHT_GRAY]粘度:{0} liquid.viscosity = [LIGHT_GRAY]粘度:{0}
liquid.temperature = [LIGHT_GRAY]温度:{0} liquid.temperature = [LIGHT_GRAY]温度:{0}
block.sand-boulder.name = 沙砂巨石 block.sand-boulder.name = 沙砂巨石
block.grass.name = 草地 block.grass.name = 草地
block.salt.name = 盐碱地 block.salt.name = 盐碱地
@@ -683,9 +736,6 @@ block.scrap-wall-large.name = 大型废墙
block.scrap-wall-huge.name = 巨型废墙 block.scrap-wall-huge.name = 巨型废墙
block.scrap-wall-gigantic.name = 超巨型废墙 block.scrap-wall-gigantic.name = 超巨型废墙
block.thruster.name = 助力器 block.thruster.name = 助力器
block.kiln.name = 熔炉
block.graphite-press.name = 石墨压缩机
block.multi-press.name = 多重压缩机
block.constructing = {0}\n[LIGHT_GRAY](建造中) block.constructing = {0}\n[LIGHT_GRAY](建造中)
block.spawn.name = 敌人出生点 block.spawn.name = 敌人出生点
block.core-shard.name = 小型核心 block.core-shard.name = 小型核心
@@ -715,10 +765,10 @@ block.pine.name = 松树
block.white-tree-dead.name = 枯萎的白树 block.white-tree-dead.name = 枯萎的白树
block.white-tree.name = 白树 block.white-tree.name = 白树
block.spore-cluster.name = 孢子簇 block.spore-cluster.name = 孢子簇
block.metal-floor.name = 金属地板 block.metal-floor.name = 金属地板1
block.metal-floor-2.name = 金属地板2 block.metal-floor-2.name = 金属地板2
block.metal-floor-3.name = 金属地板3 block.metal-floor-3.name = 金属地板3
block.metal-floor-5.name = 金属地板5 block.metal-floor-5.name = 金属地板4
block.metal-floor-damaged.name = 损坏的金属地板 block.metal-floor-damaged.name = 损坏的金属地板
block.dark-panel-1.name = 暗面板1 block.dark-panel-1.name = 暗面板1
block.dark-panel-2.name = 暗面板2 block.dark-panel-2.name = 暗面板2
@@ -731,6 +781,27 @@ block.ignarock.name = 伊格纳石头
block.hotrock.name = 热石头 block.hotrock.name = 热石头
block.magmarock.name = 岩浆石头 block.magmarock.name = 岩浆石头
block.cliffs.name = 悬崖 block.cliffs.name = 悬崖
block.duo.name = 双管炮
block.scorch.name = 火焰炮
block.scatter.name = 分裂炮
block.arc.name = 电弧
block.hail.name = 冰雹炮
block.lancer.name = 蓝瑟炮
block.wave.name = 波浪
block.swarmer.name = 蜂群
block.salvo.name = 齐射炮
block.ripple.name = 浪涌
block.cyclone.name = 气旋炮
block.fuse.name = 融合炮
block.spectre.name = 幽灵
block.meltdown.name = 熔毁
block.mechanical-drill.name = 机械钻头
block.pneumatic-drill.name = 气动钻头
block.laser-drill.name = 激光钻头
block.blast-drill.name = 爆破钻头
block.water-extractor.name = 抽水机
block.cultivator.name = 培养机
block.oil-extractor.name = 石油钻井
block.copper-wall.name = 铜墙 block.copper-wall.name = 铜墙
block.copper-wall-large.name = 大型铜墙 block.copper-wall-large.name = 大型铜墙
block.titanium-wall.name = 钛墙 block.titanium-wall.name = 钛墙
@@ -739,13 +810,10 @@ block.phase-wall.name = 相织布墙
block.phase-wall-large.name = 大型相织布墙 block.phase-wall-large.name = 大型相织布墙
block.thorium-wall.name = 钍墙 block.thorium-wall.name = 钍墙
block.thorium-wall-large.name = 大型钍墙 block.thorium-wall-large.name = 大型钍墙
block.surge-wall.name = 波动墙
block.surge-wall-large.name = 大型波动墙
block.door.name = block.door.name =
block.door-large.name = 大门 block.door-large.name = 大门
block.duo.name = 双管炮
block.scorch.name = 火焰炮
block.scatter.name = 分裂炮
block.hail.name = 冰雹炮
block.lancer.name = 蓝瑟炮
block.conveyor.name = 传送带 block.conveyor.name = 传送带
block.titanium-conveyor.name = 钛传送带 block.titanium-conveyor.name = 钛传送带
block.junction.name = 连接点 block.junction.name = 连接点
@@ -753,15 +821,28 @@ block.router.name = 路由器
block.distributor.name = 分配器 block.distributor.name = 分配器
block.sorter.name = 分类器 block.sorter.name = 分类器
block.overflow-gate.name = 溢流门 block.overflow-gate.name = 溢流门
block.phase-conveyor.name = 相织布传送带桥
block.bridge-conveyor.name = 传送带桥
block.armored-conveyor.name = 装甲传送带
block.armored-conveyor.description = 向钛传送带一样运物品,但有更好的装甲。除其他传送带,不接受任何边的输入。
block.kiln.name = 熔炉
block.graphite-press.name = 石墨压缩机
block.multi-press.name = 多重压缩机
block.mass-driver.name = 质量驱动器
block.silicon-smelter.name = 硅冶炼厂 block.silicon-smelter.name = 硅冶炼厂
block.phase-weaver.name = 相织布编织器 block.phase-weaver.name = 相织布编织器
block.pulverizer.name = 粉碎机 block.pulverizer.name = 粉碎机
block.cryofluidmixer.name = 冷冻液混合器 block.cryofluidmixer.name = 冷冻液混合器
block.melter.name = 熔炉 block.melter.name = 熔炉
block.incinerator.name = 焚化炉 block.incinerator.name = 焚化炉
block.alloy-smelter.name = 合金冶炼厂
block.spore-press.name = 孢子压缩机 block.spore-press.name = 孢子压缩机
block.separator.name = 分离机 block.separator.name = 分离机
block.coal-centrifuge.name = 煤炭离心机 block.coal-centrifuge.name = 煤炭离心机
block.plastanium-compressor.name = 塑钢压缩机
block.pyratite-mixer.name = 硫混合器
block.blast-mixer.name = 爆炸混合器
block.solar-panel.name = 太阳能电池
block.power-node.name = 能量节点 block.power-node.name = 能量节点
block.power-node-large.name = 大型能量节点 block.power-node-large.name = 大型能量节点
block.surge-tower.name = 巨浪塔 block.surge-tower.name = 巨浪塔
@@ -771,11 +852,10 @@ block.combustion-generator.name = 燃烧发电机
block.turbine-generator.name = 涡轮发电机 block.turbine-generator.name = 涡轮发电机
block.differential-generator.name = 差动发电机 block.differential-generator.name = 差动发电机
block.impact-reactor.name = 冲击反应堆 block.impact-reactor.name = 冲击反应堆
block.mechanical-drill.name = 机械钻头 block.solar-panel-large.name = 大型太阳能电池
block.pneumatic-drill.name = 气动钻头 block.thorium-reactor.name = 钍反应堆
block.laser-drill.name = 激光钻头 block.thermal-generator.name = 热能发电机
block.water-extractor.name = 抽水 block.rtg-generator.name = RTG 发电
block.cultivator.name = 培养机
block.dart-mech-pad.name = Dart 机甲平台 block.dart-mech-pad.name = Dart 机甲平台
block.delta-mech-pad.name = Delta 机甲平台 block.delta-mech-pad.name = Delta 机甲平台
block.javelin-ship-pad.name = Javelin 机甲平台 block.javelin-ship-pad.name = Javelin 机甲平台
@@ -783,28 +863,24 @@ block.trident-ship-pad.name = Trident 机甲平台
block.glaive-ship-pad.name = Glaive 机甲平台 block.glaive-ship-pad.name = Glaive 机甲平台
block.omega-mech-pad.name = Omega 机甲平台 block.omega-mech-pad.name = Omega 机甲平台
block.tau-mech-pad.name = Tau 机甲平台 block.tau-mech-pad.name = Tau 机甲平台
block.pulse-conduit.name = 脉冲导管
block.phase-conduit.name = 相织布导管桥
block.liquid-router.name = 液体路由器
block.liquid-tank.name = 储液罐
block.liquid-junction.name = 液体连接点
block.bridge-conduit.name = 导管桥
block.conduit.name = 导管 block.conduit.name = 导管
block.mechanical-pump.name = 机械泵 block.mechanical-pump.name = 机械泵
block.rotary-pump.name = 回旋泵
block.thermal-pump.name = 热能泵
block.item-source.name = 物品源 block.item-source.name = 物品源
block.item-void.name = 物品黑洞 block.item-void.name = 物品黑洞
block.liquid-source.name = 液体源 block.liquid-source.name = 液体源
block.power-void.name = 能源黑洞 block.power-void.name = 能源黑洞
block.power-source.name = 无限能源 block.power-source.name = 无限能源
block.unloader.name = 装卸器
block.vault.name = 仓库
block.wave.name = 波浪
block.swarmer.name = 蜂群
block.salvo.name = 齐射炮
block.ripple.name = 浪涌
block.phase-conveyor.name = 相织布传送带
block.bridge-conveyor.name = 传送带桥
block.plastanium-compressor.name = 塑钢压缩机
block.pyratite-mixer.name = 硫混合器
block.blast-mixer.name = 爆炸混合器
block.solar-panel.name = 太阳能电池
block.solar-panel-large.name = 大型太阳能电池
block.oil-extractor.name = 石油钻井
block.command-center.name = 指挥中心 block.command-center.name = 指挥中心
block.rally-point.name = 集合点
block.rally-point.description = 用于地面单位集合的标志。需要指挥中心发出“集合”指令才可使用。
block.draug-factory.name = 德鲁格采矿机工厂 block.draug-factory.name = 德鲁格采矿机工厂
block.spirit-factory.name = 幽灵修理机工厂 block.spirit-factory.name = 幽灵修理机工厂
block.phantom-factory.name = 鬼怪建造机工厂 block.phantom-factory.name = 鬼怪建造机工厂
@@ -816,42 +892,24 @@ block.titan-factory.name = 泰坦机甲工厂
block.fortress-factory.name = 堡垒机甲工厂 block.fortress-factory.name = 堡垒机甲工厂
block.revenant-factory.name = 亡魂战机工厂 block.revenant-factory.name = 亡魂战机工厂
block.repair-point.name = 维修点 block.repair-point.name = 维修点
block.pulse-conduit.name = 脉冲导管 block.message.name = 信息
block.phase-conduit.name = 相织布导管
block.liquid-router.name = 液体路由器
block.liquid-tank.name = 储液罐
block.liquid-junction.name = 液体连接点
block.bridge-conduit.name = 导管桥
block.rotary-pump.name = 回旋泵
block.thorium-reactor.name = 钍反应堆
block.mass-driver.name = 质量驱动器
block.blast-drill.name = 爆破钻头
block.thermal-pump.name = 热能泵
block.thermal-generator.name = 热能发电机
block.alloy-smelter.name = 合金冶炼厂
block.mender.name = 修理者 block.mender.name = 修理者
block.mend-projector.name = 修理投影器 block.mend-projector.name = 修理投影器
block.surge-wall.name = 波动墙 block.unloader.name = 装卸器
block.surge-wall-large.name = 大型波动墙 block.vault.name = 仓库
block.cyclone.name = 气旋炮
block.fuse.name = 融合炮
block.shock-mine.name = 脉冲地雷 block.shock-mine.name = 脉冲地雷
block.overdrive-projector.name = 超速投影器 block.overdrive-projector.name = 超速投影器
block.force-projector.name = 力墙投影器 block.force-projector.name = 力墙投影器
block.arc.name = 电弧
block.rtg-generator.name = RTG 发电机
block.spectre.name = 幽灵
block.meltdown.name = 熔毁
block.container.name = 容器 block.container.name = 容器
block.launch-pad.name = 发射台 block.launch-pad.name = 发射台
block.launch-pad-large.name = 大型发射台 block.launch-pad-large.name = 大型发射台
team.blue.name = team.blue.name = 胖次
team.crux.name = red team.crux.name = 姨妈红
team.sharded.name = orange team.sharded.name = 哲学黄
team.orange.name = team.orange.name = 太阳
team.derelict.name = derelict team.derelict.name = 高冷灰
team.green.name = 绿 team.green.name = 原谅绿
team.purple.name = team.purple.name = 基佬
unit.spirit.name = 幽灵修理机 unit.spirit.name = 幽灵修理机
unit.draug.name = 德鲁格采矿机 unit.draug.name = 德鲁格采矿机
unit.phantom.name = 鬼怪建造机 unit.phantom.name = 鬼怪建造机
@@ -874,7 +932,7 @@ tutorial.drill.mobile = 手动采矿效率低。\n[accent]钻头[]可以自动
tutorial.blockinfo = 每个方块具有不同的数据。每个钻头只能开采某些矿石。\n要检查块的信息和统计信息[accent]在菜单中点击问号。[]\n\n[accent]现在查看机械钻头的数据吧。[] tutorial.blockinfo = 每个方块具有不同的数据。每个钻头只能开采某些矿石。\n要检查块的信息和统计信息[accent]在菜单中点击问号。[]\n\n[accent]现在查看机械钻头的数据吧。[]
tutorial.conveyor = [accent]传送带[]可以把物资传送到核心。\n请从钻头到核心间造一条传送带。 tutorial.conveyor = [accent]传送带[]可以把物资传送到核心。\n请从钻头到核心间造一条传送带。
tutorial.conveyor.mobile = [accent]传送带[]可以把物资传送到核心。\n请从钻头到核心间造一条传送带。\n[accent]长按数秒[]并向一个方向拖动来直线放置。\n\n[accent]{0}/{1} 条传送带\n[accent]0/1 物品 tutorial.conveyor.mobile = [accent]传送带[]可以把物资传送到核心。\n请从钻头到核心间造一条传送带。\n[accent]长按数秒[]并向一个方向拖动来直线放置。\n\n[accent]{0}/{1} 条传送带\n[accent]0/1 物品
tutorial.turret = 必须建造防御建筑来击退[LIGHT_GRAY]敌人[]。\n请在核心附近造一个双管炮。 tutorial.turret = 必须建造防御建筑来击退[LIGHT_GRAY]敌人[]。\n请在核心附近造一个双管炮。
tutorial.drillturret = 双管炮需要[accent]铜[]作弹药来射击。\n可以放一个钻头在炮塔附近供应铜。 tutorial.drillturret = 双管炮需要[accent]铜[]作弹药来射击。\n可以放一个钻头在炮塔附近供应铜。
tutorial.pause = 在战斗中,您可以[accent]暂停游戏[]。\n暂停时您可以规划建筑物。\n\n按[accent]空格[]暂停。 tutorial.pause = 在战斗中,您可以[accent]暂停游戏[]。\n暂停时您可以规划建筑物。\n\n按[accent]空格[]暂停。
tutorial.pause.mobile = 在战斗中,您可以[accent]暂停游戏[]。\n暂停时您可以规划建筑物。\n\n[accent]点击左上角的按钮以暂停。 tutorial.pause.mobile = 在战斗中,您可以[accent]暂停游戏[]。\n暂停时您可以规划建筑物。\n\n[accent]点击左上角的按钮以暂停。
@@ -887,8 +945,9 @@ tutorial.deposit = 将物品从机甲拖向方块来放下物品。\n\n[accent]
tutorial.waves = [lightgray]敌人[]来了。\n\n保护核心防御2波攻击。造更多的炮塔。[accent]点击[]以射击。\n建造更多的炮塔和钻头并采更多的矿。 tutorial.waves = [lightgray]敌人[]来了。\n\n保护核心防御2波攻击。造更多的炮塔。[accent]点击[]以射击。\n建造更多的炮塔和钻头并采更多的矿。
tutorial.waves.mobile = [lightgray]敌人[]来了。\n\n保护核心防御2波攻击。造更多的炮塔。你的机甲将对敌人自动开火。\n建造更多的炮塔和钻头并采更多的矿。 tutorial.waves.mobile = [lightgray]敌人[]来了。\n\n保护核心防御2波攻击。造更多的炮塔。你的机甲将对敌人自动开火。\n建造更多的炮塔和钻头并采更多的矿。
tutorial.launch = 特定波次中,你可以[accent]发射核心[][accent]携带核心中所有资源[]离开所有的建筑。\n资源可用来研究科技。\n\n[accent]点击发射按钮。 tutorial.launch = 特定波次中,你可以[accent]发射核心[][accent]携带核心中所有资源[]离开所有的建筑。\n资源可用来研究科技。\n\n[accent]点击发射按钮。
item.copper.description = 一种有用的结构材料。在各种类型的方块中广泛使用。 item.copper.description = 一种有用的结构材料。在各种类型的方块中广泛使用。
item.lead.description = 一种基本的起始材料。广泛用于电子设备和液体运输方块 item.lead.description = 一种基本的起始材料。广泛用于电子设备和液体运输。
item.metaglass.description = 一种超级强硬的复合玻璃。通常用来传送和收藏液体。 item.metaglass.description = 一种超级强硬的复合玻璃。通常用来传送和收藏液体。
item.graphite.description = 一种用于弹药和电路绝缘的矿化碳。 item.graphite.description = 一种用于弹药和电路绝缘的矿化碳。
item.sand.description = 一种常见的材料,广泛用于冶炼,包括制作合金和助熔剂。 item.sand.description = 一种常见的材料,广泛用于冶炼,包括制作合金和助熔剂。
@@ -907,7 +966,7 @@ liquid.water.description = 最有用的液体。常用于冷却和废物处理
liquid.slag.description = 各种不同类型的熔融金属混合在一起的液体。可以被分解成其组成矿物,或作为武器喷向敌方单位。 liquid.slag.description = 各种不同类型的熔融金属混合在一起的液体。可以被分解成其组成矿物,或作为武器喷向敌方单位。
liquid.oil.description = 用于先进材料生产的液体。可以转换成煤作为燃料,或作为武器喷射和放火。 liquid.oil.description = 用于先进材料生产的液体。可以转换成煤作为燃料,或作为武器喷射和放火。
liquid.cryofluid.description = 一种由水和钛制成的惰性、无腐蚀性的液体。具有极高的热容量。广泛用作冷却剂。 liquid.cryofluid.description = 一种由水和钛制成的惰性、无腐蚀性的液体。具有极高的热容量。广泛用作冷却剂。
mech.alpha-mech.description = 标准控制机甲。基于尖刀单位具有升级的装甲和建筑能力。比Dart有更多的伤害输出。 mech.alpha-mech.description = 标准控制机甲。基于尖刀单位,具有升级的装甲和建筑能力。比 Dart 有更多的伤害输出。
mech.delta-mech.description = 一种快速,轻便的机甲,一击即退。对结构造成的伤害很小,但可以用弧形闪电武器快速杀死大量敌方单位。 mech.delta-mech.description = 一种快速,轻便的机甲,一击即退。对结构造成的伤害很小,但可以用弧形闪电武器快速杀死大量敌方单位。
mech.tau-mech.description = 后勤机甲。治疗友军。可以熄灭火焰并治疗一定范围内的友军。 mech.tau-mech.description = 后勤机甲。治疗友军。可以熄灭火焰并治疗一定范围内的友军。
mech.omega-mech.description = 一种装甲厚重的机甲用于在前线攻击。它的护甲可以阻挡高达90%的伤害。 mech.omega-mech.description = 一种装甲厚重的机甲用于在前线攻击。它的护甲可以阻挡高达90%的伤害。
@@ -926,6 +985,7 @@ unit.eruptor.description = 一种用来拆除建筑物的重型机甲。在敌
unit.wraith.description = 一种快速、一击即退的拦截器机甲。目标是发电机。 unit.wraith.description = 一种快速、一击即退的拦截器机甲。目标是发电机。
unit.ghoul.description = 一种地毯式轰炸机。通过敌人的结构进行攻击,并瞄准关键的基础设施。 unit.ghoul.description = 一种地毯式轰炸机。通过敌人的结构进行攻击,并瞄准关键的基础设施。
unit.revenant.description = 一种发射导弹的重型飞行机甲。 unit.revenant.description = 一种发射导弹的重型飞行机甲。
block.message.description = 储存一条信息。用于在盟军之间交流。
block.graphite-press.description = 把大块的煤压缩成纯石墨片。 block.graphite-press.description = 把大块的煤压缩成纯石墨片。
block.multi-press.description = 石墨压缩机的升级版。利用水和电力快速高效地处理煤炭。 block.multi-press.description = 石墨压缩机的升级版。利用水和电力快速高效地处理煤炭。
block.silicon-smelter.description = 用高纯度的焦炭来加工沙子以生产硅。 block.silicon-smelter.description = 用高纯度的焦炭来加工沙子以生产硅。
@@ -977,7 +1037,7 @@ block.mass-driver.description = 终极传送带。收集物品后将它们射向
block.mechanical-pump.description = 一种输出速度慢但没有功耗的廉价泵。 block.mechanical-pump.description = 一种输出速度慢但没有功耗的廉价泵。
block.rotary-pump.description = 先进的水泵。泵送更多液体,但需要动力。 block.rotary-pump.description = 先进的水泵。泵送更多液体,但需要动力。
block.thermal-pump.description = 终级水泵。 block.thermal-pump.description = 终级水泵。
block.conduit.description = 基本液体传输块。像传送带一样工作,但用于液体。最适用于提取器,泵或其他导管。 block.conduit.description = 基本液体传输块。像传送带一样工作,但用于液体。最适用于泵或其他导管中提取液体
block.pulse-conduit.description = 高级液体传输块。比标准导管更快地输送液体并储存更多液体。 block.pulse-conduit.description = 高级液体传输块。比标准导管更快地输送液体并储存更多液体。
block.liquid-router.description = 接受来自一个方向的液体并将它们平均输出到最多3个其他方向。也可以储存一定量的液体。用于将液体从一个源分成多个目标。 block.liquid-router.description = 接受来自一个方向的液体并将它们平均输出到最多3个其他方向。也可以储存一定量的液体。用于将液体从一个源分成多个目标。
block.liquid-tank.description = 存储大量液体。当存在对材料的非恒定需求或作为冷却重要块的安全措施时,将其用于创建缓冲区。 block.liquid-tank.description = 存储大量液体。当存在对材料的非恒定需求或作为冷却重要块的安全措施时,将其用于创建缓冲区。

Binary file not shown.

Before

Width:  |  Height:  |  Size: 718 B

After

Width:  |  Height:  |  Size: 725 B

File diff suppressed because it is too large Load Diff

Binary file not shown.

Before

Width:  |  Height:  |  Size: 672 KiB

After

Width:  |  Height:  |  Size: 684 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 258 KiB

After

Width:  |  Height:  |  Size: 278 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 134 KiB

After

Width:  |  Height:  |  Size: 259 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 278 KiB

After

Width:  |  Height:  |  Size: 134 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 577 KiB

After

Width:  |  Height:  |  Size: 578 KiB

View File

@@ -40,6 +40,7 @@ public abstract class ClientLauncher extends ApplicationCore implements Platform
batch = new SpriteBatch(); batch = new SpriteBatch();
assets = new AssetManager(); assets = new AssetManager();
assets.setLoader(Texture.class, "." + mapExtension, new MapPreviewLoader()); assets.setLoader(Texture.class, "." + mapExtension, new MapPreviewLoader());
assets.load("sprites/error.png", Texture.class);
atlas = TextureAtlas.blankAtlas(); atlas = TextureAtlas.blankAtlas();
Vars.net = new Net(platform.getNet()); Vars.net = new Net(platform.getNet());

View File

@@ -122,8 +122,6 @@ public class Vars implements Loadable{
public static FileHandle saveDirectory; public static FileHandle saveDirectory;
/** data subdirectory used for plugins */ /** data subdirectory used for plugins */
public static FileHandle pluginDirectory; public static FileHandle pluginDirectory;
/** old map file extension, for conversion */
public static final String oldMapExtension = "mmap";
/** map file extension */ /** map file extension */
public static final String mapExtension = "msav"; public static final String mapExtension = "msav";
/** save file extension */ /** save file extension */
@@ -139,7 +137,7 @@ public class Vars implements Loadable{
public static EntityCollisions collisions; public static EntityCollisions collisions;
public static DefaultWaves defaultWaves; public static DefaultWaves defaultWaves;
public static LoopControl loops; public static LoopControl loops;
public static Platform platform; public static Platform platform = new Platform(){};
public static Plugins plugins; public static Plugins plugins;
public static World world; public static World world;

View File

@@ -1,164 +1,266 @@
package io.anuke.mindustry.ai; package io.anuke.mindustry.ai;
import io.anuke.arc.Events; import io.anuke.annotations.Annotations.*;
import io.anuke.arc.collection.IntArray; import io.anuke.arc.*;
import io.anuke.arc.collection.IntQueue; import io.anuke.arc.collection.*;
import io.anuke.arc.math.geom.Geometry; import io.anuke.arc.function.*;
import io.anuke.arc.math.geom.Point2; import io.anuke.arc.math.geom.*;
import io.anuke.arc.util.*; import io.anuke.arc.util.*;
import io.anuke.mindustry.game.EventType.TileChangeEvent; import io.anuke.arc.util.async.*;
import io.anuke.mindustry.game.EventType.WorldLoadEvent; import io.anuke.mindustry.game.EventType.*;
import io.anuke.mindustry.game.Team; import io.anuke.mindustry.game.*;
import io.anuke.mindustry.game.Teams.TeamData; import io.anuke.mindustry.gen.*;
import io.anuke.mindustry.net.Net; import io.anuke.mindustry.world.*;
import io.anuke.mindustry.world.Pos; import io.anuke.mindustry.world.meta.*;
import io.anuke.mindustry.world.Tile;
import io.anuke.mindustry.world.meta.BlockFlag;
import static io.anuke.mindustry.Vars.*; import static io.anuke.mindustry.Vars.*;
public class Pathfinder{ public class Pathfinder implements Runnable{
private static final long maxUpdate = Time.millisToNanos(4); private static final long maxUpdate = Time.millisToNanos(4);
private PathData[] paths; private static final int updateFPS = 60;
private IntArray blocked = new IntArray(); private static final int updateInterval = 1000 / updateFPS;
private static final int impassable = -1;
/** tile data, see PathTileStruct */
private int[][] tiles;
/** unordered array of path data for iteration only. DO NOT iterate ot access this in the main thread.*/
private Array<PathData> list = new Array<>();
/** Maps teams + flags to a valid path to get to that flag for that team. */
private PathData[][] pathMap = new PathData[Team.all.length][PathTarget.all.length];
/** Grid map of created path data that should not be queued again. */
private GridBits created = new GridBits(Team.all.length, PathTarget.all.length);
/** handles task scheduling on the update thread. */
private TaskQueue queue = new TaskQueue();
/** current pathfinding thread */
private @Nullable Thread thread;
public Pathfinder(){ public Pathfinder(){
Events.on(WorldLoadEvent.class, event -> clear()); Events.on(WorldLoadEvent.class, event -> {
Events.on(TileChangeEvent.class, event -> { stop();
if(net.client()) return;
for(Team team : Team.all){ //reset and update internal tile array
TeamData data = state.teams.get(team); tiles = new int[world.width()][world.height()];
if(state.teams.isActive(team) && data.team != event.tile.getTeam()){ pathMap = new PathData[Team.all.length][PathTarget.all.length];
update(event.tile, data.team); created = new GridBits(Team.all.length, PathTarget.all.length);
list = new Array<>();
for(int x = 0; x < world.width(); x++){
for(int y = 0; y < world.height(); y++){
tiles[x][y] = packTile(world.rawTile(x, y));
} }
} }
update(event.tile, event.tile.getTeam()); //special preset which may help speed things up; this is optional
preloadPath(waveTeam, PathTarget.enemyCores);
start();
});
Events.on(ResetEvent.class, event -> stop());
Events.on(TileChangeEvent.class, event -> updateTile(event.tile));
}
/** Packs a tile into its internal representation. */
private int packTile(Tile tile){
return PathTile.get(tile.cost, tile.getTeamID(), (byte)0, !tile.solid() && tile.floor().drownTime <= 0f);
}
/** Starts or restarts the pathfinding thread. */
private void start(){
stop();
thread = Threads.daemon(this);
}
/** Stops the pathfinding thread. */
private void stop(){
if(thread != null){
thread.interrupt();
thread = null;
}
queue.clear();
}
public int debugValue(Team team, int x, int y){
if(pathMap[team.ordinal()][PathTarget.enemyCores.ordinal()] == null) return 0;
return pathMap[team.ordinal()][PathTarget.enemyCores.ordinal()].weights[x][y];
}
/** Update a tile in the internal pathfinding grid. Causes a complete pathfinding reclaculation. */
public void updateTile(Tile tile){
if(net.client()) return;
int x = tile.x, y = tile.y;
tile.getLinkedTiles(t -> tiles[t.x][t.y] = packTile(t));
//can't iterate through array so use the map, which should not lead to problems
for(PathData[] arr : pathMap){
for(PathData path : arr){
if(path != null){
synchronized(path.targets){
path.targets.clear();
path.target.getTargets(path.team, path.targets);
}
}
}
}
queue.post(() -> {
for(PathData data : list){
updateTargets(data, x, y);
}
}); });
} }
public void updateSolid(Tile tile){ /** Thread implementation. */
update(tile, tile.getTeam()); @Override
} public void run(){
while(true){
if(net.client()) return;
public void update(){ queue.run();
if(net.client() || paths == null) return;
for(Team team : Team.all){ //total update time no longer than maxUpdate
if(state.teams.isActive(team)){ for(PathData data : list){
updateFrontier(team, maxUpdate); updateFrontier(data, maxUpdate / list.size);
}
try{
Thread.sleep(updateInterval);
}catch(InterruptedException e){
//stop looping when interrupted externally
return;
} }
} }
} }
public Tile getTargetTile(Team team, Tile tile){ /** Gets next tile to travel to. Main thread only. */
float[][] values = paths[team.ordinal()].weights; public Tile getTargetTile(Tile tile, Team team, PathTarget target){
if(tile == null) return null;
if(values == null || tile == null) return tile; PathData data = pathMap[team.ordinal()][target.ordinal()];
float value = values[tile.x][tile.y]; if(data == null){
//if this combination is not found, create it on request
if(!created.get(team.ordinal(), target.ordinal())){
created.set(team.ordinal(), target.ordinal());
//grab targets since this is run on main thread
IntArray targets = target.getTargets(team, new IntArray());
queue.post(() -> createPath(team, target, targets));
}
return tile;
}
Tile target = null; int[][] values = data.weights;
float tl = 0f; int value = values[tile.x][tile.y];
Tile current = null;
int tl = 0;
for(Point2 point : Geometry.d8){ for(Point2 point : Geometry.d8){
int dx = tile.x + point.x, dy = tile.y + point.y; int dx = tile.x + point.x, dy = tile.y + point.y;
Tile other = world.tile(dx, dy); Tile other = world.tile(dx, dy);
if(other == null) continue; if(other == null) continue;
if(values[dx][dy] < value && (target == null || values[dx][dy] < tl) && if(values[dx][dy] < value && (current == null || values[dx][dy] < tl) && !other.solid() && other.floor().drownTime <= 0 &&
!other.solid() && other.floor().drownTime <= 0 &&
!(point.x != 0 && point.y != 0 && (world.solid(tile.x + point.x, tile.y) || world.solid(tile.x, tile.y + point.y)))){ //diagonal corner trap !(point.x != 0 && point.y != 0 && (world.solid(tile.x + point.x, tile.y) || world.solid(tile.x, tile.y + point.y)))){ //diagonal corner trap
target = other; current = other;
tl = values[dx][dy]; tl = values[dx][dy];
} }
} }
if(target == null || tl == Float.MAX_VALUE) return tile; if(current == null || tl == impassable) return tile;
return target; return current;
} }
public float getValueforTeam(Team team, int x, int y){ /** @return whether a tile can be passed through by this team. Pathfinding thread only.*/
return paths == null || paths[team.ordinal()].weights == null || team.ordinal() >= paths.length ? 0 : Structs.inBounds(x, y, paths[team.ordinal()].weights) ? paths[team.ordinal()].weights[x][y] : 0; private boolean passable(int x, int y, Team team){
} int tile = tiles[x][y];
return PathTile.passable(tile) || (PathTile.team(tile) != team.ordinal() && PathTile.team(tile) != Team.derelict.ordinal());
private boolean passable(Tile tile, Team team){
return ((!tile.solid()) || (tile.breakable() && (tile.getTeam() != team))) && tile.floor().drownTime <= 0f;
} }
/** /**
* Clears the frontier, increments the search and sets up all flow sources. * Clears the frontier, increments the search and sets up all flow sources.
* This only occurs for active teams. * This only occurs for active teams.
*/ */
private void update(Tile tile, Team team){ private void updateTargets(PathData path, int x, int y){
//make sure team exists if(!Structs.inBounds(x, y, path.weights)) return;
if(paths != null && paths[team.ordinal()] != null && paths[team.ordinal()].weights != null && Structs.inBounds(tile.x, tile.y, paths[team.ordinal()].weights)){
PathData path = paths[team.ordinal()];
if(path.weights[tile.x][tile.y] <= 0.1f){ if(path.weights[x][y] == 0){
//this was a previous target //this was a previous target
path.frontier.clear();
}else if(!path.frontier.isEmpty()){
return;
}
//impassable tiles have a weight of float.max
if(!passable(tile, team)){
path.weights[tile.x][tile.y] = Float.MAX_VALUE;
}
//increment search, clear frontier
path.search++;
path.frontier.clear(); path.frontier.clear();
path.lastSearchTime = Time.millis(); }else if(!path.frontier.isEmpty()){
//skip if this path is processing
return;
}
//add all targets to the frontier //assign impassability to the tile
for(Tile other : indexer.getEnemy(team, BlockFlag.target)){ if(!passable(x, y, path.team)){
path.weights[other.x][other.y] = 0; path.weights[x][y] = impassable;
path.searches[other.x][other.y] = (short)path.search; }
path.frontier.addFirst(other.pos());
//increment search, clear frontier
path.search++;
path.frontier.clear();
synchronized(path.targets){
//add targets
for(int i = 0; i < path.targets.size; i++){
int pos = path.targets.get(i);
int tx = Pos.x(pos), ty = Pos.y(pos);
path.weights[tx][ty] = 0;
path.searches[tx][ty] = (short)path.search;
path.frontier.addFirst(pos);
} }
} }
} }
private void createFor(Team team){ private void preloadPath(Team team, PathTarget target){
PathData path = new PathData(); updateFrontier(createPath(team, target, target.getTargets(team, new IntArray())), -1);
path.weights = new float[world.width()][world.height()]; }
path.searches = new short[world.width()][world.height()];
path.search++;
path.frontier.ensureCapacity((world.width() + world.height()) * 3);
paths[team.ordinal()] = path; /** Created a new flowfield that aims to get to a certain target for a certain team.
* Pathfinding thread only. */
private PathData createPath(Team team, PathTarget target, IntArray targets){
PathData path = new PathData(team, target, world.width(), world.height());
list.add(path);
pathMap[team.ordinal()][target.ordinal()] = path;
//grab targets from passed array
synchronized(path.targets){
path.targets.clear();
path.targets.addAll(targets);
}
//fill with impassables by default
for(int x = 0; x < world.width(); x++){ for(int x = 0; x < world.width(); x++){
for(int y = 0; y < world.height(); y++){ for(int y = 0; y < world.height(); y++){
Tile tile = world.tile(x, y); path.weights[x][y] = impassable;
if(state.teams.areEnemies(tile.getTeam(), team)
&& tile.block().flags.contains(BlockFlag.target)){
path.frontier.addFirst(tile.pos());
path.weights[x][y] = 0;
path.searches[x][y] = (short)path.search;
}else{
path.weights[x][y] = Float.MAX_VALUE;
}
} }
} }
updateFrontier(team, -1); //add targets
for(int i = 0; i < path.targets.size; i++){
int pos = path.targets.get(i);
path.weights[Pos.x(pos)][Pos.y(pos)] = 0;
path.frontier.addFirst(pos);
}
return path;
} }
private void updateFrontier(Team team, long nsToRun){ /** Update the frontier for a path. Pathfinding thread only. */
PathData path = paths[team.ordinal()]; private void updateFrontier(PathData path, long nsToRun){
long start = Time.nanos(); long start = Time.nanos();
while(path.frontier.size > 0 && (nsToRun < 0 || Time.timeSinceNanos(start) <= nsToRun)){ while(path.frontier.size > 0 && (nsToRun < 0 || Time.timeSinceNanos(start) <= nsToRun)){
Tile tile = world.tile(path.frontier.removeLast()); Tile tile = world.tile(path.frontier.removeLast());
if(tile == null || path.weights == null) return; //something went horribly wrong, bail if(tile == null || path.weights == null) return; //something went horribly wrong, bail
float cost = path.weights[tile.x][tile.y]; int cost = path.weights[tile.x][tile.y];
//pathfinding overflowed for some reason, time to bail. the next block update will handle this, hopefully //pathfinding overflowed for some reason, time to bail. the next block update will handle this, hopefully
if(path.frontier.size >= world.width() * world.height()){ if(path.frontier.size >= world.width() * world.height()){
@@ -166,14 +268,13 @@ public class Pathfinder{
return; return;
} }
if(cost < Float.MAX_VALUE){ if(cost != impassable){
for(Point2 point : Geometry.d4){ for(Point2 point : Geometry.d4){
int dx = tile.x + point.x, dy = tile.y + point.y; int dx = tile.x + point.x, dy = tile.y + point.y;
Tile other = world.tile(dx, dy); Tile other = world.tile(dx, dy);
if(other != null && (path.weights[dx][dy] > cost + other.cost || path.searches[dx][dy] < path.search) if(other != null && (path.weights[dx][dy] > cost + other.cost || path.searches[dx][dy] < path.search) && passable(dx, dy, path.team)){
&& passable(other, team)){
if(other.cost < 0) throw new IllegalArgumentException("Tile cost cannot be negative! " + other); if(other.cost < 0) throw new IllegalArgumentException("Tile cost cannot be negative! " + other);
path.frontier.addFirst(Pos.get(dx, dy)); path.frontier.addFirst(Pos.get(dx, dy));
path.weights[dx][dy] = cost + other.cost; path.weights[dx][dy] = cost + other.cost;
@@ -184,27 +285,78 @@ public class Pathfinder{
} }
} }
private void clear(){ /** A path target defines a set of targets for a path.*/
Time.mark(); public enum PathTarget{
enemyCores((team, out) -> {
paths = new PathData[Team.all.length]; for(Tile other : indexer.getEnemy(team, BlockFlag.core)){
blocked.clear(); out.add(other.pos());
for(Team team : Team.all){
PathData path = new PathData();
paths[team.ordinal()] = path;
if(state.teams.isActive(team)){
createFor(team);
} }
//spawn points are also enemies.
if(state.rules.waves && team == defaultTeam){
for(Tile other : spawner.getGroundSpawns()){
out.add(other.pos());
}
}
}),
rallyPoints((team, out) -> {
for(Tile other : indexer.getAllied(team, BlockFlag.rally)){
out.add(other.pos());
}
});
public static final PathTarget[] all = values();
private final BiConsumer<Team, IntArray> targeter;
PathTarget(BiConsumer<Team, IntArray> targeter){
this.targeter = targeter;
}
/** Get targets. This must run on the main thread.*/
public IntArray getTargets(Team team, IntArray out){
targeter.accept(team, out);
return out;
} }
} }
/** Data for a specific flow field to some set of destinations. */
class PathData{ class PathData{
float[][] weights; /** Team this path is for. */
short[][] searches; final Team team;
int search = 0; /** Flag that is being targeted. */
long lastSearchTime; final PathTarget target;
IntQueue frontier = new IntQueue(); /** costs of getting to a specific tile */
final int[][] weights;
/** search IDs of each position - the highest, most recent search is prioritized and overwritten */
final short[][] searches;
/** search frontier, these are Pos objects */
final IntQueue frontier = new IntQueue();
/** all target positions; these positions have a cost of 0, and must be synchronized on! */
final IntArray targets = new IntArray();
/** current search ID */
int search = 1;
PathData(Team team, PathTarget target, int width, int height){
this.team = team;
this.target = target;
this.weights = new int[width][height];
this.searches = new short[width][height];
this.frontier.ensureCapacity((width + height) * 3);
}
}
/** Holds a copy of tile data for a specific tile position. */
@Struct
class PathTileStruct{
//traversal cost
byte cost;
//team of block, if applicable (0 by default)
byte team;
//type of target; TODO remove
byte type;
//whether it's viable to pass this block
boolean passable;
} }
} }

View File

@@ -1,6 +1,7 @@
package io.anuke.mindustry.content; package io.anuke.mindustry.content;
import io.anuke.arc.*; import io.anuke.arc.*;
import io.anuke.arc.collection.*;
import io.anuke.arc.graphics.*; import io.anuke.arc.graphics.*;
import io.anuke.arc.graphics.g2d.*; import io.anuke.arc.graphics.g2d.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
@@ -18,6 +19,7 @@ import io.anuke.mindustry.world.blocks.*;
import io.anuke.mindustry.world.blocks.defense.*; import io.anuke.mindustry.world.blocks.defense.*;
import io.anuke.mindustry.world.blocks.defense.turrets.*; import io.anuke.mindustry.world.blocks.defense.turrets.*;
import io.anuke.mindustry.world.blocks.distribution.*; import io.anuke.mindustry.world.blocks.distribution.*;
import io.anuke.mindustry.world.blocks.logic.*;
import io.anuke.mindustry.world.blocks.power.*; import io.anuke.mindustry.world.blocks.power.*;
import io.anuke.mindustry.world.blocks.production.*; import io.anuke.mindustry.world.blocks.production.*;
import io.anuke.mindustry.world.blocks.sandbox.*; import io.anuke.mindustry.world.blocks.sandbox.*;
@@ -48,7 +50,7 @@ public class Blocks implements ContentList{
melter, separator, sporePress, pulverizer, incinerator, coalCentrifuge, melter, separator, sporePress, pulverizer, incinerator, coalCentrifuge,
//sandbox //sandbox
powerVoid, powerSource, itemSource, liquidSource, itemVoid, powerVoid, powerSource, itemSource, liquidSource, itemVoid, message,
//defense //defense
scrapWall, scrapWallLarge, scrapWallHuge, scrapWallGigantic, thruster, //ok, these names are getting ridiculous, but at least I don't have humongous walls yet scrapWall, scrapWallLarge, scrapWallHuge, scrapWallGigantic, thruster, //ok, these names are getting ridiculous, but at least I don't have humongous walls yet
@@ -56,7 +58,7 @@ public class Blocks implements ContentList{
phaseWall, phaseWallLarge, surgeWall, surgeWallLarge, mender, mendProjector, overdriveProjector, forceProjector, shockMine, phaseWall, phaseWallLarge, surgeWall, surgeWallLarge, mender, mendProjector, overdriveProjector, forceProjector, shockMine,
//transport //transport
conveyor, titaniumConveyor, distributor, junction, itemBridge, phaseConveyor, sorter, router, overflowGate, massDriver, conveyor, titaniumConveyor, armoredConveyor, distributor, junction, itemBridge, phaseConveyor, sorter, router, overflowGate, massDriver,
//liquids //liquids
mechanicalPump, rotaryPump, thermalPump, conduit, pulseConduit, liquidRouter, liquidTank, liquidJunction, bridgeConduit, phaseConduit, mechanicalPump, rotaryPump, thermalPump, conduit, pulseConduit, liquidRouter, liquidTank, liquidJunction, bridgeConduit, phaseConduit,
@@ -733,6 +735,9 @@ public class Blocks implements ContentList{
requirements(Category.liquid, () -> state.rules.infiniteResources, ItemStack.with()); requirements(Category.liquid, () -> state.rules.infiniteResources, ItemStack.with());
alwaysUnlocked = true; alwaysUnlocked = true;
}}; }};
message = new MessageBlock("message"){{
requirements(Category.effect, ItemStack.with(Items.graphite, 5));
}};
//endregion //endregion
//region defense //region defense
@@ -901,10 +906,16 @@ public class Blocks implements ContentList{
speed = 0.08f; speed = 0.08f;
}}; }};
armoredConveyor = new ArmoredConveyor("armored-conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.metaglass, 1, Items.thorium, 1));
health = 180;
speed = 0.08f;
}};
junction = new Junction("junction"){{ junction = new Junction("junction"){{
requirements(Category.distribution, ItemStack.with(Items.copper, 1), true); requirements(Category.distribution, ItemStack.with(Items.copper, 1), true);
speed = 26; speed = 26;
capacity = 15; capacity = 12;
health = 30; health = 30;
}}; }};
@@ -912,7 +923,7 @@ public class Blocks implements ContentList{
requirements(Category.distribution, ItemStack.with(Items.lead, 4, Items.copper, 4)); requirements(Category.distribution, ItemStack.with(Items.lead, 4, Items.copper, 4));
range = 4; range = 4;
speed = 70f; speed = 70f;
bufferCapacity = 15; bufferCapacity = 14;
}}; }};
phaseConveyor = new ItemBridge("phase-conveyor"){{ phaseConveyor = new ItemBridge("phase-conveyor"){{
@@ -1646,6 +1657,7 @@ public class Blocks implements ContentList{
commandCenter = new CommandCenter("command-center"){{ commandCenter = new CommandCenter("command-center"){{
requirements(Category.units, ItemStack.with(Items.copper, 200, Items.lead, 250, Items.silicon, 250, Items.graphite, 100)); requirements(Category.units, ItemStack.with(Items.copper, 200, Items.lead, 250, Items.silicon, 250, Items.graphite, 100));
flags = EnumSet.of(BlockFlag.rally, BlockFlag.comandCenter);
size = 2; size = 2;
health = size * size * 55; health = size * size * 55;
}}; }};

View File

@@ -46,6 +46,7 @@ public class StatusEffects implements ContentList{
if(unit.getTeam() == waveTeam){ if(unit.getTeam() == waveTeam){
Events.fire(Trigger.shock); Events.fire(Trigger.shock);
} }
result.set(this, time);
})); }));
opposite(() -> burning); opposite(() -> burning);
}}; }};

View File

@@ -45,6 +45,10 @@ public class TechTree implements ContentList{
}); });
}); });
node(armoredConveyor, () -> {
});
}); });
}); });
}); });

View File

@@ -204,9 +204,18 @@ public class Control implements ApplicationListener, Loadable{
player.add(); player.add();
} }
Events.on(ClientLoadEvent.class, e -> { Events.on(ClientLoadEvent.class, e -> input.add());
Core.input.addProcessor(input); }
});
public void setInput(InputHandler newInput){
Block block = input.block;
boolean added = Core.input.getInputProcessors().contains(input);
input.remove();
this.input = newInput;
newInput.block = block;
if(added){
newInput.add();
}
} }
public void playMap(Map map, Rules rules){ public void playMap(Map map, Rules rules){
@@ -214,6 +223,8 @@ public class Control implements ApplicationListener, Loadable{
logic.reset(); logic.reset();
world.loadMap(map, rules); world.loadMap(map, rules);
state.rules = rules; state.rules = rules;
state.rules.zone = null;
state.rules.editor = false;
logic.play(); logic.play();
if(settings.getBool("savecreate") && !world.isInvalidMap()){ if(settings.getBool("savecreate") && !world.isInvalidMap()){
control.saves.addSave(map.name() + " " + new SimpleDateFormat("MMM dd h:mm", Locale.getDefault()).format(new Date())); control.saves.addSave(map.name() + " " + new SimpleDateFormat("MMM dd h:mm", Locale.getDefault()).format(new Date()));
@@ -371,11 +382,15 @@ public class Control implements ApplicationListener, Loadable{
@Override @Override
public void update(){ public void update(){
//TODO find out why this happens on Android
if(assets == null) return;
saves.update(); saves.update();
//update and load any requested assets //update and load any requested assets
assets.update(); assets.update();
input.updateController(); input.updateState();
//autosave global data if it's modified //autosave global data if it's modified
data.checkSave(); data.checkSave();

View File

@@ -227,8 +227,6 @@ public class Logic implements ApplicationListener{
collisions.collideGroups(bulletGroup, playerGroup); collisions.collideGroups(bulletGroup, playerGroup);
} }
pathfinder.update();
} }
if(!net.client() && !world.isInvalidMap() && !state.isEditor()){ if(!net.client() && !world.isInvalidMap() && !state.isEditor()){

View File

@@ -230,6 +230,15 @@ public class NetClient implements ApplicationListener{
ui.loadfrag.hide(); ui.loadfrag.hide();
} }
@Remote(variants = Variant.one, priority = PacketPriority.high)
public static void onKick(String reason){
netClient.disconnectQuietly();
state.set(State.menu);
logic.reset();
ui.showText("$disconnect", reason);
ui.loadfrag.hide();
}
@Remote(variants = Variant.both) @Remote(variants = Variant.both)
public static void onInfoMessage(String message){ public static void onInfoMessage(String message){
ui.showText("", message); ui.showText("", message);

View File

@@ -254,14 +254,13 @@ public class NetServer implements ApplicationListener{
Call.sendMessage(Strings.format("[orange]{0}[lightgray] has voted to kick[orange] {1}[].[accent] ({2}/{3})\n[lightgray]Type[orange] /vote <y/n>[] to agree.", Call.sendMessage(Strings.format("[orange]{0}[lightgray] has voted to kick[orange] {1}[].[accent] ({2}/{3})\n[lightgray]Type[orange] /vote <y/n>[] to agree.",
player.name, target.name, votes, votesRequired())); player.name, target.name, votes, votesRequired()));
//checkPass();
} }
boolean checkPass(){ boolean checkPass(){
if(votes >= votesRequired() && target.isAdded() && target.con.isConnected()){ if(votes >= votesRequired() && target.isAdded() && target.con.isConnected()){
Call.sendMessage(Strings.format("[orange]Vote passed.[scarlet] {0}[orange] will be kicked from the server.", target.name)); Call.sendMessage(Strings.format("[orange]Vote passed.[scarlet] {0}[orange] will be banned from the server for {1} minutes.", target.name, (kickDuration/60)));
admins.getInfo(target.uuid).lastKicked = Time.millis() + kickDuration*1000; target.getInfo().lastKicked = Time.millis() + kickDuration*1000;
target.con.kick(KickReason.vote); playerGroup.all().each(p -> p.uuid != null && p.uuid.equals(target.uuid), p -> p.con.kick(KickReason.vote));
map[0] = null; map[0] = null;
task.cancel(); task.cancel();
return true; return true;
@@ -331,7 +330,8 @@ public class NetServer implements ApplicationListener{
if(currentlyKicking[0] == null){ if(currentlyKicking[0] == null){
player.sendMessage("[scarlet]Nobody is being voted on."); player.sendMessage("[scarlet]Nobody is being voted on.");
}else{ }else{
if(currentlyKicking[0].voted.contains(player.uuid) || currentlyKicking[0].voted.contains(admins.getInfo(player.uuid).lastIP)){ //hosts can vote all they want
if(player.uuid != null && (currentlyKicking[0].voted.contains(player.uuid) || currentlyKicking[0].voted.contains(admins.getInfo(player.uuid).lastIP))){
player.sendMessage("[scarlet]You've already voted. Sit down."); player.sendMessage("[scarlet]You've already voted. Sit down.");
return; return;
} }
@@ -704,16 +704,10 @@ public class NetServer implements ApplicationListener{
//iterate through each player //iterate through each player
for(int i = 0; i < playerGroup.size(); i++){ for(int i = 0; i < playerGroup.size(); i++){
Player player = playerGroup.all().get(i); Player player = playerGroup.all().get(i);
if(player.isLocal) continue; if(player.isLocal || player.con == null) continue;
NetConnection connection = player.con; NetConnection connection = player.con;
if(connection == null || !connection.isConnected()){
//player disconnected, call d/c event
onDisconnect(player, "disappeared");
return;
}
if(!player.timer.get(Player.timerSync, serverSyncTime) || !connection.hasConnected) continue; if(!player.timer.get(Player.timerSync, serverSyncTime) || !connection.hasConnected) continue;
writeSnapshot(player); writeSnapshot(player);

View File

@@ -2,6 +2,7 @@ package io.anuke.mindustry.core;
import io.anuke.arc.*; import io.anuke.arc.*;
import io.anuke.arc.Input.*; import io.anuke.arc.Input.*;
import io.anuke.arc.collection.*;
import io.anuke.arc.files.*; import io.anuke.arc.files.*;
import io.anuke.arc.function.*; import io.anuke.arc.function.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
@@ -25,6 +26,14 @@ public interface Platform{
/** Steam: Share a map on the workshop.*/ /** Steam: Share a map on the workshop.*/
default void publishMap(Map map){} default void publishMap(Map map){}
/** Steam: Return external workshop maps to be loaded.*/
default Array<FileHandle> getExternalMaps(){
return Array.with();
}
/** Steam: View a map listing on the workshop.*/
default void viewMapListing(Map map){}
/** Steam: Open workshop for maps.*/ /** Steam: Open workshop for maps.*/
default void openWorkshop(){} default void openWorkshop(){}

View File

@@ -22,6 +22,7 @@ import io.anuke.mindustry.entities.type.EffectEntity;
import io.anuke.mindustry.game.EventType.*; import io.anuke.mindustry.game.EventType.*;
import io.anuke.mindustry.game.*; import io.anuke.mindustry.game.*;
import io.anuke.mindustry.graphics.*; import io.anuke.mindustry.graphics.*;
import io.anuke.mindustry.input.*;
import io.anuke.mindustry.world.*; import io.anuke.mindustry.world.*;
import io.anuke.mindustry.world.blocks.defense.ForceProjector.*; import io.anuke.mindustry.world.blocks.defense.ForceProjector.*;
@@ -128,7 +129,7 @@ public class Renderer implements ApplicationListener{
}else{ }else{
camera.position.lerpDelta(position, 0.08f); camera.position.lerpDelta(position, 0.08f);
} }
}else if(!mobile || settings.getBool("keyboard")){ }else if(control.input instanceof DesktopInput){
camera.position.lerpDelta(position, 0.08f); camera.position.lerpDelta(position, 0.08f);
} }
@@ -294,7 +295,7 @@ public class Renderer implements ApplicationListener{
overlays.drawTop(); overlays.drawTop();
playerGroup.draw(p -> !p.isDead() && !p.isLocal, Player::drawName); playerGroup.draw(p -> !p.isDead(), Player::drawName);
drawLanding(); drawLanding();

View File

@@ -325,8 +325,9 @@ public class UI implements ApplicationListener, Loadable{
cont.row(); cont.row();
cont.addImage().width(300f).pad(2).height(4f).color(Color.scarlet); cont.addImage().width(300f).pad(2).height(4f).color(Color.scarlet);
cont.row(); cont.row();
cont.add(text).pad(2f).growX().wrap(); cont.add(text).pad(2f).growX().wrap().get().setAlignment(Align.center);
buttons.addButton("$ok", this::hide).size(120, 50).pad(4); cont.row();
cont.addButton("$ok", this::hide).size(120, 50).pad(4);
}}.show(); }}.show();
} }
@@ -358,7 +359,11 @@ public class UI implements ApplicationListener, Loadable{
public void showText(String titleText, String text){ public void showText(String titleText, String text){
new Dialog(titleText){{ new Dialog(titleText){{
cont.margin(15).add(text).width(400f).wrap().get().setAlignment(Align.center, Align.center); cont.row();
cont.addImage().width(400f).pad(2).colspan(2).height(4f).color(Pal.accent);
cont.row();
cont.add(text).width(400f).wrap().get().setAlignment(Align.center, Align.center);
cont.row();
buttons.addButton("$ok", this::hide).size(90, 50).pad(4); buttons.addButton("$ok", this::hide).size(90, 50).pad(4);
}}.show(); }}.show();
} }

View File

@@ -85,37 +85,35 @@ public class MapEditorDialog extends Dialog implements Disposable{
t.row(); t.row();
if(!ios){ t.addImageTextButton("$editor.import", Icon.loadMapSmall, () ->
t.addImageTextButton("$editor.import", Icon.loadMapSmall, () -> createDialog("$editor.import",
createDialog("$editor.import", "$editor.importmap", "$editor.importmap.description", Icon.loadMap, (Runnable)loadDialog::show,
"$editor.importmap", "$editor.importmap.description", Icon.loadMap, (Runnable)loadDialog::show, "$editor.importfile", "$editor.importfile.description", Icon.file, (Runnable)() ->
"$editor.importfile", "$editor.importfile.description", Icon.file, (Runnable)() -> platform.showFileChooser(true, mapExtension, file -> ui.loadAnd(() -> {
platform.showFileChooser(true, mapExtension, file -> ui.loadAnd(() -> { maps.tryCatchMapError(() -> {
maps.tryCatchMapError(() -> { if(MapIO.isImage(file)){
if(MapIO.isImage(file)){ ui.showInfo("$editor.errorimage");
ui.showInfo("$editor.errorimage"); }else{
}else{ editor.beginEdit(MapIO.createMap(file, true));
editor.beginEdit(MapIO.createMap(file, true));
}
});
})),
"$editor.importimage", "$editor.importimage.description", Icon.fileImage, (Runnable)() ->
platform.showFileChooser(true, "png", file ->
ui.loadAnd(() -> {
try{
Pixmap pixmap = new Pixmap(file);
editor.beginEdit(pixmap);
pixmap.dispose();
}catch(Exception e){
ui.showException("$editor.errorload", e);
Log.err(e);
} }
}))) });
); })),
}
Cell cell = t.addImageTextButton("$editor.export", Icon.saveMapSmall, () -> { "$editor.importimage", "$editor.importimage.description", Icon.fileImage, (Runnable)() ->
platform.showFileChooser(true, "png", file ->
ui.loadAnd(() -> {
try{
Pixmap pixmap = new Pixmap(file);
editor.beginEdit(pixmap);
pixmap.dispose();
}catch(Exception e){
ui.showException("$editor.errorload", e);
Log.err(e);
}
})))
);
t.addImageTextButton("$editor.export", Icon.saveMapSmall, () -> {
if(!ios){ if(!ios){
platform.showFileChooser(false, mapExtension, file -> { platform.showFileChooser(false, mapExtension, file -> {
ui.loadAnd(() -> { ui.loadAnd(() -> {
@@ -143,10 +141,6 @@ public class MapEditorDialog extends Dialog implements Disposable{
}); });
} }
}); });
if(ios){
cell.size(swidth * 2f + 10, 60f).colspan(2);
}
}); });
menu.cont.row(); menu.cont.row();
@@ -154,10 +148,21 @@ public class MapEditorDialog extends Dialog implements Disposable{
if(steam){ if(steam){
menu.cont.addImageTextButton("$editor.publish.workshop", Icon.linkSmall, () -> { menu.cont.addImageTextButton("$editor.publish.workshop", Icon.linkSmall, () -> {
Map map = save(); Map map = save();
if(map != null){
platform.publishMap(map); if(map == null) return;
if(map.tags.get("description", "").length() < 4){
ui.showErrorMessage("$editor.nodescription");
return;
} }
}).padTop(-3).size(swidth * 2f + 10, 60f);
if(!Structs.contains(Gamemode.all, g -> g.valid(map))){
ui.showErrorMessage("$map.nospawn");
return;
}
platform.publishMap(map);
}).padTop(-3).size(swidth * 2f + 10, 60f).update(b -> b.setText(editor.getTags().containsKey("steamid") ? "$view.workshop" : "$editor.publish.workshop"));
menu.cont.row(); menu.cont.row();
} }
@@ -255,6 +260,7 @@ public class MapEditorDialog extends Dialog implements Disposable{
state.teams = new Teams(); state.teams = new Teams();
player.reset(); player.reset();
state.rules = Gamemode.editor.apply(lastSavedRules.copy()); state.rules = Gamemode.editor.apply(lastSavedRules.copy());
state.rules.zone = null;
world.setMap(new Map(StringMap.of( world.setMap(new Map(StringMap.of(
"name", "Editor Playtesting", "name", "Editor Playtesting",
"width", editor.width(), "width", editor.width(),
@@ -276,7 +282,9 @@ public class MapEditorDialog extends Dialog implements Disposable{
}); });
} }
private Map save(){ public Map save(){
boolean isEditor = state.rules.editor;
state.rules.editor = false;
String name = editor.getTags().get("name", "").trim(); String name = editor.getTags().get("name", "").trim();
editor.getTags().put("rules", JsonIO.write(state.rules)); editor.getTags().put("rules", JsonIO.write(state.rules));
editor.getTags().remove("width"); editor.getTags().remove("width");
@@ -300,6 +308,7 @@ public class MapEditorDialog extends Dialog implements Disposable{
menu.hide(); menu.hide();
saved = true; saved = true;
state.rules.editor = isEditor;
return returned; return returned;
} }

View File

@@ -54,7 +54,7 @@ public class MapLoadDialog extends FloatingDialog{
for(Map map : maps.all()){ for(Map map : maps.all()){
TextButton button = new TextButton(map.name(), Styles.togglet); TextButton button = new TextButton(map.name(), Styles.togglet);
button.add(new BorderImage(map.texture, 2f).setScaling(Scaling.fit)).size(16 * 4f); button.add(new BorderImage(map.safeTexture(), 2f).setScaling(Scaling.fit)).size(16 * 4f);
button.getCells().reverse(); button.getCells().reverse();
button.clicked(() -> selected = map); button.clicked(() -> selected = map);
button.getLabelCell().grow().left().padLeft(5f); button.getLabelCell().grow().left().padLeft(5f);

View File

@@ -18,6 +18,8 @@ public class EntityGroup<T extends Entity>{
private final Array<T> entityArray = new Array<>(false, 32); private final Array<T> entityArray = new Array<>(false, 32);
private final Array<T> entitiesToRemove = new Array<>(false, 32); private final Array<T> entitiesToRemove = new Array<>(false, 32);
private final Array<T> entitiesToAdd = new Array<>(false, 32); private final Array<T> entitiesToAdd = new Array<>(false, 32);
private final Array<T> intersectArray = new Array<>();
private final Rectangle intersectRect = new Rectangle();
private IntMap<T> map; private IntMap<T> map;
private QuadTree tree; private QuadTree tree;
private Consumer<T> removeListener; private Consumer<T> removeListener;
@@ -161,6 +163,15 @@ public class EntityGroup<T extends Entity>{
tree().getIntersect(out, x, y, width, height); tree().getIntersect(out, x, y, width, height);
} }
@SuppressWarnings("unchecked")
public Array<T> intersect(float x, float y, float width, float height){
intersectArray.clear();
//don't waste time for empty groups
if(isEmpty()) return intersectArray;
tree().getIntersect(intersectArray, intersectRect.set(x, y, width, height));
return intersectArray;
}
public QuadTree tree(){ public QuadTree tree(){
if(!useTree) throw new RuntimeException("This group does not support quadtrees! Enable quadtrees when creating it."); if(!useTree) throw new RuntimeException("This group does not support quadtrees! Enable quadtrees when creating it.");
return tree; return tree;

View File

@@ -47,7 +47,7 @@ public class Lightning extends TimedEntity implements DrawTrait, TimeTrait{
} }
/** Do not invoke! */ /** Do not invoke! */
@Remote(called = Loc.server) @Remote(called = Loc.server, unreliable = true)
public static void createLighting(int seed, Team team, Color color, float damage, float x, float y, float rotation, int length){ public static void createLighting(int seed, Team team, Color color, float damage, float x, float y, float rotation, int length){
Lightning l = Pools.obtain(Lightning.class, Lightning::new); Lightning l = Pools.obtain(Lightning.class, Lightning::new);

View File

@@ -16,6 +16,7 @@ import io.anuke.mindustry.game.*;
import io.anuke.mindustry.gen.*; import io.anuke.mindustry.gen.*;
import io.anuke.mindustry.type.*; import io.anuke.mindustry.type.*;
import io.anuke.mindustry.world.*; import io.anuke.mindustry.world.*;
import io.anuke.mindustry.world.blocks.*;
import io.anuke.mindustry.world.blocks.defense.DeflectorWall.*; import io.anuke.mindustry.world.blocks.defense.DeflectorWall.*;
import io.anuke.mindustry.world.blocks.units.CommandCenter.*; import io.anuke.mindustry.world.blocks.units.CommandCenter.*;
import io.anuke.mindustry.world.blocks.units.UnitFactory.*; import io.anuke.mindustry.world.blocks.units.UnitFactory.*;
@@ -99,7 +100,7 @@ public abstract class BaseUnit extends Unit implements ShooterTrait{
return indexer.getAllied(team, BlockFlag.comandCenter).size != 0 && indexer.getAllied(team, BlockFlag.comandCenter).first().entity instanceof CommandCenterEntity; return indexer.getAllied(team, BlockFlag.comandCenter).size != 0 && indexer.getAllied(team, BlockFlag.comandCenter).first().entity instanceof CommandCenterEntity;
} }
public UnitCommand getCommand(){ public @Nullable UnitCommand getCommand(){
if(isCommanded()){ if(isCommanded()){
return indexer.getAllied(team, BlockFlag.comandCenter).first().<CommandCenterEntity>entity().command; return indexer.getAllied(team, BlockFlag.comandCenter).first().<CommandCenterEntity>entity().command;
} }
@@ -173,8 +174,15 @@ public abstract class BaseUnit extends Unit implements ShooterTrait{
} }
} }
public TileEntity getClosestEnemyCore(){ public Tile getClosest(BlockFlag flag){
return Geometry.findClosest(x, y, indexer.getAllied(team, flag));
}
public Tile getClosestSpawner(){
return Geometry.findClosest(x, y, Vars.spawner.getGroundSpawns());
}
public TileEntity getClosestEnemyCore(){
for(Team enemy : Vars.state.teams.enemiesOf(team)){ for(Team enemy : Vars.state.teams.enemiesOf(team)){
Tile tile = Geometry.findClosest(x, y, Vars.state.teams.get(enemy).cores); Tile tile = Geometry.findClosest(x, y, Vars.state.teams.get(enemy).cores);
if(tile != null){ if(tile != null){
@@ -273,7 +281,7 @@ public abstract class BaseUnit extends Unit implements ShooterTrait{
return; return;
} }
if(!isFlying() && (world.tileWorld(x, y) != null && world.tileWorld(x, y).solid())){ if(!isFlying() && (world.tileWorld(x, y) != null && !(world.tileWorld(x, y).block() instanceof BuildBlock) && world.tileWorld(x, y).solid())){
kill(); kill();
} }

View File

@@ -5,6 +5,7 @@ import io.anuke.arc.graphics.g2d.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
import io.anuke.arc.math.geom.*; import io.anuke.arc.math.geom.*;
import io.anuke.arc.util.*; import io.anuke.arc.util.*;
import io.anuke.mindustry.*;
import io.anuke.mindustry.entities.*; import io.anuke.mindustry.entities.*;
import io.anuke.mindustry.entities.bullet.*; import io.anuke.mindustry.entities.bullet.*;
import io.anuke.mindustry.entities.units.*; import io.anuke.mindustry.entities.units.*;
@@ -35,13 +36,15 @@ public abstract class FlyingUnit extends BaseUnit{
if(target == null) targetClosestEnemyFlag(BlockFlag.producer); if(target == null) targetClosestEnemyFlag(BlockFlag.producer);
if(target == null) targetClosestEnemyFlag(BlockFlag.turret); if(target == null) targetClosestEnemyFlag(BlockFlag.turret);
if(target == null){
setState(patrol);
}
} }
if(target != null){ if(target == null){
target = getSpawner();
}
if(target == getSpawner() && getSpawner() != null){
circle(80f + Mathf.randomSeed(id) * 120);
}else if(target != null){
attack(type.attackLength); attack(type.attackLength);
if((Angles.near(angleTo(target), rotation, type.shootCone) || getWeapon().ignoreRotation) //bombers and such don't care about rotation if((Angles.near(angleTo(target), rotation, type.shootCone) || getWeapon().ignoreRotation) //bombers and such don't care about rotation
@@ -64,26 +67,28 @@ public abstract class FlyingUnit extends BaseUnit{
getWeapon().update(FlyingUnit.this, to.x, to.y); getWeapon().update(FlyingUnit.this, to.x, to.y);
} }
} }
}else{
target = getClosestSpawner();
moveTo(Vars.state.rules.dropZoneRadius + 120f);
} }
} }
}, },
patrol = new UnitState(){ rally = new UnitState(){
public void update(){ public void update(){
if(retarget()){ if(retarget()){
targetClosestAllyFlag(BlockFlag.rally);
targetClosest(); targetClosest();
targetClosestEnemyFlag(BlockFlag.target);
if(target != null && !Units.invalidateTarget(target, team, x, y)){ if(target != null && !Units.invalidateTarget(target, team, x, y)){
setState(attack); setState(attack);
return; return;
} }
target = getSpawner(); if(target == null) target = getSpawner();
if(target == null) target = getClosestCore();
} }
if(target != null){ if(target != null){
circle(80f + Mathf.randomSeed(id) * 120); circle(65f + Mathf.randomSeed(id) * 100);
} }
} }
}, },
@@ -109,7 +114,7 @@ public abstract class FlyingUnit extends BaseUnit{
public void onCommand(UnitCommand command){ public void onCommand(UnitCommand command){
state.set(command == UnitCommand.retreat ? retreat : state.set(command == UnitCommand.retreat ? retreat :
command == UnitCommand.attack ? attack : command == UnitCommand.attack ? attack :
command == UnitCommand.patrol ? patrol : command == UnitCommand.rally ? rally :
null); null);
} }

View File

@@ -6,6 +6,7 @@ import io.anuke.arc.math.*;
import io.anuke.arc.math.geom.*; import io.anuke.arc.math.geom.*;
import io.anuke.arc.util.*; import io.anuke.arc.util.*;
import io.anuke.mindustry.*; import io.anuke.mindustry.*;
import io.anuke.mindustry.ai.Pathfinder.*;
import io.anuke.mindustry.entities.*; import io.anuke.mindustry.entities.*;
import io.anuke.mindustry.entities.bullet.*; import io.anuke.mindustry.entities.bullet.*;
import io.anuke.mindustry.entities.units.*; import io.anuke.mindustry.entities.units.*;
@@ -13,6 +14,7 @@ import io.anuke.mindustry.game.*;
import io.anuke.mindustry.type.*; import io.anuke.mindustry.type.*;
import io.anuke.mindustry.world.*; import io.anuke.mindustry.world.*;
import io.anuke.mindustry.world.blocks.*; import io.anuke.mindustry.world.blocks.*;
import io.anuke.mindustry.world.meta.*;
import static io.anuke.mindustry.Vars.*; import static io.anuke.mindustry.Vars.*;
@@ -34,31 +36,30 @@ public abstract class GroundUnit extends BaseUnit{
TileEntity core = getClosestEnemyCore(); TileEntity core = getClosestEnemyCore();
if(core == null){ if(core == null){
setState(patrol); Tile closestSpawn = getClosestSpawner();
return; if(closestSpawn == null || !withinDst(closestSpawn, Vars.state.rules.dropZoneRadius + 85f)){
} moveToCore(PathTarget.enemyCores);
}
}else{
float dst = dst(core); float dst = dst(core);
if(dst < getWeapon().bullet.range() / 1.1f){ if(dst < getWeapon().bullet.range() / 1.1f){
target = core; target = core;
} }
if(dst > getWeapon().bullet.range() * 0.5f){ if(dst > getWeapon().bullet.range() * 0.5f){
moveToCore(); moveToCore(PathTarget.enemyCores);
}
} }
} }
}, },
patrol = new UnitState(){ rally = new UnitState(){
public void update(){ public void update(){
TileEntity target = getClosestCore(); Tile target = getClosest(BlockFlag.rally);
if(target != null){ if(target != null && dst(target) > 80f){
if(dst(target) > 400f){ moveToCore(PathTarget.rallyPoints);
moveAwayFromCore();
}else if(!(!Units.invalidateTarget(GroundUnit.this.target, GroundUnit.this) && dst(GroundUnit.this.target) < getWeapon().bullet.range())){
patrol();
}
} }
} }
}, },
@@ -76,7 +77,7 @@ public abstract class GroundUnit extends BaseUnit{
public void onCommand(UnitCommand command){ public void onCommand(UnitCommand command){
state.set(command == UnitCommand.retreat ? retreat : state.set(command == UnitCommand.retreat ? retreat :
command == UnitCommand.attack ? attack : command == UnitCommand.attack ? attack :
command == UnitCommand.patrol ? patrol : command == UnitCommand.rally ? rally :
null); null);
} }
@@ -220,10 +221,10 @@ public abstract class GroundUnit extends BaseUnit{
velocity.add(vec); velocity.add(vec);
} }
protected void moveToCore(){ protected void moveToCore(PathTarget path){
Tile tile = world.tileWorld(x, y); Tile tile = world.tileWorld(x, y);
if(tile == null) return; if(tile == null) return;
Tile targetTile = pathfinder.getTargetTile(team, tile); Tile targetTile = pathfinder.getTargetTile(tile, team, path);
if(tile == targetTile) return; if(tile == targetTile) return;
@@ -242,11 +243,18 @@ public abstract class GroundUnit extends BaseUnit{
} }
} }
if(enemy == null){
for(Team team : Vars.state.teams.enemiesOf(team)){
enemy = team;
break;
}
}
if(enemy == null) return; if(enemy == null) return;
Tile tile = world.tileWorld(x, y); Tile tile = world.tileWorld(x, y);
if(tile == null) return; if(tile == null) return;
Tile targetTile = pathfinder.getTargetTile(enemy, tile); Tile targetTile = pathfinder.getTargetTile(tile, enemy, PathTarget.enemyCores);
TileEntity core = getClosestCore(); TileEntity core = getClosestCore();
if(tile == targetTile || core == null || dst(core) < 120f) return; if(tile == targetTile || core == null || dst(core) < 120f) return;

View File

@@ -7,6 +7,7 @@ import io.anuke.arc.graphics.*;
import io.anuke.arc.graphics.g2d.*; import io.anuke.arc.graphics.g2d.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
import io.anuke.arc.math.geom.*; import io.anuke.arc.math.geom.*;
import io.anuke.arc.scene.ui.*;
import io.anuke.arc.scene.ui.layout.*; import io.anuke.arc.scene.ui.layout.*;
import io.anuke.arc.util.*; import io.anuke.arc.util.*;
import io.anuke.arc.util.pooling.*; import io.anuke.arc.util.pooling.*;
@@ -382,19 +383,21 @@ public class Player extends Unit implements BuilderMinerTrait, ShooterTrait{
font.setUseIntegerPositions(false); font.setUseIntegerPositions(false);
font.getData().setScale(0.25f / Scl.scl(1f)); font.getData().setScale(0.25f / Scl.scl(1f));
layout.setText(font, name); layout.setText(font, name);
Draw.color(0f, 0f, 0f, 0.3f);
Fill.rect(x, y + nameHeight - layout.height / 2, layout.width + 2, layout.height + 3);
Draw.color();
font.setColor(color);
font.draw(name, x, y + nameHeight, 0, Align.center, false); if(!isLocal){
Draw.color(0f, 0f, 0f, 0.3f);
Fill.rect(x, y + nameHeight - layout.height / 2, layout.width + 2, layout.height + 3);
Draw.color();
font.setColor(color);
font.draw(name, x, y + nameHeight, 0, Align.center, false);
if(isAdmin){ if(isAdmin){
float s = 3f; float s = 3f;
Draw.color(color.r * 0.5f, color.g * 0.5f, color.b * 0.5f, 1f); Draw.color(color.r * 0.5f, color.g * 0.5f, color.b * 0.5f, 1f);
Draw.rect(Core.atlas.find("icon-admin-badge"), x + layout.width / 2f + 2 + 1, y + nameHeight - 1.5f, s, s); Draw.rect(Core.atlas.find("icon-admin-badge"), x + layout.width / 2f + 2 + 1, y + nameHeight - 1.5f, s, s);
Draw.color(color); Draw.color(color);
Draw.rect(Core.atlas.find("icon-admin-badge"), x + layout.width / 2f + 2 + 1, y + nameHeight - 1f, s, s); Draw.rect(Core.atlas.find("icon-admin-badge"), x + layout.width / 2f + 2 + 1, y + nameHeight - 1f, s, s);
}
} }
if(Core.settings.getBool("playerchat") && ((textFadeTime > 0 && lastText != null) || isTyping)){ if(Core.settings.getBool("playerchat") && ((textFadeTime > 0 && lastText != null) || isTyping)){
@@ -567,7 +570,7 @@ public class Player extends Unit implements BuilderMinerTrait, ShooterTrait{
data.unlockContent(mech); data.unlockContent(mech);
} }
if(mobile && !Core.settings.getBool("keyboard")){ if(control.input instanceof MobileInput){
updateTouch(); updateTouch();
}else{ }else{
updateKeyboard(); updateKeyboard();
@@ -604,7 +607,7 @@ public class Player extends Unit implements BuilderMinerTrait, ShooterTrait{
float xa = Core.input.axis(Binding.move_x); float xa = Core.input.axis(Binding.move_x);
float ya = Core.input.axis(Binding.move_y); float ya = Core.input.axis(Binding.move_y);
if(!Core.input.keyDown(Binding.gridMode)){ if(!Core.input.keyDown(Binding.gridMode) && !(Core.scene.getKeyboardFocus() instanceof TextField)){
movement.y += ya * speed; movement.y += ya * speed;
movement.x += xa * speed; movement.x += xa * speed;
} }
@@ -723,50 +726,41 @@ public class Player extends Unit implements BuilderMinerTrait, ShooterTrait{
//update shooting if not building, not mining and there's ammo left //update shooting if not building, not mining and there's ammo left
if(!isBuilding() && getMineTile() == null){ if(!isBuilding() && getMineTile() == null){
//autofire: mobile only! //autofire
if(mobile){ if(target == null){
if(target == null){ isShooting = false;
isShooting = false; if(Core.settings.getBool("autotarget")){
if(Core.settings.getBool("autotarget")){ target = Units.closestTarget(team, x, y, getWeapon().bullet.range(), u -> u.getTeam() != Team.derelict, u -> u.getTeam() != Team.derelict);
target = Units.closestTarget(team, x, y, getWeapon().bullet.range(), u -> u.getTeam() != Team.derelict, u -> u.getTeam() != Team.derelict);
if(mech.canHeal && target == null){ if(mech.canHeal && target == null){
target = Geometry.findClosest(x, y, indexer.getDamaged(Team.sharded)); target = Geometry.findClosest(x, y, indexer.getDamaged(Team.sharded));
if(target != null && dst(target) > getWeapon().bullet.range()){ if(target != null && dst(target) > getWeapon().bullet.range()){
target = null; target = null;
}else if(target != null){ }else if(target != null){
target = ((Tile)target).entity; target = ((Tile)target).entity;
}
}
if(target != null){
setMineTile(null);
} }
} }
}else if(target.isValid() || (target instanceof TileEntity && ((TileEntity)target).damaged() && target.getTeam() == team &&
mech.canHeal && dst(target) < getWeapon().bullet.range())){ if(target != null){
//rotate toward and shoot the target setMineTile(null);
if(mech.turnCursor){
rotation = Mathf.slerpDelta(rotation, angleTo(target), 0.2f);
} }
}
Vector2 intercept = Predict.intercept(this, target, getWeapon().bullet.speed); }else if(target.isValid() || (target instanceof TileEntity && ((TileEntity)target).damaged() && target.getTeam() == team &&
mech.canHeal && dst(target) < getWeapon().bullet.range())){
pointerX = intercept.x; //rotate toward and shoot the target
pointerY = intercept.y; if(mech.turnCursor){
rotation = Mathf.slerpDelta(rotation, angleTo(target), 0.2f);
updateShooting();
isShooting = true;
} }
}else if(isShooting()){ Vector2 intercept = Predict.intercept(this, target, getWeapon().bullet.speed);
Vector2 vec = Core.input.mouseWorld(control.input.getMouseX(),
control.input.getMouseY()); pointerX = intercept.x;
pointerX = vec.x; pointerY = intercept.y;
pointerY = vec.y;
updateShooting(); updateShooting();
isShooting = true;
} }
} }
} }
@@ -832,7 +826,7 @@ public class Player extends Unit implements BuilderMinerTrait, ShooterTrait{
} }
public boolean isShooting(){ public boolean isShooting(){
return isShooting && (!isBoosting || mech.flying) && mining == null; return isShooting && (boostHeat < 0.1f || mech.flying) && mining == null;
} }
public void updateRespawning(){ public void updateRespawning(){

View File

@@ -2,6 +2,7 @@ package io.anuke.mindustry.entities.type;
import io.anuke.annotations.Annotations.*; import io.anuke.annotations.Annotations.*;
import io.anuke.arc.*; import io.anuke.arc.*;
import io.anuke.arc.collection.*;
import io.anuke.arc.graphics.*; import io.anuke.arc.graphics.*;
import io.anuke.arc.graphics.g2d.*; import io.anuke.arc.graphics.g2d.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
@@ -212,15 +213,25 @@ public abstract class Unit extends DestructibleEntity implements SaveTrait, Targ
float radScl = 1.5f; float radScl = 1.5f;
float fsize = getSize() / radScl; float fsize = getSize() / radScl;
moveVector.setZero(); moveVector.setZero();
float cx = x - fsize/2f, cy = y - fsize/2f;
Units.nearby(x - fsize/2f, y - fsize/2f, fsize, fsize, en -> { for(Team team : Team.all){
if(en == this || en.isFlying() != isFlying()) return; avoid(unitGroups[team.ordinal()].intersect(cx, cy, fsize, fsize));
}
avoid(playerGroup.intersect(cx, cy, fsize, fsize));
velocity.add(moveVector.x / mass() * Time.delta(), moveVector.y / mass() * Time.delta());
}
private void avoid(Array<? extends Unit> arr){
float radScl = 1.5f;
for(Unit en : arr){
if(en.isFlying() != isFlying()) continue;
float dst = dst(en); float dst = dst(en);
float scl = Mathf.clamp(1f - dst / (getSize()/(radScl*2f) + en.getSize()/(radScl*2f))); float scl = Mathf.clamp(1f - dst / (getSize()/(radScl*2f) + en.getSize()/(radScl*2f)));
moveVector.add(Tmp.v1.set((x - en.x) * scl, (y - en.y) * scl).limit(0.4f)); moveVector.add(Tmp.v1.set((x - en.x) * scl, (y - en.y) * scl).limit(0.4f));
}); }
velocity.add(moveVector.x / mass() * Time.delta(), moveVector.y / mass() * Time.delta());
} }
public @Nullable TileEntity getClosestCore(){ public @Nullable TileEntity getClosestCore(){

View File

@@ -32,12 +32,12 @@ public class Statuses implements Saveable{
if(statuses.size > 0){ if(statuses.size > 0){
//check for opposite effects //check for opposite effects
for(StatusEntry entry : statuses){ for(StatusEntry entry : statuses){
if(entry.effect == null) continue;
//extend effect //extend effect
if(entry.effect == effect){ if(entry.effect == effect){
entry.time = Math.max(entry.time, duration); entry.time = Math.max(entry.time, duration);
return; return;
}else if(entry.effect.reactsWith(effect)){ //find opposite }else if(entry.effect.reactsWith(effect)){ //find opposite
globalResult.effect = entry.effect;
entry.effect.getTransition(unit, effect, entry.time, duration, globalResult); entry.effect.getTransition(unit, effect, entry.time, duration, globalResult);
entry.time = globalResult.time; entry.time = globalResult.time;
@@ -84,10 +84,6 @@ public class Statuses implements Saveable{
removals.clear(); removals.clear();
for(StatusEntry entry : statuses){ for(StatusEntry entry : statuses){
if(entry.effect == null){
removals.add(entry);
continue;
}
entry.time = Math.max(entry.time - Time.delta(), 0); entry.time = Math.max(entry.time - Time.delta(), 0);
applied.set(entry.effect.id); applied.set(entry.effect.id);

View File

@@ -3,7 +3,7 @@ package io.anuke.mindustry.entities.units;
import io.anuke.arc.*; import io.anuke.arc.*;
public enum UnitCommand{ public enum UnitCommand{
attack, retreat, patrol; attack, retreat, rally;
private final String localized; private final String localized;
public static final UnitCommand[] all = values(); public static final UnitCommand[] all = values();

View File

@@ -17,9 +17,9 @@ public class MusicControl{
private static final float finTime = 120f, foutTime = 120f, musicInterval = 60 * 60 * 3f, musicChance = 0.6f, musicWaveChance = 0.5f; private static final float finTime = 120f, foutTime = 120f, musicInterval = 60 * 60 * 3f, musicChance = 0.6f, musicWaveChance = 0.5f;
/** normal, ambient music, plays at any time */ /** normal, ambient music, plays at any time */
public final Array<Music> ambientMusic = Array.with(Musics.game1, Musics.game3, Musics.game4, Musics.game6); public Array<Music> ambientMusic = Array.with();
/** darker music, used in times of conflict */ /** darker music, used in times of conflict */
public final Array<Music> darkMusic = Array.with(Musics.game2, Musics.game5, Musics.game7); public Array<Music> darkMusic = Array.with();
private Music lastRandomPlayed; private Music lastRandomPlayed;
private Interval timer = new Interval(); private Interval timer = new Interval();
private @Nullable Music current; private @Nullable Music current;
@@ -27,6 +27,11 @@ public class MusicControl{
private boolean silenced; private boolean silenced;
public MusicControl(){ public MusicControl(){
Events.on(ClientLoadEvent.class, e -> {
ambientMusic = Array.with(Musics.game1, Musics.game3, Musics.game4, Musics.game6);
darkMusic = Array.with(Musics.game2, Musics.game5, Musics.game7);
});
//only run music 10 seconds after a wave spawns //only run music 10 seconds after a wave spawns
Events.on(WaveEvent.class, e -> Time.run(60f * 10f, () -> { Events.on(WaveEvent.class, e -> Time.run(60f * 10f, () -> {
if(Mathf.chance(musicWaveChance)){ if(Mathf.chance(musicWaveChance)){

View File

@@ -187,7 +187,7 @@ public class Tutorial{
} }
},; },;
protected final String line = Core.bundle.has("tutorial." + name() + ".mobile") && mobile ? "tutorial." + name() + ".mobile" : "tutorial." + name(); protected String line = "";
protected final Function<String, String> text; protected final Function<String, String> text;
protected Array<String> sentences; protected Array<String> sentences;
protected final BooleanProvider done; protected final BooleanProvider done;
@@ -203,7 +203,10 @@ public class Tutorial{
/** displayed tutorial stage text.*/ /** displayed tutorial stage text.*/
public String text(){ public String text(){
if(sentences == null) this.sentences = Array.select(Core.bundle.get(line).split("\n"), s -> !s.isEmpty()); if(sentences == null){
this.line = Core.bundle.has("tutorial." + name() + ".mobile") && mobile ? "tutorial." + name() + ".mobile" : "tutorial." + name();
this.sentences = Array.select(Core.bundle.get(line).split("\n"), s -> !s.isEmpty());
}
String line = sentences.get(control.tutorial.sentence); String line = sentences.get(control.tutorial.sentence);
return line.contains("{") ? text.get(line) : line; return line.contains("{") ? text.get(line) : line;
} }

View File

@@ -33,7 +33,7 @@ public class Version{
PropertiesUtils.load(map, file.reader()); PropertiesUtils.load(map, file.reader());
type = map.get("type"); type = map.get("type");
number = Integer.parseInt(map.get("number")); number = Integer.parseInt(map.get("number", "4"));
modifier = map.get("modifier"); modifier = map.get("modifier");
if(map.get("build").contains(".")){ if(map.get("build").contains(".")){
String[] split = map.get("build").split("\\."); String[] split = map.get("build").split("\\.");

View File

@@ -55,7 +55,7 @@ public class Pixelator implements Disposable{
Draw.rect(Draw.wrap(buffer.getTexture()), Core.camera.position.x, Core.camera.position.y, Core.camera.width, -Core.camera.height); Draw.rect(Draw.wrap(buffer.getTexture()), Core.camera.position.x, Core.camera.position.y, Core.camera.width, -Core.camera.height);
Draw.blend(); Draw.blend();
playerGroup.draw(p -> !p.isDead() && !p.isLocal, Player::drawName); playerGroup.draw(p -> !p.isDead(), Player::drawName);
Core.camera.position.set(px, py); Core.camera.position.set(px, py);
Core.settings.put("animatedwater", hadWater); Core.settings.put("animatedwater", hadWater);

View File

@@ -236,6 +236,15 @@ public class DesktopInput extends InputHandler{
selectY = tileY(Core.input.mouseY()); selectY = tileY(Core.input.mouseY());
} }
if (mode == placing && block != null){
if (!overrideLineRotation && !Core.input.keyDown(Binding.diagonal_placement) && (selectX != cursorX || selectY != cursorY) && ((int) Core.input.axisTap(Binding.rotate) != 0)){
rotation = ((int)((Angles.angle(selectX, selectY, cursorX, cursorY) + 45) / 90f)) % 4;
overrideLineRotation = true;
}
}else{
overrideLineRotation = false;
}
if(Core.input.keyRelease(Binding.break_block) || Core.input.keyRelease(Binding.select)){ if(Core.input.keyRelease(Binding.break_block) || Core.input.keyRelease(Binding.select)){
if(mode == placing && block != null){ //touch up while placing, place everything in selection if(mode == placing && block != null){ //touch up while placing, place everything in selection
@@ -280,7 +289,7 @@ public class DesktopInput extends InputHandler{
} }
@Override @Override
public void updateController(){ public void updateState(){
if(state.is(State.menu)){ if(state.is(State.menu)){
droppingItem = false; droppingItem = false;
mode = none; mode = none;

View File

@@ -38,6 +38,7 @@ public abstract class InputHandler implements InputProcessor{
public final OverlayFragment frag = new OverlayFragment(); public final OverlayFragment frag = new OverlayFragment();
public Block block; public Block block;
public boolean overrideLineRotation;
public int rotation; public int rotation;
public boolean droppingItem; public boolean droppingItem;
@@ -58,7 +59,7 @@ public abstract class InputHandler implements InputProcessor{
@Remote(targets = Loc.both, forward = true, called = Loc.server) @Remote(targets = Loc.both, forward = true, called = Loc.server)
public static void transferInventory(Player player, Tile tile){ public static void transferInventory(Player player, Tile tile){
if(!player.timer.get(Player.timerTransfer, 40)) return; if(player == null || player.timer == null || !player.timer.get(Player.timerTransfer, 40)) return;
if(net.server() && (player.item().amount <= 0 || player.isTransferring|| !tile.interactable(player.getTeam()))){ if(net.server() && (player.item().amount <= 0 || player.isTransferring|| !tile.interactable(player.getTeam()))){
throw new ValidateException(player, "Player cannot transfer an item."); throw new ValidateException(player, "Player cannot transfer an item.");
} }
@@ -132,7 +133,7 @@ public abstract class InputHandler implements InputProcessor{
} }
public void updateController(){ public void updateState(){
} }
@@ -273,6 +274,23 @@ public abstract class InputHandler implements InputProcessor{
public void remove(){ public void remove(){
Core.input.removeProcessor(this); Core.input.removeProcessor(this);
frag.remove(); frag.remove();
if(Core.scene != null){
Table table = (Table)Core.scene.find("inputTable");
if(table != null){
table.clear();
}
}
}
public void add(){
Core.input.addProcessor(this);
if(Core.scene != null){
Table table = (Table)Core.scene.find("inputTable");
if(table != null){
table.clear();
buildUI(table);
}
}
} }
public boolean canShoot(){ public boolean canShoot(){
@@ -363,7 +381,10 @@ public abstract class InputHandler implements InputProcessor{
} }
float angle = Angles.angle(startX, startY, endX, endY); float angle = Angles.angle(startX, startY, endX, endY);
int baseRotation = (startX == endX && startY == endY) ? rotation : ((int)((angle + 45) / 90f)) % 4; int baseRotation = rotation;
if (!overrideLineRotation || diagonal){
baseRotation = (startX == endX && startY == endY) ? rotation : ((int)((angle + 45) / 90f)) % 4;
}
Tmp.r3.set(-1, -1, 0, 0); Tmp.r3.set(-1, -1, 0, 0);
@@ -377,7 +398,11 @@ public abstract class InputHandler implements InputProcessor{
Point2 next = i == points.size - 1 ? null : points.get(i + 1); Point2 next = i == points.size - 1 ? null : points.get(i + 1);
line.x = point.x; line.x = point.x;
line.y = point.y; line.y = point.y;
line.rotation = next != null ? Tile.relativeTo(point.x, point.y, next.x, next.y) : baseRotation; if (!overrideLineRotation || diagonal){
line.rotation = next != null ? Tile.relativeTo(point.x, point.y, next.x, next.y) : baseRotation;
}else{
line.rotation = rotation;
}
line.last = next == null; line.last = next == null;
cons.accept(line); cons.accept(line);

View File

@@ -36,6 +36,7 @@ public class MobileInput extends InputHandler implements GestureListener{
//gesture data //gesture data
private Vector2 vector = new Vector2(); private Vector2 vector = new Vector2();
private float lastZoom = -1; private float lastZoom = -1;
private GestureDetector detector;
/** Position where the player started dragging a line. */ /** Position where the player started dragging a line. */
private int lineStartX, lineStartY; private int lineStartX, lineStartY;
@@ -65,38 +66,6 @@ public class MobileInput extends InputHandler implements GestureListener{
private int prevX, prevY, prevRotation; private int prevX, prevY, prevRotation;
public MobileInput(){
Events.on(ClientLoadEvent.class, e -> {
GestureDetector dec = new GestureDetector(20, 0.5f, 0.4f, 0.15f, this){
boolean clearMouse = false;
@Override
public boolean touchDown(int x, int y, int pointer, KeyCode button){
if(Core.scene.hasMouse(x, y)){
clearMouse = true;
return false;
}
return super.touchDown(x, y, pointer, button);
}
@Override
public boolean touchDragged(int x, int y, int pointer){
if(!clearMouse){
return super.touchDragged(x, y, pointer);
}
return false;
}
@Override
public boolean touchUp(int x, int y, int pointer, KeyCode button){
clearMouse = false;
return super.touchUp(x, y, pointer, button);
}
};
Core.input.getInputProcessors().insert(0, dec);
});
}
//region utility methods //region utility methods
/** Check and assign targets for a specific position. */ /** Check and assign targets for a specific position. */
@@ -322,6 +291,7 @@ public class MobileInput extends InputHandler implements GestureListener{
}).visible(() -> !selection.isEmpty()).name("confirmplace"); }).visible(() -> !selection.isEmpty()).name("confirmplace");
Core.scene.table(t -> { Core.scene.table(t -> {
t.setName("cancelMobile");
t.bottom().left().visible(() -> (player.isBuilding() || block != null || mode == breaking) && !state.is(State.menu)); t.bottom().left().visible(() -> (player.isBuilding() || block != null || mode == breaking) && !state.is(State.menu));
t.addImageTextButton("$cancel", Icon.cancelSmall, () -> { t.addImageTextButton("$cancel", Icon.cancelSmall, () -> {
player.clearBuilding(); player.clearBuilding();
@@ -471,6 +441,24 @@ public class MobileInput extends InputHandler implements GestureListener{
//endregion //endregion
//region input events //region input events
@Override
public void add(){
Core.input.addProcessor(detector = new GestureDetector(20, 0.5f, 0.4f, 0.15f, this));
super.add();
}
@Override
public void remove(){
super.remove();
if(detector != null){
Core.input.removeProcessor(detector);
}
if(Core.scene != null && Core.scene.find("cancelMobile") != null){
Core.scene.find("cancelMobile").remove();
}
}
@Override @Override
public boolean touchDown(int screenX, int screenY, int pointer, KeyCode button){ public boolean touchDown(int screenX, int screenY, int pointer, KeyCode button){
if(state.is(State.menu) || player.isDead()) return false; if(state.is(State.menu) || player.isDead()) return false;

View File

@@ -20,6 +20,8 @@ public class Map implements Comparable<Map>{
public final FileHandle file; public final FileHandle file;
/** Format version. */ /** Format version. */
public final int version; public final int version;
/** Whether this map is managed, e.g. downloaded from the Steam workshop.*/
public boolean workshop;
/** Map width/height, shorts. */ /** Map width/height, shorts. */
public int width, height; public int width, height;
/** Preview texture. */ /** Preview texture. */
@@ -57,8 +59,12 @@ public class Map implements Comparable<Map>{
return Core.settings.getInt("hiscore" + file.nameWithoutExtension(), 0); return Core.settings.getInt("hiscore" + file.nameWithoutExtension(), 0);
} }
public Texture safeTexture(){
return texture == null ? Core.assets.get("sprites/error.png") : texture;
}
public FileHandle previewFile(){ public FileHandle previewFile(){
return Vars.mapPreviewDirectory.child(file.nameWithoutExtension() + ".png"); return Vars.mapPreviewDirectory.child((workshop ? file.parent().name() : file.nameWithoutExtension()) + ".png");
} }
public FileHandle cacheFile(){ public FileHandle cacheFile(){
@@ -127,6 +133,8 @@ public class Map implements Comparable<Map>{
@Override @Override
public int compareTo(Map map){ public int compareTo(Map map){
int work = -Boolean.compare(workshop, map.workshop);
if(work != 0) return work;
int type = -Boolean.compare(custom, map.custom); int type = -Boolean.compare(custom, map.custom);
if(type != 0) return type; if(type != 0) return type;
int modes = Boolean.compare(Gamemode.pvp.valid(this), Gamemode.pvp.valid(map)); int modes = Boolean.compare(Gamemode.pvp.valid(this), Gamemode.pvp.valid(map));

View File

@@ -5,6 +5,8 @@ import io.anuke.arc.assets.loaders.*;
import io.anuke.arc.assets.loaders.resolvers.*; import io.anuke.arc.assets.loaders.resolvers.*;
import io.anuke.arc.collection.*; import io.anuke.arc.collection.*;
import io.anuke.arc.files.*; import io.anuke.arc.files.*;
import io.anuke.arc.graphics.*;
import io.anuke.arc.util.*;
import io.anuke.mindustry.*; import io.anuke.mindustry.*;
import io.anuke.mindustry.game.*; import io.anuke.mindustry.game.*;
@@ -19,12 +21,27 @@ public class MapPreviewLoader extends TextureLoader{
try{ try{
super.loadAsync(manager, fileName, file.sibling(file.nameWithoutExtension()), parameter); super.loadAsync(manager, fileName, file.sibling(file.nameWithoutExtension()), parameter);
}catch(Exception e){ }catch(Exception e){
e.printStackTrace(); Log.err(e);
MapPreviewParameter param = (MapPreviewParameter)parameter; MapPreviewParameter param = (MapPreviewParameter)parameter;
Vars.maps.queueNewPreview(param.map); Vars.maps.queueNewPreview(param.map);
} }
} }
@Override
public Texture loadSync(AssetManager manager, String fileName, FileHandle file, TextureParameter parameter){
try{
return super.loadSync(manager, fileName, file, parameter);
}catch(Throwable e){
Log.err(e);
try{
return new Texture(file);
}catch(Throwable e2){
Log.err(e2);
return new Texture("sprites/error.png");
}
}
}
@Override @Override
public Array<AssetDescriptor> getDependencies(String fileName, FileHandle file, TextureParameter parameter){ public Array<AssetDescriptor> getDependencies(String fileName, FileHandle file, TextureParameter parameter){
return Array.with(new AssetDescriptor<>("contentcreate", Content.class)); return Array.with(new AssetDescriptor<>("contentcreate", Content.class));

View File

@@ -81,6 +81,7 @@ public class Maps{
/** Load all maps. Should be called at application start. */ /** Load all maps. Should be called at application start. */
public void load(){ public void load(){
//defaults; must work
try{ try{
for(String name : defaultMapNames){ for(String name : defaultMapNames){
FileHandle file = Core.files.internal("maps/" + name + "." + mapExtension); FileHandle file = Core.files.internal("maps/" + name + "." + mapExtension);
@@ -90,7 +91,27 @@ public class Maps{
throw new RuntimeException(e); throw new RuntimeException(e);
} }
loadCustomMaps(); //custom
for(FileHandle file : customMapDirectory.list()){
try{
if(file.extension().equalsIgnoreCase(mapExtension)){
loadMap(file, true);
}
}catch(Exception e){
Log.err("Failed to load custom map file '{0}'!", file);
Log.err(e);
}
}
//workshop
for(FileHandle file : platform.getExternalMaps()){
try{
loadMap(file, false).workshop = true;
}catch(Exception e){
Log.err("Failed to load workshop map file '{0}'!", file);
Log.err(e);
}
}
} }
public void reload(){ public void reload(){
@@ -174,14 +195,6 @@ public class Maps{
} }
} }
/** Creates a legacy map by converting it to a non-legacy map and pasting it in a temp directory.
* Should be followed up by {@link #importMap(FileHandle)} .*/
public Map makeLegacyMap(FileHandle file) throws IOException{
FileHandle dst = tmpDirectory.child("conversion_map." + mapExtension);
LegacyMapIO.convertMap(file, dst);
return MapIO.createMap(dst, true);
}
/** Import a map, then save it. This updates all values and stored data necessary. */ /** Import a map, then save it. This updates all values and stored data necessary. */
public void importMap(FileHandle file) throws IOException{ public void importMap(FileHandle file) throws IOException{
FileHandle dest = findFile(); FileHandle dest = findFile();
@@ -203,7 +216,6 @@ public class Maps{
if(error[0] != null){ if(error[0] != null){
throw new IOException(error[0]); throw new IOException(error[0]);
} }
} }
/** Attempts to run the following code; /** Attempts to run the following code;
@@ -314,7 +326,7 @@ public class Maps{
for(Map map : maps){ for(Map map : maps){
//try to load preview //try to load preview
if(map.previewFile().exists()){ if(map.previewFile().exists()){
//this may fail, but calls createNewPreview //this may fail, but calls queueNewPreview
Core.assets.load(new AssetDescriptor<>(map.previewFile().path() + "." + mapExtension, Texture.class, new MapPreviewParameter(map))).loaded = t -> map.texture = (Texture)t; Core.assets.load(new AssetDescriptor<>(map.previewFile().path() + "." + mapExtension, Texture.class, new MapPreviewParameter(map))).loaded = t -> map.texture = (Texture)t;
try{ try{
@@ -332,7 +344,7 @@ public class Maps{
private void createAllPreviews(){ private void createAllPreviews(){
Core.app.post(() -> { Core.app.post(() -> {
for(Map map : previewList){ for(Map map : previewList){
createNewPreview(map, e -> Core.app.post(() -> map.texture = new Texture("sprites/error.png"))); createNewPreview(map, e -> Core.app.post(() -> map.texture = Core.assets.get("sprites/error.png")));
} }
previewList.clear(); previewList.clear();
}); });
@@ -407,16 +419,4 @@ public class Maps{
return map; return map;
} }
private void loadCustomMaps(){
for(FileHandle file : customMapDirectory.list()){
try{
if(file.extension().equalsIgnoreCase(mapExtension)){
loadMap(file, true);
}
}catch(Exception e){
Log.err("Failed to load custom map file '{0}'!", file);
Log.err(e);
}
}
}
} }

View File

@@ -25,8 +25,8 @@ public class CrashSender{
try{ try{
exception.printStackTrace(); exception.printStackTrace();
//don't create crash logs for me (anuke) or custom builds, as it's expected //don't create crash logs for custom builds, as it's expected
if(System.getProperty("user.name").equals("anuke") || Version.build == -1) return; if(Version.build == -1) return;
//attempt to load version regardless //attempt to load version regardless
if(Version.number == 0){ if(Version.number == 0){

View File

@@ -46,7 +46,9 @@ public class Net{
t = t.getCause(); t = t.getCause();
} }
String error = t.getMessage() == null ? "" : t.getMessage().toLowerCase(); String baseError = Strings.getFinalMesage(e);
String error = baseError == null ? "" : baseError.toLowerCase();
String type = t.getClass().toString().toLowerCase(); String type = t.getClass().toString().toLowerCase();
boolean isError = false; boolean isError = false;

View File

@@ -29,6 +29,7 @@ public abstract class NetConnection{
this.address = address; this.address = address;
} }
/** Kick with a special, localized reason. Use this if possible. */
public void kick(KickReason reason){ public void kick(KickReason reason){
Log.info("Kicking connection {0}; Reason: {1}", address, reason.name()); Log.info("Kicking connection {0}; Reason: {1}", address, reason.name());
@@ -45,6 +46,23 @@ public abstract class NetConnection{
netServer.admins.save(); netServer.admins.save();
} }
/** Kick with an arbitrary reason. */
public void kick(String reason){
Log.info("Kicking connection {0}; Reason: {1}", address, reason);
if(player != null && player.uuid != null){
PlayerInfo info = netServer.admins.getInfo(player.uuid);
info.timesKicked++;
info.lastKicked = Math.max(Time.millis(), info.lastKicked);
}
Call.onKick(this, reason);
Time.runTask(2f, this::close);
netServer.admins.save();
}
public boolean isConnected(){ public boolean isConnected(){
return true; return true;
} }

View File

@@ -67,7 +67,7 @@ public class Plugins{
URLClassLoader classLoader = new URLClassLoader(new URL[]{jar.file().toURI().toURL()}, ClassLoader.getSystemClassLoader()); URLClassLoader classLoader = new URLClassLoader(new URL[]{jar.file().toURI().toURL()}, ClassLoader.getSystemClassLoader());
Class<?> main = classLoader.loadClass(meta.main); Class<?> main = classLoader.loadClass(meta.main);
metas.put(main, meta); metas.put(main, meta);
return new LoadedPlugin(jar, zip, (Plugin)main.newInstance(), meta); return new LoadedPlugin(jar, zip, (Plugin)main.getDeclaredConstructor().newInstance(), meta);
} }
/** Represents a plugin that has been loaded from a jar file.*/ /** Represents a plugin that has been loaded from a jar file.*/

View File

@@ -20,5 +20,7 @@ public enum Category{
/** Things that upgrade the player such as mech pads. */ /** Things that upgrade the player such as mech pads. */
upgrade, upgrade,
/** Things for storage or passive effects. */ /** Things for storage or passive effects. */
effect effect;
public static final Category[] all = values();
} }

View File

@@ -5,7 +5,7 @@ import io.anuke.arc.collection.ObjectMap;
import io.anuke.arc.function.Supplier; import io.anuke.arc.function.Supplier;
import io.anuke.arc.graphics.Color; import io.anuke.arc.graphics.Color;
import io.anuke.arc.math.Mathf; import io.anuke.arc.math.Mathf;
import io.anuke.arc.util.Time; import io.anuke.arc.util.*;
import io.anuke.mindustry.content.Fx; import io.anuke.mindustry.content.Fx;
import io.anuke.mindustry.entities.Effects; import io.anuke.mindustry.entities.Effects;
import io.anuke.mindustry.entities.Effects.Effect; import io.anuke.mindustry.entities.Effects.Effect;

View File

@@ -13,13 +13,7 @@ public class ControlsDialog extends KeybindDialog{
setFillParent(true); setFillParent(true);
title.setAlignment(Align.center); title.setAlignment(Align.center);
titleTable.row(); titleTable.row();
titleTable.add(new Image()) titleTable.add(new Image()).growX().height(3f).pad(4f).get().setColor(Pal.accent);
.growX().height(3f).pad(4f).get().setColor(Pal.accent);
if(Vars.mobile){
cont.row();
cont.add("$keybinds.mobile")
.center().growX().wrap().get().setAlignment(Align.center);
}
} }
@Override @Override

View File

@@ -48,7 +48,7 @@ public class CustomGameDialog extends FloatingDialog{
maps.row(); maps.row();
} }
ImageButton image = new ImageButton(new TextureRegion(map.texture), Styles.cleari); ImageButton image = new ImageButton(new TextureRegion(map.safeTexture()), Styles.cleari);
image.margin(5); image.margin(5);
image.top(); image.top();
@@ -72,7 +72,7 @@ public class CustomGameDialog extends FloatingDialog{
image.add(img).size(images); image.add(img).size(images);
BorderImage border = new BorderImage(map.texture, 3f); BorderImage border = new BorderImage(map.safeTexture(), 3f);
border.setScaling(Scaling.fit); border.setScaling(Scaling.fit);
image.replaceImage(border); image.replaceImage(border);

View File

@@ -195,6 +195,8 @@ public class LoadDialog extends FloatingDialog{
try{ try{
net.reset(); net.reset();
slot.load(); slot.load();
state.rules.editor = false;
state.rules.zone = null;
state.set(State.playing); state.set(State.playing);
}catch(SaveException e){ }catch(SaveException e){
Log.err(e); Log.err(e);

View File

@@ -69,7 +69,7 @@ public class MapPlayDialog extends FloatingDialog{
cont.row(); cont.row();
cont.addImageTextButton("$customize", Icon.toolsSmall, () -> dialog.show(rules, () -> rules = map.applyRules(selectedGamemode))).width(230); cont.addImageTextButton("$customize", Icon.toolsSmall, () -> dialog.show(rules, () -> rules = map.applyRules(selectedGamemode))).width(230);
cont.row(); cont.row();
cont.add(new BorderImage(map.texture, 3f)).size(mobile && !Core.graphics.isPortrait() ? 150f : 250f).get().setScaling(Scaling.fit); cont.add(new BorderImage(map.safeTexture(), 3f)).size(mobile && !Core.graphics.isPortrait() ? 150f : 250f).get().setScaling(Scaling.fit);
//only maps with survival are valid for high scores //only maps with survival are valid for high scores
if(Gamemode.survival.valid(map)){ if(Gamemode.survival.valid(map)){
cont.row(); cont.row();

View File

@@ -4,7 +4,6 @@ import io.anuke.arc.*;
import io.anuke.arc.graphics.*; import io.anuke.arc.graphics.*;
import io.anuke.arc.input.*; import io.anuke.arc.input.*;
import io.anuke.arc.math.*; import io.anuke.arc.math.*;
import io.anuke.arc.scene.event.*;
import io.anuke.arc.scene.ui.*; import io.anuke.arc.scene.ui.*;
import io.anuke.arc.scene.ui.layout.*; import io.anuke.arc.scene.ui.layout.*;
import io.anuke.arc.util.*; import io.anuke.arc.util.*;
@@ -53,12 +52,18 @@ public class MapsDialog extends FloatingDialog{
buttons.addImageTextButton("$editor.newmap", Icon.add, () -> { buttons.addImageTextButton("$editor.newmap", Icon.add, () -> {
ui.showTextInput("$editor.newmap", "$name", "", text -> { ui.showTextInput("$editor.newmap", "$name", "", text -> {
ui.loadAnd(() -> { Runnable show = () -> ui.loadAnd(() -> {
hide(); hide();
ui.editor.show(); ui.editor.show();
ui.editor.editor.getTags().put("name", text); ui.editor.editor.getTags().put("name", text);
Events.fire(new MapMakeEvent()); Events.fire(new MapMakeEvent());
}); });
if(maps.byName(text) != null){
ui.showErrorMessage("$editor.exists");
}else{
show.run();
}
}); });
}).size(210f, 64f); }).size(210f, 64f);
@@ -137,9 +142,9 @@ public class MapsDialog extends FloatingDialog{
button.row(); button.row();
button.addImage().growX().pad(4).color(Pal.gray); button.addImage().growX().pad(4).color(Pal.gray);
button.row(); button.row();
button.stack(new Image(map.texture).setScaling(Scaling.fit), new BorderImage(map.texture).setScaling(Scaling.fit)).size(mapsize - 20f); button.stack(new Image(map.safeTexture()).setScaling(Scaling.fit), new BorderImage(map.safeTexture()).setScaling(Scaling.fit)).size(mapsize - 20f);
button.row(); button.row();
button.add(map.custom ? "$custom" : "$builtin").color(Color.gray).padTop(3); button.add(map.custom ? "$custom" : map.workshop ? "$workshop" : "$builtin").color(Color.gray).padTop(3);
i++; i++;
} }
@@ -160,7 +165,7 @@ public class MapsDialog extends FloatingDialog{
float mapsize = Core.graphics.isPortrait() ? 160f : 300f; float mapsize = Core.graphics.isPortrait() ? 160f : 300f;
Table table = dialog.cont; Table table = dialog.cont;
table.stack(new Image(map.texture).setScaling(Scaling.fit), new BorderImage(map.texture).setScaling(Scaling.fit)).size(mapsize); table.stack(new Image(map.safeTexture()).setScaling(Scaling.fit), new BorderImage(map.safeTexture()).setScaling(Scaling.fit)).size(mapsize);
table.table(Styles.black, desc -> { table.table(Styles.black, desc -> {
desc.top(); desc.top();
@@ -199,13 +204,17 @@ public class MapsDialog extends FloatingDialog{
} }
}).fillX().height(54f).marginLeft(10); }).fillX().height(54f).marginLeft(10);
table.addImageTextButton("$delete", Icon.trash16Small, () -> { table.addImageTextButton(map.workshop ? "$view.workshop" : "$delete", map.workshop ? Icon.linkSmall : Icon.trash16Small, () -> {
ui.showConfirm("$confirm", Core.bundle.format("map.delete", map.name()), () -> { if(map.workshop){
maps.removeMap(map); platform.viewMapListing(map);
dialog.hide(); }else{
setup(); ui.showConfirm("$confirm", Core.bundle.format("map.delete", map.name()), () -> {
}); maps.removeMap(map);
}).fillX().height(54f).marginLeft(10).disabled(!map.custom).touchable(map.custom ? Touchable.enabled : Touchable.disabled); dialog.hide();
setup();
});
}
}).fillX().height(54f).marginLeft(10).disabled(!map.workshop && !map.custom);
dialog.show(); dialog.show();
} }

View File

@@ -58,7 +58,7 @@ public class PausedDialog extends FloatingDialog{
cont.row(); cont.row();
cont.addButton("$hostserver", () -> { cont.addButton("$hostserver", () -> {
if(net.active() && steam){ if(net.server() && steam){
platform.inviteFriends(); platform.inviteFriends();
}else{ }else{
if(steam){ if(steam){
@@ -67,12 +67,12 @@ public class PausedDialog extends FloatingDialog{
ui.host.show(); ui.host.show();
} }
} }
}).disabled(b -> net.active() && !steam).colspan(2).width(dw * 2 + 20f).update(e -> e.setText(net.active() && steam ? "$invitefriends" : "$hostserver")); }).disabled(b -> !((steam && net.server()) || !net.active())).colspan(2).width(dw * 2 + 20f).update(e -> e.setText(net.server() && steam ? "$invitefriends" : "$hostserver"));
} }
cont.row(); cont.row();
cont.addButton("$quit", this::showQuitConfirm).colspan(2).width(dw + 10f); cont.addButton("$quit", this::showQuitConfirm).colspan(2).width(dw + 10f).update(s -> s.setText(control.saves.getCurrent() != null && control.saves.getCurrent().isAutosave() ? "$save.quit" : "$quit"));
}else{ }else{
cont.defaults().size(120f).pad(5); cont.defaults().size(120f).pad(5);
@@ -91,7 +91,7 @@ public class PausedDialog extends FloatingDialog{
cont.addRowImageTextButton("$hostserver.mobile", Icon.host, ui.host::show).disabled(b -> net.active()); cont.addRowImageTextButton("$hostserver.mobile", Icon.host, ui.host::show).disabled(b -> net.active());
cont.addRowImageTextButton("$quit", Icon.quit, this::showQuitConfirm); cont.addRowImageTextButton("$quit", Icon.quit, this::showQuitConfirm).update(s -> s.setText(control.saves.getCurrent() != null && control.saves.getCurrent().isAutosave() ? "$save.quit" : "$quit"));
} }
} }

View File

@@ -17,6 +17,7 @@ import io.anuke.mindustry.core.GameState.*;
import io.anuke.mindustry.game.EventType.*; import io.anuke.mindustry.game.EventType.*;
import io.anuke.mindustry.gen.*; import io.anuke.mindustry.gen.*;
import io.anuke.mindustry.graphics.*; import io.anuke.mindustry.graphics.*;
import io.anuke.mindustry.input.*;
import io.anuke.mindustry.ui.*; import io.anuke.mindustry.ui.*;
import static io.anuke.arc.Core.bundle; import static io.anuke.arc.Core.bundle;
@@ -126,24 +127,21 @@ public class SettingsMenuDialog extends SettingsDialog{
t.row(); t.row();
//iOS doesn't have a file chooser. t.addButton("$data.import", style, () -> ui.showConfirm("$confirm", "$data.import.confirm", () -> platform.showFileChooser(true, "zip", file -> {
//if(!ios){ try{
t.addButton("$data.import", style, () -> ui.showConfirm("$confirm", "$data.import.confirm", () -> platform.showFileChooser(true, "zip", file -> { data.importData(file);
try{ Core.app.exit();
data.importData(file); }catch(IllegalArgumentException e){
Core.app.exit(); ui.showErrorMessage("$data.invalid");
}catch(IllegalArgumentException e){ }catch(Exception e){
e.printStackTrace();
if(e.getMessage() == null || !e.getMessage().contains("too short")){
ui.showException(e);
}else{
ui.showErrorMessage("$data.invalid"); ui.showErrorMessage("$data.invalid");
}catch(Exception e){
e.printStackTrace();
if(e.getMessage() == null || !e.getMessage().contains("too short")){
ui.showException(e);
}else{
ui.showErrorMessage("$data.invalid");
}
} }
}))); }
//} })));
}); });
ScrollPane pane = new ScrollPane(prefs); ScrollPane pane = new ScrollPane(prefs);
@@ -205,8 +203,20 @@ public class SettingsMenuDialog extends SettingsDialog{
game.screenshakePref(); game.screenshakePref();
if(mobile){ if(mobile){
game.checkPref("autotarget", true); game.checkPref("autotarget", true);
game.checkPref("keyboard", false); game.checkPref("keyboard", false, val -> control.setInput(val ? new DesktopInput() : new MobileInput()));
if(Core.settings.getBool("keyboard")){
control.setInput(new DesktopInput());
}
} }
//the issue with touchscreen support on desktop is that:
//1) I can't test it
//2) the SDL backend doesn't support multitouch
/*else{
game.checkPref("touchscreen", false, val -> control.setInput(!val ? new DesktopInput() : new MobileInput()));
if(Core.settings.getBool("touchscreen")){
control.setInput(new MobileInput());
}
}*/
game.sliderPref("saveinterval", 60, 10, 5 * 120, i -> Core.bundle.format("setting.seconds", i)); game.sliderPref("saveinterval", 60, 10, 5 * 120, i -> Core.bundle.format("setting.seconds", i));
if(!mobile){ if(!mobile){
@@ -294,7 +304,7 @@ public class SettingsMenuDialog extends SettingsDialog{
} }
}); });
graphics.checkPref("linear", false, b -> { graphics.checkPref("linear", !mobile, b -> {
for(Texture tex : Core.atlas.getTextures()){ for(Texture tex : Core.atlas.getTextures()){
TextureFilter filter = b ? TextureFilter.Linear : TextureFilter.Nearest; TextureFilter filter = b ? TextureFilter.Linear : TextureFilter.Nearest;
tex.setFilter(filter, filter); tex.setFilter(filter, filter);

View File

@@ -1,17 +1,14 @@
package io.anuke.mindustry.ui.fragments; package io.anuke.mindustry.ui.fragments;
import io.anuke.arc.Core; import io.anuke.arc.*;
import io.anuke.arc.math.Interpolation; import io.anuke.arc.math.*;
import io.anuke.arc.math.geom.Vector2; import io.anuke.arc.scene.*;
import io.anuke.arc.scene.Element; import io.anuke.arc.scene.actions.*;
import io.anuke.arc.scene.Group; import io.anuke.arc.scene.ui.layout.*;
import io.anuke.arc.scene.actions.Actions; import io.anuke.arc.util.*;
import io.anuke.arc.scene.ui.layout.Table; import io.anuke.mindustry.content.*;
import io.anuke.arc.util.Align; import io.anuke.mindustry.core.GameState.*;
import io.anuke.mindustry.content.Blocks; import io.anuke.mindustry.world.*;
import io.anuke.mindustry.core.GameState.State;
import io.anuke.mindustry.world.Block;
import io.anuke.mindustry.world.Tile;
import static io.anuke.mindustry.Vars.*; import static io.anuke.mindustry.Vars.*;
@@ -66,10 +63,10 @@ public class BlockConfigFragment extends Fragment{
} }
table.setOrigin(Align.center); table.setOrigin(Align.center);
Vector2 pos = Core.input.mouseScreen(tile.drawx(), tile.drawy() - tile.block().size * tilesize / 2f - 1);
table.setPosition(pos.x, pos.y, Align.top);
if(configTile == null || configTile.block() == Blocks.air || configTile.block() != configBlock){ if(configTile == null || configTile.block() == Blocks.air || configTile.block() != configBlock){
hideConfig(); hideConfig();
}else{
configTile.block().updateTableAlign(tile, table);
} }
}); });
} }

View File

@@ -32,7 +32,7 @@ import static io.anuke.mindustry.Vars.*;
public class BlockInventoryFragment extends Fragment{ public class BlockInventoryFragment extends Fragment{
private final static float holdWithdraw = 20f; private final static float holdWithdraw = 20f;
private Table table; private Table table = new Table();
private Tile tile; private Tile tile;
private float holdTime = 0f; private float holdTime = 0f;
private boolean holding; private boolean holding;
@@ -52,7 +52,6 @@ public class BlockInventoryFragment extends Fragment{
@Override @Override
public void build(Group parent){ public void build(Group parent){
table = new Table();
table.setName("inventory"); table.setName("inventory");
table.setTransform(true); table.setTransform(true);
parent.setTransform(true); parent.setTransform(true);
@@ -150,7 +149,7 @@ public class BlockInventoryFragment extends Fragment{
image.addListener(new InputListener(){ image.addListener(new InputListener(){
@Override @Override
public boolean touchDown(InputEvent event, float x, float y, int pointer, KeyCode button){ public boolean touchDown(InputEvent event, float x, float y, int pointer, KeyCode button){
if(!canPick.get() || !tile.entity.items.has(item)) return false; if(!canPick.get() || tile == null || tile.entity == null || tile.entity.items == null || !tile.entity.items.has(item)) return false;
int amount = Math.min(1, player.maxAccepted(item)); int amount = Math.min(1, player.maxAccepted(item));
if(amount > 0){ if(amount > 0){
Call.requestItem(player, tile, item, amount); Call.requestItem(player, tile, item, amount);

View File

@@ -100,7 +100,7 @@ public class ChatFragment extends Table{
fieldlabel.setStyle(fieldlabel.getStyle()); fieldlabel.setStyle(fieldlabel.getStyle());
chatfield = new TextField("", new TextField.TextFieldStyle(scene.getStyle(TextField.TextFieldStyle.class))); chatfield = new TextField("", new TextField.TextFieldStyle(scene.getStyle(TextField.TextFieldStyle.class)));
chatfield.setFilter((field, c) -> field.getText().length() < Vars.maxTextLength); chatfield.setMaxLength(Vars.maxTextLength);
chatfield.getStyle().background = null; chatfield.getStyle().background = null;
chatfield.getStyle().font = Fonts.chat; chatfield.getStyle().font = Fonts.chat;
chatfield.getStyle().fontColor = Color.white; chatfield.getStyle().fontColor = Color.white;

View File

@@ -572,9 +572,6 @@ public class HudFragment extends Fragment{
} }
shown = !shown; shown = !shown;
if(flip != null){
flip.getParent().act(Core.graphics.getDeltaTime());
}
} }
private void addWaveTable(Button table){ private void addWaveTable(Button table){

View File

@@ -26,7 +26,7 @@ public class PlacementFragment extends Fragment{
Array<Block> returnArray = new Array<>(); Array<Block> returnArray = new Array<>();
Array<Category> returnCatArray = new Array<>(); Array<Category> returnCatArray = new Array<>();
boolean[] categoryEmpty = new boolean[Category.values().length]; boolean[] categoryEmpty = new boolean[Category.all.length];
Category currentCategory = Category.distribution; Category currentCategory = Category.distribution;
Block hovered, lastDisplay; Block hovered, lastDisplay;
Tile lastHover; Tile lastHover;
@@ -91,7 +91,7 @@ public class PlacementFragment extends Fragment{
int i = 0; int i = 0;
for(KeyCode key : inputCatGrid){ for(KeyCode key : inputCatGrid){
if(Core.input.keyDown(key)){ if(Core.input.keyDown(key)){
input.block = getByCategory(Category.values()[i]).first(); input.block = getByCategory(Category.all[i]).first();
currentCategory = input.block.buildCategory; currentCategory = input.block.buildCategory;
} }
i++; i++;
@@ -116,7 +116,6 @@ public class PlacementFragment extends Fragment{
full.bottom().right().visible(() -> ui.hudfrag.shown()); full.bottom().right().visible(() -> ui.hudfrag.shown());
full.table(frame -> { full.table(frame -> {
InputHandler input = control.input;
//rebuilds the category table with the correct recipes //rebuilds the category table with the correct recipes
Runnable rebuildCategory = () -> { Runnable rebuildCategory = () -> {
@@ -140,7 +139,7 @@ public class PlacementFragment extends Fragment{
ImageButton button = blockTable.addImageButton(Icon.lockedSmall, Styles.selecti, () -> { ImageButton button = blockTable.addImageButton(Icon.lockedSmall, Styles.selecti, () -> {
if(unlocked(block)){ if(unlocked(block)){
input.block = input.block == block ? null : block; control.input.block = control.input.block == block ? null : block;
} }
}).size(46f).group(group).name("block-" + block.name).get(); }).size(46f).group(group).name("block-" + block.name).get();
@@ -150,7 +149,7 @@ public class PlacementFragment extends Fragment{
TileEntity core = player.getClosestCore(); TileEntity core = player.getClosestCore();
Color color = state.rules.infiniteResources || (core != null && (core.items.has(block.buildRequirements, state.rules.buildCostMultiplier) || state.rules.infiniteResources)) ? Color.white : Color.gray; Color color = state.rules.infiniteResources || (core != null && (core.items.has(block.buildRequirements, state.rules.buildCostMultiplier) || state.rules.infiniteResources)) ? Color.white : Color.gray;
button.forEach(elem -> elem.setColor(color)); button.forEach(elem -> elem.setColor(color));
button.setChecked(input.block == block); button.setChecked(control.input.block == block);
}); });
button.hovered(() -> hovered = block); button.hovered(() -> hovered = block);
@@ -250,7 +249,7 @@ public class PlacementFragment extends Fragment{
blocksSelect.margin(4).marginTop(0); blocksSelect.margin(4).marginTop(0);
blocksSelect.table(blocks -> blockTable = blocks).grow(); blocksSelect.table(blocks -> blockTable = blocks).grow();
blocksSelect.row(); blocksSelect.row();
blocksSelect.table(input::buildUI).growX(); blocksSelect.table(control.input::buildUI).name("inputTable").growX();
}).fillY().bottom().touchable(Touchable.enabled); }).fillY().bottom().touchable(Touchable.enabled);
frame.table(categories -> { frame.table(categories -> {
categories.defaults().size(50f); categories.defaults().size(50f);
@@ -258,7 +257,7 @@ public class PlacementFragment extends Fragment{
ButtonGroup<ImageButton> group = new ButtonGroup<>(); ButtonGroup<ImageButton> group = new ButtonGroup<>();
//update category empty values //update category empty values
for(Category cat : Category.values()){ for(Category cat : Category.all){
Array<Block> blocks = getByCategory(cat); Array<Block> blocks = getByCategory(cat);
categoryEmpty[cat.ordinal()] = blocks.isEmpty() || !unlocked(blocks.first()); categoryEmpty[cat.ordinal()] = blocks.isEmpty() || !unlocked(blocks.first());
} }
@@ -281,7 +280,7 @@ public class PlacementFragment extends Fragment{
rebuildCategory.run(); rebuildCategory.run();
frame.update(() -> { frame.update(() -> {
if(gridUpdate(input)) rebuildCategory.run(); if(gridUpdate(control.input)) rebuildCategory.run();
}); });
}); });
}); });
@@ -289,7 +288,7 @@ public class PlacementFragment extends Fragment{
Array<Category> getCategories(){ Array<Category> getCategories(){
returnCatArray.clear(); returnCatArray.clear();
returnCatArray.addAll(Category.values()); returnCatArray.addAll(Category.all);
returnCatArray.sort((c1, c2) -> Boolean.compare(categoryEmpty[c1.ordinal()], categoryEmpty[c2.ordinal()])); returnCatArray.sort((c1, c2) -> Boolean.compare(categoryEmpty[c1.ordinal()], categoryEmpty[c2.ordinal()]));
return returnCatArray; return returnCatArray;
} }

View File

@@ -129,6 +129,11 @@ public class PlayerListFragment extends Fragment{
t.addImageButton(Icon.zoomSmall, Styles.clearPartiali, () -> Call.onAdminRequest(user, AdminAction.trace)); t.addImageButton(Icon.zoomSmall, Styles.clearPartiali, () -> Call.onAdminRequest(user, AdminAction.trace));
}).padRight(12).size(bs + 10f, bs); }).padRight(12).size(bs + 10f, bs);
}else if((!user.isLocal && !user.isAdmin) && net.client() && playerGroup.size() >= 3){ //votekick
button.add().growY();
button.addImageButton(Icon.banSmall, Styles.clearPartiali,
() -> ui.showConfirm("$confirm", "$confirmvotekick", () -> Call.sendChatMessage("/votekick " + user.name))).size(h);
} }
content.add(button).padBottom(-6).width(350f).maxHeight(h + 14); content.add(button).padBottom(-6).width(350f).maxHeight(h + 14);

View File

@@ -440,11 +440,17 @@ public class Block extends BlockStorage{
/** /**
* Called when this block is tapped to build a UI on the table. * Called when this block is tapped to build a UI on the table.
* {@link #configurable} able} must return true for this to be called. * {@link #configurable} must return true for this to be called.
*/ */
public void buildTable(Tile tile, Table table){ public void buildTable(Tile tile, Table table){
} }
/** Update table alignment after configuring.*/
public void updateTableAlign(Tile tile, Table table){
Vector2 pos = Core.input.mouseScreen(tile.drawx(), tile.drawy() - tile.block().size * tilesize / 2f - 1);
table.setPosition(pos.x, pos.y, Align.top);
}
/** /**
* Called when another tile is tapped while this block is selected. * Called when another tile is tapped while this block is selected.
* Returns whether or not this block should be deselected. * Returns whether or not this block should be deselected.

View File

@@ -111,7 +111,7 @@ public abstract class BlockStorage extends UnlockableContent{
Tile other = proximity.get((i + dump) % proximity.size); Tile other = proximity.get((i + dump) % proximity.size);
Tile in = Edges.getFacingEdge(tile, other); Tile in = Edges.getFacingEdge(tile, other);
if(other.getTeam() == tile.getTeam() && other.block().hasLiquids && canDumpLiquid(tile, other, liquid)){ if(other.getTeam() == tile.getTeam() && other.block().hasLiquids && canDumpLiquid(tile, other, liquid) && other.entity.liquids != null){
float ofract = other.entity.liquids.get(liquid) / other.block().liquidCapacity; float ofract = other.entity.liquids.get(liquid) / other.block().liquidCapacity;
float fract = tile.entity.liquids.get(liquid) / liquidCapacity; float fract = tile.entity.liquids.get(liquid) / liquidCapacity;

Some files were not shown because too many files have changed in this diff Show More