Silly Minecraft mod that adds Asbestos

Compare changes

Choose any two refs to compare.

Changed files
+2890 -2220
gradle
src
common
main
kotlin
resources
assets
data
fabric
forge
main
kotlin
resources
assets
data
+4
.gitignore
··· 102 102 103 103 .gradle 104 104 build/ 105 + .kotlin 105 106 106 107 # Ignore Gradle GUI config 107 108 gradle-app.setting ··· 116 117 117 118 # Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored) 118 119 !gradle-wrapper.jar 120 + 121 + .envrc 122 + .direnv/
+103 -44
build.gradle.kts
··· 1 + import net.msrandom.stubs.GenerateStubApi 2 + import org.jetbrains.kotlin.gradle.dsl.KotlinProjectExtension 3 + import org.jetbrains.kotlin.gradle.tasks.KotlinCompile 4 + import org.jetbrains.kotlin.gradle.dsl.KotlinVersion 5 + 1 6 plugins { 2 7 id("maven-publish") 3 8 kotlin("jvm") version libs.versions.kotlin ··· 11 16 mavenFabric() 12 17 main() 13 18 } 14 - maven("https://maven.wispforest.io") 15 19 maven("https://maven.kosmx.dev/") 16 - maven("https://maven.ladysnake.org/releases") 17 - maven("https://maven.is-immensely.gay/releases") 18 - maven("https://maven.is-immensely.gay/nightly") 20 + maven("https://maven.wispforest.io") 19 21 maven("https://maven.terraformersmc.com/") 20 22 maven("https://maven.isxander.dev/releases") 23 + maven("https://maven.is-immensely.gay/nightly") 24 + maven("https://maven.is-immensely.gay/releases") 25 + maven("https://nexus.resourcefulbees.com/repository/maven-public/") 26 + maven("https://pkgs.dev.azure.com/djtheredstoner/DevAuth/_packaging/public/maven/v1") 21 27 } 22 28 23 29 version = "1.0.0" ··· 32 38 description = "Adds Asbestos and all of it's consequences" 33 39 license = "Polyform Shield 1.0.0" 34 40 icon = "assets/asbestos/icon.png" 41 + url = "https://tangled.sh/@lesbian.skin/cfs" 42 + sources = "https://tangled.sh/@lesbian.skin/cfs" 35 43 36 - custom(buildMap { 37 - put("cardinal-components", listOf("asbestos:mesothelioma")) 38 - }) 44 + author("Naomi Roberts") 45 + } 39 46 40 - author("Naomi Roberts") 47 + common { 48 + dependencies { 49 + modCompileOnly(libs.kritter) 50 + modCompileOnly(libs.cynosure) 51 + } 41 52 } 42 53 43 - singleTarget { 44 - fabric { 45 - loaderVersion = libs.versions.fabric.loader 54 + fabric { 55 + loaderVersion = libs.versions.fabric.loader 56 + 57 + includedClient() 58 + 59 + withSourcesJar() 60 + 61 + runs { 62 + client() 63 + server() 64 + } 65 + 66 + dependencies { 67 + // fabric stuff 68 + fabricApi(libs.versions.fabric.api) 69 + modImplementation(libs.fabric.kotlin) 70 + 71 + // kritter 72 + modImplementation(libs.fabric.kritter) 73 + include(libs.fabric.kritter) 74 + 75 + // cynosure 76 + modImplementation(libs.fabric.cynosure) 77 + 78 + // yacl 79 + modImplementation(libs.fabric.yacl) 80 + 81 + // modmenu 82 + modImplementation(libs.fabric.modmenu) 83 + 84 + // DevAuth 85 + modRuntimeOnly(libs.fabric.devauth) 86 + } 87 + 88 + metadata { 89 + custom("cynosure", mapOf( 90 + "autosubscription" to true 91 + )) 92 + 93 + entrypoint("main") { 94 + value = "xyz.naomieow.asbestos.AsbestosFabric::init" 95 + adapter = "kotlin" 96 + } 97 + entrypoint("client") { 98 + value = "xyz.naomieow.asbestos.client.AsbestosClientFabric::init" 99 + adapter = "kotlin" 100 + } 101 + entrypoint("modmenu") { 102 + value = "xyz.naomieow.asbestos.client.ModMenuIntegration" 103 + adapter = "kotlin" 104 + } 105 + } 46 106 47 - includedClient() 107 + forge { 108 + loaderVersion = libs.versions.forge.loader 48 109 49 110 runs { 50 111 server() ··· 52 113 } 53 114 54 115 dependencies { 55 - // fabric stuff 56 - modImplementation(libs.fabric.kotlin) 57 - modImplementation(libs.fabric.loader) 58 - modImplementation(libs.fabric.api) 116 + // forge stuff 117 + modImplementation(libs.forge.kotlin) 59 118 60 119 // kritter 61 - modCompileOnly(libs.kritter) 62 - modImplementation(libs.fabric.kritter) 63 - include(libs.fabric.kritter) 120 + modImplementation(libs.forge.kritter) 121 + include(libs.forge.kritter) 64 122 65 - // yacl 66 - modImplementation(libs.fabric.yacl) 123 + // cynosure 124 + modImplementation(libs.forge.cynosure) 67 125 68 - // Cardinal Components API 69 - modImplementation(libs.cca.base) 70 - include(libs.cca.base) 71 - modImplementation(libs.cca.entity) 72 - include(libs.cca.entity) 126 + // yacl 127 + modImplementation(libs.forge.yacl) 73 128 74 - // modmenu 75 - modImplementation(libs.fabric.modmenu) 129 + // DevAuth 130 + modRuntimeOnly(libs.forge.devauth) 76 131 } 77 132 78 133 metadata { 79 - entrypoint("main") { 80 - value = "xyz.naomieow.asbestos.AsbestosMod" 81 - adapter = "kotlin" 82 - } 83 - entrypoint("client") { 84 - value = "xyz.naomieow.asbestos.AsbestosModClient" 85 - adapter = "kotlin" 86 - } 87 - entrypoint("cardinal-components-entity") { 88 - value = "xyz.naomieow.asbestos.AsbestosMod" 89 - adapter = "kotlin" 90 - } 91 - entrypoint("modmenu") { 92 - value = "xyz.naomieow.asbestos.config.ModMenuIntegration" 93 - adapter = "kotlin" 94 - } 134 + loaderVersion("4") 135 + modLoader = "kotlinforforge" 95 136 } 137 + 96 138 } 139 + } 140 + } 141 + 142 + configure<KotlinProjectExtension> { 143 + jvmToolchain(17) 144 + explicitApi() 145 + } 146 + 147 + tasks.named("createCommonApiStub", GenerateStubApi::class) { 148 + excludes.add(libs.kritter.get().group) 149 + excludes.add(libs.cynosure.get().group) 150 + } 151 + 152 + tasks.withType<KotlinCompile> { 153 + compilerOptions { 154 + languageVersion = KotlinVersion.KOTLIN_2_2 155 + freeCompilerArgs = listOf("-Xmulti-platform", "-Xno-check-actual", "-Xexpect-actual-classes") 97 156 } 98 157 }
+27
flake.lock
··· 1 + { 2 + "nodes": { 3 + "nixpkgs": { 4 + "locked": { 5 + "lastModified": 1762361079, 6 + "narHash": "sha256-lz718rr1BDpZBYk7+G8cE6wee3PiBUpn8aomG/vLLiY=", 7 + "owner": "NixOS", 8 + "repo": "nixpkgs", 9 + "rev": "ffcdcf99d65c61956d882df249a9be53e5902ea5", 10 + "type": "github" 11 + }, 12 + "original": { 13 + "owner": "NixOS", 14 + "ref": "nixpkgs-unstable", 15 + "repo": "nixpkgs", 16 + "type": "github" 17 + } 18 + }, 19 + "root": { 20 + "inputs": { 21 + "nixpkgs": "nixpkgs" 22 + } 23 + } 24 + }, 25 + "root": "root", 26 + "version": 7 27 + }
+41
flake.nix
··· 1 + { 2 + inputs = { 3 + nixpkgs.url = "github:NixOS/nixpkgs/nixpkgs-unstable"; 4 + }; 5 + 6 + outputs = {nixpkgs, ...} @ inputs: let 7 + lib = nixpkgs.lib; 8 + supportedSystems = ["x86_64-linux" "aarch64-linux" "x86_64-darwin" "aarch64-darwin"]; 9 + forEachSupportedSystem = f: 10 + lib.genAttrs supportedSystems (system: 11 + f { 12 + pkgs = import nixpkgs {inherit system;}; 13 + }); 14 + in { 15 + devShells = forEachSupportedSystem ({pkgs}: let 16 + java = pkgs.temurin-bin-17; 17 + 18 + nativeBuildInputs = with pkgs; [ 19 + java 20 + kotlin 21 + kotlin-language-server 22 + ]; 23 + 24 + buildInputs = with pkgs; [ 25 + libGL 26 + glfw3-minecraft 27 + flite 28 + libpulseaudio 29 + ]; 30 + in { 31 + default = pkgs.mkShell { 32 + inherit nativeBuildInputs buildInputs; 33 + 34 + env = { 35 + LD_LIBRARY_PATH = lib.makeLibraryPath buildInputs; 36 + JAVA_HOME = "${java.home}"; 37 + }; 38 + }; 39 + }); 40 + }; 41 + }
+1 -1
gradle/wrapper/gradle-wrapper.properties
··· 1 1 distributionBase=GRADLE_USER_HOME 2 2 distributionPath=wrapper/dists 3 - distributionUrl=https\://services.gradle.org/distributions/gradle-8.14.2-bin.zip 3 + distributionUrl=https\://services.gradle.org/distributions/gradle-9.1.0-bin.zip 4 4 networkTimeout=10000 5 5 zipStoreBase=GRADLE_USER_HOME 6 6 zipStorePath=wrapper/dists
+21 -11
libs.versions.toml
··· 1 1 [versions] 2 2 # Common 3 - cloche = "0.10.13" 4 - kotlin = "2.1.0" 5 - cca = "5.2.2" 6 - kritter = "0.1.1+1.20.1" 3 + cloche = "0.16.8" 4 + kotlin = "2.2.0" 5 + kritter = "0.1.12+1.20.1" 6 + cynosure = "0.1.0.189" 7 + devauth = "1.2.1" 7 8 # Fabric 8 - fabric-kotlin = "1.13.0+kotlin.2.1.0" 9 - fabric-loader= "0.16.14" 10 - fabric-api = "0.92.6+1.20.1" 9 + fabric-kotlin = "1.13.4+kotlin.2.2.0" 10 + fabric-loader= "0.17.3" 11 + fabric-api = "0.92.6" 11 12 fabric-modmenu = "7.2.2" 12 13 fabric-yacl = "3.6.6+1.20.1-fabric" 14 + # Forge 15 + forge-kotlin = "4.11.0" 16 + forge-loader = "47.4.0" 17 + forge-yacl = "3.6.6+1.20.1-forge" 13 18 14 19 [libraries] 15 20 # Common 16 - cca-base = { module = "dev.onyxstudios.cardinal-components-api:cardinal-components-base", version.ref = "cca" } 17 - cca-entity = { module = "dev.onyxstudios.cardinal-components-api:cardinal-components-entity", version.ref = "cca" } 18 21 kritter = { module = "uwu.serenity.kritter:kritter-common", version.ref = "kritter" } 22 + cynosure = { module = "dev.mayaqq.cynosure:cynosure-common", version.ref = "cynosure" } 19 23 # Fabric 20 24 fabric-kotlin = { module = "net.fabricmc:fabric-language-kotlin", version.ref = "fabric-kotlin" } 21 - fabric-loader = { module = "net.fabricmc:fabric-loader", version.ref = "fabric-loader" } 22 - fabric-api = { module = "net.fabricmc.fabric-api:fabric-api", version.ref = "fabric-api" } 23 25 fabric-kritter = { module = "uwu.serenity.kritter:kritter-fabric", version.ref = "kritter" } 24 26 fabric-modmenu = { module = "com.terraformersmc:modmenu", version.ref = "fabric-modmenu" } 25 27 fabric-yacl = { module = "dev.isxander:yet-another-config-lib", version.ref = "fabric-yacl" } 28 + fabric-cynosure = { module = "dev.mayaqq.cynosure:cynosure-fabric", version.ref = "cynosure" } 29 + fabric-devauth = { module = "me.djtheredstoner:DevAuth-fabric", version.ref = "devauth" } 30 + # Forge 31 + forge-kotlin = { module = "thedarkcolour:kotlinforforge", version.ref = "forge-kotlin" } 32 + forge-kritter = { module = "uwu.serenity.kritter:kritter-forge", version.ref = "kritter" } 33 + forge-yacl = { module = "dev.isxander:yet-another-config-lib", version.ref = "forge-yacl" } 34 + forge-cynosure = { module = "dev.mayaqq.cynosure:cynosure-forge", version.ref = "cynosure" } 35 + forge-devauth = { module = "me.djtheredstoner:DevAuth-forge-latest", version.ref = "devauth" } 26 36 27 37 [plugins] 28 38 cloche = { id = "earth.terrarium.cloche", version.ref = "cloche" }
+81
src/common/main/kotlin/xyz/naomieow/asbestos/Asbestos.kt
··· 1 + package xyz.naomieow.asbestos 2 + 3 + import dev.mayaqq.cynosure.blocks.poi.anyInRange 4 + import dev.mayaqq.cynosure.events.api.EventSubscriber 5 + import dev.mayaqq.cynosure.events.api.Subscription 6 + import dev.mayaqq.cynosure.events.entity.player.PlayerTickEvent 7 + import net.minecraft.core.registries.Registries 8 + import net.minecraft.resources.ResourceKey 9 + import net.minecraft.resources.ResourceLocation 10 + import net.minecraft.server.level.ServerLevel 11 + import net.minecraft.world.effect.MobEffectInstance 12 + import net.minecraft.world.level.block.Block 13 + import net.minecraft.world.level.levelgen.placement.PlacedFeature 14 + import org.slf4j.Logger 15 + import org.slf4j.LoggerFactory 16 + import uwu.serenity.kritter.RegistryManager 17 + import xyz.naomieow.asbestos.block.AsbestosBlocks 18 + import xyz.naomieow.asbestos.config.AsbestosConfig 19 + import xyz.naomieow.asbestos.item.AsbestosCreativeTabs 20 + import xyz.naomieow.asbestos.item.AsbestosItems 21 + import xyz.naomieow.asbestos.menu.ModMenuTypes 22 + import xyz.naomieow.asbestos.mesothelioma.getMesothelioma 23 + import xyz.naomieow.asbestos.mesothelioma.setMesothelioma 24 + import xyz.naomieow.asbestos.mob_effect.AsbestosMobEffects 25 + import xyz.naomieow.asbestos.poi.AsbestosPOIs 26 + import xyz.naomieow.asbestos.util.countPpePieces 27 + import xyz.naomieow.asbestos.util.isProtectedFromAsbestos 28 + 29 + public const val MOD_ID: String = "asbestos" 30 + public const val MOD_NAME: String = "Carcinogenic Fibrous Silicate" 31 + 32 + @Suppress("NOTHING_TO_INLINE") 33 + public inline fun id(path: String): ResourceLocation { 34 + return ResourceLocation(MOD_ID, path) 35 + } 36 + 37 + @EventSubscriber 38 + public object Asbestos : 39 + Logger by LoggerFactory.getLogger(MOD_NAME), 40 + RegistryManager by RegistryManager(MOD_ID) { 41 + public val harmfulPassiveBlocks: Array<Block> by lazy { arrayOf(AsbestosBlocks.AsbestosBlock) } 42 + public val serpentinitePlacedFeatureKey: ResourceKey<PlacedFeature> = ResourceKey.create( 43 + Registries.PLACED_FEATURE, 44 + id("serpentinite") 45 + ) 46 + 47 + public fun init() { 48 + AsbestosMobEffects.register() 49 + AsbestosBlocks.register() 50 + AsbestosItems.register() 51 + AsbestosCreativeTabs.register() 52 + AsbestosPOIs.register() 53 + ModMenuTypes.register() 54 + info("Now entitled to financial compensation..") 55 + } 56 + 57 + 58 + @Subscription 59 + public fun onPlayerTick(event: PlayerTickEvent.Begin) { 60 + val player = event.player 61 + when (val level = player.level()) { 62 + is ServerLevel -> { 63 + if (level.poiManager.anyInRange( 64 + AsbestosPOIs.carcinogenicBlock, 65 + player.blockPosition(), 66 + AsbestosConfig.offset 67 + ) 68 + && level.server.tickCount % (AsbestosConfig.period * (1 + player.countPpePieces()) * 20) == 0.0f 69 + && !player.isProtectedFromAsbestos() 70 + ) { 71 + val exposure = player.getMesothelioma() 72 + player.setMesothelioma(exposure + 1) 73 + info("Set player exposure to ${player.getMesothelioma()} after ${AsbestosConfig.period * (1 + player.countPpePieces())} seconds, exposure was previously $exposure") 74 + if (exposure >= AsbestosConfig.threshold) { 75 + player.addEffect(MobEffectInstance(AsbestosMobEffects.mesotheliomaMobEffect, -1)) 76 + } 77 + } 78 + } 79 + } 80 + } 81 + }
+49
src/common/main/kotlin/xyz/naomieow/asbestos/armor/ProtectiveMaterial.kt
··· 1 + package xyz.naomieow.asbestos.armor 2 + 3 + import net.minecraft.sounds.SoundEvent 4 + import net.minecraft.sounds.SoundEvents 5 + import net.minecraft.world.item.ArmorItem 6 + import net.minecraft.world.item.ArmorMaterial 7 + import net.minecraft.world.item.Items 8 + import net.minecraft.world.item.crafting.Ingredient 9 + 10 + public class ProtectiveMaterial : ArmorMaterial { 11 + override fun getDurabilityForType(type: ArmorItem.Type): Int { 12 + return BASE_DURABILITY[type.slot.index] 13 + } 14 + 15 + override fun getDefenseForType(type: ArmorItem.Type): Int { 16 + return PROTECTION_VALUES[type.slot.index] 17 + } 18 + 19 + override fun getEnchantmentValue(): Int { 20 + return 4 21 + } 22 + 23 + override fun getEquipSound(): SoundEvent { 24 + return SoundEvents.WOOL_HIT 25 + } 26 + 27 + override fun getRepairIngredient(): Ingredient { 28 + return Ingredient.of(Items.STRING) 29 + } 30 + 31 + override fun getName(): String { 32 + return "asbestos_protective" 33 + } 34 + 35 + override fun getToughness(): Float { 36 + return 0f 37 + } 38 + 39 + override fun getKnockbackResistance(): Float { 40 + return 0f 41 + } 42 + 43 + public companion object { 44 + private val BASE_DURABILITY = intArrayOf(13, 15, 16, 11) 45 + private val PROTECTION_VALUES = intArrayOf(1, 1, 2, 1) 46 + 47 + public val INSTANCE: ProtectiveMaterial = ProtectiveMaterial() 48 + } 49 + }
+62
src/common/main/kotlin/xyz/naomieow/asbestos/block/AsbestosBlocks.kt
··· 1 + package xyz.naomieow.asbestos.block 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.world.level.block.Block 5 + import net.minecraft.world.level.block.Blocks 6 + import uwu.serenity.kritter.api.Registrar 7 + import uwu.serenity.kritter.stdlib.block 8 + import xyz.naomieow.asbestos.Asbestos 9 + 10 + @Suppress("UNUSED") 11 + public object AsbestosBlocks : Registrar<Block> by Asbestos..Registries.BLOCK { 12 + public val AsbestosBlock: Block by block("asbestos_block", { properties -> 13 + CarcinogenicBlock(properties, 40) 14 + }) { 15 + copyProperties(Blocks::WHITE_WOOL) 16 + properties { 17 + destroyTime(1.0f) 18 + simpleItem() 19 + } 20 + } 21 + 22 + public val SerpentiniteBlock: Block by block("serpentinite_block", { properties -> 23 + CarcinogenicBlock(properties, 20) 24 + }) { 25 + copyProperties(Blocks::STONE) 26 + properties { 27 + destroyTime(3.0f) 28 + requiresCorrectToolForDrops() 29 + simpleItem() 30 + } 31 + } 32 + 33 + public val PopcornCeilingBlock: Block by block("popcorn_ceiling_block", { properties -> 34 + CarcinogenicBlock(properties, 20) 35 + }) { 36 + copyProperties(Blocks::OAK_PLANKS) 37 + properties { 38 + destroyTime(2.0f) 39 + simpleItem() 40 + } 41 + } 42 + 43 + public val AsbestosTileBlock: Block by block("asbestos_tile_block", { properties -> 44 + CarcinogenicBlock(properties, 20) 45 + }) { 46 + copyProperties(Blocks::NETHER_BRICKS) 47 + properties { 48 + destroyTime(3.0f) 49 + simpleItem() 50 + } 51 + } 52 + 53 + public val AsbestosRoofBlock: Block by block("asbestos_roof_block", { properties -> 54 + AsbestosRoofBlock(properties, 20) 55 + }) { 56 + copyProperties { AsbestosTileBlock } 57 + properties { 58 + noOcclusion() 59 + simpleItem() 60 + } 61 + } 62 + }
+76
src/common/main/kotlin/xyz/naomieow/asbestos/block/AsbestosRoofBlock.kt
··· 1 + package xyz.naomieow.asbestos.block 2 + 3 + //import net.fabricmc.api.EnvType 4 + //import net.fabricmc.api.Environment 5 + //import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap 6 + //import net.fabricmc.loader.api.FabricLoader 7 + //import net.minecraft.client.renderer.RenderType 8 + import net.minecraft.core.BlockPos 9 + import net.minecraft.core.Direction 10 + import net.minecraft.world.item.context.BlockPlaceContext 11 + import net.minecraft.world.level.BlockGetter 12 + import net.minecraft.world.level.block.Block 13 + import net.minecraft.world.level.block.state.BlockState 14 + import net.minecraft.world.level.block.state.StateDefinition 15 + import net.minecraft.world.level.block.state.properties.BlockStateProperties 16 + import net.minecraft.world.phys.shapes.CollisionContext 17 + import net.minecraft.world.phys.shapes.Shapes 18 + import net.minecraft.world.phys.shapes.VoxelShape 19 + 20 + public class AsbestosRoofBlock(settings: Properties, dangerLevel: Int) : CarcinogenicBlock(settings, dangerLevel) { 21 + init { 22 + registerDefaultState( 23 + this.getStateDefinition().any() 24 + .setValue<Direction?, Direction?>(BlockStateProperties.HORIZONTAL_FACING, Direction.NORTH) 25 + ) 26 + } 27 + 28 + override fun createBlockStateDefinition(builder: StateDefinition.Builder<Block?, BlockState?>) { 29 + builder.add(BlockStateProperties.HORIZONTAL_FACING) 30 + } 31 + 32 + @Deprecated("Deprecated in Java") 33 + override fun getShape( 34 + state: BlockState, 35 + world: BlockGetter, 36 + pos: BlockPos, 37 + context: CollisionContext 38 + ): VoxelShape { 39 + val dir = state.getValue<Direction?>(BlockStateProperties.HORIZONTAL_FACING) 40 + return when (dir) { 41 + Direction.NORTH -> Shapes.or( 42 + Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 43 + Shapes.box(0.0, 0.5, 0.5, 1.0, 1.0, 1.0) 44 + ) 45 + 46 + Direction.SOUTH -> Shapes.or( 47 + Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 48 + Shapes.box(0.0, 0.5, 0.0, 1.0, 1.0, 0.5) 49 + ) 50 + 51 + Direction.EAST -> Shapes.or( 52 + Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 53 + Shapes.box(0.0, 0.5, 0.0, 0.5, 1.0, 1.0) 54 + ) 55 + 56 + Direction.WEST -> Shapes.or( 57 + Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 58 + Shapes.box(0.5, 0.5, 0.0, 1.0, 1.0, 1.0) 59 + ) 60 + 61 + else -> Shapes.block() 62 + } 63 + } 64 + 65 + override fun getStateForPlacement(ctx: BlockPlaceContext): BlockState? { 66 + return this.defaultBlockState().setValue( 67 + BlockStateProperties.HORIZONTAL_FACING, 68 + ctx.horizontalDirection.opposite 69 + ) 70 + } 71 + 72 + @Deprecated("Deprecated in Java") 73 + override fun getShadeBrightness(state: BlockState, world: BlockGetter, pos: BlockPos): Float { 74 + return 1.0f 75 + } 76 + }
+33
src/common/main/kotlin/xyz/naomieow/asbestos/block/CarcinogenicBlock.kt
··· 1 + package xyz.naomieow.asbestos.block 2 + 3 + import net.minecraft.core.BlockPos 4 + import net.minecraft.world.entity.player.Player 5 + import net.minecraft.world.item.Item 6 + import net.minecraft.world.level.Level 7 + import net.minecraft.world.level.block.Block 8 + import net.minecraft.world.level.block.state.BlockState 9 + import xyz.naomieow.asbestos.item.AsbestosItems 10 + import xyz.naomieow.asbestos.mesothelioma.getMesothelioma 11 + import xyz.naomieow.asbestos.mesothelioma.setMesothelioma 12 + import xyz.naomieow.asbestos.util.isProtectedFromAsbestos 13 + 14 + public open class CarcinogenicBlock(settings: Properties, private val dangerLevel: Int) : Block(settings) { 15 + override fun playerWillDestroy(world: Level, pos: BlockPos, state: BlockState, player: Player) { 16 + super.playerWillDestroy(world, pos, state, player) 17 + if (!player.isProtectedFromAsbestos()) { 18 + val exposure = player.getMesothelioma() 19 + player.setMesothelioma(exposure + 1) 20 + } 21 + } 22 + 23 + public companion object { 24 + public val PROTECTIVE_ARMOUR: Array<Item> by lazy { 25 + arrayOf<Item>( 26 + AsbestosItems.PPEHelmet, 27 + AsbestosItems.PPEChestplate, 28 + AsbestosItems.PPELeggings, 29 + AsbestosItems.PPEBoots 30 + ) 31 + } 32 + } 33 + }
+110
src/common/main/kotlin/xyz/naomieow/asbestos/cancer_meter/CancerMeter.kt
··· 1 + package xyz.naomieow.asbestos.cancer_meter 2 + 3 + import net.minecraft.nbt.CompoundTag 4 + import net.minecraft.nbt.ListTag 5 + import net.minecraft.network.chat.Component 6 + import net.minecraft.world.Container 7 + import net.minecraft.world.MenuProvider 8 + import net.minecraft.world.SimpleContainer 9 + import net.minecraft.world.entity.player.Inventory 10 + import net.minecraft.world.entity.player.Player 11 + import net.minecraft.world.inventory.AbstractContainerMenu 12 + import net.minecraft.world.item.ItemStack 13 + import xyz.naomieow.asbestos.menu.CancerMeterMenu 14 + 15 + public class CancerMeter( 16 + private val stack: ItemStack? = null 17 + ) { 18 + public fun createMenuProvider(title: Component): MenuProvider { 19 + return CancerMeterMenuProvider(title, this) 20 + } 21 + 22 + public fun createMenu(syncId: Int, playerInventory: Inventory): CancerMeterMenu { 23 + return CancerMeterMenu(syncId, playerInventory, this) 24 + } 25 + 26 + public fun writeContent(content: Collection<IndexedContent>): CompoundTag { 27 + val tag = CompoundTag() 28 + val listTag = ListTag() 29 + 30 + content.forEach { slot -> 31 + val slotTag = CompoundTag() 32 + slotTag.putInt("Slot", slot.index) 33 + slotTag.put("Content", slot.content.save(CompoundTag())) 34 + listTag.add(slotTag) 35 + } 36 + 37 + tag.put("Items", listTag) 38 + return tag 39 + } 40 + 41 + public fun useItemStack(callback: (ItemStack) -> Unit) { 42 + if (this.stack != null) { 43 + callback(this.stack) 44 + } 45 + } 46 + 47 + public fun <T> supply(default: T, callback: (ItemStack) -> T): T { 48 + return if (this.stack != null) { 49 + callback(this.stack) 50 + } else { 51 + default 52 + } 53 + } 54 + 55 + public companion object { 56 + public const val TAG_KEY: String = "CancerMeter" 57 + 58 + public fun readContent(tag: CompoundTag): Collection<IndexedContent> { 59 + val list = mutableListOf<IndexedContent>() 60 + val listTag = tag.getList("Items", ListTag.TAG_COMPOUND.toInt()) 61 + 62 + for (i in 0..<listTag.size) { 63 + val slotData = listTag.getCompound(i) 64 + val slotIndex = slotData.getInt("Slot") 65 + list.add(IndexedContent(slotIndex, ItemStack.of(slotData.getCompound("Content")))) 66 + } 67 + 68 + return list 69 + } 70 + } 71 + } 72 + 73 + private class CancerMeterMenuProvider( 74 + val title: Component, 75 + val cancerMeter: CancerMeter, 76 + ) : MenuProvider { 77 + override fun getDisplayName(): Component { 78 + return title 79 + } 80 + 81 + override fun createMenu( 82 + syncId: Int, 83 + playerInventory: Inventory, 84 + player: Player 85 + ): AbstractContainerMenu { 86 + return CancerMeterMenu(syncId, playerInventory, this.cancerMeter) 87 + } 88 + } 89 + 90 + public data class IndexedContent(val index: Int, val content: ItemStack) 91 + 92 + public fun Collection<IndexedContent>.toContainer(size: Int): Container { 93 + val container = SimpleContainer(size) 94 + this.forEach { 95 + container.setItem(it.index, it.content) 96 + } 97 + return container 98 + } 99 + 100 + public fun Container.toIndexedCollection(): Collection<IndexedContent> { 101 + val list = mutableListOf<IndexedContent>() 102 + for (i in 0..<this.containerSize) { 103 + val stack = this.getItem(i) 104 + if (stack.isEmpty) { 105 + continue 106 + } 107 + list.add(IndexedContent(i, stack)) 108 + } 109 + return list 110 + }
+11
src/common/main/kotlin/xyz/naomieow/asbestos/client/AsbestosClient.kt
··· 1 + @file:EventSubscriber(env = [Environment.CLIENT]) 2 + 3 + package xyz.naomieow.asbestos.client 4 + 5 + import dev.mayaqq.cynosure.core.Environment 6 + import dev.mayaqq.cynosure.events.api.EventSubscriber 7 + import xyz.naomieow.asbestos.client.screen.AsbestosScreens 8 + 9 + public fun asbestosClient() { 10 + AsbestosScreens.register() 11 + }
+10
src/common/main/kotlin/xyz/naomieow/asbestos/client/screen/AsbestosScreens.kt
··· 1 + package xyz.naomieow.asbestos.client.screen 2 + 3 + import net.minecraft.client.gui.screens.MenuScreens 4 + import xyz.naomieow.asbestos.menu.ModMenuTypes 5 + 6 + public object AsbestosScreens { 7 + public fun register() { 8 + MenuScreens.register(ModMenuTypes.CancerMeter, ::CancerMeterScreen) 9 + } 10 + }
+95
src/common/main/kotlin/xyz/naomieow/asbestos/client/screen/CancerMeterScreen.kt
··· 1 + package xyz.naomieow.asbestos.client.screen 2 + 3 + import net.minecraft.client.gui.GuiGraphics 4 + import net.minecraft.client.gui.screens.inventory.AbstractContainerScreen 5 + import net.minecraft.network.chat.Component 6 + import net.minecraft.resources.ResourceLocation 7 + import net.minecraft.world.entity.player.Inventory 8 + import xyz.naomieow.asbestos.config.AsbestosConfig 9 + import xyz.naomieow.asbestos.id 10 + import xyz.naomieow.asbestos.menu.CancerMeterMenu 11 + import xyz.naomieow.asbestos.util.MouseUtil 12 + import java.util.* 13 + 14 + public class CancerMeterScreen( 15 + public var menu: CancerMeterMenu, 16 + inventory: Inventory, 17 + title: Component, 18 + ) : AbstractContainerScreen<CancerMeterMenu>( 19 + menu, 20 + inventory, 21 + title 22 + ) { 23 + override fun renderBg(context: GuiGraphics, delta: Float, mouseX: Int, mouseY: Int) { 24 + val x = (width - imageWidth) / 2 25 + val y = (height - imageHeight) / 2 26 + context.blit( 27 + texture, 28 + x, y, 29 + 0, 0, 30 + imageWidth, 31 + imageHeight 32 + ) 33 + drawCancerProgress(context, x + 109, y + 56) 34 + } 35 + 36 + override fun renderLabels(context: GuiGraphics, mouseX: Int, mouseY: Int) { 37 + val x = (width - imageWidth) / 2 38 + val y = (height - imageHeight) / 2 39 + 40 + if (isMouseAboveArea(mouseX, mouseY, x, y, 108, 55, 58, 7)) { 41 + context.renderTooltip( 42 + font, 43 + listOf( 44 + Component.literal( 45 + "${menu.getCancerLevel()}/${AsbestosConfig.threshold}" 46 + ) 47 + ), 48 + Optional.empty(), 49 + mouseX - x, 50 + mouseY - y 51 + ) 52 + } 53 + context.drawString( 54 + this.font, 55 + this.playerInventoryTitle, 56 + this.inventoryLabelX, 57 + this.inventoryLabelY + 2, 58 + 4210752, 59 + false 60 + ) 61 + } 62 + 63 + override fun render(context: GuiGraphics, mouseX: Int, mouseY: Int, delta: Float) { 64 + renderBackground(context) 65 + super.render(context, mouseX, mouseY, delta) 66 + renderTooltip(context, mouseX, mouseY) 67 + } 68 + 69 + private fun drawCancerProgress(context: GuiGraphics, x: Int, y: Int) { 70 + val offset = menu.getCancerLevel() * 58 / AsbestosConfig.threshold 71 + context.blit( 72 + texture, 73 + x, y, 74 + 176, 56, 75 + offset, 7 76 + ) 77 + } 78 + 79 + private fun isMouseAboveArea( 80 + mouseX: Int, mouseY: Int, 81 + x: Int, y: Int, 82 + offsetX: Int, offsetY: Int, 83 + width: Int, height: Int 84 + ): Boolean { 85 + return MouseUtil.isMouseOver( 86 + mouseX.toDouble(), mouseY.toDouble(), 87 + x + offsetX, y + offsetY, 88 + width, height 89 + ) 90 + } 91 + 92 + private companion object { 93 + private val texture: ResourceLocation = id("textures/gui/cancer_meter.png") 94 + } 95 + }
+42
src/common/main/kotlin/xyz/naomieow/asbestos/config/AsbestosConfig.kt
··· 1 + package xyz.naomieow.asbestos.config 2 + 3 + import dev.isxander.yacl3.config.v2.api.ConfigClassHandler 4 + import dev.isxander.yacl3.config.v2.api.SerialEntry 5 + import dev.isxander.yacl3.config.v2.api.serializer.GsonConfigSerializerBuilder 6 + import dev.isxander.yacl3.platform.YACLPlatform 7 + import xyz.naomieow.asbestos.id 8 + 9 + public class AsbestosConfig { 10 + public companion object { 11 + @JvmField 12 + @SerialEntry 13 + public var offset: Int = 3 14 + 15 + @JvmField 16 + @SerialEntry 17 + public var period: Float = 5.0f 18 + 19 + @JvmField 20 + @SerialEntry 21 + public var threshold: Int = 180 22 + 23 + @JvmField 24 + @SerialEntry 25 + public var exsanguination: Float = 1.0f 26 + 27 + public val Handler: ConfigClassHandler<AsbestosConfig> = 28 + ConfigClassHandler.createBuilder(AsbestosConfig::class.java) 29 + .id(id("asbestos_config")) 30 + .serializer { config -> 31 + GsonConfigSerializerBuilder.create(config) 32 + .setPath( 33 + YACLPlatform 34 + .getConfigDir() 35 + .resolve("asbestos.json5") 36 + ) 37 + .setJson5(true) 38 + .build() 39 + } 40 + .build() 41 + } 42 + }
+28
src/common/main/kotlin/xyz/naomieow/asbestos/damage/AsbestosDamageTypes.kt
··· 1 + package xyz.naomieow.asbestos.damage 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.resources.ResourceKey 5 + import net.minecraft.world.damagesource.DamageSource 6 + import net.minecraft.world.damagesource.DamageType 7 + import net.minecraft.world.level.Level 8 + import xyz.naomieow.asbestos.id 9 + 10 + public object AsbestosDamageTypes { 11 + public val MESOTHELIOMA: ResourceKey<DamageType> = ResourceKey.create( 12 + Registries.DAMAGE_TYPE, 13 + id("mesothelioma") 14 + ) 15 + public val BLOOD_EXTRACT: ResourceKey<DamageType> = ResourceKey.create( 16 + Registries.DAMAGE_TYPE, 17 + id("blood_extract") 18 + ) 19 + 20 + public fun of(level: Level, key: ResourceKey<DamageType>): DamageSource { 21 + return DamageSource( 22 + level 23 + .registryAccess() 24 + .registryOrThrow(Registries.DAMAGE_TYPE) 25 + .getHolderOrThrow(key) 26 + ) 27 + } 28 + }
+35
src/common/main/kotlin/xyz/naomieow/asbestos/item/AsbestosCreativeTabs.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.network.chat.Component 5 + import net.minecraft.world.item.CreativeModeTab 6 + import uwu.serenity.kritter.api.Registrar 7 + import uwu.serenity.kritter.stdlib.creativeTab 8 + import xyz.naomieow.asbestos.Asbestos 9 + import xyz.naomieow.asbestos.block.AsbestosBlocks 10 + 11 + @Suppress("UNUSED") 12 + public object AsbestosCreativeTabs : Registrar<CreativeModeTab> by Asbestos..Registries.CREATIVE_MODE_TAB { 13 + public val Asbestos: CreativeModeTab by creativeTab("asbestos") { 14 + title = Component.translatable("itemGroup.asbestos.asbestos") 15 + icon { AsbestosItems.AsbestosFibers.defaultInstance } 16 + displayItems { 17 + // Items 18 + accept(AsbestosItems.AsbestosFibers) 19 + accept(AsbestosItems.IronScraper) 20 + accept(AsbestosItems.EmptySyringe) 21 + accept(AsbestosItems.FilledSyringe) 22 + accept(AsbestosItems.CancerMeter) 23 + accept(AsbestosItems.PPEHelmet) 24 + accept(AsbestosItems.PPEChestplate) 25 + accept(AsbestosItems.PPELeggings) 26 + accept(AsbestosItems.PPEBoots) 27 + // Blocks 28 + accept(AsbestosBlocks.AsbestosBlock) 29 + accept(AsbestosBlocks.SerpentiniteBlock) 30 + accept(AsbestosBlocks.PopcornCeilingBlock) 31 + accept(AsbestosBlocks.AsbestosTileBlock) 32 + accept(AsbestosBlocks.AsbestosRoofBlock) 33 + } 34 + } 35 + }
+89
src/common/main/kotlin/xyz/naomieow/asbestos/item/AsbestosItems.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.world.effect.MobEffectInstance 5 + import net.minecraft.world.effect.MobEffects 6 + import net.minecraft.world.food.FoodProperties 7 + import net.minecraft.world.item.ArmorItem 8 + import net.minecraft.world.item.Item 9 + import net.minecraft.world.item.Rarity 10 + import uwu.serenity.kritter.api.Registrar 11 + import uwu.serenity.kritter.stdlib.item 12 + import xyz.naomieow.asbestos.Asbestos 13 + 14 + @Suppress("UNUSED") 15 + public object AsbestosItems : Registrar<Item> by Asbestos..Registries.ITEM { 16 + public val AsbestosFibers: Item by item("asbestos_fibers", ::Item) { 17 + properties { 18 + fireResistant() 19 + food( 20 + FoodProperties.Builder() 21 + .alwaysEat() 22 + .effect( 23 + MobEffectInstance( 24 + MobEffects.WITHER, 25 + 30 * 20, 4, 26 + false, false 27 + ), 1.0f 28 + ) 29 + .build() 30 + ) 31 + } 32 + } 33 + 34 + public val IronScraper: Item by item("iron_scraper", { properties -> 35 + ScraperItem( 36 + ScraperItemMaterial.INSTANCE, 37 + 0.0f, -3.0f, 38 + properties, 39 + ) 40 + }) 41 + 42 + public val FilledSyringe: Item by item("filled_syringe", ::FilledSyringeItem) { 43 + properties { 44 + stacksTo(1) 45 + rarity(Rarity.RARE) 46 + } 47 + } 48 + 49 + public val EmptySyringe: Item by item("empty_syringe", ::EmptySyringeItem) { 50 + properties { 51 + stacksTo(16) 52 + } 53 + } 54 + 55 + public val CancerMeter: Item by item("cancer_meter", ::CancerMeterItem) { 56 + properties { 57 + stacksTo(1) 58 + rarity(Rarity.UNCOMMON) 59 + } 60 + } 61 + 62 + public val PPEHelmet: Item by item("ppe_helmet", { properties -> 63 + PPEArmorItem( 64 + ArmorItem.Type.HELMET, 65 + properties 66 + ) 67 + }) 68 + 69 + public val PPEChestplate: Item by item("ppe_chestplate", { properties -> 70 + PPEArmorItem( 71 + ArmorItem.Type.CHESTPLATE, 72 + properties 73 + ) 74 + }) 75 + 76 + public val PPELeggings: Item by item("ppe_leggings", { properties -> 77 + PPEArmorItem( 78 + ArmorItem.Type.LEGGINGS, 79 + properties 80 + ) 81 + }) 82 + 83 + public val PPEBoots: Item by item("ppe_boots", { properties -> 84 + PPEArmorItem( 85 + ArmorItem.Type.BOOTS, 86 + properties 87 + ) 88 + }) 89 + }
+59
src/common/main/kotlin/xyz/naomieow/asbestos/item/CancerMeterItem.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.ChatFormatting 4 + import net.minecraft.network.chat.Component 5 + import net.minecraft.sounds.SoundEvents 6 + import net.minecraft.sounds.SoundSource 7 + import net.minecraft.world.InteractionHand 8 + import net.minecraft.world.InteractionResultHolder 9 + import net.minecraft.world.entity.player.Player 10 + import net.minecraft.world.item.Item 11 + import net.minecraft.world.item.ItemStack 12 + import net.minecraft.world.item.TooltipFlag 13 + import net.minecraft.world.level.Level 14 + import xyz.naomieow.asbestos.cancer_meter.CancerMeter 15 + import xyz.naomieow.asbestos.config.AsbestosConfig 16 + 17 + public class CancerMeterItem( 18 + properties: Properties 19 + ) : Item( 20 + properties 21 + ) { 22 + override fun use(level: Level, player: Player, hand: InteractionHand): InteractionResultHolder<ItemStack?> { 23 + if (!level.isClientSide && !player.isCrouching) { 24 + val stack = player.getItemInHand(hand) 25 + val cancerMeter = CancerMeter(stack) 26 + player.openMenu(cancerMeter.createMenuProvider(stack.displayName)) 27 + } 28 + 29 + player.playNotifySound( 30 + SoundEvents.SPYGLASS_USE, 31 + SoundSource.PLAYERS, 32 + level.random.nextFloat(), 33 + level.random.nextFloat() 34 + ) 35 + return super.use(level, player, hand) 36 + } 37 + 38 + 39 + @Suppress("WRONG_NULLABILITY_FOR_JAVA_OVERRIDE") 40 + override fun appendHoverText(stack: ItemStack, level: Level?, tooltip: MutableList<Component>, flag: TooltipFlag) { 41 + val contents = CancerMeter.readContent(stack.orCreateTag.getCompound(CancerMeter.TAG_KEY)) 42 + when (val syringe = contents.firstOrNull()) { 43 + null -> {} 44 + else -> { 45 + val tag = syringe.content.orCreateTag 46 + val playerName = tag.getString(FilledSyringeItem.NAME_KEY) 47 + val exposureAmount = tag.getInt(FilledSyringeItem.CANCER_LEVEL_KEY) 48 + tooltip.add( 49 + Component.translatable("tooltip.asbestos.player_blood", playerName) 50 + .withStyle(ChatFormatting.GRAY) 51 + ) 52 + tooltip.add( 53 + Component.translatable("tooltip.asbestos.cancer_level", exposureAmount, AsbestosConfig.threshold) 54 + .withStyle(ChatFormatting.GRAY) 55 + ) 56 + } 57 + } 58 + } 59 + }
+59
src/common/main/kotlin/xyz/naomieow/asbestos/item/EmptySyringeItem.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.sounds.SoundEvents 4 + import net.minecraft.sounds.SoundSource 5 + import net.minecraft.world.InteractionHand 6 + import net.minecraft.world.InteractionResult 7 + import net.minecraft.world.InteractionResultHolder 8 + import net.minecraft.world.entity.LivingEntity 9 + import net.minecraft.world.entity.player.Player 10 + import net.minecraft.world.item.Item 11 + import net.minecraft.world.item.ItemStack 12 + import net.minecraft.world.level.Level 13 + import xyz.naomieow.asbestos.config.AsbestosConfig 14 + import xyz.naomieow.asbestos.damage.AsbestosDamageTypes 15 + 16 + public class EmptySyringeItem( 17 + properties: Properties 18 + ) : Item( 19 + properties 20 + ) { 21 + override fun use(world: Level, user: Player, hand: InteractionHand): InteractionResultHolder<ItemStack> { 22 + useEmptySyringe(user, user, hand, world) 23 + return InteractionResultHolder.consume<ItemStack>(user.getItemInHand(hand)) 24 + } 25 + 26 + override fun interactLivingEntity( 27 + stack: ItemStack, 28 + user: Player, 29 + entity: LivingEntity, 30 + hand: InteractionHand 31 + ): InteractionResult { 32 + useEmptySyringe(user, entity, hand, user.level()) 33 + return InteractionResult.CONSUME 34 + } 35 + 36 + private fun useEmptySyringe(user: Player, target: LivingEntity, hand: InteractionHand, world: Level) { 37 + world.playSound( 38 + null, 39 + user.blockPosition(), 40 + SoundEvents.BOTTLE_FILL, 41 + SoundSource.PLAYERS, 42 + 1.0f, 1.0f 43 + ) 44 + val handStack = user.getItemInHand(hand) 45 + val newStack = ItemStack(AsbestosItems.FilledSyringe, 1) 46 + newStack.tag = handStack.getOrCreateTag().copy() 47 + FilledSyringeItem.writeNbt(target, newStack) 48 + target.hurt( 49 + AsbestosDamageTypes.of(user.level(), AsbestosDamageTypes.BLOOD_EXTRACT), 50 + AsbestosConfig.exsanguination 51 + ) 52 + if (!user.abilities.instabuild) { 53 + handStack.shrink(1) 54 + } 55 + if (!user.inventory.add(newStack)) { 56 + user.drop(newStack, false) 57 + } 58 + } 59 + }
+46
src/common/main/kotlin/xyz/naomieow/asbestos/item/FilledSyringeItem.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.ChatFormatting 4 + import net.minecraft.network.chat.Component 5 + import net.minecraft.world.entity.LivingEntity 6 + import net.minecraft.world.entity.player.Player 7 + import net.minecraft.world.item.Item 8 + import net.minecraft.world.item.ItemStack 9 + import net.minecraft.world.item.TooltipFlag 10 + import net.minecraft.world.level.Level 11 + import xyz.naomieow.asbestos.mesothelioma.getMesothelioma 12 + 13 + public class FilledSyringeItem( 14 + properties: Properties 15 + ) : Item( 16 + properties 17 + ) { 18 + @Suppress("WRONG_NULLABILITY_FOR_JAVA_OVERRIDE") 19 + override fun appendHoverText(stack: ItemStack, level: Level?, tooltip: MutableList<Component>, flag: TooltipFlag) { 20 + when (val tag = stack.tag) { 21 + null -> {} 22 + else -> { 23 + val playerName = tag.getString(NAME_KEY) 24 + tooltip.add( 25 + Component.translatable("tooltip.asbestos.player_blood", playerName) 26 + .withStyle(ChatFormatting.GRAY) 27 + ) 28 + } 29 + } 30 + } 31 + 32 + public companion object { 33 + public const val NAME_KEY: String = "PlayerName" 34 + public const val CANCER_LEVEL_KEY: String = "CancerLevel" 35 + 36 + public fun writeNbt(target: LivingEntity, syringe: ItemStack) { 37 + when (target) { 38 + is Player -> { 39 + val tag = syringe.getOrCreateTag() 40 + tag.putString(NAME_KEY, target.gameProfile.name) 41 + tag.putInt(CANCER_LEVEL_KEY, target.getMesothelioma()) 42 + } 43 + } 44 + } 45 + } 46 + }
+45
src/common/main/kotlin/xyz/naomieow/asbestos/item/PPEArmorItem.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import dev.mayaqq.cynosure.items.extensions.CustomTooltip 4 + import net.minecraft.ChatFormatting 5 + import net.minecraft.network.chat.Component 6 + import net.minecraft.world.entity.player.Player 7 + import net.minecraft.world.item.ArmorItem 8 + import net.minecraft.world.item.ItemStack 9 + import net.minecraft.world.item.TooltipFlag 10 + import xyz.naomieow.asbestos.armor.ProtectiveMaterial 11 + import xyz.naomieow.asbestos.config.AsbestosConfig 12 + import xyz.naomieow.asbestos.util.countPpePieces 13 + 14 + public class PPEArmorItem(type: ArmorItem.Type, properties: Properties) : 15 + ArmorItem(ProtectiveMaterial.INSTANCE, type, properties), 16 + CustomTooltip { 17 + override fun MutableList<Component>.modifyTooltip( 18 + stack: ItemStack, 19 + player: Player?, 20 + flags: TooltipFlag 21 + ) { 22 + val currentSeconds = AsbestosConfig.period * (1 + (player?.countPpePieces() ?: -1)) 23 + this.add( 24 + 1, Component.translatable("tooltip.asbestos.ppe_explanation.line1", AsbestosConfig.period, currentSeconds) 25 + .withStyle(ChatFormatting.GRAY) 26 + ) 27 + this.add( 28 + 2, Component.translatable("tooltip.asbestos.ppe_explanation.line2", AsbestosConfig.period, currentSeconds) 29 + .withStyle(ChatFormatting.GRAY) 30 + ) 31 + this.add( 32 + 3, Component.translatable("tooltip.asbestos.ppe_explanation.line3", AsbestosConfig.period, currentSeconds) 33 + .withStyle(ChatFormatting.GRAY) 34 + ) 35 + this.add(4, Component.literal("")) 36 + this.add( 37 + 5, Component.translatable("tooltip.asbestos.when_full_set") 38 + .withStyle(ChatFormatting.GRAY) 39 + ) 40 + this.add( 41 + 6, Component.translatable("tooltip.asbestos.airborne_immune") 42 + .withStyle(ChatFormatting.BLUE) 43 + ) 44 + } 45 + }
+28
src/common/main/kotlin/xyz/naomieow/asbestos/item/ScraperItem.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.tags.TagKey 5 + import net.minecraft.world.item.DiggerItem 6 + import net.minecraft.world.item.Tier 7 + import net.minecraft.world.level.block.Block 8 + import xyz.naomieow.asbestos.id 9 + 10 + public class ScraperItem( 11 + tier: Tier, 12 + attackDamage: Float, 13 + attackSpeed: Float, 14 + properties: Properties 15 + ) : DiggerItem( 16 + attackDamage, 17 + attackSpeed, 18 + tier, 19 + AFFECTED_BLOCKS, 20 + properties 21 + ) { 22 + public companion object { 23 + private val AFFECTED_BLOCKS: TagKey<Block> = TagKey.create( 24 + Registries.BLOCK, 25 + id("scrapeable") 26 + ) 27 + } 28 + }
+36
src/common/main/kotlin/xyz/naomieow/asbestos/item/ScraperItemMaterial.kt
··· 1 + package xyz.naomieow.asbestos.item 2 + 3 + import net.minecraft.world.item.Items 4 + import net.minecraft.world.item.Tier 5 + import net.minecraft.world.item.crafting.Ingredient 6 + 7 + public class ScraperItemMaterial : Tier { 8 + override fun getUses(): Int { 9 + return 300 10 + } 11 + 12 + override fun getSpeed(): Float { 13 + return 5.0f 14 + } 15 + 16 + override fun getAttackDamageBonus(): Float { 17 + return 2.5f 18 + } 19 + 20 + @Deprecated("Deprecated in Java") 21 + override fun getLevel(): Int { 22 + return 1 23 + } 24 + 25 + override fun getEnchantmentValue(): Int { 26 + return 10 27 + } 28 + 29 + override fun getRepairIngredient(): Ingredient { 30 + return Ingredient.of(Items.IRON_INGOT) 31 + } 32 + 33 + public companion object { 34 + public val INSTANCE: ScraperItemMaterial = ScraperItemMaterial() 35 + } 36 + }
+111
src/common/main/kotlin/xyz/naomieow/asbestos/menu/CancerMeterMenu.kt
··· 1 + package xyz.naomieow.asbestos.menu 2 + 3 + import net.minecraft.world.Container 4 + import net.minecraft.world.SimpleContainer 5 + import net.minecraft.world.entity.player.Inventory 6 + import net.minecraft.world.entity.player.Player 7 + import net.minecraft.world.inventory.AbstractContainerMenu 8 + import net.minecraft.world.inventory.ClickType 9 + import net.minecraft.world.inventory.Slot 10 + import net.minecraft.world.item.ItemStack 11 + import xyz.naomieow.asbestos.cancer_meter.CancerMeter 12 + import xyz.naomieow.asbestos.cancer_meter.toContainer 13 + import xyz.naomieow.asbestos.cancer_meter.toIndexedCollection 14 + import xyz.naomieow.asbestos.item.AsbestosItems 15 + import xyz.naomieow.asbestos.item.FilledSyringeItem 16 + 17 + public class CancerMeterMenu( 18 + syncId: Int, 19 + private val playerInventory: Inventory, 20 + public val cancerMeter: CancerMeter, 21 + ) : AbstractContainerMenu(ModMenuTypes.CancerMeter, syncId) { 22 + private val container: Container = this.cancerMeter.supply(SimpleContainer(SIZE)) { 23 + CancerMeter.readContent(it.orCreateTag.getCompound(CancerMeter.TAG_KEY)) 24 + .toContainer(SIZE) 25 + } 26 + 27 + init { 28 + this.initializeSlots() 29 + } 30 + 31 + override fun stillValid(player: Player): Boolean { 32 + return true 33 + } 34 + 35 + public override fun quickMoveStack(player: Player, index: Int): ItemStack { 36 + var stack = ItemStack.EMPTY 37 + val slot = this.slots[index] 38 + 39 + if (slot.hasItem()) { 40 + val stack2 = slot.item 41 + stack = stack2.copy() 42 + 43 + if (index < this.container.containerSize) { 44 + if (!this.moveItemStackTo(stack2, this.container.containerSize, this.slots.size, true)) { 45 + return ItemStack.EMPTY 46 + } 47 + } else if (!this.moveItemStackTo(stack2, 0, this.container.containerSize, false)) { 48 + return ItemStack.EMPTY 49 + } 50 + 51 + if (stack2.isEmpty) { 52 + slot.setByPlayer(ItemStack.EMPTY) 53 + } else { 54 + slot.setChanged() 55 + } 56 + } 57 + 58 + return stack 59 + } 60 + 61 + override fun removed(player: Player) { 62 + this.cancerMeter.useItemStack { 63 + it.orCreateTag.put(CancerMeter.TAG_KEY, this.cancerMeter.writeContent(this.container.toIndexedCollection())) 64 + } 65 + this.container.stopOpen(player) 66 + super.removed(player) 67 + } 68 + 69 + override fun clicked(index: Int, button: Int, clickType: ClickType, player: Player) { 70 + val offset = player.inventory.selected + 27 + this.container.containerSize 71 + 72 + if (index >= 0 && offset == index && clickType != ClickType.CLONE) { 73 + return 74 + } 75 + 76 + super.clicked(index, button, clickType, player) 77 + } 78 + 79 + public fun getCancerLevel(): Int { 80 + val tag = this.container.getItem(0).orCreateTag 81 + return if (tag.contains(FilledSyringeItem.CANCER_LEVEL_KEY)) { 82 + tag.getInt(FilledSyringeItem.CANCER_LEVEL_KEY) 83 + } else { 84 + 0 85 + } 86 + } 87 + 88 + private fun initializeSlots() { 89 + this.addSlot(object : Slot(this.container, 0, 80, 54) { 90 + override fun mayPlace(stack: ItemStack): Boolean { 91 + return stack.`is`(AsbestosItems.FilledSyringe) 92 + } 93 + }) 94 + 95 + // Player Inventory 96 + for (row in 0..2) { 97 + for (column in 0..8) { 98 + this.addSlot(Slot(this.playerInventory, column + row * 9 + 9, 8 + column * 18, 84 + row * 18)) 99 + } 100 + } 101 + 102 + // Player Hotbar 103 + for (slot in 0..8) { 104 + this.addSlot(Slot(this.playerInventory, slot, 8 + slot * 18, 142)) 105 + } 106 + } 107 + 108 + private companion object { 109 + private const val SIZE: Int = 1 110 + } 111 + }
+20
src/common/main/kotlin/xyz/naomieow/asbestos/menu/ModMenuTypes.kt
··· 1 + package xyz.naomieow.asbestos.menu 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.world.flag.FeatureFlags 5 + import net.minecraft.world.inventory.MenuType 6 + import uwu.serenity.kritter.api.Registrar 7 + import uwu.serenity.kritter.api.entry 8 + import xyz.naomieow.asbestos.Asbestos 9 + import xyz.naomieow.asbestos.cancer_meter.CancerMeter 10 + 11 + public object ModMenuTypes : Registrar<MenuType<*>> by Asbestos..Registries.MENU { 12 + public val CancerMeter: MenuType<CancerMeterMenu> by entry( 13 + "cancer_meter", 14 + { 15 + MenuType({ syncId, playerInventory -> 16 + val cancerMeter = CancerMeter() 17 + return@MenuType cancerMeter.createMenu(syncId, playerInventory) 18 + }, FeatureFlags.DEFAULT_FLAGS) 19 + }) 20 + }
+7
src/common/main/kotlin/xyz/naomieow/asbestos/mesothelioma/Mesothelioma.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import net.minecraft.world.entity.player.Player 4 + 5 + public expect fun Player.getMesothelioma(): Int 6 + 7 + public expect fun Player.setMesothelioma(value: Int)
+11
src/common/main/kotlin/xyz/naomieow/asbestos/mob_effect/AsbestosMobEffects.kt
··· 1 + package xyz.naomieow.asbestos.mob_effect 2 + 3 + import net.minecraft.core.registries.Registries 4 + import net.minecraft.world.effect.MobEffect 5 + import uwu.serenity.kritter.api.Registrar 6 + import uwu.serenity.kritter.api.entry 7 + import xyz.naomieow.asbestos.Asbestos 8 + 9 + public object AsbestosMobEffects : Registrar<MobEffect> by Asbestos..Registries.MOB_EFFECT { 10 + public val mesotheliomaMobEffect: MesotheliomaMobEffect by entry("mesothelioma", ::MesotheliomaMobEffect) 11 + }
+38
src/common/main/kotlin/xyz/naomieow/asbestos/mob_effect/MesotheliomaMobEffect.kt
··· 1 + package xyz.naomieow.asbestos.mob_effect 2 + 3 + import net.minecraft.world.effect.MobEffect 4 + import net.minecraft.world.effect.MobEffectCategory 5 + import net.minecraft.world.effect.MobEffectInstance 6 + import net.minecraft.world.effect.MobEffects 7 + import net.minecraft.world.entity.LivingEntity 8 + import net.minecraft.world.entity.player.Player 9 + import xyz.naomieow.asbestos.config.AsbestosConfig 10 + import xyz.naomieow.asbestos.damage.AsbestosDamageTypes 11 + import xyz.naomieow.asbestos.mesothelioma.getMesothelioma 12 + 13 + public class MesotheliomaMobEffect : MobEffect( 14 + MobEffectCategory.HARMFUL, 15 + 0x302412, 16 + ) { 17 + 18 + override fun isDurationEffectTick(duration: Int, amplifier: Int): Boolean { 19 + return true 20 + } 21 + 22 + override fun applyEffectTick(entity: LivingEntity, amplifier: Int) { 23 + super.applyEffectTick(entity, amplifier) 24 + if (entity is Player) { 25 + val exposure: Int = entity.getMesothelioma() 26 + if (exposure >= (AsbestosConfig.Companion.threshold / 1.5f)) { 27 + entity.addEffect(MobEffectInstance(MobEffects.MOVEMENT_SLOWDOWN, -1, 1)) 28 + } 29 + 30 + if (exposure >= AsbestosConfig.Companion.threshold) { 31 + entity.hurt( 32 + AsbestosDamageTypes.of(entity.level(), AsbestosDamageTypes.MESOTHELIOMA), 33 + (1 shl amplifier).toFloat() 34 + ) 35 + } 36 + } 37 + } 38 + }
+31
src/common/main/kotlin/xyz/naomieow/asbestos/poi/AsbestosPOIs.kt
··· 1 + package xyz.naomieow.asbestos.poi 2 + 3 + import dev.mayaqq.cynosure.blocks.poi.PoiHelpers 4 + import dev.mayaqq.cynosure.core.Loader 5 + import dev.mayaqq.cynosure.core.currentLoader 6 + import net.minecraft.core.registries.Registries 7 + import net.minecraft.world.entity.ai.village.poi.PoiType 8 + import uwu.serenity.kritter.api.Registrar 9 + import uwu.serenity.kritter.api.entry 10 + import xyz.naomieow.asbestos.Asbestos 11 + import xyz.naomieow.asbestos.block.AsbestosBlocks 12 + 13 + public object AsbestosPOIs : Registrar<PoiType> by Asbestos..Registries.POINT_OF_INTEREST_TYPE { 14 + public val carcinogenicBlock: PoiType by entry("carcinogenic_block", { 15 + PoiType( 16 + PoiHelpers.states( 17 + AsbestosBlocks.AsbestosBlock, 18 + AsbestosBlocks.AsbestosRoofBlock, 19 + AsbestosBlocks.AsbestosTileBlock, 20 + AsbestosBlocks.SerpentiniteBlock, 21 + AsbestosBlocks.PopcornCeilingBlock, 22 + ), 0, 1 23 + ) 24 + }) { 25 + onRegister { 26 + if (currentLoader == Loader.FABRIC) { 27 + PoiHelpers.registerState(it) 28 + } 29 + } 30 + } 31 + }
+15
src/common/main/kotlin/xyz/naomieow/asbestos/util/MouseUtil.kt
··· 1 + package xyz.naomieow.asbestos.util 2 + 3 + public object MouseUtil { 4 + public fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int): Boolean { 5 + return isMouseOver(mouseX, mouseY, x, y, 16) 6 + } 7 + 8 + public fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int, size: Int): Boolean { 9 + return isMouseOver(mouseX, mouseY, x, y, size, size) 10 + } 11 + 12 + public fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int, sizeX: Int, sizeY: Int): Boolean { 13 + return (mouseX >= x && mouseX <= x + sizeX) && (mouseY >= y && mouseY <= y + sizeY) 14 + } 15 + }
+23
src/common/main/kotlin/xyz/naomieow/asbestos/util/PlayerUtil.kt
··· 1 + package xyz.naomieow.asbestos.util 2 + 3 + import net.minecraft.world.entity.player.Player 4 + import xyz.naomieow.asbestos.block.CarcinogenicBlock.Companion.PROTECTIVE_ARMOUR 5 + 6 + 7 + public fun Player.isProtectedFromAsbestos(): Boolean { 8 + var protected = true 9 + this.armorSlots.forEach { 10 + protected = protected && PROTECTIVE_ARMOUR.contains(it.item) 11 + } 12 + return protected 13 + } 14 + 15 + public fun Player.countPpePieces(): Int { 16 + var pieces = 0 17 + this.armorSlots.forEach { 18 + if (PROTECTIVE_ARMOUR.contains(it.item)) { 19 + pieces += 1 20 + } 21 + } 22 + return pieces 23 + }
+12
src/common/main/kotlin/xyz/naomieow/asbestos/util/VectorUtil.kt
··· 1 + package xyz.naomieow.asbestos.util 2 + 3 + import net.minecraft.core.Vec3i 4 + import net.minecraft.world.phys.Vec3 5 + 6 + public fun Vec3.toVector3i(): Vec3i { 7 + return Vec3i( 8 + this.x.toInt(), 9 + this.y.toInt(), 10 + this.z.toInt(), 11 + ) 12 + }
+7
src/common/main/resources/assets/asbestos/blockstates/asbestos_block.json
··· 1 + { 2 + "variants": { 3 + "": { 4 + "model": "asbestos:block/asbestos_block" 5 + } 6 + } 7 + }
+19
src/common/main/resources/assets/asbestos/blockstates/asbestos_roof_block.json
··· 1 + { 2 + "variants": { 3 + "facing=north": { 4 + "model": "asbestos:block/asbestos_roof_block" 5 + }, 6 + "facing=east": { 7 + "model": "asbestos:block/asbestos_roof_block", 8 + "y": 90 9 + }, 10 + "facing=south": { 11 + "model": "asbestos:block/asbestos_roof_block", 12 + "y": 180 13 + }, 14 + "facing=west": { 15 + "model": "asbestos:block/asbestos_roof_block", 16 + "y": 270 17 + } 18 + } 19 + }
+7
src/common/main/resources/assets/asbestos/blockstates/asbestos_tile_block.json
··· 1 + { 2 + "variants": { 3 + "": { 4 + "model": "asbestos:block/asbestos_tile_block" 5 + } 6 + } 7 + }
+7
src/common/main/resources/assets/asbestos/blockstates/popcorn_ceiling_block.json
··· 1 + { 2 + "variants": { 3 + "": { 4 + "model": "asbestos:block/popcorn_ceiling_block" 5 + } 6 + } 7 + }
+7
src/common/main/resources/assets/asbestos/blockstates/serpentinite_block.json
··· 1 + { 2 + "variants": { 3 + "": { 4 + "model": "asbestos:block/serpentinite_block" 5 + } 6 + } 7 + }
src/common/main/resources/assets/asbestos/icon.png

This is a binary file and will not be displayed.

+50
src/common/main/resources/assets/asbestos/icon.svg
··· 1 + <?xml version="1.0" encoding="UTF-8" standalone="no"?> 2 + <!-- Created with Inkscape (http://www.inkscape.org/) --> 3 + 4 + <svg 5 + xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" 6 + xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" 7 + width="200mm" 8 + height="200mm" 9 + viewBox="0 0 200 200" 10 + version="1.1" 11 + id="svg1" 12 + inkscape:version="1.3 (0e150ed6c4, 2023-07-21)" 13 + sodipodi:docname="icon.svg" 14 + inkscape:export-filename="icon.png" 15 + inkscape:export-xdpi="96" 16 + inkscape:export-ydpi="96" 17 + xmlns="http://www.w3.org/2000/svg" 18 + > 19 + <sodipodi:namedview 20 + id="namedview1" 21 + pagecolor="#8b8b8b" 22 + bordercolor="#000000" 23 + borderopacity="0.25" 24 + inkscape:showpageshadow="2" 25 + inkscape:pageopacity="0.0" 26 + inkscape:pagecheckerboard="0" 27 + inkscape:deskcolor="#d1d1d1" 28 + inkscape:document-units="mm" 29 + inkscape:zoom="0.79375" 30 + inkscape:cx="283.46457" 31 + inkscape:cy="362.20472" 32 + inkscape:window-width="1920" 33 + inkscape:window-height="1129" 34 + inkscape:window-x="1912" 35 + inkscape:window-y="-8" 36 + inkscape:window-maximized="1" 37 + inkscape:current-layer="layer1" 38 + inkscape:export-bgcolor="#8b8b8bff"/> 39 + <defs 40 + id="defs1"/> 41 + <g 42 + inkscape:label="Layer 1" 43 + inkscape:groupmode="layer" 44 + id="layer1"> 45 + <path 46 + d="m 151.54918,54.73157 c 0,15.389796 -9.1391,28.942512 -23.02764,36.880045 v 7.486928 c 0,6.135127 -5.14524,11.091747 -11.51381,11.091747 H 82.466288 c -6.368586,0 -11.513819,-4.95662 -11.513819,-11.091747 V 91.611615 C 57.063925,83.639431 47.924844,70.086703 47.924844,54.73157 c 0,-24.505837 23.207526,-44.366987 51.812166,-44.366987 28.60463,0 51.81217,19.86115 51.81217,44.366987 z M 79.58783,71.369188 a 11.513819,11.09175 0 1 0 0,-22.1835 11.513819,11.09175 0 1 0 0,22.1835 z M 131.4,60.277438 a 11.513815,11.091746 0 1 0 -23.02763,0 11.513815,11.091746 0 1 0 23.02763,0 z M 20.363641,105.23367 c 2.842476,-5.476553 9.750764,-7.694897 15.435715,-4.95662 l 63.937654,30.77959 63.93764,-30.77959 c 5.68495,-2.738277 12.59324,-0.519933 15.43571,4.95662 2.84248,5.47654 0.53971,12.13159 -5.14523,14.86986 l -48.46597,23.362 48.50195,23.36199 c 5.68494,2.73826 7.98771,9.39331 5.14524,14.86986 -2.84248,5.47656 -9.75077,7.6949 -15.43572,4.95663 l -63.97362,-30.7796 -63.937654,30.7796 c -5.684951,2.73827 -12.593239,0.51993 -15.435715,-4.95663 -2.842461,-5.47655 -0.539703,-12.1316 5.145234,-14.86986 l 48.46597,-23.36199 -48.46597,-23.362 c -5.684937,-2.73827 -7.987695,-9.39332 -5.145234,-14.86986 z" 47 + id="path1" 48 + style="stroke-width:0.35315;fill:#ffffff;fill-opacity:1"/> 49 + </g> 50 + </svg>
+37
src/common/main/resources/assets/asbestos/lang/en_us.json
··· 1 + { 2 + "itemGroup.asbestos.asbestos": "Asbestos", 3 + "item.asbestos.asbestos_fibers": "Asbestos Fibers", 4 + "item.asbestos.iron_scraper": "Iron Scraper", 5 + "item.asbestos.ppe_helmet": "PPE Helmet", 6 + "item.asbestos.ppe_chestplate": "PPE Chestplate", 7 + "item.asbestos.ppe_leggings": "PPE Leggings", 8 + "item.asbestos.ppe_boots": "PPE Boots", 9 + "item.asbestos.filled_syringe": "Filled Syringe", 10 + "item.asbestos.empty_syringe": "Empty Syringe", 11 + "item.asbestos.cancer_meter": "Cancer Meter", 12 + "block.asbestos.asbestos_block": "Asbestos", 13 + "block.asbestos.asbestos_tile_block": "Asbestos Tiling", 14 + "block.asbestos.asbestos_roof_block": "Asbestos Roof", 15 + "block.asbestos.serpentinite_block": "Serpentinite", 16 + "block.asbestos.popcorn_ceiling_block": "Popcorn Ceiling", 17 + "effect.asbestos.mesothelioma": "Mesothelioma", 18 + "effect.asbestos.mesothelioma.description": "A type of cancer that covers the mesothelium of your organs. Caused by exposure to asbestos.", 19 + "death.attack.mesothelioma": "%1$s was entitled to financial compensation", 20 + "death.attack.blood_extract": "%1$s died from exsanguination", 21 + "text.config.asbestos_config.title": "Asbestos Config", 22 + "text.config.asbestos_config.option.offset": "Offset (Blocks)", 23 + "text.config.asbestos_config.option.offset.desc": "The distance, in blocks, that players will gain cancer from Carcinogenic blocks", 24 + "text.config.asbestos_config.option.period": "Period (Seconds)", 25 + "text.config.asbestos_config.option.period.desc": "The time, in seconds, that it takes for a player to gain a \"point\" of cancer.", 26 + "text.config.asbestos_config.option.threshold": "Mesothelioma Threshold", 27 + "text.config.asbestos_config.option.threshold.desc": "The threshold a player has to cross to be inflicted with mesothelioma.", 28 + "text.config.asbestos_config.option.exsanguination": "Syringe Damage", 29 + "text.config.asbestos_config.option.exsanguination.desc": "Damage caused to a player when they extract blood using a syringe.", 30 + "tooltip.asbestos.player_blood": "Player: %1$s", 31 + "tooltip.asbestos.cancer_level": "Concentration: %1$s/%2$s", 32 + "tooltip.asbestos.ppe_explanation.line1": "Each piece worn grants %1$s extra", 33 + "tooltip.asbestos.ppe_explanation.line2": "seconds between asbestos concentration", 34 + "tooltip.asbestos.ppe_explanation.line3": "increasing. Currently %2$s seconds.", 35 + "tooltip.asbestos.when_full_set": "When full set worn:", 36 + "tooltip.asbestos.airborne_immune": "Immune to airborne Asbestos" 37 + }
+6
src/common/main/resources/assets/asbestos/models/block/asbestos_block.json
··· 1 + { 2 + "parent": "block/cube_all", 3 + "textures": { 4 + "all": "asbestos:block/asbestos_block" 5 + } 6 + }
+497
src/common/main/resources/assets/asbestos/models/block/asbestos_roof_block.json
··· 1 + { 2 + "credit": "Made with Blockbench", 3 + "parent": "block/block", 4 + "textures": { 5 + "0": "asbestos:block/asbestos_roof_top", 6 + "1": "asbestos:block/asbestos_roof_side", 7 + "particle": "asbestos:block/asbestos_roof_top" 8 + }, 9 + "elements": [ 10 + { 11 + "from": [ 12 + 0.001, 13 + 0, 14 + 1 15 + ], 16 + "to": [ 17 + 2, 18 + 2, 19 + 16 20 + ], 21 + "faces": { 22 + "north": { 23 + "uv": [ 24 + 8, 25 + 7, 26 + 10, 27 + 9 28 + ], 29 + "texture": "#1" 30 + }, 31 + "east": { 32 + "uv": [ 33 + 1, 34 + 0, 35 + 16, 36 + 16 37 + ], 38 + "texture": "#1" 39 + }, 40 + "south": { 41 + "uv": [ 42 + 14, 43 + 7, 44 + 16, 45 + 9 46 + ], 47 + "texture": "#1", 48 + "cullface": "south" 49 + }, 50 + "west": { 51 + "uv": [ 52 + 0, 53 + 0, 54 + 15, 55 + 16 56 + ], 57 + "rotation": 180, 58 + "texture": "#1" 59 + }, 60 + "up": { 61 + "uv": [ 62 + 0, 63 + 0, 64 + 15, 65 + 16 66 + ], 67 + "rotation": 90, 68 + "texture": "#1" 69 + }, 70 + "down": { 71 + "uv": [ 72 + 1, 73 + 0, 74 + 16, 75 + 16 76 + ], 77 + "rotation": 270, 78 + "texture": "#1", 79 + "cullface": "down" 80 + } 81 + } 82 + }, 83 + { 84 + "from": [ 85 + 14, 86 + 0, 87 + 1 88 + ], 89 + "to": [ 90 + 15.999, 91 + 2, 92 + 16 93 + ], 94 + "faces": { 95 + "north": { 96 + "uv": [ 97 + 9, 98 + 7, 99 + 11, 100 + 9 101 + ], 102 + "texture": "#1" 103 + }, 104 + "east": { 105 + "uv": [ 106 + 1, 107 + 0, 108 + 16, 109 + 16 110 + ], 111 + "rotation": 180, 112 + "texture": "#1" 113 + }, 114 + "south": { 115 + "uv": [ 116 + 11, 117 + 7, 118 + 13, 119 + 9 120 + ], 121 + "texture": "#1", 122 + "cullface": "south" 123 + }, 124 + "west": { 125 + "uv": [ 126 + 1, 127 + 0, 128 + 16, 129 + 16 130 + ], 131 + "texture": "#1" 132 + }, 133 + "up": { 134 + "uv": [ 135 + 0, 136 + 0, 137 + 15, 138 + 16 139 + ], 140 + "rotation": 270, 141 + "texture": "#1" 142 + }, 143 + "down": { 144 + "uv": [ 145 + 0, 146 + 0, 147 + 15, 148 + 16 149 + ], 150 + "rotation": 90, 151 + "texture": "#1", 152 + "cullface": "down" 153 + } 154 + } 155 + }, 156 + { 157 + "from": [ 158 + 14, 159 + 2, 160 + 14 161 + ], 162 + "to": [ 163 + 15.999, 164 + 15, 165 + 16 166 + ], 167 + "faces": { 168 + "north": { 169 + "uv": [ 170 + 0, 171 + 0, 172 + 13, 173 + 16 174 + ], 175 + "rotation": 90, 176 + "texture": "#1" 177 + }, 178 + "east": { 179 + "uv": [ 180 + 0, 181 + 0, 182 + 13, 183 + 16 184 + ], 185 + "rotation": 270, 186 + "texture": "#1" 187 + }, 188 + "south": { 189 + "uv": [ 190 + 0, 191 + 0, 192 + 13, 193 + 16 194 + ], 195 + "rotation": 90, 196 + "texture": "#1", 197 + "cullface": "south" 198 + }, 199 + "west": { 200 + "uv": [ 201 + 0, 202 + 0, 203 + 13, 204 + 16 205 + ], 206 + "rotation": 270, 207 + "texture": "#1" 208 + }, 209 + "up": { 210 + "uv": [ 211 + 2, 212 + 0, 213 + 4, 214 + 2 215 + ], 216 + "rotation": 270, 217 + "texture": "#1" 218 + } 219 + } 220 + }, 221 + { 222 + "from": [ 223 + 0.001, 224 + 2, 225 + 14 226 + ], 227 + "to": [ 228 + 2, 229 + 15, 230 + 16 231 + ], 232 + "rotation": { 233 + "angle": 0, 234 + "axis": "y", 235 + "origin": [ 236 + 1, 237 + 8, 238 + 15 239 + ] 240 + }, 241 + "faces": { 242 + "north": { 243 + "uv": [ 244 + 0, 245 + 0, 246 + 13, 247 + 16 248 + ], 249 + "rotation": 270, 250 + "texture": "#1" 251 + }, 252 + "east": { 253 + "uv": [ 254 + 0, 255 + 0, 256 + 13, 257 + 16 258 + ], 259 + "rotation": 90, 260 + "texture": "#1" 261 + }, 262 + "south": { 263 + "uv": [ 264 + 0, 265 + 0, 266 + 13, 267 + 16 268 + ], 269 + "rotation": 270, 270 + "texture": "#1", 271 + "cullface": "south" 272 + }, 273 + "west": { 274 + "uv": [ 275 + 0, 276 + 0, 277 + 13, 278 + 16 279 + ], 280 + "rotation": 90, 281 + "texture": "#1" 282 + }, 283 + "up": { 284 + "uv": [ 285 + 5, 286 + 12, 287 + 7, 288 + 14 289 + ], 290 + "texture": "#1" 291 + } 292 + } 293 + }, 294 + { 295 + "from": [ 296 + 2, 297 + 0, 298 + 14 299 + ], 300 + "to": [ 301 + 14, 302 + 2, 303 + 16 304 + ], 305 + "faces": { 306 + "north": { 307 + "uv": [ 308 + 0, 309 + 0, 310 + 12, 311 + 16 312 + ], 313 + "texture": "#1" 314 + }, 315 + "south": { 316 + "uv": [ 317 + 0, 318 + 0, 319 + 12, 320 + 16 321 + ], 322 + "rotation": 180, 323 + "texture": "#1", 324 + "cullface": "south" 325 + }, 326 + "up": { 327 + "uv": [ 328 + 0, 329 + 0, 330 + 12, 331 + 16 332 + ], 333 + "texture": "#1" 334 + }, 335 + "down": { 336 + "uv": [ 337 + 0, 338 + 0, 339 + 12, 340 + 16 341 + ], 342 + "texture": "#1", 343 + "cullface": "down" 344 + } 345 + } 346 + }, 347 + { 348 + "from": [ 349 + 2.001, 350 + 13, 351 + 14 352 + ], 353 + "to": [ 354 + 14, 355 + 15, 356 + 16 357 + ], 358 + "faces": { 359 + "north": { 360 + "uv": [ 361 + 0, 362 + 0, 363 + 12, 364 + 16 365 + ], 366 + "texture": "#1" 367 + }, 368 + "south": { 369 + "uv": [ 370 + 0, 371 + 0, 372 + 12, 373 + 16 374 + ], 375 + "rotation": 180, 376 + "texture": "#1", 377 + "cullface": "south" 378 + }, 379 + "up": { 380 + "uv": [ 381 + 0, 382 + 0, 383 + 12, 384 + 16 385 + ], 386 + "texture": "#1" 387 + }, 388 + "down": { 389 + "uv": [ 390 + 0, 391 + 0, 392 + 12, 393 + 16 394 + ], 395 + "texture": "#1" 396 + } 397 + } 398 + }, 399 + { 400 + "from": [ 401 + 0, 402 + 0.70711, 403 + -0.70711 404 + ], 405 + "to": [ 406 + 16, 407 + 23.35711, 408 + 0.29289 409 + ], 410 + "rotation": { 411 + "angle": 45, 412 + "axis": "x", 413 + "origin": [ 414 + 0, 415 + 0.70711, 416 + -0.70711 417 + ] 418 + }, 419 + "faces": { 420 + "north": { 421 + "uv": [ 422 + 0, 423 + 0, 424 + 16, 425 + 16 426 + ], 427 + "texture": "#0" 428 + }, 429 + "east": { 430 + "uv": [ 431 + 0, 432 + 0, 433 + 1, 434 + 16 435 + ], 436 + "texture": "#0", 437 + "cullface": "east" 438 + }, 439 + "south": { 440 + "uv": [ 441 + 0, 442 + 0, 443 + 16, 444 + 16 445 + ], 446 + "texture": "#0" 447 + }, 448 + "west": { 449 + "uv": [ 450 + 7, 451 + 0, 452 + 8, 453 + 16 454 + ], 455 + "texture": "#0", 456 + "cullface": "west" 457 + }, 458 + "up": { 459 + "uv": [ 460 + 0, 461 + 8, 462 + 16, 463 + 8 464 + ], 465 + "rotation": 180, 466 + "texture": "#0", 467 + "cullface": "up" 468 + }, 469 + "down": { 470 + "uv": [ 471 + 0, 472 + 8, 473 + 16, 474 + 8 475 + ], 476 + "rotation": 180, 477 + "texture": "#0", 478 + "cullface": "north" 479 + } 480 + } 481 + } 482 + ], 483 + "display": { 484 + "fixed": { 485 + "rotation": [ 486 + 0, 487 + 90, 488 + 0 489 + ], 490 + "scale": [ 491 + 0.5, 492 + 0.5, 493 + 0.5 494 + ] 495 + } 496 + } 497 + }
+6
src/common/main/resources/assets/asbestos/models/block/asbestos_tile_block.json
··· 1 + { 2 + "parent": "block/cube_all", 3 + "textures": { 4 + "all": "asbestos:block/asbestos_tiles" 5 + } 6 + }
+8
src/common/main/resources/assets/asbestos/models/block/popcorn_ceiling_block.json
··· 1 + { 2 + "parent": "block/cube_bottom_top", 3 + "textures": { 4 + "top": "asbestos:block/popcorn_top", 5 + "bottom": "asbestos:block/popcorn_bottom", 6 + "side": "asbestos:block/popcorn_side" 7 + } 8 + }
+6
src/common/main/resources/assets/asbestos/models/block/serpentinite_block.json
··· 1 + { 2 + "parent": "block/cube_all", 3 + "textures": { 4 + "all": "asbestos:block/serpentinite_block" 5 + } 6 + }
+3
src/common/main/resources/assets/asbestos/models/item/asbestos_block.json
··· 1 + { 2 + "parent": "asbestos:block/asbestos_block" 3 + }
+6
src/common/main/resources/assets/asbestos/models/item/asbestos_fibers.json
··· 1 + { 2 + "parent": "minecraft:item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/asbestos_fibers" 5 + } 6 + }
+3
src/common/main/resources/assets/asbestos/models/item/asbestos_roof_block.json
··· 1 + { 2 + "parent": "asbestos:block/asbestos_roof_block" 3 + }
+3
src/common/main/resources/assets/asbestos/models/item/asbestos_tile_block.json
··· 1 + { 2 + "parent": "asbestos:block/asbestos_tile_block" 3 + }
+6
src/common/main/resources/assets/asbestos/models/item/cancer_meter.json
··· 1 + { 2 + "parent": "minecraft:item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/cancer_meter" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/empty_syringe.json
··· 1 + { 2 + "parent": "minecraft:item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/empty_syringe" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/filled_syringe.json
··· 1 + { 2 + "parent": "minecraft:item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/filled_syringe" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/iron_scraper.json
··· 1 + { 2 + "parent": "minecraft:item/handheld", 3 + "textures": { 4 + "layer0": "asbestos:item/iron_scraper" 5 + } 6 + }
+3
src/common/main/resources/assets/asbestos/models/item/popcorn_ceiling_block.json
··· 1 + { 2 + "parent": "asbestos:block/popcorn_ceiling_block" 3 + }
+6
src/common/main/resources/assets/asbestos/models/item/ppe_boots.json
··· 1 + { 2 + "parent": "item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/ppe_boots" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/ppe_chestplate.json
··· 1 + { 2 + "parent": "item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/ppe_chestplate" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/ppe_helmet.json
··· 1 + { 2 + "parent": "item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/ppe_helmet" 5 + } 6 + }
+6
src/common/main/resources/assets/asbestos/models/item/ppe_leggings.json
··· 1 + { 2 + "parent": "item/generated", 3 + "textures": { 4 + "layer0": "asbestos:item/ppe_leggings" 5 + } 6 + }
+3
src/common/main/resources/assets/asbestos/models/item/serpentinite_block.json
··· 1 + { 2 + "parent": "asbestos:block/serpentinite_block" 3 + }
src/common/main/resources/assets/asbestos/textures/block/asbestos_block.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/asbestos_roof_side.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/asbestos_roof_top.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/asbestos_tiles.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/popcorn_bottom.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/popcorn_side.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/popcorn_top.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/block/serpentinite_block.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/gui/cancer_meter.ase

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/gui/cancer_meter.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/asbestos_fibers.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/cancer_meter.aseprite

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/cancer_meter.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/empty_syringe.aseprite

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/empty_syringe.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/filled_syringe.aseprite

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/filled_syringe.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/iron_scraper.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/ppe_boots.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/ppe_chestplate.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/ppe_helmet.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/item/ppe_leggings.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/asbestos/textures/mob_effect/mesothelioma.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/minecraft/textures/models/armor/asbestos_protective_layer_1.png

This is a binary file and will not be displayed.

src/common/main/resources/assets/minecraft/textures/models/armor/asbestos_protective_layer_2.png

This is a binary file and will not be displayed.

+5
src/common/main/resources/data/asbestos/damage_type/blood_extract.json
··· 1 + { 2 + "message_id": "blood_extract", 3 + "exhaustion": 0.1, 4 + "scaling": "when_caused_by_living_non_player" 5 + }
+5
src/common/main/resources/data/asbestos/damage_type/mesothelioma.json
··· 1 + { 2 + "message_id": "mesothelioma", 3 + "exhaustion": 0.1, 4 + "scaling": "when_caused_by_living_non_player" 5 + }
+6
src/common/main/resources/data/asbestos/forge/biome_modifier/serpentinite_feature.json
··· 1 + { 2 + "type": "forge:add_features", 3 + "biomes": "#minecraft:is_overworld", 4 + "features": "asbestos:serpentinite", 5 + "step": "underground_ores" 6 + }
+34
src/common/main/resources/data/asbestos/loot_tables/blocks/asbestos_block.json
··· 1 + { 2 + "type": "minecraft:block", 3 + "pools": [ 4 + { 5 + "rolls": 1, 6 + "entries": [ 7 + { 8 + "type": "minecraft:item", 9 + "name": "asbestos:asbestos_block", 10 + "weight": 10 11 + }, 12 + { 13 + "type": "minecraft:item", 14 + "name": "asbestos:asbestos_fibers", 15 + "weight": 1, 16 + "functions": [ 17 + { 18 + "function": "set_count", 19 + "count": { 20 + "min": 1, 21 + "max": 4 22 + } 23 + } 24 + ] 25 + } 26 + ], 27 + "conditions": [ 28 + { 29 + "condition": "minecraft:survives_explosion" 30 + } 31 + ] 32 + } 33 + ] 34 + }
+19
src/common/main/resources/data/asbestos/loot_tables/blocks/asbestos_roof_block.json
··· 1 + { 2 + "type": "minecraft:block", 3 + "pools": [ 4 + { 5 + "rolls": 1, 6 + "entries": [ 7 + { 8 + "type": "minecraft:item", 9 + "name": "asbestos:asbestos_roof_block" 10 + } 11 + ], 12 + "conditions": [ 13 + { 14 + "condition": "minecraft:survives_explosion" 15 + } 16 + ] 17 + } 18 + ] 19 + }
+19
src/common/main/resources/data/asbestos/loot_tables/blocks/asbestos_tile_block.json
··· 1 + { 2 + "type": "minecraft:block", 3 + "pools": [ 4 + { 5 + "rolls": 1, 6 + "entries": [ 7 + { 8 + "type": "minecraft:item", 9 + "name": "asbestos:asbestos_tile_block" 10 + } 11 + ], 12 + "conditions": [ 13 + { 14 + "condition": "minecraft:survives_explosion" 15 + } 16 + ] 17 + } 18 + ] 19 + }
+19
src/common/main/resources/data/asbestos/loot_tables/blocks/popcorn_ceiling_block.json
··· 1 + { 2 + "type": "minecraft:block", 3 + "pools": [ 4 + { 5 + "rolls": 1, 6 + "entries": [ 7 + { 8 + "type": "minecraft:item", 9 + "name": "asbestos:popcorn_ceiling_block" 10 + } 11 + ], 12 + "conditions": [ 13 + { 14 + "condition": "minecraft:survives_explosion" 15 + } 16 + ] 17 + } 18 + ] 19 + }
+29
src/common/main/resources/data/asbestos/loot_tables/blocks/serpentinite_block.json
··· 1 + { 2 + "type": "minecraft:block", 3 + "pools": [ 4 + { 5 + "rolls": 1, 6 + "entries": [ 7 + { 8 + "type": "minecraft:item", 9 + "name": "asbestos:asbestos_fibers", 10 + "weight": 1, 11 + "functions": [ 12 + { 13 + "function": "set_count", 14 + "count": { 15 + "min": 2, 16 + "max": 6 17 + } 18 + } 19 + ] 20 + } 21 + ], 22 + "conditions": [ 23 + { 24 + "condition": "minecraft:survives_explosion" 25 + } 26 + ] 27 + } 28 + ] 29 + }
+15
src/common/main/resources/data/asbestos/recipes/asbestos_block.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "AA", 5 + "AA" 6 + ], 7 + "key": { 8 + "A": { 9 + "item": "asbestos:asbestos_fibers" 10 + } 11 + }, 12 + "result": { 13 + "item": "asbestos:asbestos_block" 14 + } 15 + }
+23
src/common/main/resources/data/asbestos/recipes/asbestos_roof_block.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "WA ", 5 + "WBA", 6 + "WWW" 7 + ], 8 + "key": { 9 + "A": { 10 + "item": "asbestos:asbestos_fibers" 11 + }, 12 + "B": { 13 + "item": "minecraft:stone_bricks" 14 + }, 15 + "W": { 16 + "tag": "minecraft:planks" 17 + } 18 + }, 19 + "result": { 20 + "item": "asbestos:asbestos_roof_block", 21 + "count": 4 22 + } 23 + }
+19
src/common/main/resources/data/asbestos/recipes/asbestos_tile_block.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "AB", 5 + "BA" 6 + ], 7 + "key": { 8 + "A": { 9 + "item": "asbestos:asbestos_fibers" 10 + }, 11 + "B": { 12 + "item": "minecraft:polished_andesite" 13 + } 14 + }, 15 + "result": { 16 + "item": "asbestos:asbestos_tile_block", 17 + "count": 4 18 + } 19 + }
+19
src/common/main/resources/data/asbestos/recipes/cancer_meter.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + " X ", 5 + "XSX", 6 + " X " 7 + ], 8 + "key": { 9 + "X": { 10 + "item": "minecraft:iron_ingot" 11 + }, 12 + "S": { 13 + "item": "asbestos:asbestos_fibers" 14 + } 15 + }, 16 + "result": { 17 + "item": "asbestos:cancer_meter" 18 + } 19 + }
+22
src/common/main/resources/data/asbestos/recipes/empty_syringe.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + " I", 5 + " B ", 6 + "N " 7 + ], 8 + "key": { 9 + "I": { 10 + "item": "minecraft:iron_ingot" 11 + }, 12 + "B": { 13 + "item": "minecraft:glass_bottle" 14 + }, 15 + "N": { 16 + "item": "minecraft:iron_nugget" 17 + } 18 + }, 19 + "result": { 20 + "item": "asbestos:empty_syringe" 21 + } 22 + }
+22
src/common/main/resources/data/asbestos/recipes/iron_scraper.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + " NI", 5 + " IN", 6 + "S " 7 + ], 8 + "key": { 9 + "N": { 10 + "item": "minecraft:iron_nugget" 11 + }, 12 + "I": { 13 + "item": "minecraft:iron_ingot" 14 + }, 15 + "S": { 16 + "item": "minecraft:stick" 17 + } 18 + }, 19 + "result": { 20 + "item": "asbestos:iron_scraper" 21 + } 22 + }
+22
src/common/main/resources/data/asbestos/recipes/popcorn_ceiling_block.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "PP", 5 + "AD" 6 + ], 7 + "key": { 8 + "P": { 9 + "tag": "minecraft:planks" 10 + }, 11 + "A": { 12 + "item": "asbestos:asbestos_block" 13 + }, 14 + "D": { 15 + "item": "minecraft:white_dye" 16 + } 17 + }, 18 + "result": { 19 + "item": "asbestos:popcorn_ceiling_block", 20 + "count": 4 21 + } 22 + }
+16
src/common/main/resources/data/asbestos/recipes/ppe_boots.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + " ", 5 + "S S", 6 + "S S" 7 + ], 8 + "key": { 9 + "S": { 10 + "item": "minecraft:string" 11 + } 12 + }, 13 + "result": { 14 + "item": "asbestos:ppe_boots" 15 + } 16 + }
+16
src/common/main/resources/data/asbestos/recipes/ppe_chestplate.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "S S", 5 + "SSS", 6 + "SSS" 7 + ], 8 + "key": { 9 + "S": { 10 + "item": "minecraft:string" 11 + } 12 + }, 13 + "result": { 14 + "item": "asbestos:ppe_chestplate" 15 + } 16 + }
+19
src/common/main/resources/data/asbestos/recipes/ppe_helmet.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "SSS", 5 + "SGS", 6 + "S S" 7 + ], 8 + "key": { 9 + "S": { 10 + "item": "minecraft:string" 11 + }, 12 + "G": { 13 + "item": "minecraft:black_stained_glass_pane" 14 + } 15 + }, 16 + "result": { 17 + "item": "asbestos:ppe_helmet" 18 + } 19 + }
+16
src/common/main/resources/data/asbestos/recipes/ppe_leggings.json
··· 1 + { 2 + "type": "minecraft:crafting_shaped", 3 + "pattern": [ 4 + "SSS", 5 + "S S", 6 + "S S" 7 + ], 8 + "key": { 9 + "S": { 10 + "item": "minecraft:string" 11 + } 12 + }, 13 + "result": { 14 + "item": "asbestos:ppe_leggings" 15 + } 16 + }
+8
src/common/main/resources/data/asbestos/tags/blocks/scrapable.json
··· 1 + { 2 + "replace": false, 3 + "values": [ 4 + "asbestos:asbestos_block", 5 + "asbestos:popcorn_ceiling_block", 6 + "asbestos:asbestos_tile_block" 7 + ] 8 + }
+18
src/common/main/resources/data/asbestos/worldgen/configured_feature/serpentinite_overworld.json
··· 1 + { 2 + "type": "minecraft:ore", 3 + "config": { 4 + "size": 5, 5 + "discard_chance_on_air_exposure": 0, 6 + "targets": [ 7 + { 8 + "target": { 9 + "predicate_type": "minecraft:tag_match", 10 + "tag": "minecraft:deepslate_ore_replaceables" 11 + }, 12 + "state": { 13 + "Name": "asbestos:serpentinite_block" 14 + } 15 + } 16 + ] 17 + } 18 + }
+24
src/common/main/resources/data/asbestos/worldgen/placed_feature/serpentinite.json
··· 1 + { 2 + "feature": "asbestos:serpentinite_overworld", 3 + "placement": [ 4 + { 5 + "type": "minecraft:count", 6 + "count": 20 7 + }, 8 + { 9 + "type": "minecraft:in_square" 10 + }, 11 + { 12 + "type": "minecraft:height_range", 13 + "height": { 14 + "type": "minecraft:uniform", 15 + "min_inclusive": { 16 + "above_bottom": 0 17 + }, 18 + "max_inclusive": { 19 + "absolute": 0 20 + } 21 + } 22 + } 23 + ] 24 + }
+6
src/common/main/resources/data/minecraft/tags/blocks/mineable/axe.json
··· 1 + { 2 + "replace": false, 3 + "values": [ 4 + "asbestos:popcorn_ceiling_block" 5 + ] 6 + }
+7
src/common/main/resources/data/minecraft/tags/blocks/mineable/pickaxe.json
··· 1 + { 2 + "replace": false, 3 + "values": [ 4 + "asbestos:serpentinite_block", 5 + "asbestos:asbestos_roof_block" 6 + ] 7 + }
+6
src/common/main/resources/data/minecraft/tags/damage_type/bypasses_cooldown.json
··· 1 + { 2 + "replace": false, 3 + "values": [ 4 + "asbestos:blood_extract" 5 + ] 6 + }
+6
src/common/main/resources/pack.mcmeta
··· 1 + { 2 + "pack": { 3 + "pack_format": 9, 4 + "description": "Assets for Asbestos" 5 + } 6 + }
+16
src/fabric/main/kotlin/xyz/naomieow/asbestos/AsbestosFabric.kt
··· 1 + @file:JvmName("AsbestosFabric") 2 + 3 + package xyz.naomieow.asbestos 4 + 5 + import net.fabricmc.fabric.api.biome.v1.BiomeModifications 6 + import net.fabricmc.fabric.api.biome.v1.BiomeSelectors 7 + import net.minecraft.world.level.levelgen.GenerationStep 8 + 9 + fun init() { 10 + Asbestos.init() 11 + BiomeModifications.addFeature( 12 + BiomeSelectors.foundInOverworld(), 13 + GenerationStep.Decoration.UNDERGROUND_ORES, 14 + Asbestos.serpentinitePlacedFeatureKey 15 + ) 16 + }
+7
src/fabric/main/kotlin/xyz/naomieow/asbestos/client/AsbestosClientFabric.kt
··· 1 + @file:JvmName("AsbestosClientFabric") 2 + 3 + package xyz.naomieow.asbestos.client 4 + 5 + fun init() { 6 + asbestosClient() 7 + }
+72
src/fabric/main/kotlin/xyz/naomieow/asbestos/client/ModMenuIntegration.kt
··· 1 + package xyz.naomieow.asbestos.client 2 + 3 + import com.terraformersmc.modmenu.api.ConfigScreenFactory 4 + import com.terraformersmc.modmenu.api.ModMenuApi 5 + import dev.isxander.yacl3.api.ConfigCategory 6 + import dev.isxander.yacl3.api.Option 7 + import dev.isxander.yacl3.api.OptionDescription 8 + import dev.isxander.yacl3.api.YetAnotherConfigLib 9 + import dev.isxander.yacl3.api.controller.FloatFieldControllerBuilder 10 + import dev.isxander.yacl3.api.controller.IntegerFieldControllerBuilder 11 + import dev.isxander.yacl3.api.controller.IntegerSliderControllerBuilder 12 + import net.minecraft.network.chat.Component 13 + import xyz.naomieow.asbestos.config.AsbestosConfig.Companion.exsanguination 14 + import xyz.naomieow.asbestos.config.AsbestosConfig.Companion.offset 15 + import xyz.naomieow.asbestos.config.AsbestosConfig.Companion.period 16 + import xyz.naomieow.asbestos.config.AsbestosConfig.Companion.threshold 17 + 18 + class ModMenuIntegration : ModMenuApi { 19 + override fun getModConfigScreenFactory(): ConfigScreenFactory<*> { 20 + return ConfigScreenFactory { parent -> 21 + YetAnotherConfigLib.createBuilder() 22 + .title(Component.translatable("text.config.asbestos_config.title")) 23 + .category( 24 + ConfigCategory.createBuilder() 25 + .name(Component.translatable("text.config.asbestos_config.title")) 26 + .option( 27 + Option.createBuilder<Int>() 28 + .name(Component.translatable("text.config.asbestos_config.option.offset")) 29 + .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.offset.desc"))) 30 + .binding(3, { offset }) { value -> 31 + offset = value 32 + } 33 + .controller { 34 + IntegerSliderControllerBuilder 35 + .create(it) 36 + .step(1) 37 + .range(0, 32) 38 + } 39 + .build()) 40 + .option( 41 + Option.createBuilder<Float>() 42 + .name(Component.translatable("text.config.asbestos_config.option.period")) 43 + .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.period.desc"))) 44 + .binding(5.0f, { period }) { value -> 45 + period = value 46 + } 47 + .controller(FloatFieldControllerBuilder::create) 48 + .build()) 49 + .option( 50 + Option.createBuilder<Int>() 51 + .name(Component.translatable("text.config.asbestos_config.option.threshold")) 52 + .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.threshold.desc"))) 53 + .binding(180, { threshold }) { value -> 54 + threshold = value 55 + } 56 + .controller(IntegerFieldControllerBuilder::create) 57 + .build()) 58 + .option( 59 + Option.createBuilder<Float>() 60 + .name(Component.translatable("text.config.asbestos_config.option.exsanguination")) 61 + .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.exsanguination.desc"))) 62 + .binding(1.0f, { exsanguination }) { value -> 63 + exsanguination = value 64 + } 65 + .controller(FloatFieldControllerBuilder::create) 66 + .build()) 67 + .build()) 68 + .build() 69 + .generateScreen(parent) 70 + } 71 + } 72 + }
+14
src/fabric/main/kotlin/xyz/naomieow/asbestos/mesothelioma/Mesothelioma.kt
··· 1 + @file:Suppress("ACTUAL_WITHOUT_EXPECT", "UnstableApiUsage") 2 + 3 + package xyz.naomieow.asbestos.mesothelioma 4 + 5 + import net.fabricmc.fabric.api.attachment.v1.AttachmentTarget 6 + import net.minecraft.world.entity.player.Player 7 + 8 + actual fun Player.getMesothelioma(): Int { 9 + return (this as AttachmentTarget).getAttachedOrSet(MesotheliomaAttachment.mesothelioma, 0) 10 + } 11 + 12 + actual fun Player.setMesothelioma(value: Int) { 13 + (this as AttachmentTarget).setAttached(MesotheliomaAttachment.mesothelioma, value) 14 + }
+15
src/fabric/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesotheliomaAttachment.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import com.mojang.serialization.Codec 4 + 5 + import net.fabricmc.fabric.api.attachment.v1.AttachmentRegistry 6 + import net.fabricmc.fabric.api.attachment.v1.AttachmentType 7 + import xyz.naomieow.asbestos.id 8 + 9 + // TODO: Doesn't sync/write properly on world quit 10 + public object MesotheliomaAttachment { 11 + public val mesothelioma: AttachmentType<Int> = AttachmentRegistry.createPersistent( 12 + id("mesothelioma"), 13 + Codec.INT, 14 + ) 15 + }
+37
src/forge/main/kotlin/xyz/naomieow/asbestos/AsbestosForge.kt
··· 1 + package xyz.naomieow.asbestos 2 + 3 + import net.minecraft.world.entity.Entity 4 + import net.minecraft.world.entity.player.Player 5 + import net.minecraft.world.inventory.MenuType 6 + import net.minecraftforge.common.capabilities.RegisterCapabilitiesEvent 7 + import net.minecraftforge.event.AttachCapabilitiesEvent 8 + import net.minecraftforge.eventbus.api.SubscribeEvent 9 + import net.minecraftforge.fml.common.Mod 10 + import net.minecraftforge.registries.DeferredRegister 11 + import net.minecraftforge.registries.ForgeRegistries 12 + import xyz.naomieow.asbestos.mesothelioma.MesotheliomaCapability 13 + import xyz.naomieow.asbestos.mesothelioma.MesotheliomaCapabilityProvider 14 + 15 + @Mod(MOD_ID) 16 + class AsbestosForge { 17 + init { 18 + Asbestos.init() 19 + } 20 + 21 + @SubscribeEvent 22 + fun registerCapabilities(event: RegisterCapabilitiesEvent) { 23 + MesotheliomaCapability.register(event) 24 + } 25 + 26 + @SubscribeEvent 27 + fun attachEntityCapabilities(event: AttachCapabilitiesEvent<Entity>) { 28 + when (event.`object`) { 29 + is Player -> MesotheliomaCapabilityProvider.attach(event) 30 + } 31 + } 32 + 33 + companion object { 34 + val menuTypeRegister: DeferredRegister<MenuType<*>> = 35 + DeferredRegister.create(ForgeRegistries.MENU_TYPES, MOD_ID) 36 + } 37 + }
+13
src/forge/main/kotlin/xyz/naomieow/asbestos/client/AsbestosClientForge.kt
··· 1 + @file:EventBusSubscriber(modid = MOD_ID, bus = EventBusSubscriber.Bus.MOD) 2 + 3 + package xyz.naomieow.asbestos.client 4 + 5 + import net.minecraftforge.eventbus.api.SubscribeEvent 6 + import net.minecraftforge.fml.common.Mod.EventBusSubscriber 7 + import net.minecraftforge.fml.event.lifecycle.FMLClientSetupEvent 8 + import xyz.naomieow.asbestos.MOD_ID 9 + 10 + @SubscribeEvent 11 + fun onClientInit(event: FMLClientSetupEvent) { 12 + event.enqueueWork(::asbestosClient) 13 + }
+9
src/forge/main/kotlin/xyz/naomieow/asbestos/mesothelioma/IMesotheliomaCapability.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import net.minecraft.nbt.CompoundTag 4 + import net.minecraftforge.common.util.INBTSerializable 5 + 6 + interface IMesotheliomaCapability : INBTSerializable<CompoundTag> { 7 + fun getValue(): Int 8 + fun setValue(value: Int) 9 + }
+13
src/forge/main/kotlin/xyz/naomieow/asbestos/mesothelioma/Mesothelioma.kt
··· 1 + @file:Suppress("ACTUAL_WITHOUT_EXPECT") 2 + 3 + package xyz.naomieow.asbestos.mesothelioma 4 + 5 + import net.minecraft.world.entity.player.Player 6 + 7 + actual fun Player.getMesothelioma(): Int { 8 + return this.getCapability(MesotheliomaCapability.instance).resolve().get().getValue() 9 + } 10 + 11 + actual fun Player.setMesothelioma(value: Int) { 12 + this.getCapability(MesotheliomaCapability.instance).resolve().get().setValue(value) 13 + }
+15
src/forge/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesotheliomaCapability.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import net.minecraftforge.common.capabilities.Capability 4 + import net.minecraftforge.common.capabilities.CapabilityManager 5 + import net.minecraftforge.common.capabilities.CapabilityToken 6 + import net.minecraftforge.common.capabilities.RegisterCapabilitiesEvent 7 + 8 + object MesotheliomaCapability { 9 + val instance: Capability<IMesotheliomaCapability> = 10 + CapabilityManager.get<IMesotheliomaCapability>(object : CapabilityToken<IMesotheliomaCapability>() {}) 11 + 12 + fun register(event: RegisterCapabilitiesEvent) { 13 + event.register(IMesotheliomaCapability::class.java) 14 + } 15 + }
+44
src/forge/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesotheliomaCapabilityProvider.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import net.minecraft.core.Direction 4 + import net.minecraft.nbt.CompoundTag 5 + import net.minecraft.world.entity.Entity 6 + import net.minecraftforge.common.capabilities.Capability 7 + import net.minecraftforge.common.capabilities.ICapabilitySerializable 8 + import net.minecraftforge.common.util.LazyOptional 9 + import net.minecraftforge.event.AttachCapabilitiesEvent 10 + import xyz.naomieow.asbestos.id 11 + 12 + class MesotheliomaCapabilityProvider : ICapabilitySerializable<CompoundTag> { 13 + private val backend: IMesotheliomaCapability = MesotheliomaImplementation() 14 + private val optionalData: LazyOptional<IMesotheliomaCapability> = LazyOptional.of { backend } 15 + 16 + private fun invalidiate() { 17 + optionalData.invalidate() 18 + } 19 + 20 + override fun <T : Any?> getCapability( 21 + capability: Capability<T?>, 22 + direction: Direction? 23 + ): LazyOptional<T?> { 24 + return MesotheliomaCapability.instance.orEmpty(capability, this.optionalData) 25 + } 26 + 27 + override fun serializeNBT(): CompoundTag { 28 + return this.backend.serializeNBT() 29 + } 30 + 31 + override fun deserializeNBT(tag: CompoundTag) { 32 + return this.backend.deserializeNBT(tag) 33 + } 34 + 35 + companion object { 36 + val identifier = id("mesothelioma_cap") 37 + 38 + fun attach(event: AttachCapabilitiesEvent<Entity>) { 39 + val provider: MesotheliomaCapabilityProvider = MesotheliomaCapabilityProvider() 40 + 41 + event.addCapability(identifier, provider) 42 + } 43 + } 44 + }
+30
src/forge/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesotheliomaImplementation.kt
··· 1 + package xyz.naomieow.asbestos.mesothelioma 2 + 3 + import net.minecraft.nbt.CompoundTag 4 + 5 + class MesotheliomaImplementation : IMesotheliomaCapability { 6 + private var mesothelioma: Int = 0 7 + 8 + override fun getValue(): Int { 9 + return mesothelioma 10 + } 11 + 12 + override fun setValue(value: Int) { 13 + mesothelioma = value 14 + } 15 + 16 + override fun serializeNBT(): CompoundTag { 17 + val tag: CompoundTag = CompoundTag() 18 + tag.putInt(MESOTHELIOMA_NBT_KEY, mesothelioma) 19 + return tag 20 + } 21 + 22 + override fun deserializeNBT(tag: CompoundTag) { 23 + mesothelioma = tag.getInt(MESOTHELIOMA_NBT_KEY) 24 + } 25 + 26 + private companion object { 27 + private const val MESOTHELIOMA_NBT_KEY: String = "mesothelioma" 28 + } 29 + 30 + }
-77
src/main/kotlin/xyz/naomieow/asbestos/AsbestosMod.kt
··· 1 - package xyz.naomieow.asbestos 2 - 3 - import dev.onyxstudios.cca.api.v3.component.ComponentKey 4 - import dev.onyxstudios.cca.api.v3.component.ComponentRegistryV3 5 - import dev.onyxstudios.cca.api.v3.entity.EntityComponentFactoryRegistry 6 - import dev.onyxstudios.cca.api.v3.entity.EntityComponentInitializer 7 - import dev.onyxstudios.cca.api.v3.entity.RespawnCopyStrategy 8 - import net.fabricmc.api.ModInitializer 9 - import net.fabricmc.fabric.api.biome.v1.BiomeModifications 10 - import net.fabricmc.fabric.api.biome.v1.BiomeSelectors 11 - import net.minecraft.core.Registry 12 - import net.minecraft.core.registries.BuiltInRegistries 13 - import net.minecraft.core.registries.Registries 14 - import net.minecraft.resources.ResourceKey 15 - import net.minecraft.resources.ResourceLocation 16 - import net.minecraft.world.effect.MobEffect 17 - import net.minecraft.world.level.block.Block 18 - import net.minecraft.world.level.levelgen.GenerationStep 19 - import net.minecraft.world.level.levelgen.placement.PlacedFeature 20 - import uwu.serenity.kritter.RegistryManager 21 - import xyz.naomieow.asbestos.block.ModBlocks 22 - import xyz.naomieow.asbestos.config.AsbestosConfig 23 - import xyz.naomieow.asbestos.item.ModCreativeTabs 24 - import xyz.naomieow.asbestos.item.ModItems 25 - import xyz.naomieow.asbestos.mesothelioma.IMesoComponent 26 - import xyz.naomieow.asbestos.mesothelioma.MesoStatusEffect 27 - import xyz.naomieow.asbestos.mesothelioma.PlayerMesoComponent 28 - import xyz.naomieow.asbestos.screen.ModMenuTypes 29 - 30 - const val MOD_ID: String = "asbestos" 31 - 32 - internal inline fun id(path: String): ResourceLocation { 33 - return ResourceLocation(MOD_ID, path) 34 - } 35 - 36 - 37 - object AsbestosMod: ModInitializer, EntityComponentInitializer, RegistryManager by RegistryManager(MOD_ID) { 38 - val MESOTHELIOMA: ComponentKey<IMesoComponent> = ComponentRegistryV3.INSTANCE.getOrCreate( 39 - id("mesothelioma"), 40 - IMesoComponent::class.java 41 - ) 42 - val MESO_STATUS: MobEffect = MesoStatusEffect() 43 - val HARMFUL_PASSIVE_BLOCKS: Array<Block> by lazy { arrayOf(ModBlocks.AsbestosBlock) } 44 - val SERPENTINITE_PLACED_KEY: ResourceKey<PlacedFeature> = ResourceKey.create( 45 - Registries.PLACED_FEATURE, 46 - id("serpentinite") 47 - ) 48 - 49 - override fun registerEntityComponentFactories(registry: EntityComponentFactoryRegistry) { 50 - registry.registerForPlayers( 51 - MESOTHELIOMA, 52 - ::PlayerMesoComponent, 53 - RespawnCopyStrategy.NEVER_COPY 54 - ) 55 - } 56 - 57 - override fun onInitialize() { 58 - ModBlocks.register() 59 - ModItems.register() 60 - ModMenuTypes.register() 61 - ModCreativeTabs.register() 62 - 63 - Registry.register( 64 - BuiltInRegistries.MOB_EFFECT, 65 - id("mesothelioma"), 66 - MESO_STATUS 67 - ) 68 - 69 - BiomeModifications.addFeature( 70 - BiomeSelectors.foundInOverworld(), 71 - GenerationStep.Decoration.UNDERGROUND_ORES, 72 - SERPENTINITE_PLACED_KEY 73 - ) 74 - 75 - ModScheduler.init() 76 - } 77 - }
-16
src/main/kotlin/xyz/naomieow/asbestos/AsbestosModClient.kt
··· 1 - package xyz.naomieow.asbestos 2 - 3 - import net.fabricmc.api.ClientModInitializer 4 - import net.fabricmc.api.EnvType 5 - import net.fabricmc.api.Environment 6 - import net.minecraft.client.gui.screens.MenuScreens 7 - import xyz.naomieow.asbestos.screen.CancerMeterScreen 8 - import xyz.naomieow.asbestos.screen.ModMenuTypes 9 - 10 - @Environment(EnvType.CLIENT) 11 - class AsbestosModClient : ClientModInitializer { 12 - override fun onInitializeClient() { 13 - MenuScreens.register(ModMenuTypes.CancerMeter, ::CancerMeterScreen) 14 - } 15 - 16 - }
-55
src/main/kotlin/xyz/naomieow/asbestos/ModScheduler.kt
··· 1 - package xyz.naomieow.asbestos 2 - 3 - import net.fabricmc.fabric.api.event.lifecycle.v1.ServerTickEvents 4 - import net.minecraft.core.BlockPos 5 - import net.minecraft.server.MinecraftServer 6 - import net.minecraft.server.level.ServerLevel 7 - import net.minecraft.server.level.ServerPlayer 8 - import net.minecraft.world.effect.MobEffectInstance 9 - import xyz.naomieow.asbestos.block.CarcinogenicBlock 10 - import xyz.naomieow.asbestos.config.AsbestosConfig 11 - import java.util.function.Consumer 12 - 13 - object ModScheduler { 14 - fun init() { 15 - ServerTickEvents.END_SERVER_TICK.register(ServerTickEvents.EndTick { server: MinecraftServer -> 16 - if (server.tickCount % (AsbestosConfig.period * 20.0f) == 0.0f) { 17 - server.allLevels.forEach(Consumer { level: ServerLevel -> 18 - level.players().forEach( 19 - Consumer { player: ServerPlayer -> 20 - val exposure = AsbestosMod.MESOTHELIOMA.get(player).getMeso() 21 - if (exposure >= (AsbestosConfig.threshold / 2)) { 22 - player.addEffect(MobEffectInstance(AsbestosMod.MESO_STATUS, -1)) 23 - } 24 - 25 - if (CarcinogenicBlock.isProtectedFromAsbestos(player)) { 26 - return@Consumer 27 - } 28 - 29 - val offset = AsbestosConfig.offset 30 - findasbestos@ for (i in -offset..< offset) { 31 - for (j in -offset..< offset) { 32 - for (k in -offset..< offset) { 33 - val offsetPos = player.position() 34 - .add(i.toDouble(), j.toDouble(), k.toDouble()) 35 - val pos = BlockPos( 36 - offsetPos.x().toInt(), 37 - offsetPos.y().toInt(), 38 - offsetPos.z().toInt() 39 - ) 40 - val block = level.getBlockState(pos).block 41 - if (listOf(*AsbestosMod.HARMFUL_PASSIVE_BLOCKS) 42 - .contains(block) 43 - ) { 44 - AsbestosMod.MESOTHELIOMA.get(player).setMeso(exposure + 1) 45 - break@findasbestos 46 - } 47 - } 48 - } 49 - } 50 - }) 51 - }) 52 - } 53 - }) 54 - } 55 - }
-49
src/main/kotlin/xyz/naomieow/asbestos/armor/ProtectiveMaterial.kt
··· 1 - package xyz.naomieow.asbestos.armor 2 - 3 - import net.minecraft.sounds.SoundEvent 4 - import net.minecraft.sounds.SoundEvents 5 - import net.minecraft.world.item.ArmorItem 6 - import net.minecraft.world.item.ArmorMaterial 7 - import net.minecraft.world.item.Items 8 - import net.minecraft.world.item.crafting.Ingredient 9 - 10 - class ProtectiveMaterial : ArmorMaterial { 11 - override fun getDurabilityForType(type: ArmorItem.Type): Int { 12 - return BASE_DURABILITY[type.slot.index] 13 - } 14 - 15 - override fun getDefenseForType(type: ArmorItem.Type): Int { 16 - return PROTECTION_VALUES[type.slot.index] 17 - } 18 - 19 - override fun getEnchantmentValue(): Int { 20 - return 4 21 - } 22 - 23 - override fun getEquipSound(): SoundEvent { 24 - return SoundEvents.WOOL_HIT 25 - } 26 - 27 - override fun getRepairIngredient(): Ingredient { 28 - return Ingredient.of(Items.STRING) 29 - } 30 - 31 - override fun getName(): String { 32 - return "asbestos_protective" 33 - } 34 - 35 - override fun getToughness(): Float { 36 - return 0f 37 - } 38 - 39 - override fun getKnockbackResistance(): Float { 40 - return 0f 41 - } 42 - 43 - companion object { 44 - private val BASE_DURABILITY = intArrayOf(13, 15, 16, 11) 45 - private val PROTECTION_VALUES = intArrayOf(1, 1, 2, 1) 46 - 47 - val INSTANCE: ProtectiveMaterial = ProtectiveMaterial() 48 - } 49 - }
-80
src/main/kotlin/xyz/naomieow/asbestos/block/AsbestosRoofBlock.kt
··· 1 - package xyz.naomieow.asbestos.block 2 - 3 - import net.fabricmc.api.EnvType 4 - import net.fabricmc.api.Environment 5 - import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap 6 - import net.fabricmc.loader.api.FabricLoader 7 - import net.minecraft.client.renderer.RenderType 8 - import net.minecraft.core.BlockPos 9 - import net.minecraft.core.Direction 10 - import net.minecraft.world.item.context.BlockPlaceContext 11 - import net.minecraft.world.level.BlockGetter 12 - import net.minecraft.world.level.block.Block 13 - import net.minecraft.world.level.block.state.BlockState 14 - import net.minecraft.world.level.block.state.StateDefinition 15 - import net.minecraft.world.level.block.state.properties.BlockStateProperties 16 - import net.minecraft.world.phys.shapes.CollisionContext 17 - import net.minecraft.world.phys.shapes.Shapes 18 - import net.minecraft.world.phys.shapes.VoxelShape 19 - 20 - class AsbestosRoofBlock(settings: Properties, dangerLevel: Int) : CarcinogenicBlock(settings, dangerLevel) { 21 - init { 22 - registerDefaultState( 23 - this.getStateDefinition().any() 24 - .setValue<Direction?, Direction?>(BlockStateProperties.HORIZONTAL_FACING, Direction.NORTH) 25 - ) 26 - if (FabricLoader.getInstance().environmentType != EnvType.SERVER) { 27 - BlockRenderLayerMap.INSTANCE.putBlock(this, RenderType.cutout()) 28 - } 29 - } 30 - 31 - override fun createBlockStateDefinition(builder: StateDefinition.Builder<Block?, BlockState?>) { 32 - builder.add(BlockStateProperties.HORIZONTAL_FACING) 33 - } 34 - 35 - @Deprecated("Deprecated in Java") 36 - override fun getShape( 37 - state: BlockState, 38 - world: BlockGetter, 39 - pos: BlockPos, 40 - context: CollisionContext 41 - ): VoxelShape { 42 - val dir = state.getValue<Direction?>(BlockStateProperties.HORIZONTAL_FACING) 43 - return when (dir) { 44 - Direction.NORTH -> Shapes.or( 45 - Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 46 - Shapes.box(0.0, 0.5, 0.5, 1.0, 1.0, 1.0) 47 - ) 48 - 49 - Direction.SOUTH -> Shapes.or( 50 - Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 51 - Shapes.box(0.0, 0.5, 0.0, 1.0, 1.0, 0.5) 52 - ) 53 - 54 - Direction.EAST -> Shapes.or( 55 - Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 56 - Shapes.box(0.0, 0.5, 0.0, 0.5, 1.0, 1.0) 57 - ) 58 - 59 - Direction.WEST -> Shapes.or( 60 - Shapes.box(0.0, 0.0, 0.0, 1.0, 0.5, 1.0), 61 - Shapes.box(0.5, 0.5, 0.0, 1.0, 1.0, 1.0) 62 - ) 63 - 64 - else -> Shapes.block() 65 - } 66 - } 67 - 68 - override fun getStateForPlacement(ctx: BlockPlaceContext): BlockState? { 69 - return this.defaultBlockState().setValue( 70 - BlockStateProperties.HORIZONTAL_FACING, 71 - ctx.horizontalDirection.opposite 72 - ) 73 - } 74 - 75 - @Deprecated("Deprecated in Java") 76 - @Environment(EnvType.CLIENT) 77 - override fun getShadeBrightness(state: BlockState, world: BlockGetter, pos: BlockPos): Float { 78 - return 1.0f 79 - } 80 - }
-38
src/main/kotlin/xyz/naomieow/asbestos/block/CarcinogenicBlock.kt
··· 1 - package xyz.naomieow.asbestos.block 2 - 3 - import net.minecraft.core.BlockPos 4 - import net.minecraft.world.entity.player.Player 5 - import net.minecraft.world.item.Item 6 - import net.minecraft.world.level.Level 7 - import net.minecraft.world.level.block.Block 8 - import net.minecraft.world.level.block.state.BlockState 9 - import xyz.naomieow.asbestos.AsbestosMod 10 - import xyz.naomieow.asbestos.item.ModItems 11 - 12 - open class CarcinogenicBlock(settings: Properties, private val dangerLevel: Int) : Block(settings) { 13 - override fun playerWillDestroy(world: Level, pos: BlockPos, state: BlockState, player: Player) { 14 - super.playerWillDestroy(world, pos, state, player) 15 - if (!isProtectedFromAsbestos(player)) { 16 - val exposure = AsbestosMod.MESOTHELIOMA.get(player).getMeso() 17 - AsbestosMod.MESOTHELIOMA.get(player).setMeso(exposure + dangerLevel) 18 - } 19 - } 20 - 21 - companion object { 22 - val PROTECTIVE_ARMOUR: Array<Item> by lazy { arrayOf<Item>( 23 - ModItems.PPEHelmet, 24 - ModItems.PPEChestplate, 25 - ModItems.PPELeggings, 26 - ModItems.PPEBoots 27 - ) } 28 - 29 - fun isProtectedFromAsbestos(player: Player): Boolean { 30 - for (item in player.armorSlots) { 31 - if (!listOf(*PROTECTIVE_ARMOUR).contains(item.item)) { 32 - return false 33 - } 34 - } 35 - return true 36 - } 37 - } 38 - }
-62
src/main/kotlin/xyz/naomieow/asbestos/block/ModBlocks.kt
··· 1 - package xyz.naomieow.asbestos.block 2 - 3 - import net.minecraft.core.registries.Registries 4 - import net.minecraft.world.level.block.Block 5 - import net.minecraft.world.level.block.Blocks 6 - import uwu.serenity.kritter.api.Registrar 7 - import uwu.serenity.kritter.stdlib.block 8 - import xyz.naomieow.asbestos.AsbestosMod 9 - 10 - @Suppress("UNUSED") 11 - object ModBlocks: Registrar<Block> by AsbestosMod..Registries.BLOCK { 12 - val AsbestosBlock: Block by block("asbestos_block", { properties -> 13 - CarcinogenicBlock(properties, 40) 14 - }) { 15 - copyProperties(Blocks::WHITE_WOOL) 16 - properties { 17 - destroyTime(1.0f) 18 - simpleItem() 19 - } 20 - } 21 - 22 - val SerpentiniteBlock: Block by block("serpentinite_block", { properties -> 23 - CarcinogenicBlock(properties, 20) 24 - }) { 25 - copyProperties(Blocks::STONE) 26 - properties { 27 - destroyTime(3.0f) 28 - requiresCorrectToolForDrops() 29 - simpleItem() 30 - } 31 - } 32 - 33 - val PopcornCeilingBlock: Block by block("popcorn_ceiling_block", { properties -> 34 - CarcinogenicBlock(properties, 20) 35 - }) { 36 - copyProperties(Blocks::OAK_PLANKS) 37 - properties { 38 - destroyTime(2.0f) 39 - simpleItem() 40 - } 41 - } 42 - 43 - val AsbestosTileBlock: Block by block("asbestos_tile_block", { properties -> 44 - CarcinogenicBlock(properties, 20) 45 - }) { 46 - copyProperties(Blocks::NETHER_BRICKS) 47 - properties { 48 - destroyTime(3.0f) 49 - simpleItem() 50 - } 51 - } 52 - 53 - val AsbestosRoofBlock: Block by block("asbestos_roof_block", { properties -> 54 - CarcinogenicBlock(properties, 20) 55 - }) { 56 - copyProperties { AsbestosTileBlock } 57 - properties { 58 - noOcclusion() 59 - simpleItem() 60 - } 61 - } 62 - }
-102
src/main/kotlin/xyz/naomieow/asbestos/config/AsbestosConfig.kt
··· 1 - package xyz.naomieow.asbestos.config 2 - 3 - import dev.isxander.yacl3.api.ConfigCategory 4 - import dev.isxander.yacl3.api.Option 5 - import dev.isxander.yacl3.api.OptionDescription 6 - import dev.isxander.yacl3.api.YetAnotherConfigLib 7 - import dev.isxander.yacl3.api.controller.ControllerBuilder 8 - import dev.isxander.yacl3.api.controller.FloatFieldControllerBuilder 9 - import dev.isxander.yacl3.api.controller.IntegerFieldControllerBuilder 10 - import dev.isxander.yacl3.api.controller.IntegerSliderControllerBuilder 11 - import dev.isxander.yacl3.config.v2.api.ConfigClassHandler 12 - import dev.isxander.yacl3.config.v2.api.SerialEntry 13 - import dev.isxander.yacl3.config.v2.api.serializer.GsonConfigSerializerBuilder 14 - import dev.isxander.yacl3.dsl.binding 15 - import dev.isxander.yacl3.dsl.controller 16 - import dev.isxander.yacl3.gui.controllers.slider.IntegerSliderController 17 - import dev.isxander.yacl3.impl.YetAnotherConfigLibImpl 18 - import net.fabricmc.loader.api.FabricLoader 19 - import net.minecraft.client.gui.screens.Screen 20 - import net.minecraft.network.chat.Component 21 - import xyz.naomieow.asbestos.id 22 - 23 - class AsbestosConfig { 24 - companion object { 25 - @JvmField 26 - @SerialEntry 27 - var offset: Int = 3 28 - 29 - @JvmField 30 - @SerialEntry 31 - var period: Float = 5.0f 32 - 33 - @JvmField 34 - @SerialEntry 35 - var threshold: Int = 180 36 - 37 - @JvmField 38 - @SerialEntry 39 - var exsanguination: Float = 1.0f 40 - 41 - fun screen(parent: Screen?): Screen { 42 - return YetAnotherConfigLib.createBuilder() 43 - .title(Component.translatable("text.config.asbestos_config.title")) 44 - .category(ConfigCategory.createBuilder() 45 - .name(Component.translatable("text.config.asbestos_config.title")) 46 - .option(Option.createBuilder<Int>() 47 - .name(Component.translatable("text.config.asbestos_config.option.offset")) 48 - .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.offset.desc"))) 49 - .binding(3, { offset }) { value -> 50 - offset = value 51 - } 52 - .controller { 53 - IntegerSliderControllerBuilder 54 - .create(it) 55 - .step(1) 56 - .range(0, 32) 57 - } 58 - .build()) 59 - .option(Option.createBuilder<Float>() 60 - .name(Component.translatable("text.config.asbestos_config.option.period")) 61 - .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.period.desc"))) 62 - .binding(5.0f, { period }) { value -> 63 - period = value 64 - } 65 - .controller(FloatFieldControllerBuilder::create) 66 - .build()) 67 - .option(Option.createBuilder<Int>() 68 - .name(Component.translatable("text.config.asbestos_config.option.threshold")) 69 - .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.threshold.desc"))) 70 - .binding(180, { threshold }) { value -> 71 - threshold = value 72 - } 73 - .controller(IntegerFieldControllerBuilder::create) 74 - .build()) 75 - .option(Option.createBuilder<Float>() 76 - .name(Component.translatable("text.config.asbestos_config.option.exsanguination")) 77 - .description(OptionDescription.of(Component.translatable("text.config.asbestos_config.option.exsanguination.desc"))) 78 - .binding(1.0f, { exsanguination }) { value -> 79 - exsanguination = value 80 - } 81 - .controller(FloatFieldControllerBuilder::create) 82 - .build()) 83 - .build()) 84 - .build() 85 - .generateScreen(parent) 86 - } 87 - 88 - val Handler: ConfigClassHandler<AsbestosConfig> = ConfigClassHandler.createBuilder(AsbestosConfig::class.java) 89 - .id(id("asbestos_config")) 90 - .serializer { config -> 91 - GsonConfigSerializerBuilder.create(config) 92 - .setPath(FabricLoader 93 - .getInstance() 94 - .configDir 95 - .resolve("asbestos.json5") 96 - ) 97 - .setJson5(true) 98 - .build() 99 - } 100 - .build() 101 - } 102 - }
-13
src/main/kotlin/xyz/naomieow/asbestos/config/ModMenuIntegration.kt
··· 1 - package xyz.naomieow.asbestos.config 2 - 3 - import com.terraformersmc.modmenu.api.ConfigScreenFactory 4 - import com.terraformersmc.modmenu.api.ModMenuApi 5 - import net.minecraft.client.gui.screens.Screen 6 - 7 - class ModMenuIntegration: ModMenuApi { 8 - override fun getModConfigScreenFactory(): ConfigScreenFactory<*> { 9 - return ConfigScreenFactory { parent -> 10 - AsbestosConfig.screen(parent) 11 - } 12 - } 13 - }
-27
src/main/kotlin/xyz/naomieow/asbestos/damage/ModDamageTypes.kt
··· 1 - package xyz.naomieow.asbestos.damage 2 - 3 - import net.minecraft.core.registries.Registries 4 - import net.minecraft.resources.ResourceKey 5 - import net.minecraft.world.damagesource.DamageSource 6 - import net.minecraft.world.damagesource.DamageType 7 - import net.minecraft.world.level.Level 8 - import xyz.naomieow.asbestos.id 9 - 10 - object ModDamageTypes { 11 - val MESOTHELIOMA: ResourceKey<DamageType> = ResourceKey.create( 12 - Registries.DAMAGE_TYPE, 13 - id("mesothelioma") 14 - ) 15 - val BLOOD_EXTRACT: ResourceKey<DamageType> = ResourceKey.create( 16 - Registries.DAMAGE_TYPE, 17 - id("blood_extract") 18 - ) 19 - 20 - fun of(level: Level, key: ResourceKey<DamageType>): DamageSource { 21 - return DamageSource(level 22 - .registryAccess() 23 - .registryOrThrow(Registries.DAMAGE_TYPE) 24 - .getHolderOrThrow(key) 25 - ) 26 - } 27 - }
-152
src/main/kotlin/xyz/naomieow/asbestos/inventory/CancerMeterInventory.kt
··· 1 - package xyz.naomieow.asbestos.inventory 2 - 3 - import net.fabricmc.fabric.api.screenhandler.v1.ExtendedScreenHandlerFactory 4 - import net.minecraft.core.NonNullList 5 - import net.minecraft.nbt.CompoundTag 6 - import net.minecraft.nbt.ListTag 7 - import net.minecraft.network.FriendlyByteBuf 8 - import net.minecraft.network.chat.Component 9 - import net.minecraft.server.level.ServerPlayer 10 - import net.minecraft.world.entity.player.Inventory 11 - import net.minecraft.world.entity.player.Player 12 - import net.minecraft.world.inventory.AbstractContainerMenu 13 - import net.minecraft.world.item.ItemStack 14 - import net.minecraft.world.level.Level 15 - import xyz.naomieow.asbestos.screen.CancerMeterScreenHandler 16 - 17 - class CancerMeterInventory( 18 - private var stack: ItemStack, 19 - private val player: Player, 20 - private val screenId: Byte, 21 - ): ICancerMeterInventory { 22 - private var inventory: InventoryImproved = createInventory(1) 23 - 24 - init { 25 - readAllData(stack.orCreateTag) 26 - } 27 - 28 - fun setStack(itemStack: ItemStack) { 29 - stack = itemStack 30 - } 31 - 32 - override fun getInventory(): InventoryImproved { 33 - return inventory 34 - } 35 - 36 - override fun writeAllData(tag: CompoundTag) { 37 - writeItems(tag) 38 - } 39 - 40 - override fun readAllData(tag: CompoundTag) { 41 - readItems(tag) 42 - } 43 - 44 - override fun writeItems(tag: CompoundTag) { 45 - writeTag(tag, inventory.getStacks(), true) 46 - } 47 - 48 - override fun readItems(tag: CompoundTag) { 49 - readTag(tag, inventory.getStacks()) 50 - } 51 - 52 - override fun getLevel(): Level { 53 - return player.level() 54 - } 55 - 56 - override fun getScreenID(): Byte { 57 - return screenId 58 - } 59 - 60 - override fun getItemStack(): ItemStack { 61 - return stack 62 - } 63 - 64 - override fun setUsingPlayer(player: Player?) { } 65 - 66 - override fun markDataDirty(vararg dataIds: Byte) { 67 - if (getLevel().isClientSide) { 68 - return 69 - } 70 - 71 - for (data in dataIds) { 72 - when (data) { 73 - ICancerMeterInventory.Companion.INVENTORY_DATA -> CancerMeterInventory.writeTag( 74 - stack.getOrCreateTag(), 75 - getInventory().getStacks(), 76 - true 77 - ) 78 - ICancerMeterInventory.Companion.COMBINED_INVENTORY_DATA -> writeItems(stack.getOrCreateTag()) 79 - ICancerMeterInventory.Companion.ALL_DATA -> writeAllData(stack.getOrCreateTag()) 80 - } 81 - } 82 - } 83 - 84 - override fun markDirty() { } 85 - 86 - private fun createInventory(size: Int): InventoryImproved { 87 - return object : InventoryImproved(NonNullList.withSize(size, ItemStack.EMPTY)) { 88 - override fun setChanged() { 89 - markDataDirty(ICancerMeterInventory.Companion.COMBINED_INVENTORY_DATA) 90 - } 91 - } 92 - } 93 - 94 - companion object { 95 - fun openHandledScreen(player: Player, stack: ItemStack, screenID: Byte) { 96 - if (!player.level().isClientSide()) { 97 - player.openMenu(object : ExtendedScreenHandlerFactory { 98 - override fun writeScreenOpeningData(player: ServerPlayer, buf: FriendlyByteBuf) { 99 - buf.writeByte(screenID.toInt()) 100 - } 101 - 102 - override fun getDisplayName(): Component { 103 - return Component.translatable("screen.asbestos.cancer_meter") 104 - } 105 - 106 - override fun createMenu( 107 - syncId: Int, 108 - playerInventory: Inventory, 109 - player: Player 110 - ): AbstractContainerMenu { 111 - return CancerMeterScreenHandler( 112 - syncId, 113 - playerInventory, 114 - CancerMeterInventory(stack, player, screenID) 115 - ) 116 - } 117 - }) 118 - } 119 - } 120 - 121 - private fun writeTag(tag: CompoundTag, stacks: NonNullList<ItemStack>, setIfEmpty: Boolean): CompoundTag { 122 - val tags = ListTag() 123 - for (i in stacks.indices) { 124 - val itemStack = stacks[i] 125 - if (!itemStack.isEmpty) { 126 - val newTag = CompoundTag() 127 - newTag.putByte("Slot", i.toByte()) 128 - itemStack.save(newTag) 129 - tags.add(newTag) 130 - } 131 - } 132 - 133 - if (!tags.isEmpty() || setIfEmpty) { 134 - tag.put("Inventory", tags) 135 - } 136 - 137 - return tag 138 - } 139 - 140 - private fun readTag(tag: CompoundTag, stacks: NonNullList<ItemStack>) { 141 - val tags = tag.getList("Inventory", 10) 142 - 143 - for (i in tags.indices) { 144 - val newTag = tags.getCompound(i) 145 - val j = newTag.getByte("Slot").toInt() and 255 146 - if (j >= 0 && j < stacks.size) { 147 - stacks[j] = ItemStack.of(newTag) 148 - } 149 - } 150 - } 151 - } 152 - }
-27
src/main/kotlin/xyz/naomieow/asbestos/inventory/ICancerMeterInventory.kt
··· 1 - package xyz.naomieow.asbestos.inventory 2 - 3 - import net.minecraft.nbt.CompoundTag 4 - import net.minecraft.world.entity.player.Player 5 - import net.minecraft.world.item.ItemStack 6 - import net.minecraft.world.level.Level 7 - 8 - interface ICancerMeterInventory { 9 - fun writeItems(tag: CompoundTag) 10 - fun readItems(tag: CompoundTag) 11 - fun writeAllData(tag: CompoundTag) 12 - fun readAllData(tag: CompoundTag) 13 - fun getInventory(): InventoryImproved 14 - fun getScreenID(): Byte 15 - fun getLevel(): Level 16 - fun getItemStack(): ItemStack 17 - fun setUsingPlayer(player: Player?) 18 - fun markDataDirty(vararg dataIds: Byte) 19 - fun markDirty() 20 - 21 - companion object { 22 - const val INVENTORY_DATA: Byte = 0 23 - const val COMBINED_INVENTORY_DATA: Byte = 1 24 - const val SLOT_DATA: Byte = 2 25 - const val ALL_DATA: Byte = 3 26 - } 27 - }
-78
src/main/kotlin/xyz/naomieow/asbestos/inventory/InventoryImproved.kt
··· 1 - package xyz.naomieow.asbestos.inventory 2 - 3 - import net.minecraft.core.NonNullList 4 - import net.minecraft.world.Container 5 - import net.minecraft.world.ContainerHelper 6 - import net.minecraft.world.entity.player.Player 7 - import net.minecraft.world.item.ItemStack 8 - import xyz.naomieow.asbestos.item.ModItems 9 - 10 - /* 11 - * Converted from Tiviacz1337's InventoryImproved from Travelers Backpack: 12 - * https://github.com/Tiviacz1337/Travelers-Backpack/blob/3dc0bfeec381537a5ce85c2ae1e6e00d62542206/src/main/java/com/tiviacz/travelersbackpack/inventory/InventoryImproved.java 13 - */ 14 - abstract class InventoryImproved( 15 - @get:JvmName("getInventoryStacks") 16 - protected var stacks: NonNullList<ItemStack> 17 - ): Container { 18 - fun getStacks(): NonNullList<ItemStack> { 19 - return stacks 20 - } 21 - 22 - override fun getContainerSize(): Int { 23 - return stacks.size 24 - } 25 - override fun isEmpty(): Boolean { 26 - for (i in 0..< containerSize) { 27 - if (!getItem(i).isEmpty) { 28 - return false 29 - } 30 - } 31 - return true 32 - } 33 - 34 - override fun getItem(slot: Int): ItemStack { 35 - return stacks[slot] 36 - } 37 - 38 - override fun removeItem(slot: Int, amount: Int): ItemStack { 39 - val itemStack = ContainerHelper.removeItem(stacks, slot, amount) 40 - 41 - if (!itemStack.isEmpty) { 42 - setChanged() 43 - } 44 - return itemStack 45 - } 46 - 47 - override fun removeItemNoUpdate(slot: Int): ItemStack { 48 - val itemStack = stacks[slot] 49 - if (itemStack.isEmpty) { 50 - return ItemStack.EMPTY 51 - } else { 52 - stacks[slot] = ItemStack.EMPTY 53 - return itemStack 54 - } 55 - } 56 - 57 - override fun setItem(slot: Int, itemStack: ItemStack) { 58 - stacks[slot] = itemStack 59 - if (!itemStack.isEmpty && itemStack.count > maxStackSize) { 60 - itemStack.count = maxStackSize 61 - } 62 - 63 - setChanged() 64 - } 65 - 66 - abstract override fun setChanged() 67 - 68 - override fun canPlaceItem(slot: Int, itemStack: ItemStack): Boolean { 69 - return itemStack.item !== ModItems.CancerMeter 70 - } 71 - 72 - override fun stillValid(player: Player): Boolean { 73 - return true 74 - } 75 - 76 - override fun clearContent() { 77 - } 78 - }
-27
src/main/kotlin/xyz/naomieow/asbestos/item/CancerMeterItem.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.world.InteractionHand 4 - import net.minecraft.world.InteractionResultHolder 5 - import net.minecraft.world.entity.player.Player 6 - import net.minecraft.world.item.Item 7 - import net.minecraft.world.item.ItemStack 8 - import net.minecraft.world.level.Level 9 - import xyz.naomieow.asbestos.inventory.CancerMeterInventory 10 - 11 - class CancerMeterItem( 12 - properties: Properties 13 - ): Item( 14 - properties 15 - ) { 16 - override fun use(world: Level, user: Player, hand: InteractionHand): InteractionResultHolder<ItemStack?> { 17 - val itemStack = user.getItemInHand(hand) 18 - if (hand == InteractionHand.OFF_HAND) { 19 - return InteractionResultHolder.fail<ItemStack?>(itemStack) 20 - } 21 - 22 - if (!world.isClientSide()) { 23 - CancerMeterInventory.openHandledScreen(user, user.mainHandItem, 1.toByte()) 24 - } 25 - return InteractionResultHolder.sidedSuccess<ItemStack?>(itemStack, world.isClientSide()) 26 - } 27 - }
-61
src/main/kotlin/xyz/naomieow/asbestos/item/EmptySyringeItem.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.sounds.SoundEvents 4 - import net.minecraft.sounds.SoundSource 5 - import net.minecraft.world.InteractionHand 6 - import net.minecraft.world.InteractionResult 7 - import net.minecraft.world.InteractionResultHolder 8 - import net.minecraft.world.entity.LivingEntity 9 - import net.minecraft.world.entity.player.Player 10 - import net.minecraft.world.item.Item 11 - import net.minecraft.world.item.ItemStack 12 - import net.minecraft.world.level.Level 13 - import xyz.naomieow.asbestos.AsbestosMod 14 - import xyz.naomieow.asbestos.config.AsbestosConfig 15 - import xyz.naomieow.asbestos.damage.ModDamageTypes 16 - 17 - class EmptySyringeItem( 18 - properties: Item.Properties 19 - ): Item( 20 - properties 21 - ) { 22 - override fun use(world: Level, user: Player, hand: InteractionHand): InteractionResultHolder<ItemStack> { 23 - useEmptySyringe(user, user, hand, world) 24 - return InteractionResultHolder.consume<ItemStack>(user.getItemInHand(hand)) 25 - } 26 - 27 - override fun interactLivingEntity( 28 - stack: ItemStack, 29 - user: Player, 30 - entity: LivingEntity, 31 - hand: InteractionHand 32 - ): InteractionResult { 33 - val world = user.level() 34 - useEmptySyringe(user, entity, hand, world) 35 - return InteractionResult.CONSUME 36 - } 37 - 38 - private fun useEmptySyringe(user: Player, target: LivingEntity, hand: InteractionHand, world: Level) { 39 - world.playSound( 40 - null, 41 - user.blockPosition(), 42 - SoundEvents.BOTTLE_FILL, 43 - SoundSource.PLAYERS, 44 - 1.0f, 1.0f 45 - ) 46 - val handStack = user.getItemInHand(hand) 47 - val newStack = ItemStack(ModItems.FilledSyringe, 1) 48 - newStack.tag = handStack.getOrCreateTag().copy() 49 - FilledSyringeItem.writeNbt(target, newStack) 50 - target.hurt( 51 - ModDamageTypes.of(user.level(), ModDamageTypes.BLOOD_EXTRACT), 52 - AsbestosConfig.exsanguination 53 - ) 54 - if (!user.inventory.add(newStack)) { 55 - user.drop(newStack, false) 56 - } 57 - if (!user.abilities.instabuild) { 58 - handStack.shrink(1) 59 - } 60 - } 61 - }
-34
src/main/kotlin/xyz/naomieow/asbestos/item/FilledSyringeItem.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.ChatFormatting 4 - import net.minecraft.network.chat.Component 5 - import net.minecraft.world.entity.EntityType 6 - import net.minecraft.world.entity.LivingEntity 7 - import net.minecraft.world.entity.player.Player 8 - import net.minecraft.world.item.Item 9 - import net.minecraft.world.item.ItemStack 10 - import xyz.naomieow.asbestos.AsbestosMod 11 - 12 - class FilledSyringeItem( 13 - properties: Properties 14 - ): Item( 15 - properties 16 - ) { 17 - companion object { 18 - private const val TYPE_KEY: String = "EntityType" 19 - private const val CANCER_KEY: String = "CancerMeter" 20 - 21 - fun writeNbt(target: LivingEntity, syringe: ItemStack) { 22 - val nbt = syringe.getOrCreateTag() 23 - syringe.setHoverName(Component.translatable( 24 - "item.asbestos.filled_syringe", 25 - target.name) 26 - .withStyle(ChatFormatting.RESET) 27 - ) 28 - nbt.putString(TYPE_KEY, EntityType.getKey(target.type).toString()) 29 - if (target is Player) { 30 - nbt.putInt(CANCER_KEY, AsbestosMod.MESOTHELIOMA.get(target).getMeso()) 31 - } 32 - } 33 - } 34 - }
-36
src/main/kotlin/xyz/naomieow/asbestos/item/ModCreativeTabs.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.core.registries.Registries 4 - import net.minecraft.network.chat.Component 5 - import net.minecraft.world.item.CreativeModeTab 6 - import uwu.serenity.kritter.api.Registrar 7 - import uwu.serenity.kritter.api.entry.RegistryEntry 8 - import uwu.serenity.kritter.stdlib.creativeTab 9 - import xyz.naomieow.asbestos.AsbestosMod 10 - import xyz.naomieow.asbestos.block.ModBlocks 11 - 12 - @Suppress("UNUSED") 13 - object ModCreativeTabs: Registrar<CreativeModeTab> by AsbestosMod..Registries.CREATIVE_MODE_TAB { 14 - val Asbestos: RegistryEntry<CreativeModeTab> = creativeTab("asbestos") { 15 - title = Component.translatable("itemGroup.asbestos.asbestos") 16 - icon { ModItems.AsbestosFibers.defaultInstance } 17 - displayItems { 18 - // Items 19 - accept(ModItems.AsbestosFibers) 20 - accept(ModItems.IronScraper) 21 - accept(ModItems.EmptySyringe) 22 - accept(ModItems.FilledSyringe) 23 - accept(ModItems.CancerMeter) 24 - accept(ModItems.PPEHelmet) 25 - accept(ModItems.PPEChestplate) 26 - accept(ModItems.PPELeggings) 27 - accept(ModItems.PPEBoots) 28 - // Blocks 29 - accept(ModBlocks.AsbestosBlock) 30 - accept(ModBlocks.SerpentiniteBlock) 31 - accept(ModBlocks.PopcornCeilingBlock) 32 - accept(ModBlocks.AsbestosTileBlock) 33 - accept(ModBlocks.AsbestosRoofBlock) 34 - } 35 - } 36 - }
-88
src/main/kotlin/xyz/naomieow/asbestos/item/ModItems.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.core.registries.Registries 4 - import net.minecraft.world.effect.MobEffectInstance 5 - import net.minecraft.world.effect.MobEffects 6 - import net.minecraft.world.food.FoodProperties 7 - import net.minecraft.world.item.ArmorItem 8 - import net.minecraft.world.item.Item 9 - import uwu.serenity.kritter.api.Registrar 10 - import uwu.serenity.kritter.stdlib.item 11 - import xyz.naomieow.asbestos.AsbestosMod 12 - import xyz.naomieow.asbestos.armor.ProtectiveMaterial 13 - 14 - @Suppress("UNUSED") 15 - object ModItems: Registrar<Item> by AsbestosMod..Registries.ITEM { 16 - val AsbestosFibers by item("asbestos_fibers", ::Item) { 17 - properties { 18 - fireResistant() 19 - food(FoodProperties.Builder() 20 - .alwaysEat() 21 - .effect(MobEffectInstance( 22 - MobEffects.WITHER, 23 - 30 * 20, 4, 24 - false, false 25 - ), 1.0f) 26 - .build() 27 - ) 28 - } 29 - } 30 - 31 - val IronScraper by item("iron_scraper", { properties -> 32 - ScraperItem( 33 - ScraperItemMaterial.INSTANCE, 34 - 0.0f, -3.0f, 35 - properties, 36 - ) 37 - }) 38 - 39 - val FilledSyringe by item("filled_syringe", ::FilledSyringeItem) { 40 - properties { 41 - stacksTo(1) 42 - } 43 - } 44 - 45 - val EmptySyringe by item("empty_syringe", ::EmptySyringeItem) { 46 - properties { 47 - stacksTo(16) 48 - } 49 - } 50 - 51 - val CancerMeter by item("cancer_meter", ::CancerMeterItem) { 52 - properties { 53 - stacksTo(1) 54 - } 55 - } 56 - 57 - val PPEHelmet by item("ppe_helmet", { properties -> 58 - ArmorItem( 59 - ProtectiveMaterial.INSTANCE, 60 - ArmorItem.Type.HELMET, 61 - properties 62 - ) 63 - }) 64 - 65 - val PPEChestplate by item("ppe_chestplate", { properties -> 66 - ArmorItem( 67 - ProtectiveMaterial.INSTANCE, 68 - ArmorItem.Type.CHESTPLATE, 69 - properties 70 - ) 71 - }) 72 - 73 - val PPELeggings by item("ppe_leggings", { properties -> 74 - ArmorItem( 75 - ProtectiveMaterial.INSTANCE, 76 - ArmorItem.Type.LEGGINGS, 77 - properties 78 - ) 79 - }) 80 - 81 - val PPEBoots by item("ppe_boots", { properties -> 82 - ArmorItem( 83 - ProtectiveMaterial.INSTANCE, 84 - ArmorItem.Type.BOOTS, 85 - properties 86 - ) 87 - }) 88 - }
-28
src/main/kotlin/xyz/naomieow/asbestos/item/ScraperItem.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.core.registries.Registries 4 - import net.minecraft.tags.TagKey 5 - import net.minecraft.world.item.DiggerItem 6 - import net.minecraft.world.item.Tier 7 - import net.minecraft.world.level.block.Block 8 - import xyz.naomieow.asbestos.id 9 - 10 - class ScraperItem( 11 - tier: Tier, 12 - attackDamage: Float, 13 - attackSpeed: Float, 14 - properties: Properties 15 - ): DiggerItem( 16 - attackDamage, 17 - attackSpeed, 18 - tier, 19 - AFFECTED_BLOCKS, 20 - properties 21 - ) { 22 - companion object { 23 - private val AFFECTED_BLOCKS: TagKey<Block> = TagKey.create( 24 - Registries.BLOCK, 25 - id("scrapeable") 26 - ) 27 - } 28 - }
-35
src/main/kotlin/xyz/naomieow/asbestos/item/ScraperItemMaterial.kt
··· 1 - package xyz.naomieow.asbestos.item 2 - 3 - import net.minecraft.world.item.Items 4 - import net.minecraft.world.item.Tier 5 - import net.minecraft.world.item.crafting.Ingredient 6 - 7 - class ScraperItemMaterial: Tier { 8 - override fun getUses(): Int { 9 - return 300 10 - } 11 - 12 - override fun getSpeed(): Float { 13 - return 5.0f 14 - } 15 - 16 - override fun getAttackDamageBonus(): Float { 17 - return 2.5f 18 - } 19 - 20 - override fun getLevel(): Int { 21 - return 1 22 - } 23 - 24 - override fun getEnchantmentValue(): Int { 25 - return 10 26 - } 27 - 28 - override fun getRepairIngredient(): Ingredient { 29 - return Ingredient.of(Items.IRON_INGOT) 30 - } 31 - 32 - companion object { 33 - val INSTANCE: ScraperItemMaterial = ScraperItemMaterial() 34 - } 35 - }
-8
src/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesoComponent.kt
··· 1 - package xyz.naomieow.asbestos.mesothelioma 2 - 3 - import dev.onyxstudios.cca.api.v3.component.ComponentV3 4 - 5 - interface IMesoComponent: ComponentV3 { 6 - fun getMeso(): Int 7 - fun setMeso(exposure: Int) 8 - }
-35
src/main/kotlin/xyz/naomieow/asbestos/mesothelioma/MesoStatusEffect.kt
··· 1 - package xyz.naomieow.asbestos.mesothelioma 2 - 3 - import net.minecraft.world.effect.MobEffect 4 - import net.minecraft.world.effect.MobEffectCategory 5 - import net.minecraft.world.effect.MobEffectInstance 6 - import net.minecraft.world.effect.MobEffects 7 - import net.minecraft.world.entity.LivingEntity 8 - import net.minecraft.world.entity.player.Player 9 - import xyz.naomieow.asbestos.AsbestosMod 10 - import xyz.naomieow.asbestos.config.AsbestosConfig 11 - import xyz.naomieow.asbestos.damage.ModDamageTypes 12 - 13 - class MesoStatusEffect: MobEffect( 14 - MobEffectCategory.HARMFUL, 15 - 0x302412, 16 - ) { 17 - 18 - override fun isDurationEffectTick(duration: Int, amplifier: Int): Boolean { 19 - return true 20 - } 21 - 22 - override fun applyEffectTick(entity: LivingEntity, amplifier: Int) { 23 - super.applyEffectTick(entity, amplifier) 24 - if (entity is Player) { 25 - val exposure: Int = AsbestosMod.MESOTHELIOMA.get(entity).getMeso() 26 - if (exposure >= (AsbestosConfig.threshold / 1.5f)) { 27 - entity.addEffect(MobEffectInstance(MobEffects.MOVEMENT_SLOWDOWN, -1, 1)) 28 - } 29 - 30 - if (exposure >= AsbestosConfig.threshold) { 31 - entity.hurt(ModDamageTypes.of(entity.level(), ModDamageTypes.MESOTHELIOMA), (1 shl amplifier).toFloat()) 32 - } 33 - } 34 - } 35 - }
-29
src/main/kotlin/xyz/naomieow/asbestos/mesothelioma/PlayerMesoComponent.kt
··· 1 - package xyz.naomieow.asbestos.mesothelioma 2 - 3 - import dev.onyxstudios.cca.api.v3.component.sync.AutoSyncedComponent 4 - import net.minecraft.nbt.CompoundTag 5 - import net.minecraft.world.entity.player.Player 6 - import xyz.naomieow.asbestos.AsbestosMod 7 - 8 - class PlayerMesoComponent( 9 - var playerEntity: Player 10 - ): IMesoComponent, AutoSyncedComponent { 11 - private var mesothelioma: Int = 0 12 - 13 - override fun readFromNbt(tag: CompoundTag) { 14 - setMeso(tag.getInt("mesothelioma")) 15 - } 16 - 17 - override fun writeToNbt(tag: CompoundTag) { 18 - tag.putInt("mesothelioma", getMeso()) 19 - } 20 - 21 - override fun getMeso(): Int { 22 - return mesothelioma 23 - } 24 - 25 - override fun setMeso(exposure: Int) { 26 - mesothelioma = exposure 27 - AsbestosMod.MESOTHELIOMA.sync(playerEntity) 28 - } 29 - }
-96
src/main/kotlin/xyz/naomieow/asbestos/screen/CancerMeterScreen.kt
··· 1 - package xyz.naomieow.asbestos.screen 2 - 3 - import net.fabricmc.api.EnvType 4 - import net.fabricmc.api.Environment 5 - import net.minecraft.client.gui.GuiGraphics 6 - import net.minecraft.client.gui.screens.inventory.AbstractContainerScreen 7 - import net.minecraft.network.chat.Component 8 - import net.minecraft.resources.ResourceLocation 9 - import net.minecraft.world.entity.player.Inventory 10 - import xyz.naomieow.asbestos.id 11 - import xyz.naomieow.asbestos.config.AsbestosConfig 12 - import xyz.naomieow.asbestos.screen.util.MouseUtil 13 - import java.util.Optional 14 - 15 - @Environment(EnvType.CLIENT) 16 - class CancerMeterScreen( 17 - abstractContainerMenu: CancerMeterScreenHandler, 18 - inventory: Inventory, 19 - component: Component, 20 - ): AbstractContainerScreen<CancerMeterScreenHandler>( 21 - abstractContainerMenu, 22 - inventory, 23 - component 24 - ) { 25 - private val TEXTURE: ResourceLocation = id("textures/gui/cancer_meter.png") 26 - var screenHandler = abstractContainerMenu; 27 - 28 - override fun render(context: GuiGraphics, mouseX: Int, mouseY: Int, delta: Float) { 29 - renderBackground(context) 30 - super.render(context, mouseX, mouseY, delta) 31 - renderTooltip(context, mouseX, mouseY) 32 - } 33 - 34 - override fun renderBg(context: GuiGraphics, delta: Float, mouseX: Int, mouseY: Int) { 35 - val x = (width - imageWidth) / 2 36 - val y = (height - imageHeight) / 2 37 - context.blit( 38 - TEXTURE, 39 - x, y, 40 - 0, 0, 41 - imageWidth, 42 - imageHeight 43 - ) 44 - drawCancerProgress(context, x + 109, y + 56) 45 - } 46 - 47 - override fun renderLabels(context: GuiGraphics, mouseX: Int, mouseY: Int) { 48 - val x = (width - imageWidth) / 2 49 - val y = (height - imageHeight) / 2 50 - 51 - if (isMouseAboveArea(mouseX, mouseY, x, y, 108, 55, 58, 7)) { 52 - context.renderTooltip( 53 - font, 54 - listOf( 55 - Component.literal( 56 - screenHandler.getCancerMeter().toString() + "/" + AsbestosConfig.threshold 57 - ) 58 - ), 59 - Optional.empty(), 60 - mouseX - x, 61 - mouseY - y 62 - ) 63 - } 64 - context.drawString( 65 - this.font, 66 - this.playerInventoryTitle, 67 - this.inventoryLabelX, 68 - this.inventoryLabelY + 2, 69 - 4210752, 70 - false 71 - ) 72 - } 73 - 74 - private fun drawCancerProgress(context: GuiGraphics, x: Int, y: Int) { 75 - val offset = screenHandler.getCancerMeter() * 58 / AsbestosConfig.threshold 76 - context.blit( 77 - TEXTURE, 78 - x, y, 79 - 176, 56, 80 - offset, 7 81 - ) 82 - } 83 - 84 - private fun isMouseAboveArea( 85 - mouseX: Int, mouseY: Int, 86 - x: Int, y: Int, 87 - offsetX: Int, offsetY: Int, 88 - width: Int, height: Int 89 - ): Boolean { 90 - return MouseUtil.isMouseOver( 91 - mouseX.toDouble(), mouseY.toDouble(), 92 - x + offsetX, y + offsetY, 93 - width, height 94 - ) 95 - } 96 - }
-144
src/main/kotlin/xyz/naomieow/asbestos/screen/CancerMeterScreenHandler.kt
··· 1 - package xyz.naomieow.asbestos.screen 2 - 3 - import net.minecraft.network.FriendlyByteBuf 4 - import net.minecraft.world.entity.EquipmentSlot 5 - import net.minecraft.world.entity.player.Inventory 6 - import net.minecraft.world.entity.player.Player 7 - import net.minecraft.world.inventory.AbstractContainerMenu 8 - import net.minecraft.world.inventory.MenuType 9 - import net.minecraft.world.inventory.Slot 10 - import net.minecraft.world.item.ItemStack 11 - import xyz.naomieow.asbestos.inventory.CancerMeterInventory 12 - import xyz.naomieow.asbestos.inventory.ICancerMeterInventory 13 - import xyz.naomieow.asbestos.item.CancerMeterItem 14 - import xyz.naomieow.asbestos.item.ModItems 15 - import java.util.* 16 - 17 - class CancerMeterScreenHandler( 18 - type: MenuType<*>, 19 - syncId: Int, 20 - var playerInventory: Inventory, 21 - var inventory: ICancerMeterInventory, 22 - ): AbstractContainerMenu(type, syncId) { 23 - constructor( 24 - syncId: Int, 25 - playerInventory: Inventory, 26 - buf: FriendlyByteBuf 27 - ): this(syncId, playerInventory, createInventory(playerInventory, buf)) 28 - 29 - constructor( 30 - syncId: Int, 31 - playerInventory: Inventory, 32 - inventory: ICancerMeterInventory, 33 - ): this(ModMenuTypes.CancerMeter, syncId, playerInventory, inventory) 34 - 35 - init { 36 - addSlot(object : Slot(inventory.getInventory(), 0, 80, 54) { 37 - override fun mayPlace(stack: ItemStack): Boolean { 38 - return stack.`is`(ModItems.FilledSyringe) 39 - } 40 - }) 41 - 42 - addPlayerInventory(playerInventory) 43 - addPlayerHotbar(playerInventory) 44 - } 45 - 46 - override fun quickMoveStack(player: Player, slotIndex: Int): ItemStack { 47 - var itemStack = ItemStack.EMPTY 48 - val slot = this.slots[slotIndex] 49 - if (slot.hasItem()) { 50 - val stackInSlot = slot.item 51 - itemStack = stackInSlot.copy() 52 - if (slotIndex == 0) { 53 - if (!this.moveItemStackTo(stackInSlot, INVENTORY_START, HOTBAR_END, true)) { 54 - return ItemStack.EMPTY 55 - } 56 - slot.onQuickCraft(stackInSlot, itemStack) 57 - } else if (itemStack.`is`(ModItems.FilledSyringe)) { 58 - if (!this.moveItemStackTo(stackInSlot, 0, 1, false)) { 59 - return ItemStack.EMPTY 60 - } 61 - } else if (slotIndex >= INVENTORY_START && slotIndex < INVENTORY_END) { 62 - if (!this.moveItemStackTo(stackInSlot, HOTBAR_START, HOTBAR_END, false)) { 63 - return ItemStack.EMPTY 64 - } 65 - } else if (slotIndex >= HOTBAR_START && slotIndex < HOTBAR_END) { 66 - if (!this.moveItemStackTo(stackInSlot, INVENTORY_START, INVENTORY_END, false)) { 67 - return ItemStack.EMPTY 68 - } 69 - } else { 70 - if (!this.moveItemStackTo(stackInSlot, INVENTORY_START, HOTBAR_END, false)) { 71 - return ItemStack.EMPTY 72 - } 73 - } 74 - 75 - if (stackInSlot.isEmpty) { 76 - slot.setByPlayer(ItemStack.EMPTY) 77 - } else { 78 - slot.setChanged() 79 - } 80 - 81 - if (stackInSlot.count == itemStack.count) { 82 - return ItemStack.EMPTY 83 - } 84 - 85 - slot.onTake(player, stackInSlot) 86 - 87 - if (slotIndex == 0) { 88 - player.drop(stackInSlot, false) 89 - } 90 - } 91 - return itemStack 92 - } 93 - 94 - override fun stillValid(player: Player): Boolean { 95 - return true 96 - } 97 - 98 - private fun addPlayerInventory(inventory: Inventory) { 99 - for (row in 0..2) { 100 - for (column in 0..8) { 101 - this.addSlot(Slot(inventory, column + row * 9 + 9, 8 + column * 18, 84 + row * 18)) 102 - } 103 - } 104 - } 105 - 106 - private fun addPlayerHotbar(inventory: Inventory) { 107 - for (slot in 0..8) { 108 - this.addSlot(Slot(inventory, slot, 8 + slot * 18, 142)) 109 - } 110 - } 111 - 112 - fun getCancerMeter(): Int { 113 - val nbt = this.inventory.getInventory().getItem(0).getOrCreateTag() 114 - return if (nbt.contains("CancerMeter")) nbt.getInt("CancerMeter") else 0 115 - } 116 - 117 - companion object { 118 - private const val INVENTORY_START: Int = 1 119 - private const val INVENTORY_END: Int = 28 120 - private const val HOTBAR_START: Int = 28 121 - private const val HOTBAR_END: Int = 37 122 - 123 - private fun createInventory(playerInventory: Inventory?, buf: FriendlyByteBuf?): CancerMeterInventory { 124 - Objects.requireNonNull<Inventory?>(playerInventory) 125 - Objects.requireNonNull<FriendlyByteBuf?>(buf) 126 - 127 - val stack: ItemStack 128 - val screenID = buf!!.readByte() 129 - 130 - if (screenID.toInt() == 1) { 131 - stack = playerInventory!!.player.getItemBySlot(EquipmentSlot.MAINHAND) 132 - } else { 133 - stack = ItemStack.EMPTY 134 - } 135 - 136 - if (stack.item is CancerMeterItem) { 137 - if (screenID.toInt() == 1) { 138 - return CancerMeterInventory(stack, playerInventory!!.player, screenID) 139 - } 140 - } 141 - throw IllegalStateException("Incorrect ItemStack $stack") 142 - } 143 - } 144 - }
-22
src/main/kotlin/xyz/naomieow/asbestos/screen/ModMenuTypes.kt
··· 1 - package xyz.naomieow.asbestos.screen 2 - 3 - import net.fabricmc.fabric.api.screenhandler.v1.ExtendedScreenHandlerType 4 - import net.minecraft.core.Registry 5 - import net.minecraft.core.registries.BuiltInRegistries 6 - import net.minecraft.world.inventory.MenuType 7 - import xyz.naomieow.asbestos.id 8 - 9 - object ModMenuTypes 10 - // : Registrar<MenuType<*>> by AsbestosMod..Registries.MENU 11 - { 12 - val CancerMeter: MenuType<CancerMeterScreenHandler> = 13 - ExtendedScreenHandlerType(::CancerMeterScreenHandler) 14 - 15 - fun register() { 16 - Registry.register( 17 - BuiltInRegistries.MENU, 18 - id("cancer_meter"), 19 - CancerMeter 20 - ) 21 - } 22 - }
-18
src/main/kotlin/xyz/naomieow/asbestos/screen/util/MouseUtil.kt
··· 1 - package xyz.naomieow.asbestos.screen.util 2 - 3 - object MouseUtil { 4 - @JvmStatic 5 - fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int): Boolean { 6 - return isMouseOver(mouseX, mouseY, x, y, 16) 7 - } 8 - 9 - @JvmStatic 10 - fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int, size: Int): Boolean { 11 - return isMouseOver(mouseX, mouseY, x, y, size, size) 12 - } 13 - 14 - @JvmStatic 15 - fun isMouseOver(mouseX: Double, mouseY: Double, x: Int, y: Int, sizeX: Int, sizeY: Int): Boolean { 16 - return (mouseX >= x && mouseX <= x + sizeX) && (mouseY >= y && mouseY <= y + sizeY) 17 - } 18 - }
-7
src/main/resources/assets/asbestos/blockstates/asbestos_block.json
··· 1 - { 2 - "variants": { 3 - "": { 4 - "model": "asbestos:block/asbestos_block" 5 - } 6 - } 7 - }
-19
src/main/resources/assets/asbestos/blockstates/asbestos_roof_block.json
··· 1 - { 2 - "variants": { 3 - "facing=north": { 4 - "model": "asbestos:block/asbestos_roof_block" 5 - }, 6 - "facing=east": { 7 - "model": "asbestos:block/asbestos_roof_block", 8 - "y": 90 9 - }, 10 - "facing=south": { 11 - "model": "asbestos:block/asbestos_roof_block", 12 - "y": 180 13 - }, 14 - "facing=west": { 15 - "model": "asbestos:block/asbestos_roof_block", 16 - "y": 270 17 - } 18 - } 19 - }
-7
src/main/resources/assets/asbestos/blockstates/asbestos_tile_block.json
··· 1 - { 2 - "variants": { 3 - "": { 4 - "model": "asbestos:block/asbestos_tile_block" 5 - } 6 - } 7 - }
-7
src/main/resources/assets/asbestos/blockstates/popcorn_ceiling_block.json
··· 1 - { 2 - "variants": { 3 - "": { 4 - "model": "asbestos:block/popcorn_ceiling_block" 5 - } 6 - } 7 - }
-7
src/main/resources/assets/asbestos/blockstates/serpentinite_block.json
··· 1 - { 2 - "variants": { 3 - "": { 4 - "model": "asbestos:block/serpentinite_block" 5 - } 6 - } 7 - }
src/main/resources/assets/asbestos/icon.png

This is a binary file and will not be displayed.

-50
src/main/resources/assets/asbestos/icon.svg
··· 1 - <?xml version="1.0" encoding="UTF-8" standalone="no"?> 2 - <!-- Created with Inkscape (http://www.inkscape.org/) --> 3 - 4 - <svg 5 - width="200mm" 6 - height="200mm" 7 - viewBox="0 0 200 200" 8 - version="1.1" 9 - id="svg1" 10 - inkscape:version="1.3 (0e150ed6c4, 2023-07-21)" 11 - sodipodi:docname="icon.svg" 12 - inkscape:export-filename="icon.png" 13 - inkscape:export-xdpi="96" 14 - inkscape:export-ydpi="96" 15 - xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" 16 - xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" 17 - xmlns="http://www.w3.org/2000/svg" 18 - xmlns:svg="http://www.w3.org/2000/svg"> 19 - <sodipodi:namedview 20 - id="namedview1" 21 - pagecolor="#8b8b8b" 22 - bordercolor="#000000" 23 - borderopacity="0.25" 24 - inkscape:showpageshadow="2" 25 - inkscape:pageopacity="0.0" 26 - inkscape:pagecheckerboard="0" 27 - inkscape:deskcolor="#d1d1d1" 28 - inkscape:document-units="mm" 29 - inkscape:zoom="0.79375" 30 - inkscape:cx="283.46457" 31 - inkscape:cy="362.20472" 32 - inkscape:window-width="1920" 33 - inkscape:window-height="1129" 34 - inkscape:window-x="1912" 35 - inkscape:window-y="-8" 36 - inkscape:window-maximized="1" 37 - inkscape:current-layer="layer1" 38 - inkscape:export-bgcolor="#8b8b8bff" /> 39 - <defs 40 - id="defs1" /> 41 - <g 42 - inkscape:label="Layer 1" 43 - inkscape:groupmode="layer" 44 - id="layer1"> 45 - <path 46 - d="m 151.54918,54.73157 c 0,15.389796 -9.1391,28.942512 -23.02764,36.880045 v 7.486928 c 0,6.135127 -5.14524,11.091747 -11.51381,11.091747 H 82.466288 c -6.368586,0 -11.513819,-4.95662 -11.513819,-11.091747 V 91.611615 C 57.063925,83.639431 47.924844,70.086703 47.924844,54.73157 c 0,-24.505837 23.207526,-44.366987 51.812166,-44.366987 28.60463,0 51.81217,19.86115 51.81217,44.366987 z M 79.58783,71.369188 a 11.513819,11.09175 0 1 0 0,-22.1835 11.513819,11.09175 0 1 0 0,22.1835 z M 131.4,60.277438 a 11.513815,11.091746 0 1 0 -23.02763,0 11.513815,11.091746 0 1 0 23.02763,0 z M 20.363641,105.23367 c 2.842476,-5.476553 9.750764,-7.694897 15.435715,-4.95662 l 63.937654,30.77959 63.93764,-30.77959 c 5.68495,-2.738277 12.59324,-0.519933 15.43571,4.95662 2.84248,5.47654 0.53971,12.13159 -5.14523,14.86986 l -48.46597,23.362 48.50195,23.36199 c 5.68494,2.73826 7.98771,9.39331 5.14524,14.86986 -2.84248,5.47656 -9.75077,7.6949 -15.43572,4.95663 l -63.97362,-30.7796 -63.937654,30.7796 c -5.684951,2.73827 -12.593239,0.51993 -15.435715,-4.95663 -2.842461,-5.47655 -0.539703,-12.1316 5.145234,-14.86986 l 48.46597,-23.36199 -48.46597,-23.362 c -5.684937,-2.73827 -7.987695,-9.39332 -5.145234,-14.86986 z" 47 - id="path1" 48 - style="stroke-width:0.35315;fill:#ffffff;fill-opacity:1" /> 49 - </g> 50 - </svg>
-30
src/main/resources/assets/asbestos/lang/en_us.json
··· 1 - { 2 - "itemGroup.asbestos.asbestos": "Asbestos", 3 - "item.asbestos.asbestos_fibers": "Asbestos Fibers", 4 - "item.asbestos.iron_scraper": "Iron Scraper", 5 - "item.asbestos.ppe_helmet": "PPE Helmet", 6 - "item.asbestos.ppe_chestplate": "PPE Chestplate", 7 - "item.asbestos.ppe_leggings": "PPE Leggings", 8 - "item.asbestos.ppe_boots": "PPE Boots", 9 - "item.asbestos.filled_syringe": "%1$s's Blood", 10 - "item.asbestos.empty_syringe": "Empty Syringe", 11 - "item.asbestos.cancer_meter": "Cancer Meter", 12 - "block.asbestos.asbestos_block": "Asbestos", 13 - "block.asbestos.asbestos_tile_block": "Asbestos Tiling", 14 - "block.asbestos.asbestos_roof_block": "Asbestos Roof", 15 - "block.asbestos.serpentinite_block": "Serpentinite", 16 - "block.asbestos.popcorn_ceiling_block": "Popcorn Ceiling", 17 - "effect.asbestos.mesothelioma": "Mesothelioma", 18 - "effect.asbestos.mesothelioma.description": "A type of cancer that covers the mesothelium of your organs. Caused by exposure to asbestos.", 19 - "death.attack.mesothelioma": "%1$s was entitled to financial compensation", 20 - "death.attack.blood_extract": "%1$s died from exsanguination", 21 - "text.config.asbestos_config.title": "Asbestos Config", 22 - "text.config.asbestos_config.option.offset": "Offset (Blocks)", 23 - "text.config.asbestos_config.option.offset.desc": "The distance, in blocks, that players will gain cancer from Carcinogenic blocks", 24 - "text.config.asbestos_config.option.period": "Period (Seconds)", 25 - "text.config.asbestos_config.option.period.desc": "The time, in seconds, that it takes for a player to gain a \"point\" of cancer.", 26 - "text.config.asbestos_config.option.threshold": "Mesothelioma Threshold", 27 - "text.config.asbestos_config.option.threshold.desc": "The threshold a player has to cross to be inflicted with mesothelioma.", 28 - "text.config.asbestos_config.option.exsanguination": "Syringe Damage", 29 - "text.config.asbestos_config.option.exsanguination.desc": "Damage caused to a player when they extract blood using a syringe." 30 - }
-6
src/main/resources/assets/asbestos/models/block/asbestos_block.json
··· 1 - { 2 - "parent": "block/cube_all", 3 - "textures": { 4 - "all": "asbestos:block/asbestos_block" 5 - } 6 - }
-97
src/main/resources/assets/asbestos/models/block/asbestos_roof_block.json
··· 1 - { 2 - "credit": "Made with Blockbench", 3 - "parent": "block/block", 4 - "textures": { 5 - "0": "asbestos:block/asbestos_roof_top", 6 - "1": "asbestos:block/asbestos_roof_side", 7 - "particle": "asbestos:block/asbestos_roof_top" 8 - }, 9 - "elements": [ 10 - { 11 - "from": [0.001, 0, 1], 12 - "to": [2, 2, 16], 13 - "faces": { 14 - "north": {"uv": [8, 7, 10, 9], "texture": "#1"}, 15 - "east": {"uv": [1, 0, 16, 16], "texture": "#1"}, 16 - "south": {"uv": [14, 7, 16, 9], "texture": "#1", "cullface": "south"}, 17 - "west": {"uv": [0, 0, 15, 16], "rotation": 180, "texture": "#1"}, 18 - "up": {"uv": [0, 0, 15, 16], "rotation": 90, "texture": "#1"}, 19 - "down": {"uv": [1, 0, 16, 16], "rotation": 270, "texture": "#1", "cullface": "down"} 20 - } 21 - }, 22 - { 23 - "from": [14, 0, 1], 24 - "to": [15.999, 2, 16], 25 - "faces": { 26 - "north": {"uv": [9, 7, 11, 9], "texture": "#1"}, 27 - "east": {"uv": [1, 0, 16, 16], "rotation": 180, "texture": "#1"}, 28 - "south": {"uv": [11, 7, 13, 9], "texture": "#1", "cullface": "south"}, 29 - "west": {"uv": [1, 0, 16, 16], "texture": "#1"}, 30 - "up": {"uv": [0, 0, 15, 16], "rotation": 270, "texture": "#1"}, 31 - "down": {"uv": [0, 0, 15, 16], "rotation": 90, "texture": "#1", "cullface": "down"} 32 - } 33 - }, 34 - { 35 - "from": [14, 2, 14], 36 - "to": [15.999, 15, 16], 37 - "faces": { 38 - "north": {"uv": [0, 0, 13, 16], "rotation": 90, "texture": "#1"}, 39 - "east": {"uv": [0, 0, 13, 16], "rotation": 270, "texture": "#1"}, 40 - "south": {"uv": [0, 0, 13, 16], "rotation": 90, "texture": "#1", "cullface": "south"}, 41 - "west": {"uv": [0, 0, 13, 16], "rotation": 270, "texture": "#1"}, 42 - "up": {"uv": [2, 0, 4, 2], "rotation": 270, "texture": "#1"} 43 - } 44 - }, 45 - { 46 - "from": [0.001, 2, 14], 47 - "to": [2, 15, 16], 48 - "rotation": {"angle": 0, "axis": "y", "origin": [1, 8, 15]}, 49 - "faces": { 50 - "north": {"uv": [0, 0, 13, 16], "rotation": 270, "texture": "#1"}, 51 - "east": {"uv": [0, 0, 13, 16], "rotation": 90, "texture": "#1"}, 52 - "south": {"uv": [0, 0, 13, 16], "rotation": 270, "texture": "#1", "cullface": "south"}, 53 - "west": {"uv": [0, 0, 13, 16], "rotation": 90, "texture": "#1"}, 54 - "up": {"uv": [5, 12, 7, 14], "texture": "#1"} 55 - } 56 - }, 57 - { 58 - "from": [2, 0, 14], 59 - "to": [14, 2, 16], 60 - "faces": { 61 - "north": {"uv": [0, 0, 12, 16], "texture": "#1"}, 62 - "south": {"uv": [0, 0, 12, 16], "rotation": 180, "texture": "#1", "cullface": "south"}, 63 - "up": {"uv": [0, 0, 12, 16], "texture": "#1"}, 64 - "down": {"uv": [0, 0, 12, 16], "texture": "#1", "cullface": "down"} 65 - } 66 - }, 67 - { 68 - "from": [2.001, 13, 14], 69 - "to": [14, 15, 16], 70 - "faces": { 71 - "north": {"uv": [0, 0, 12, 16], "texture": "#1"}, 72 - "south": {"uv": [0, 0, 12, 16], "rotation": 180, "texture": "#1", "cullface": "south"}, 73 - "up": {"uv": [0, 0, 12, 16], "texture": "#1"}, 74 - "down": {"uv": [0, 0, 12, 16], "texture": "#1"} 75 - } 76 - }, 77 - { 78 - "from": [0, 0.70711, -0.70711], 79 - "to": [16, 23.35711, 0.29289], 80 - "rotation": {"angle": 45, "axis": "x", "origin": [0, 0.70711, -0.70711]}, 81 - "faces": { 82 - "north": {"uv": [0, 0, 16, 16], "texture": "#0"}, 83 - "east": {"uv": [0, 0, 1, 16], "texture": "#0", "cullface": "east"}, 84 - "south": {"uv": [0, 0, 16, 16], "texture": "#0"}, 85 - "west": {"uv": [7, 0, 8, 16], "texture": "#0", "cullface": "west"}, 86 - "up": {"uv": [0, 8, 16, 8], "rotation": 180, "texture": "#0", "cullface": "up"}, 87 - "down": {"uv": [0, 8, 16, 8], "rotation": 180, "texture": "#0", "cullface": "north"} 88 - } 89 - } 90 - ], 91 - "display": { 92 - "fixed": { 93 - "rotation": [0, 90, 0], 94 - "scale": [0.5, 0.5, 0.5] 95 - } 96 - } 97 - }
-6
src/main/resources/assets/asbestos/models/block/asbestos_tile_block.json
··· 1 - { 2 - "parent": "block/cube_all", 3 - "textures": { 4 - "all": "asbestos:block/asbestos_tiles" 5 - } 6 - }
-8
src/main/resources/assets/asbestos/models/block/popcorn_ceiling_block.json
··· 1 - { 2 - "parent": "block/cube_bottom_top", 3 - "textures": { 4 - "top": "asbestos:block/popcorn_top", 5 - "bottom": "asbestos:block/popcorn_bottom", 6 - "side": "asbestos:block/popcorn_side" 7 - } 8 - }
-6
src/main/resources/assets/asbestos/models/block/serpentinite_block.json
··· 1 - { 2 - "parent": "block/cube_all", 3 - "textures": { 4 - "all": "asbestos:block/serpentinite_block" 5 - } 6 - }
-3
src/main/resources/assets/asbestos/models/item/asbestos_block.json
··· 1 - { 2 - "parent": "asbestos:block/asbestos_block" 3 - }
-6
src/main/resources/assets/asbestos/models/item/asbestos_fibers.json
··· 1 - { 2 - "parent": "minecraft:item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/asbestos_fibers" 5 - } 6 - }
-3
src/main/resources/assets/asbestos/models/item/asbestos_roof_block.json
··· 1 - { 2 - "parent": "asbestos:block/asbestos_roof_block" 3 - }
-3
src/main/resources/assets/asbestos/models/item/asbestos_tile_block.json
··· 1 - { 2 - "parent": "asbestos:block/asbestos_tile_block" 3 - }
-6
src/main/resources/assets/asbestos/models/item/cancer_meter.json
··· 1 - { 2 - "parent": "minecraft:item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/cancer_meter" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/empty_syringe.json
··· 1 - { 2 - "parent": "minecraft:item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/empty_syringe" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/filled_syringe.json
··· 1 - { 2 - "parent": "minecraft:item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/filled_syringe" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/iron_scraper.json
··· 1 - { 2 - "parent": "minecraft:item/handheld", 3 - "textures": { 4 - "layer0": "asbestos:item/iron_scraper" 5 - } 6 - }
-3
src/main/resources/assets/asbestos/models/item/popcorn_ceiling_block.json
··· 1 - { 2 - "parent": "asbestos:block/popcorn_ceiling_block" 3 - }
-6
src/main/resources/assets/asbestos/models/item/ppe_boots.json
··· 1 - { 2 - "parent": "item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/ppe_boots" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/ppe_chestplate.json
··· 1 - { 2 - "parent": "item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/ppe_chestplate" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/ppe_helmet.json
··· 1 - { 2 - "parent": "item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/ppe_helmet" 5 - } 6 - }
-6
src/main/resources/assets/asbestos/models/item/ppe_leggings.json
··· 1 - { 2 - "parent": "item/generated", 3 - "textures": { 4 - "layer0": "asbestos:item/ppe_leggings" 5 - } 6 - }
-3
src/main/resources/assets/asbestos/models/item/serpentinite_block.json
··· 1 - { 2 - "parent": "asbestos:block/serpentinite_block" 3 - }
src/main/resources/assets/asbestos/textures/block/asbestos_block.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/asbestos_roof_side.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/asbestos_roof_top.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/asbestos_tiles.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/popcorn_bottom.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/popcorn_side.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/popcorn_top.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/block/serpentinite_block.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/gui/cancer_meter.ase

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/gui/cancer_meter.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/asbestos_fibers.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/cancer_meter.aseprite

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/cancer_meter.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/empty_syringe.aseprite

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/empty_syringe.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/filled_syringe.aseprite

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/filled_syringe.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/iron_scraper.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/ppe_boots.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/ppe_chestplate.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/ppe_helmet.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/item/ppe_leggings.png

This is a binary file and will not be displayed.

src/main/resources/assets/asbestos/textures/mob_effect/mesothelioma.png

This is a binary file and will not be displayed.

src/main/resources/assets/minecraft/textures/models/armor/asbestos_protective_layer_1.png

This is a binary file and will not be displayed.

src/main/resources/assets/minecraft/textures/models/armor/asbestos_protective_layer_2.png

This is a binary file and will not be displayed.

-5
src/main/resources/data/asbestos/damage_type/blood_extract.json
··· 1 - { 2 - "message_id": "blood_extract", 3 - "exhaustion": 0.1, 4 - "scaling": "when_caused_by_living_non_player" 5 - }
-5
src/main/resources/data/asbestos/damage_type/mesothelioma.json
··· 1 - { 2 - "message_id": "mesothelioma", 3 - "exhaustion": 0.1, 4 - "scaling": "when_caused_by_living_non_player" 5 - }
-34
src/main/resources/data/asbestos/loot_tables/blocks/asbestos_block.json
··· 1 - { 2 - "type": "minecraft:block", 3 - "pools": [ 4 - { 5 - "rolls": 1, 6 - "entries": [ 7 - { 8 - "type": "minecraft:item", 9 - "name": "asbestos:asbestos_block", 10 - "weight": 10 11 - }, 12 - { 13 - "type": "minecraft:item", 14 - "name": "asbestos:asbestos_fibers", 15 - "weight": 1, 16 - "functions": [ 17 - { 18 - "function": "set_count", 19 - "count": { 20 - "min": 1, 21 - "max": 4 22 - } 23 - } 24 - ] 25 - } 26 - ], 27 - "conditions": [ 28 - { 29 - "condition": "minecraft:survives_explosion" 30 - } 31 - ] 32 - } 33 - ] 34 - }
-19
src/main/resources/data/asbestos/loot_tables/blocks/asbestos_roof_block.json
··· 1 - { 2 - "type": "minecraft:block", 3 - "pools": [ 4 - { 5 - "rolls": 1, 6 - "entries": [ 7 - { 8 - "type": "minecraft:item", 9 - "name": "asbestos:asbestos_roof_block" 10 - } 11 - ], 12 - "conditions": [ 13 - { 14 - "condition": "minecraft:survives_explosion" 15 - } 16 - ] 17 - } 18 - ] 19 - }
-19
src/main/resources/data/asbestos/loot_tables/blocks/asbestos_tile_block.json
··· 1 - { 2 - "type": "minecraft:block", 3 - "pools": [ 4 - { 5 - "rolls": 1, 6 - "entries": [ 7 - { 8 - "type": "minecraft:item", 9 - "name": "asbestos:asbestos_tile_block" 10 - } 11 - ], 12 - "conditions": [ 13 - { 14 - "condition": "minecraft:survives_explosion" 15 - } 16 - ] 17 - } 18 - ] 19 - }
-19
src/main/resources/data/asbestos/loot_tables/blocks/popcorn_ceiling_block.json
··· 1 - { 2 - "type": "minecraft:block", 3 - "pools": [ 4 - { 5 - "rolls": 1, 6 - "entries": [ 7 - { 8 - "type": "minecraft:item", 9 - "name": "asbestos:popcorn_ceiling_block" 10 - } 11 - ], 12 - "conditions": [ 13 - { 14 - "condition": "minecraft:survives_explosion" 15 - } 16 - ] 17 - } 18 - ] 19 - }
-29
src/main/resources/data/asbestos/loot_tables/blocks/serpentinite_block.json
··· 1 - { 2 - "type": "minecraft:block", 3 - "pools": [ 4 - { 5 - "rolls": 1, 6 - "entries": [ 7 - { 8 - "type": "minecraft:item", 9 - "name": "asbestos:asbestos_fibers", 10 - "weight": 1, 11 - "functions": [ 12 - { 13 - "function": "set_count", 14 - "count": { 15 - "min": 2, 16 - "max": 6 17 - } 18 - } 19 - ] 20 - } 21 - ], 22 - "conditions": [ 23 - { 24 - "condition": "minecraft:survives_explosion" 25 - } 26 - ] 27 - } 28 - ] 29 - }
-15
src/main/resources/data/asbestos/recipes/asbestos_block.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "AA", 5 - "AA" 6 - ], 7 - "key": { 8 - "A": { 9 - "item": "asbestos:asbestos_fibers" 10 - } 11 - }, 12 - "result": { 13 - "item": "asbestos:asbestos_block" 14 - } 15 - }
-23
src/main/resources/data/asbestos/recipes/asbestos_roof_block.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "WA ", 5 - "WBA", 6 - "WWW" 7 - ], 8 - "key": { 9 - "A": { 10 - "item": "asbestos:asbestos_fibers" 11 - }, 12 - "B": { 13 - "item": "minecraft:stone_bricks" 14 - }, 15 - "W": { 16 - "tag": "minecraft:planks" 17 - } 18 - }, 19 - "result": { 20 - "item": "asbestos:asbestos_roof_block", 21 - "count": 4 22 - } 23 - }
-19
src/main/resources/data/asbestos/recipes/asbestos_tile_block.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "AB", 5 - "BA" 6 - ], 7 - "key": { 8 - "A": { 9 - "item": "asbestos:asbestos_fibers" 10 - }, 11 - "B": { 12 - "item": "minecraft:polished_andesite" 13 - } 14 - }, 15 - "result": { 16 - "item": "asbestos:asbestos_tile_block", 17 - "count": 4 18 - } 19 - }
-19
src/main/resources/data/asbestos/recipes/cancer_meter.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - " X ", 5 - "XSX", 6 - " X " 7 - ], 8 - "key": { 9 - "X": { 10 - "item": "minecraft:iron_ingot" 11 - }, 12 - "S": { 13 - "item": "asbestos:asbestos_fibers" 14 - } 15 - }, 16 - "result": { 17 - "item": "asbestos:cancer_meter" 18 - } 19 - }
-22
src/main/resources/data/asbestos/recipes/empty_syringe.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - " I", 5 - " B ", 6 - "N " 7 - ], 8 - "key": { 9 - "I": { 10 - "item": "minecraft:iron_ingot" 11 - }, 12 - "B": { 13 - "item": "minecraft:glass_bottle" 14 - }, 15 - "N": { 16 - "item": "minecraft:iron_nugget" 17 - } 18 - }, 19 - "result": { 20 - "item": "asbestos:empty_syringe" 21 - } 22 - }
-22
src/main/resources/data/asbestos/recipes/iron_scraper.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - " NI", 5 - " IN", 6 - "S " 7 - ], 8 - "key": { 9 - "N": { 10 - "item": "minecraft:iron_nugget" 11 - }, 12 - "I": { 13 - "item": "minecraft:iron_ingot" 14 - }, 15 - "S": { 16 - "item": "minecraft:stick" 17 - } 18 - }, 19 - "result": { 20 - "item": "asbestos:iron_scraper" 21 - } 22 - }
-22
src/main/resources/data/asbestos/recipes/popcorn_ceiling_block.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "PP", 5 - "AD" 6 - ], 7 - "key": { 8 - "P": { 9 - "tag": "minecraft:planks" 10 - }, 11 - "A": { 12 - "item": "asbestos:asbestos_block" 13 - }, 14 - "D": { 15 - "item": "minecraft:white_dye" 16 - } 17 - }, 18 - "result": { 19 - "item": "asbestos:popcorn_ceiling_block", 20 - "count": 4 21 - } 22 - }
-16
src/main/resources/data/asbestos/recipes/ppe_boots.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - " ", 5 - "S S", 6 - "S S" 7 - ], 8 - "key": { 9 - "S": { 10 - "item": "minecraft:string" 11 - } 12 - }, 13 - "result": { 14 - "item": "asbestos:ppe_boots" 15 - } 16 - }
-16
src/main/resources/data/asbestos/recipes/ppe_chestplate.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "S S", 5 - "SSS", 6 - "SSS" 7 - ], 8 - "key": { 9 - "S": { 10 - "item": "minecraft:string" 11 - } 12 - }, 13 - "result": { 14 - "item": "asbestos:ppe_chestplate" 15 - } 16 - }
-19
src/main/resources/data/asbestos/recipes/ppe_helmet.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "SSS", 5 - "SGS", 6 - "S S" 7 - ], 8 - "key": { 9 - "S": { 10 - "item": "minecraft:string" 11 - }, 12 - "G": { 13 - "item": "minecraft:black_stained_glass_pane" 14 - } 15 - }, 16 - "result": { 17 - "item": "asbestos:ppe_helmet" 18 - } 19 - }
-16
src/main/resources/data/asbestos/recipes/ppe_leggings.json
··· 1 - { 2 - "type": "minecraft:crafting_shaped", 3 - "pattern": [ 4 - "SSS", 5 - "S S", 6 - "S S" 7 - ], 8 - "key": { 9 - "S": { 10 - "item": "minecraft:string" 11 - } 12 - }, 13 - "result": { 14 - "item": "asbestos:ppe_leggings" 15 - } 16 - }
-8
src/main/resources/data/asbestos/tags/blocks/scrapable.json
··· 1 - { 2 - "replace": false, 3 - "values": [ 4 - "asbestos:asbestos_block", 5 - "asbestos:popcorn_ceiling_block", 6 - "asbestos:asbestos_tile_block" 7 - ] 8 - }
-18
src/main/resources/data/asbestos/worldgen/configured_feature/serpentinite_overworld.json
··· 1 - { 2 - "type": "minecraft:ore", 3 - "config": { 4 - "size": 5, 5 - "discard_chance_on_air_exposure": 0, 6 - "targets": [ 7 - { 8 - "target": { 9 - "predicate_type": "minecraft:tag_match", 10 - "tag": "minecraft:deepslate_ore_replaceables" 11 - }, 12 - "state": { 13 - "Name": "asbestos:serpentinite_block" 14 - } 15 - } 16 - ] 17 - } 18 - }
-24
src/main/resources/data/asbestos/worldgen/placed_feature/serpentinite.json
··· 1 - { 2 - "feature": "asbestos:serpentinite_overworld", 3 - "placement": [ 4 - { 5 - "type": "minecraft:count", 6 - "count": 20 7 - }, 8 - { 9 - "type": "minecraft:in_square" 10 - }, 11 - { 12 - "type": "minecraft:height_range", 13 - "height": { 14 - "type": "minecraft:uniform", 15 - "min_inclusive": { 16 - "above_bottom": 0 17 - }, 18 - "max_inclusive": { 19 - "absolute": 0 20 - } 21 - } 22 - } 23 - ] 24 - }
-6
src/main/resources/data/minecraft/tags/blocks/mineable/axe.json
··· 1 - { 2 - "replace": false, 3 - "values": [ 4 - "asbestos:popcorn_ceiling_block" 5 - ] 6 - }
-7
src/main/resources/data/minecraft/tags/blocks/mineable/pickaxe.json
··· 1 - { 2 - "replace": false, 3 - "values": [ 4 - "asbestos:serpentinite_block", 5 - "asbestos:asbestos_roof_block" 6 - ] 7 - }
-6
src/main/resources/data/minecraft/tags/damage_type/bypasses_cooldown.json
··· 1 - { 2 - "replace": false, 3 - "values": [ 4 - "asbestos:blood_extract" 5 - ] 6 - }