diff --git a/build.gradle.kts b/build.gradle.kts index 74c43863e..d831e2766 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -47,6 +47,7 @@ val jeiVersion = project.property("jei.version").toString() val badpacketsVersion = project.property("badpackets.version").toString() val wthitVersion = project.property("wthit.version").toString() val architecturyVersion = project.property("architectury.version").toString() +val appleskinVersion = project.property("appleskin.version").toString() val objVersion = project.property("obj.version").toString() plugins { @@ -191,6 +192,11 @@ repositories { includeGroup("mezz.jei") } } + maven("https://maven.ryanliptak.com/") { + content { + includeGroup("squeek.appleskin") + } + } } configurations { @@ -230,6 +236,7 @@ dependencies { "compat"("me.shedaniel.cloth:cloth-config-fabric:$clothConfigVersion") "compat"("mcp.mobius.waila:wthit:fabric-$wthitVersion") "compat"("dev.architectury:architectury-fabric:$architecturyVersion") // required for REI fluid support + "compat"("squeek.appleskin:appleskin-fabric:$appleskinVersion") multicompat(group = "me.shedaniel", api = "RoughlyEnoughItems-api-fabric", diff --git a/gradle.properties b/gradle.properties index c9b2bb6fc..7449f8f45 100644 --- a/gradle.properties +++ b/gradle.properties @@ -23,3 +23,4 @@ badpackets.version=0.6.1 wthit.version=10.4.0 obj.version=0.4.0 architectury.version=11.1.17 +appleskin.version=mc1.20.3-2.5.1 \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/blockstates/air_lock_seal.json b/src/main/generated/assets/galacticraft/blockstates/air_lock_seal.json index e710442b0..c83bb5b7b 100644 --- a/src/main/generated/assets/galacticraft/blockstates/air_lock_seal.json +++ b/src/main/generated/assets/galacticraft/blockstates/air_lock_seal.json @@ -1,7 +1,10 @@ { "variants": { - "": { - "model": "galacticraft:block/air_lock_seal" - } + "facing=north": { "model": "galacticraft:block/air_lock_seal", "y": 90, "uvlock": true }, + "facing=east": { "model": "galacticraft:block/air_lock_seal", "uvlock": true }, + "facing=south": { "model": "galacticraft:block/air_lock_seal", "y": 90, "uvlock": true }, + "facing=west": { "model": "galacticraft:block/air_lock_seal", "uvlock": true }, + "facing=up": { "model": "galacticraft:block/air_lock_seal", "x": 90, "uvlock": true }, + "facing=down": { "model": "galacticraft:block/air_lock_seal", "x": 90, "uvlock": true } } } \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/blockstates/mars_copper_ore.json b/src/main/generated/assets/galacticraft/blockstates/mars_copper_ore.json new file mode 100644 index 000000000..c416a59f6 --- /dev/null +++ b/src/main/generated/assets/galacticraft/blockstates/mars_copper_ore.json @@ -0,0 +1,7 @@ +{ + "variants": { + "": { + "model": "galacticraft:block/mars_copper_ore" + } + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/blockstates/mars_iron_ore.json b/src/main/generated/assets/galacticraft/blockstates/mars_iron_ore.json new file mode 100644 index 000000000..b3bf4bdb2 --- /dev/null +++ b/src/main/generated/assets/galacticraft/blockstates/mars_iron_ore.json @@ -0,0 +1,7 @@ +{ + "variants": { + "": { + "model": "galacticraft:block/mars_iron_ore" + } + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/blockstates/mars_tin_ore.json b/src/main/generated/assets/galacticraft/blockstates/mars_tin_ore.json new file mode 100644 index 000000000..ed3e42255 --- /dev/null +++ b/src/main/generated/assets/galacticraft/blockstates/mars_tin_ore.json @@ -0,0 +1,7 @@ +{ + "variants": { + "": { + "model": "galacticraft:block/mars_tin_ore" + } + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/lang/en_us.json b/src/main/generated/assets/galacticraft/lang/en_us.json index 636dd08f9..9cdb97afa 100644 --- a/src/main/generated/assets/galacticraft/lang/en_us.json +++ b/src/main/generated/assets/galacticraft/lang/en_us.json @@ -18,6 +18,9 @@ "block.galacticraft.aluminum_decoration_stairs": "Aluminum Decoration Stairs", "block.galacticraft.aluminum_decoration_wall": "Aluminum Decoration Wall", "block.galacticraft.aluminum_ore": "Aluminum Ore", + "block.galacticraft.mars_iron_ore": "Mars Iron Ore", + "block.galacticraft.mars_copper_ore": "Mars Copper Ore", + "block.galacticraft.mars_tin_ore": "Mars Tin Ore", "block.galacticraft.aluminum_wire": "Aluminum Wire", "block.galacticraft.asteroid_rock": "Asteroid Rock", "block.galacticraft.asteroid_rock_block_1": "Asteroid Rock", @@ -348,11 +351,6 @@ "item.galacticraft.blue_solar_wafer": "Blue Solar Wafer", "item.galacticraft.brown_parachute": "Brown Parachute", "item.galacticraft.burger_bun": "Burger Bun", - "item.galacticraft.canned_beef": "Canned Beef", - "item.galacticraft.canned_dehydrated_apple": "Canned Dehydrated Apple", - "item.galacticraft.canned_dehydrated_carrot": "Canned Dehydrated Carrot", - "item.galacticraft.canned_dehydrated_melon": "Canned Dehydrated Melon", - "item.galacticraft.canned_dehydrated_potato": "Canned Dehydrated Potato", "item.galacticraft.canvas": "Canvas", "item.galacticraft.carbon_fragments": "Carbon Fragments", "item.galacticraft.cargo_rocket_schematic": "Cargo Rocket Schematic", @@ -460,6 +458,7 @@ "item.galacticraft.tier_2_rocket_schematic": "Tier 2 Rocket Schematic", "item.galacticraft.tier_3_rocket_schematic": "Tier 3 Rocket Schematic", "item.galacticraft.tin_canister": "Tin Canister", + "item.galacticraft.empty_food_can": "Empty Food Can", "item.galacticraft.tin_ingot": "Tin Ingot", "item.galacticraft.tin_nugget": "Tin Nugget", "item.galacticraft.titanium_axe": "Titanium Axe", @@ -481,8 +480,8 @@ "itemGroup.galacticraft.machines": "Galacticraft Machines", "key.galacticraft.open_celestial_screen": "Open Celestial Map", "key.galacticraft.rocket.inventory": "Open Rocket Inventory", - "planet.galacticraft.asteroids": "Asteroids", - "planet.galacticraft.asteroids.description": "", + "planet.galacticraft.asteroid": "Asteroids", + "planet.galacticraft.asteroid.description": "", "planet.galacticraft.earth": "Earth", "planet.galacticraft.earth.description": "The Overworld", "planet.galacticraft.jupiter": "Jupiter", diff --git a/src/main/generated/assets/galacticraft/models/block/mars_copper_ore.json b/src/main/generated/assets/galacticraft/models/block/mars_copper_ore.json new file mode 100644 index 000000000..226f812c0 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/block/mars_copper_ore.json @@ -0,0 +1,6 @@ +{ + "parent": "minecraft:block/cube_all", + "textures": { + "all": "galacticraft:block/mars_copper_ore" + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/block/mars_iron_ore.json b/src/main/generated/assets/galacticraft/models/block/mars_iron_ore.json new file mode 100644 index 000000000..bc485b0d7 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/block/mars_iron_ore.json @@ -0,0 +1,6 @@ +{ + "parent": "minecraft:block/cube_all", + "textures": { + "all": "galacticraft:block/mars_iron_ore" + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/block/mars_tin_ore.json b/src/main/generated/assets/galacticraft/models/block/mars_tin_ore.json new file mode 100644 index 000000000..4658b67c1 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/block/mars_tin_ore.json @@ -0,0 +1,6 @@ +{ + "parent": "minecraft:block/cube_all", + "textures": { + "all": "galacticraft:block/mars_tin_ore" + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/block/vapor_spout.json b/src/main/generated/assets/galacticraft/models/block/vapor_spout.json index db6739d21..2ee192ca0 100644 --- a/src/main/generated/assets/galacticraft/models/block/vapor_spout.json +++ b/src/main/generated/assets/galacticraft/models/block/vapor_spout.json @@ -2,6 +2,6 @@ "parent": "minecraft:block/cube_top", "textures": { "side": "galacticraft:block/soft_venus_rock", - "top": "galacticraft:block/vapor_spout" + "top": "galacticraft:block/vapor_spout_block_top" } } \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_beef.json b/src/main/generated/assets/galacticraft/models/item/canned_beef.json deleted file mode 100644 index 1adb6b36c..000000000 --- a/src/main/generated/assets/galacticraft/models/item/canned_beef.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "parent": "minecraft:item/generated", - "textures": { - "layer0": "galacticraft:item/canned_beef" - } -} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_apple.json b/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_apple.json deleted file mode 100644 index 4fb438ca7..000000000 --- a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_apple.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "parent": "minecraft:item/generated", - "textures": { - "layer0": "galacticraft:item/canned_dehydrated_apple" - } -} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_carrot.json b/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_carrot.json deleted file mode 100644 index 7313bcbd1..000000000 --- a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_carrot.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "parent": "minecraft:item/generated", - "textures": { - "layer0": "galacticraft:item/canned_dehydrated_carrot" - } -} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_melon.json b/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_melon.json deleted file mode 100644 index 2926a2db4..000000000 --- a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_melon.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "parent": "minecraft:item/generated", - "textures": { - "layer0": "galacticraft:item/canned_dehydrated_melon" - } -} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_potato.json b/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_potato.json deleted file mode 100644 index 3ff71bf5d..000000000 --- a/src/main/generated/assets/galacticraft/models/item/canned_dehydrated_potato.json +++ /dev/null @@ -1,6 +0,0 @@ -{ - "parent": "minecraft:item/generated", - "textures": { - "layer0": "galacticraft:item/canned_dehydrated_potato" - } -} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/canned_food.json b/src/main/generated/assets/galacticraft/models/item/canned_food.json new file mode 100644 index 000000000..a2fc16bd0 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/item/canned_food.json @@ -0,0 +1,7 @@ +{ + "parent": "minecraft:item/generated", + "textures": { + "layer0": "galacticraft:item/canned_food_template", + "layer1": "galacticraft:item/canned_food_label" + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/empty_can.json b/src/main/generated/assets/galacticraft/models/item/empty_can.json new file mode 100644 index 000000000..a2fc16bd0 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/item/empty_can.json @@ -0,0 +1,7 @@ +{ + "parent": "minecraft:item/generated", + "textures": { + "layer0": "galacticraft:item/canned_food_template", + "layer1": "galacticraft:item/canned_food_label" + } +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/mars_copper_ore.json b/src/main/generated/assets/galacticraft/models/item/mars_copper_ore.json new file mode 100644 index 000000000..df33c244f --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/item/mars_copper_ore.json @@ -0,0 +1,3 @@ +{ + "parent": "galacticraft:block/mars_copper_ore" +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/mars_iron_ore.json b/src/main/generated/assets/galacticraft/models/item/mars_iron_ore.json new file mode 100644 index 000000000..cf75d390d --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/item/mars_iron_ore.json @@ -0,0 +1,3 @@ +{ + "parent": "galacticraft:block/mars_iron_ore" +} \ No newline at end of file diff --git a/src/main/generated/assets/galacticraft/models/item/mars_tin_ore.json b/src/main/generated/assets/galacticraft/models/item/mars_tin_ore.json new file mode 100644 index 000000000..8d6ed6830 --- /dev/null +++ b/src/main/generated/assets/galacticraft/models/item/mars_tin_ore.json @@ -0,0 +1,3 @@ +{ + "parent": "galacticraft:block/mars_tin_ore" +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_beef.json b/src/main/generated/data/galacticraft/advancements/recipes/food/canned_beef.json deleted file mode 100644 index 92a9a0977..000000000 --- a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_beef.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_the_recipe": { - "conditions": { - "recipe": "galacticraft:canned_beef" - }, - "trigger": "minecraft:recipe_unlocked" - }, - "has_tin_canister": { - "conditions": { - "items": [ - { - "items": [ - "galacticraft:tin_canister" - ] - } - ] - }, - "trigger": "minecraft:inventory_changed" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_tin_canister" - ] - ], - "rewards": { - "recipes": [ - "galacticraft:canned_beef" - ] - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_apple.json b/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_apple.json deleted file mode 100644 index 1f8deaf63..000000000 --- a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_apple.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_the_recipe": { - "conditions": { - "recipe": "galacticraft:canned_dehydrated_apple" - }, - "trigger": "minecraft:recipe_unlocked" - }, - "has_tin_canister": { - "conditions": { - "items": [ - { - "items": [ - "galacticraft:tin_canister" - ] - } - ] - }, - "trigger": "minecraft:inventory_changed" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_tin_canister" - ] - ], - "rewards": { - "recipes": [ - "galacticraft:canned_dehydrated_apple" - ] - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_carrot.json b/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_carrot.json deleted file mode 100644 index b054d6ee0..000000000 --- a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_carrot.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_the_recipe": { - "conditions": { - "recipe": "galacticraft:canned_dehydrated_carrot" - }, - "trigger": "minecraft:recipe_unlocked" - }, - "has_tin_canister": { - "conditions": { - "items": [ - { - "items": [ - "galacticraft:tin_canister" - ] - } - ] - }, - "trigger": "minecraft:inventory_changed" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_tin_canister" - ] - ], - "rewards": { - "recipes": [ - "galacticraft:canned_dehydrated_carrot" - ] - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_melon.json b/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_melon.json deleted file mode 100644 index bbad9edf3..000000000 --- a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_melon.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_the_recipe": { - "conditions": { - "recipe": "galacticraft:canned_dehydrated_melon" - }, - "trigger": "minecraft:recipe_unlocked" - }, - "has_tin_canister": { - "conditions": { - "items": [ - { - "items": [ - "galacticraft:tin_canister" - ] - } - ] - }, - "trigger": "minecraft:inventory_changed" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_tin_canister" - ] - ], - "rewards": { - "recipes": [ - "galacticraft:canned_dehydrated_melon" - ] - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_potato.json b/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_potato.json deleted file mode 100644 index 7a3117b12..000000000 --- a/src/main/generated/data/galacticraft/advancements/recipes/food/canned_dehydrated_potato.json +++ /dev/null @@ -1,34 +0,0 @@ -{ - "parent": "minecraft:recipes/root", - "criteria": { - "has_the_recipe": { - "conditions": { - "recipe": "galacticraft:canned_dehydrated_potato" - }, - "trigger": "minecraft:recipe_unlocked" - }, - "has_tin_canister": { - "conditions": { - "items": [ - { - "items": [ - "galacticraft:tin_canister" - ] - } - ] - }, - "trigger": "minecraft:inventory_changed" - } - }, - "requirements": [ - [ - "has_the_recipe", - "has_tin_canister" - ] - ], - "rewards": { - "recipes": [ - "galacticraft:canned_dehydrated_potato" - ] - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/celestial_body/asteroid.json b/src/main/generated/data/galacticraft/celestial_body/asteroid.json new file mode 100644 index 000000000..614064d34 --- /dev/null +++ b/src/main/generated/data/galacticraft/celestial_body/asteroid.json @@ -0,0 +1,46 @@ +{ + "type": "galacticraft:planet", + "config": { + "parent": "galacticraft:sol", + "access_weight": 2, + "atmosphere": { + "composition": {}, + "pressure": 0, + "temperature": -1.5 + }, + "celestial_handler": "galacticraft:default", + "day_length": 99999999, + "day_temperature": -1.5, + "description": "planet.galacticraft.asteroid.description", + "display": { + "type": "galacticraft:icon", + "config": { + "height": 16, + "scale": 1.0, + "texture": "galacticraft:textures/gui/celestialbodies/asteroid.png", + "u": 0, + "v": 0, + "width": 16 + } + }, + "galaxy": "galacticraft:milky_way", + "gravity": 0.1, + "name": "planet.galacticraft.asteroid", + "night_temperature": -1.5, + "position": { + "type": "galacticraft:orbital", + "config": { + "distance": 0.75, + "orbit_time": 0.6152793169021606, + "phase_shift": 2.0, + "planet": true + } + }, + "ring": { + "type": "galacticraft:default", + "config": {} + }, + "teleporter": "galacticraft:lander", + "world": "galacticraft:asteroid" + } +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/dimension/asteroid.json b/src/main/generated/data/galacticraft/dimension/asteroid.json new file mode 100644 index 000000000..39778a08e --- /dev/null +++ b/src/main/generated/data/galacticraft/dimension/asteroid.json @@ -0,0 +1,12 @@ +{ + "type": "galacticraft:asteroid", + "generator": { + "type": "galacticraft:asteroid_chunk_generator", + "biomeSource": { + "type": "minecraft:fixed", + "biome": "galacticraft:asteroid_field" + }, + "par2": 1000, + "dimensionKey": "galacticraft:asteroid" + } +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/dimension_type/asteroid.json b/src/main/generated/data/galacticraft/dimension_type/asteroid.json new file mode 100644 index 000000000..c7c23e877 --- /dev/null +++ b/src/main/generated/data/galacticraft/dimension_type/asteroid.json @@ -0,0 +1,25 @@ +{ + "ambient_light": 0.1, + "bed_works": false, + "coordinate_scale": 1.0, + "effects": "galacticraft:asteroid", + "has_ceiling": false, + "has_raids": false, + "has_skylight": true, + "height": 384, + "infiniburn": "#galacticraft:infiniburn_asteroid", + "logical_height": 384, + "min_y": -64, + "monster_spawn_block_light_limit": 0, + "monster_spawn_light_level": { + "type": "minecraft:uniform", + "value": { + "max_inclusive": 7, + "min_inclusive": 0 + } + }, + "natural": false, + "piglin_safe": false, + "respawn_anchor_works": false, + "ultrawarm": false +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/loot_tables/blocks/lunaslate_copper_ore.json b/src/main/generated/data/galacticraft/loot_tables/blocks/lunaslate_copper_ore.json index 077224bed..0d022cc63 100644 --- a/src/main/generated/data/galacticraft/loot_tables/blocks/lunaslate_copper_ore.json +++ b/src/main/generated/data/galacticraft/loot_tables/blocks/lunaslate_copper_ore.json @@ -24,7 +24,7 @@ } } ], - "name": "galacticraft:moon_copper_ore" + "name": "galacticraft:lunaslate_copper_ore" }, { "type": "minecraft:item", diff --git a/src/main/generated/data/galacticraft/loot_tables/blocks/mars_copper_ore.json b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_copper_ore.json new file mode 100644 index 000000000..c997c10b0 --- /dev/null +++ b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_copper_ore.json @@ -0,0 +1,58 @@ +{ + "type": "minecraft:block", + "pools": [ + { + "bonus_rolls": 0.0, + "entries": [ + { + "type": "minecraft:alternatives", + "children": [ + { + "type": "minecraft:item", + "conditions": [ + { + "condition": "minecraft:match_tool", + "predicate": { + "enchantments": [ + { + "enchantment": "minecraft:silk_touch", + "levels": { + "min": 1 + } + } + ] + } + } + ], + "name": "galacticraft:mars_copper_ore" + }, + { + "type": "minecraft:item", + "functions": [ + { + "add": false, + "count": { + "type": "minecraft:uniform", + "max": 5.0, + "min": 2.0 + }, + "function": "minecraft:set_count" + }, + { + "enchantment": "minecraft:fortune", + "formula": "minecraft:ore_drops", + "function": "minecraft:apply_bonus" + }, + { + "function": "minecraft:explosion_decay" + } + ], + "name": "minecraft:raw_copper" + } + ] + } + ], + "rolls": 1.0 + } + ] +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/loot_tables/blocks/mars_iron_ore.json b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_iron_ore.json new file mode 100644 index 000000000..38762f0e2 --- /dev/null +++ b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_iron_ore.json @@ -0,0 +1,49 @@ +{ + "type": "minecraft:block", + "pools": [ + { + "bonus_rolls": 0.0, + "entries": [ + { + "type": "minecraft:alternatives", + "children": [ + { + "type": "minecraft:item", + "conditions": [ + { + "condition": "minecraft:match_tool", + "predicate": { + "enchantments": [ + { + "enchantment": "minecraft:silk_touch", + "levels": { + "min": 1 + } + } + ] + } + } + ], + "name": "minecraft:iron_ore" + }, + { + "type": "minecraft:item", + "functions": [ + { + "enchantment": "minecraft:fortune", + "formula": "minecraft:ore_drops", + "function": "minecraft:apply_bonus" + }, + { + "function": "minecraft:explosion_decay" + } + ], + "name": "minecraft:raw_iron" + } + ] + } + ], + "rolls": 1.0 + } + ] +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/loot_tables/blocks/mars_tin_ore.json b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_tin_ore.json new file mode 100644 index 000000000..fd7ed36c1 --- /dev/null +++ b/src/main/generated/data/galacticraft/loot_tables/blocks/mars_tin_ore.json @@ -0,0 +1,49 @@ +{ + "type": "minecraft:block", + "pools": [ + { + "bonus_rolls": 0.0, + "entries": [ + { + "type": "minecraft:alternatives", + "children": [ + { + "type": "minecraft:item", + "conditions": [ + { + "condition": "minecraft:match_tool", + "predicate": { + "enchantments": [ + { + "enchantment": "minecraft:silk_touch", + "levels": { + "min": 1 + } + } + ] + } + } + ], + "name": "galacticraft:mars_tin_ore" + }, + { + "type": "minecraft:item", + "functions": [ + { + "enchantment": "minecraft:fortune", + "formula": "minecraft:ore_drops", + "function": "minecraft:apply_bonus" + }, + { + "function": "minecraft:explosion_decay" + } + ], + "name": "galacticraft:raw_tin" + } + ] + } + ], + "rolls": 1.0 + } + ] +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/recipes/canned_beef.json b/src/main/generated/data/galacticraft/recipes/canned_beef.json deleted file mode 100644 index 3da5fe375..000000000 --- a/src/main/generated/data/galacticraft/recipes/canned_beef.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "galacticraft:tin_canister" - }, - { - "item": "galacticraft:ground_beef" - }, - { - "item": "galacticraft:ground_beef" - } - ], - "result": { - "item": "galacticraft:canned_beef" - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_apple.json b/src/main/generated/data/galacticraft/recipes/canned_dehydrated_apple.json deleted file mode 100644 index 30db3e903..000000000 --- a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_apple.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "galacticraft:tin_canister" - }, - { - "item": "minecraft:apple" - }, - { - "item": "minecraft:apple" - } - ], - "result": { - "item": "galacticraft:canned_dehydrated_apple" - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_carrot.json b/src/main/generated/data/galacticraft/recipes/canned_dehydrated_carrot.json deleted file mode 100644 index c80bd8ade..000000000 --- a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_carrot.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "galacticraft:tin_canister" - }, - { - "item": "minecraft:carrot" - }, - { - "item": "minecraft:carrot" - } - ], - "result": { - "item": "galacticraft:canned_dehydrated_carrot" - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_melon.json b/src/main/generated/data/galacticraft/recipes/canned_dehydrated_melon.json deleted file mode 100644 index 77043b4c2..000000000 --- a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_melon.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "galacticraft:tin_canister" - }, - { - "item": "minecraft:melon_slice" - }, - { - "item": "minecraft:melon_slice" - } - ], - "result": { - "item": "galacticraft:canned_dehydrated_melon" - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_potato.json b/src/main/generated/data/galacticraft/recipes/canned_dehydrated_potato.json deleted file mode 100644 index 01d0ba042..000000000 --- a/src/main/generated/data/galacticraft/recipes/canned_dehydrated_potato.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "type": "minecraft:crafting_shapeless", - "category": "misc", - "ingredients": [ - { - "item": "galacticraft:tin_canister" - }, - { - "item": "minecraft:potato" - }, - { - "item": "minecraft:potato" - } - ], - "result": { - "item": "galacticraft:canned_dehydrated_potato" - } -} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/tags/dimension_type/space.json b/src/main/generated/data/galacticraft/tags/dimension_type/space.json index 9641dbd16..b2229f1dd 100644 --- a/src/main/generated/data/galacticraft/tags/dimension_type/space.json +++ b/src/main/generated/data/galacticraft/tags/dimension_type/space.json @@ -2,6 +2,7 @@ "replace": false, "values": [ "galacticraft:moon", - "galacticraft:venus" + "galacticraft:venus", + "galacticraft:asteroid" ] } \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/tags/worldgen/biome/asteroid.json b/src/main/generated/data/galacticraft/tags/worldgen/biome/asteroid.json new file mode 100644 index 000000000..66fb4071e --- /dev/null +++ b/src/main/generated/data/galacticraft/tags/worldgen/biome/asteroid.json @@ -0,0 +1,6 @@ +{ + "replace": false, + "values": [ + "galacticraft:asteroid_field" + ] +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/worldgen/biome/asteroid_field.json b/src/main/generated/data/galacticraft/worldgen/biome/asteroid_field.json new file mode 100644 index 000000000..ce8c1488f --- /dev/null +++ b/src/main/generated/data/galacticraft/worldgen/biome/asteroid_field.json @@ -0,0 +1,61 @@ +{ + "carvers": {}, + "downfall": 0.5, + "effects": { + "fog_color": 0, + "mood_sound": { + "block_search_extent": 8, + "offset": 2.0, + "sound": "minecraft:ambient.cave", + "tick_delay": 6000 + }, + "music": { + "max_delay": 24000, + "min_delay": 12000, + "replace_current_music": false, + "sound": "galacticraft:music.music_moon" + }, + "sky_color": 0, + "water_color": 0, + "water_fog_color": 0 + }, + "features": [], + "has_precipitation": true, + "spawn_costs": {}, + "spawners": { + "ambient": [], + "axolotls": [], + "creature": [], + "misc": [], + "monster": [ + { + "type": "galacticraft:evolved_spider", + "maxCount": 4, + "minCount": 4, + "weight": 100 + }, + { + "type": "galacticraft:evolved_zombie", + "maxCount": 4, + "minCount": 4, + "weight": 95 + }, + { + "type": "galacticraft:evolved_skeleton", + "maxCount": 4, + "minCount": 4, + "weight": 100 + }, + { + "type": "galacticraft:evolved_creeper", + "maxCount": 4, + "minCount": 4, + "weight": 100 + } + ], + "underground_water_creature": [], + "water_ambient": [], + "water_creature": [] + }, + "temperature": -2.0 +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/worldgen/custom_terrain/asteroid/AsteroidChunkGenerator b/src/main/generated/data/galacticraft/worldgen/custom_terrain/asteroid/AsteroidChunkGenerator new file mode 100644 index 000000000..e69de29bb diff --git a/src/main/generated/data/galacticraft/worldgen/density_function/asteroid/final_density.json b/src/main/generated/data/galacticraft/worldgen/density_function/asteroid/final_density.json new file mode 100644 index 000000000..feb1cdbd3 --- /dev/null +++ b/src/main/generated/data/galacticraft/worldgen/density_function/asteroid/final_density.json @@ -0,0 +1,18 @@ +{ + "type": "minecraft:add", + "argument1": { + "type": "minecraft:y_clamped_gradient", + "from_value": 1.0, + "from_y": 0, + "to_value": -1.0, + "to_y": 90 + }, + "argument2": { + "type": "minecraft:old_blended_noise", + "smear_scale_multiplier": 8.0, + "xz_factor": 80.0, + "xz_scale": 0.25, + "y_factor": 160.0, + "y_scale": 0.375 + } +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/worldgen/multi_noise_biome_source_parameter_list/asteroid.json b/src/main/generated/data/galacticraft/worldgen/multi_noise_biome_source_parameter_list/asteroid.json new file mode 100644 index 000000000..0d5076475 --- /dev/null +++ b/src/main/generated/data/galacticraft/worldgen/multi_noise_biome_source_parameter_list/asteroid.json @@ -0,0 +1,3 @@ +{ + "preset": "galacticraft:asteroid" +} \ No newline at end of file diff --git a/src/main/generated/data/galacticraft/worldgen/noise_settings/asteroid.json b/src/main/generated/data/galacticraft/worldgen/noise_settings/asteroid.json new file mode 100644 index 000000000..b3eb28f45 --- /dev/null +++ b/src/main/generated/data/galacticraft/worldgen/noise_settings/asteroid.json @@ -0,0 +1,133 @@ +{ + "aquifers_enabled": false, + "default_block": { + "Name": "galacticraft:hard_venus_rock" + }, + "default_fluid": { + "Name": "minecraft:air" + }, + "disable_mob_generation": false, + "legacy_random_source": false, + "noise": { + "height": 256, + "min_y": -32, + "size_horizontal": 1, + "size_vertical": 2 + }, + "noise_router": { + "barrier": 0.0, + "continents": 0.0, + "depth": 0.0, + "erosion": 0.0, + "final_density": { + "type": "minecraft:blend_density", + "argument": "galacticraft:asteroid/final_density" + }, + "fluid_level_floodedness": 0.0, + "fluid_level_spread": 0.0, + "initial_density_without_jaggedness": { + "type": "minecraft:noise", + "noise": "minecraft:spaghetti_3d_1", + "xz_scale": 1.0, + "y_scale": 1.0 + }, + "lava": 0.0, + "ridges": 0.0, + "temperature": 0.0, + "vegetation": 0.0, + "vein_gap": 0.0, + "vein_ridged": 0.0, + "vein_toggle": 0.0 + }, + "ore_veins_enabled": true, + "sea_level": -32, + "spawn_target": [ + { + "continentalness": [ + -0.11, + 1.0 + ], + "depth": 0.0, + "erosion": [ + -1.0, + 1.0 + ], + "humidity": [ + -1.0, + 1.0 + ], + "offset": 0.0, + "temperature": [ + -1.0, + 1.0 + ], + "weirdness": [ + -1.0, + -0.16 + ] + }, + { + "continentalness": [ + -0.11, + 1.0 + ], + "depth": 0.0, + "erosion": [ + -1.0, + 1.0 + ], + "humidity": [ + -1.0, + 1.0 + ], + "offset": 0.0, + "temperature": [ + -1.0, + 1.0 + ], + "weirdness": [ + 0.16, + 1.0 + ] + } + ], + "surface_rule": { + "type": "minecraft:sequence", + "sequence": [ + { + "type": "minecraft:condition", + "if_true": { + "type": "minecraft:biome", + "biome_is": [ + "galacticraft:asteroid_field" + ] + }, + "then_run": { + "type": "minecraft:block", + "result_state": { + "Name": "galacticraft:hard_venus_rock" + } + } + }, + { + "type": "minecraft:condition", + "if_true": { + "type": "minecraft:vertical_gradient", + "false_at_and_above": { + "above_bottom": 5 + }, + "random_name": "minecraft:bedrock_floor", + "true_at_and_below": { + "above_bottom": 0 + } + }, + "then_run": { + "type": "minecraft:block", + "result_state": { + "Name": "minecraft:bedrock" + } + } + } + ] + } +} \ No newline at end of file diff --git a/src/main/java/dev/galacticraft/api/perlin/FishyNoise.java b/src/main/java/dev/galacticraft/api/perlin/FishyNoise.java new file mode 100644 index 000000000..5daaa8b33 --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/FishyNoise.java @@ -0,0 +1,133 @@ +package dev.galacticraft.api.perlin; + +import java.util.Random; + +public class FishyNoise +{ + int[] perm = new int[512]; + + public float[][] grad2d = new float[][] { { 1, 0 }, { .9239F, .3827F }, { .707107F, 0.707107F }, { .3827F, .9239F }, { 0, 1 }, { -.3827F, .9239F }, { -.707107F, 0.707107F }, { -.9239F, .3827F }, { -1, 0 }, { -.9239F, -.3827F }, { -.707107F, -0.707107F }, { -.3827F, -.9239F }, { 0, -1 }, { .3827F, -.9239F }, { .707107F, -0.707107F }, { .9239F, -.3827F } }; + + public int[][] grad3d = new int[][] { { 1, 1, 0 }, { -1, 1, 0 }, { 1, -1, 0 }, { -1, -1, 0 }, { 1, 0, 1 }, { -1, 0, 1 }, { 1, 0, -1 }, { -1, 0, -1 }, { 0, 1, 1 }, { 0, -1, 1 }, { 0, 1, -1 }, { 0, -1, -1 }, { 1, 1, 0 }, { -1, 1, 0 }, { 0, -1, 1 }, { 0, -1, -1 } }; + + public FishyNoise(long seed) + { + final Random rand = new Random(seed); + for (int i = 0; i < 256; i++) + { + this.perm[i] = i; //fills array with 0 - 256 + } + + for (int i = 0; i < 256; i++) // Shuffle those numbers for the random effect + { + final int j = rand.nextInt(256); + this.perm[i] = this.perm[i] ^ this.perm[j]; + this.perm[j] = this.perm[i] ^ this.perm[j]; + this.perm[i] = this.perm[i] ^ this.perm[j]; + } + + System.arraycopy(this.perm, 0, this.perm, 256, 256); + } + + private static float lerp(float x, float y, float n) + { + return x + n * (y - x); + } + + private static int fastFloor(float x) + { + return x > 0 ? (int) x : (int) x - 1; + } + + private static float fade(float n) + { + return n * n * n * (n * (n * 6 - 15) + 10); + } + + private static float dot2(float[] grad2, float x, float y) + { + return grad2[0] * x + grad2[1] * y; + } + + private static float dot3(int[] grad3, float x, float y, float z) + { + return grad3[0] * x + grad3[1] * y + grad3[2] * z; + } + + public float noise2d(float x, float y) + { + int largeX = x > 0 ? (int) x : (int) x - 1; + int largeY = y > 0 ? (int) y : (int) y - 1; + x -= largeX; + y -= largeY; + largeX &= 255; + largeY &= 255; + + final float u = x * x * x * (x * (x * 6 - 15) + 10); + final float v = y * y * y * (y * (y * 6 - 15) + 10); + + int randY = this.perm[largeY] + largeX; + int randY1 = this.perm[largeY + 1] + largeX; + float[] grad2 = this.grad2d[this.perm[randY] & 15]; + final float grad00 = grad2[0] * x + grad2[1] * y; + grad2 = this.grad2d[this.perm[randY1] & 15]; + final float grad01 = grad2[0] * x + grad2[1] * (y - 1); + grad2 = this.grad2d[this.perm[1 + randY1] & 15]; + final float grad11 = grad2[0] * (x - 1) + grad2[1] * (y - 1); + grad2 = this.grad2d[this.perm[1 + randY] & 15]; + final float grad10 = grad2[0] * (x - 1) + grad2[1] * y; + + final float lerpX0 = grad00 + u * (grad10 - grad00); + return lerpX0 + v * (grad01 + u * (grad11 - grad01) - lerpX0); + } + + public float noise3d(float x, float y, float z) + { + int unitX = x > 0 ? (int) x : (int) x - 1; + int unitY = y > 0 ? (int) y : (int) y - 1; + int unitZ = z > 0 ? (int) z : (int) z - 1; + + x -= unitX; + y -= unitY; + z -= unitZ; + + unitX &= 255; + unitY &= 255; + unitZ &= 255; + + final float u = x * x * x * (x * (x * 6 - 15) + 10); + final float v = y * y * y * (y * (y * 6 - 15) + 10); + final float w = z * z * z * (z * (z * 6 - 15) + 10); + + int randZ = this.perm[unitZ] + unitY; + int randZ1 = this.perm[unitZ + 1] + unitY; + int randYZ = this.perm[randZ] + unitX; + int randY1Z = this.perm[1 + randZ] + unitX; + int randYZ1 = this.perm[randZ1] + unitX; + int randY1Z1 = this.perm[1 + randZ1] + unitX; + int[] grad3 = this.grad3d[this.perm[randYZ] & 15]; + final float grad000 = grad3[0] * x + grad3[1] * y + grad3[2] * z; + grad3 = this.grad3d[this.perm[1 + randYZ] & 15]; + final float grad100 = grad3[0] * (x - 1) + grad3[1] * y + grad3[2] * z; + grad3 = this.grad3d[this.perm[randY1Z] & 15]; + final float grad010 = grad3[0] * x + grad3[1] * (y - 1) + grad3[2] * z; + grad3 = this.grad3d[this.perm[1 + randY1Z] & 15]; + final float grad110 = grad3[0] * (x - 1) + grad3[1] * (y - 1) + grad3[2] * z; + z--; + grad3 = this.grad3d[this.perm[randYZ1] & 15]; + final float grad001 = grad3[0] * x + grad3[1] * y + grad3[2] * z; + grad3 = this.grad3d[this.perm[1 + randYZ1] & 15]; + final float grad101 = grad3[0] * (x - 1) + grad3[1] * y + grad3[2] * z; + grad3 = this.grad3d[this.perm[randY1Z1] & 15]; + final float grad011 = grad3[0] * x + grad3[1] * (y - 1) + grad3[2] * z; + grad3 = this.grad3d[this.perm[1 + randY1Z1] & 15]; + final float grad111 = grad3[0] * (x - 1) + grad3[1] * (y - 1) + grad3[2] * z; + + float f1 = grad000 + u * (grad100 - grad000); + float f2 = grad010 + u * (grad110 - grad010); + float f3 = grad001 + u * (grad101 - grad001); + float f4 = grad011 + u * (grad111 - grad011); + float lerp1 = f1 + v * (f2 - f1); + return lerp1 + w * (f3 + v * (f4 - f3) - lerp1); + } +} diff --git a/src/main/java/dev/galacticraft/api/perlin/NoiseModule.java b/src/main/java/dev/galacticraft/api/perlin/NoiseModule.java new file mode 100644 index 000000000..3d44ac82f --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/NoiseModule.java @@ -0,0 +1,22 @@ +package dev.galacticraft.api.perlin; + +public abstract class NoiseModule +{ + public float frequencyX = 1; + public float frequencyY = 1; + public float frequencyZ = 1; + public float amplitude = 1; + + public abstract float getNoise(float i); + + public abstract float getNoise(float i, float j); + + public abstract float getNoise(float i, float j, float k); + + public void setFrequency(float frequency) + { + this.frequencyX = frequency; + this.frequencyY = frequency; + this.frequencyZ = frequency; + } +} diff --git a/src/main/java/dev/galacticraft/api/perlin/SimplexNoise.java b/src/main/java/dev/galacticraft/api/perlin/SimplexNoise.java new file mode 100644 index 000000000..e83152c00 --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/SimplexNoise.java @@ -0,0 +1,30 @@ +package dev.galacticraft.api.perlin; + +import java.util.Random; + +public class SimplexNoise +{ + int[] perm = new int[512]; + + public int[][] grad2d = new int[][] { { 0, 0 }, { 0, 1 }, { 1, 1 }, { 1, 0 } }; + + public SimplexNoise(long seed) + { + final Random rand = new Random(seed); + for (int i = 0; i < 256; i++) + { + this.perm[i] = i; // Fill up the random array with numbers 0-256 + } + + for (int i = 0; i < 256; i++) // Shuffle those numbers for the random + // effect + { + final int j = rand.nextInt(256); + this.perm[i] = this.perm[i] ^ this.perm[j]; + this.perm[j] = this.perm[i] ^ this.perm[j]; + this.perm[i] = this.perm[i] ^ this.perm[j]; + } + + System.arraycopy(this.perm, 0, this.perm, 256, 256); + } +} diff --git a/src/main/java/dev/galacticraft/api/perlin/generator/Billowed.java b/src/main/java/dev/galacticraft/api/perlin/generator/Billowed.java new file mode 100644 index 000000000..293ce2fde --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/generator/Billowed.java @@ -0,0 +1,80 @@ +package dev.galacticraft.api.perlin.generator; + +import dev.galacticraft.api.perlin.FishyNoise; +import dev.galacticraft.api.perlin.NoiseModule; + +import java.util.Random; + +public class Billowed extends NoiseModule { + private final FishyNoise noiseGen; + private final float offsetX; + private final float offsetY; + private final float offsetZ; + private final int numOctaves; + private final float persistance; + + public Billowed(long seed, int nOctaves, float p) + { + this.numOctaves = nOctaves; + this.persistance = p; + final Random rand = new Random(seed); + this.offsetX = rand.nextFloat() / 2 + 0.01F; + this.offsetY = rand.nextFloat() / 2 + 0.01F; + this.offsetZ = rand.nextFloat() / 2 + 0.01F; + this.noiseGen = new FishyNoise(seed); + } + + @Override + public float getNoise(float i) + { + i *= this.frequencyX; + float val = 0; + float curAmplitude = this.amplitude; + for (int n = 0; n < this.numOctaves; n++) + { + val += Math.abs(this.noiseGen.noise2d(i + this.offsetX, this.offsetY) * curAmplitude); + i *= 2; + curAmplitude *= this.persistance; + } + return val; + } + + @Override + public float getNoise(float i, float j) + { + i *= this.frequencyX; + j *= this.frequencyY; + if (this.numOctaves == 2) + { + return Math.abs(this.noiseGen.noise2d(i + this.offsetX, j + this.offsetY) * this.amplitude) + Math.abs(this.noiseGen.noise2d(i + i + this.offsetX, j + j + this.offsetY) * this.amplitude * this.persistance); + } + + float val = 0; + float curAmplitude = this.amplitude; + for (int n = 0; n < this.numOctaves; n++) + { + val += Math.abs(this.noiseGen.noise2d(i + this.offsetX, j + this.offsetY) * curAmplitude); + i += i; + j += j; + curAmplitude *= this.persistance; + } + return val; + } + + @Override + public float getNoise(float i, float j, float k) + { + i *= this.frequencyX; + j *= this.frequencyY; + k *= this.frequencyZ; + float val = 0; + for (int n = 0; n < this.numOctaves; n++) + { + val += Math.abs(this.noiseGen.noise3d(i + this.offsetX, j + this.offsetY, k + this.offsetZ) * this.amplitude); + i *= 2; + j *= 2; + k *= 2; + } + return val; + } +} diff --git a/src/main/java/dev/galacticraft/api/perlin/generator/Gradient.java b/src/main/java/dev/galacticraft/api/perlin/generator/Gradient.java new file mode 100644 index 000000000..ac950205a --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/generator/Gradient.java @@ -0,0 +1,88 @@ +package dev.galacticraft.api.perlin.generator; + +import dev.galacticraft.api.perlin.FishyNoise; +import dev.galacticraft.api.perlin.NoiseModule; + +import java.util.Random; + +public class Gradient extends NoiseModule +{ + private final FishyNoise noiseGen; + private final float offsetX; + private final float offsetY; + private final float offsetZ; + private final int numOctaves; + private final float persistance; + + public Gradient(long seed, int nOctaves, float p) + { + this.numOctaves = nOctaves; + this.persistance = p; + final Random rand = new Random(seed); + this.offsetX = rand.nextFloat() / 2 + 0.01F; + this.offsetY = rand.nextFloat() / 2 + 0.01F; + this.offsetZ = rand.nextFloat() / 2 + 0.01F; + this.noiseGen = new FishyNoise(seed); + } + + @Override + public float getNoise(float i) + { + i *= this.frequencyX; + float val = 0; + float curAmplitude = this.amplitude; + for (int n = 0; n < this.numOctaves; n++) + { + val += this.noiseGen.noise2d(i + this.offsetX, this.offsetY) * curAmplitude; + i *= 2; + curAmplitude *= this.persistance; + } + return val; + } + + @Override + public float getNoise(float i, float j) + { + if (this.numOctaves == 1) + { + return this.noiseGen.noise2d(i * this.frequencyX + this.offsetX, j * this.frequencyY + this.offsetY) * this.amplitude; + } + + i *= this.frequencyX; + j *= this.frequencyY; + float val = 0; + float curAmplitude = this.amplitude; + for (int n = 0; n < this.numOctaves; n++) + { + val += this.noiseGen.noise2d(i + this.offsetX, j + this.offsetY) * curAmplitude; + i *= 2; + j *= 2; + curAmplitude *= this.persistance; + } + return val; + } + + @Override + public float getNoise(float i, float j, float k) + { + if (this.numOctaves == 1) + { + return this.noiseGen.noise3d(i * this.frequencyX + this.offsetX, j * this.frequencyY + this.offsetY, k * this.frequencyZ + this.offsetZ) * this.amplitude; + } + + i *= this.frequencyX; + j *= this.frequencyY; + k *= this.frequencyZ; + float val = 0; + float curAmplitude = this.amplitude; + for (int n = 0; n < this.numOctaves; n++) + { + val += this.noiseGen.noise3d(i + this.offsetX, j + this.offsetY, k + this.offsetZ) * curAmplitude; + i *= 2; + j *= 2; + k *= 2; + curAmplitude *= this.persistance; + } + return val; + } +} diff --git a/src/main/java/dev/galacticraft/api/perlin/generator/RidgedMulti.java b/src/main/java/dev/galacticraft/api/perlin/generator/RidgedMulti.java new file mode 100644 index 000000000..8ac7c88dd --- /dev/null +++ b/src/main/java/dev/galacticraft/api/perlin/generator/RidgedMulti.java @@ -0,0 +1,142 @@ +package dev.galacticraft.api.perlin.generator; + +import dev.galacticraft.api.perlin.FishyNoise; +import dev.galacticraft.api.perlin.NoiseModule; + +import java.util.Random; + +public class RidgedMulti extends NoiseModule +{ + private final FishyNoise noiseGen; + private final float offsetX; + private final float offsetY; + private final float offsetZ; + private final int numOctaves; + + public RidgedMulti(long seed, int nOctaves) + { + this.numOctaves = nOctaves; + final Random rand = new Random(seed); + this.offsetX = rand.nextFloat() / 2 + 0.01F; + this.offsetY = rand.nextFloat() / 2 + 0.01F; + this.offsetZ = rand.nextFloat() / 2 + 0.01F; + this.noiseGen = new FishyNoise(seed); + } + + @Override + public float getNoise(float i) + { + i *= this.frequencyX; + float val = 0; + float weight = 1.0F; + final float offset = 1.0F; + final float gain = 2.0F; + for (int n = 0; n < this.numOctaves; n++) + { + float noise = this.absolute(this.noiseGen.noise2d(i + this.offsetX, this.offsetY)); + noise = offset - noise; + noise *= noise; + noise *= weight; + + weight = noise * gain; + + if (weight > 1F) + { + weight = 1F; + } + + if (weight < 0F) + { + weight = 0F; + } + + val += noise; + + i *= 2; + } + return val; + } + + @Override + public float getNoise(float i, float j) + { + i *= this.frequencyX; + j *= this.frequencyY; + float val = 0; + float weight = 1.0F; + final float offset = 1.0F; + final float gain = 2.0F; + for (int n = 0; n < this.numOctaves; n++) + { + float noise = this.absolute(this.noiseGen.noise2d(i + this.offsetX, j + this.offsetY)); + noise = offset - noise; + noise *= noise; + noise *= weight; + + weight = noise * gain; + + if (weight > 1F) + { + weight = 1F; + } + + if (weight < 0F) + { + weight = 0F; + } + + val += noise; + + i *= 2; + j *= 2; + } + return val; + } + + @Override + public float getNoise(float i, float j, float k) + { + i *= this.frequencyX; + j *= this.frequencyY; + k *= this.frequencyZ; + float val = 0F; + float weight = 1.0F; + final float offset = 1.0F; + final float gain = 2.0F; + for (int n = 0; n < this.numOctaves; n++) + { + float noise = this.absolute(this.noiseGen.noise3d(i + this.offsetX, j + this.offsetY, k + this.offsetZ)); + noise = offset - noise; + noise *= noise; + noise *= weight; + + weight = noise * gain; + + if (weight > 1F) + { + weight = 1F; + } + + if (weight < 0F) + { + weight = 0F; + } + + val += noise; + + i *= 2; + j *= 2; + k *= 2; + } + return val; + } + + private float absolute(float d) + { + if (d < 0) + { + d = -d; + } + return d; + } +} diff --git a/src/main/java/dev/galacticraft/api/vector/BlockVec3.java b/src/main/java/dev/galacticraft/api/vector/BlockVec3.java new file mode 100644 index 000000000..9af254139 --- /dev/null +++ b/src/main/java/dev/galacticraft/api/vector/BlockVec3.java @@ -0,0 +1,676 @@ +package dev.galacticraft.api.vector; +import dev.galacticraft.mod.world.dimension.GCDimensions; +import net.minecraft.CrashReport; +import net.minecraft.CrashReportCategory; +import net.minecraft.ReportedException; +import net.minecraft.commands.arguments.NbtTagArgument; +import net.minecraft.core.BlockPos; +import net.minecraft.core.Direction; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.network.chat.contents.NbtContents; +import net.minecraft.resources.ResourceKey; +import net.minecraft.server.commands.data.BlockDataAccessor; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.level.BlockGetter; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.Blocks; +import net.minecraft.world.level.block.entity.BlockEntity; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.block.state.properties.BlockStateProperties; +import net.minecraft.world.level.block.state.properties.DirectionProperty; +import net.minecraft.world.level.block.state.properties.EnumProperty; +import net.minecraft.world.level.chunk.ChunkAccess; +import net.minecraft.world.level.chunk.LevelChunk; +import net.minecraft.world.level.storage.loot.providers.nbt.NbtProvider; +import org.jetbrains.annotations.Nullable; +import org.joml.Vector3d; + +import static net.minecraft.util.Mth.floor; + + +public class BlockVec3 implements Cloneable +{ + public int x; + public int y; + public int z; + public int sideDoneBits = 0; + private static ChunkAccess chunkCached; + public static ResourceKey chunkCacheDim = Level.OVERWORLD; + private static int chunkCacheX = 1876000; // outside the world edge + private static int chunkCacheZ = 1876000; // outside the world edge + private static ChunkAccess chunkCached_Client; + public static ResourceKey chunkCacheDim_Client = Level.OVERWORLD; + private static int chunkCacheX_Client = 1876000; // outside the world edge + private static int chunkCacheZ_Client = 1876000; // outside the world edge + // INVALID_VECTOR is used in cases where a null vector cannot be used + public static final BlockVec3 INVALID_VECTOR = new BlockVec3(-1, -1, -1); + + public BlockVec3() + { + this(0, 0, 0); + } + + public BlockVec3(BlockPos pos) + { + this(pos.getX(), pos.getY(), pos.getZ()); + } + + public BlockVec3(int x, int y, int z) + { + this.x = x; + this.y = y; + this.z = z; + } + + public BlockVec3(Entity par1) + { + this.x = (int) Math.floor(par1.position().x); + this.y = (int) Math.floor(par1.position().y); + this.z = (int) Math.floor(par1.position().z); + } + + public BlockVec3(BlockEntity par1) + { + this.x = par1.getBlockPos().getX(); + this.y = par1.getBlockPos().getY(); + this.z = par1.getBlockPos().getZ(); + } + + /** + * Makes a new copy of this Vector. Prevents variable referencing problems. + */ + @Override + public final BlockVec3 clone() + { + return new BlockVec3(this.x, this.y, this.z); + } + + public BlockPos toBlockPos() + { + return new BlockPos(this.x, this.y, this.z); + } + + /** + * Get block ID at the BlockVec3 coordinates, with a forced chunk load if + * the coordinates are unloaded. + * + * @param world + * @return the block ID, or null if the y-coordinate is less than 0 or + * greater than 256 or the x or z is outside the Minecraft worldmap. + */ + public BlockState getBlockState(Level world) + { + if (this.y < 0 || this.y >= 256 || this.x < -30000000 || this.z < -30000000 || this.x >= 30000000 || this.z >= 30000000) + { + return null; + } + + int chunkx = this.x >> 4; + int chunkz = this.z >> 4; + try + { + if (!world.isClientSide()) + { + if (BlockVec3.chunkCacheX_Client == chunkx && BlockVec3.chunkCacheZ_Client == chunkz && BlockVec3.chunkCacheDim_Client == world.dimension() && BlockVec3.chunkCached_Client != null) + { + return BlockVec3.chunkCached_Client.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached_Client = chunk; + BlockVec3.chunkCacheDim_Client = world.dimension(); + BlockVec3.chunkCacheX_Client = chunkx; + BlockVec3.chunkCacheZ_Client = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + else + { + // In a typical inner loop, 80% of the time consecutive calls to + // this will be within the same chunk + if (BlockVec3.chunkCacheX == chunkx && BlockVec3.chunkCacheZ == chunkz && BlockVec3.chunkCacheDim == world.dimension() && BlockVec3.chunkCached instanceof LevelChunk) + { + return BlockVec3.chunkCached.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached = chunk; + BlockVec3.chunkCacheDim = world.dimension(); + BlockVec3.chunkCacheX = chunkx; + BlockVec3.chunkCacheZ = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + } + catch (Throwable throwable) + { + CrashReport crashreport = CrashReport.forThrowable(throwable, "Oxygen Sealer thread: Exception getting block type in world"); + CrashReportCategory crashreportcategory = crashreport.addCategory("Requested block coordinates"); + crashreportcategory.setDetail("Location", CrashReportCategory.formatLocation(world, new BlockPos(this.x, this.y, this.z))); + throw new ReportedException(crashreport); + } + } + + /** + * Get block ID at the BlockVec3 coordinates without forcing a chunk load. + * + * @param world + * @return the block ID, or null if the y-coordinate is less than 0 or + * greater than 256 or the x or z is outside the Minecraft worldmap. + * Returns Blocks.BEDROCK if the coordinates being checked are in an + * unloaded chunk + */ + public BlockState getBlockState_noChunkLoad(Level world) + { + if (this.y < 0 || this.y >= 256 || this.x < -30000000 || this.z < -30000000 || this.x >= 30000000 || this.z >= 30000000) + { + return null; + } + + int chunkx = this.x >> 4; + int chunkz = this.z >> 4; + try + { + if (world.isLoaded(new BlockPos(chunkx, this.y ,chunkz))) + { + if (!world.isClientSide()) + { + if (BlockVec3.chunkCacheX_Client == chunkx && BlockVec3.chunkCacheZ_Client == chunkz && BlockVec3.chunkCacheDim_Client == world.dimension() && BlockVec3.chunkCached_Client != null) + { + return BlockVec3.chunkCached_Client.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached_Client = chunk; + BlockVec3.chunkCacheDim_Client = world.dimension(); + BlockVec3.chunkCacheX_Client = chunkx; + BlockVec3.chunkCacheZ_Client = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + else + { + // In a typical inner loop, 80% of the time consecutive calls to + // this will be within the same chunk + if (BlockVec3.chunkCacheX == chunkx && BlockVec3.chunkCacheZ == chunkz && BlockVec3.chunkCacheDim == world.dimension() && BlockVec3.chunkCached instanceof LevelChunk) + { + return BlockVec3.chunkCached.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached = chunk; + BlockVec3.chunkCacheDim = world.dimension(); + BlockVec3.chunkCacheX = chunkx; + BlockVec3.chunkCacheZ = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + } + //Chunk doesn't exist - meaning, it is not loaded + return Blocks.BEDROCK.defaultBlockState(); + } + catch (Throwable throwable) + { + CrashReport crashreport = CrashReport.forThrowable(throwable, "Oxygen Sealer thread: Exception getting block type in world"); + CrashReportCategory crashreportcategory = crashreport.addCategory("Requested block coordinates"); + crashreportcategory.setDetail("Location", CrashReportCategory.formatLocation(world, new BlockPos(this.x, this.y, this.z))); + throw new ReportedException(crashreport); + } + } + + public BlockState getBlockState(BlockGetter par1iBlockAccess) + { + return par1iBlockAccess.getBlockState(new BlockPos(this.x, this.y, this.z)); + } + + /** + * Get block ID at the BlockVec3 coordinates without forcing a chunk load. + * Only call this 'safe' version if x and z coordinates are within the + * Minecraft world map (-30m to +30m) + * + * @param world + * @return the block ID, or null if the y-coordinate is less than 0 or + * greater than 256. Returns Blocks.BEDROCK if the coordinates being + * checked are in an unloaded chunk + */ + @Nullable + public BlockState getBlockStateSafe_noChunkLoad(Level world) + { + if (this.y < 0 || this.y >= 256) + { + return null; + } + + int chunkx = this.x >> 4; + int chunkz = this.z >> 4; + try + { + if (world.isLoaded(new BlockPos(chunkx, this.y ,chunkz))) + { + if (!world.isClientSide()) + { + if (BlockVec3.chunkCacheX_Client == chunkx && BlockVec3.chunkCacheZ_Client == chunkz && BlockVec3.chunkCacheDim_Client == world.dimension() && BlockVec3.chunkCached_Client != null) + { + return BlockVec3.chunkCached_Client.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached_Client = chunk; + BlockVec3.chunkCacheDim_Client = world.dimension(); + BlockVec3.chunkCacheX_Client = chunkx; + BlockVec3.chunkCacheZ_Client = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + else + { + // In a typical inner loop, 80% of the time consecutive calls to + // this will be within the same chunk + if (BlockVec3.chunkCacheX == chunkx && BlockVec3.chunkCacheZ == chunkz && BlockVec3.chunkCacheDim == world.dimension() && BlockVec3.chunkCached instanceof LevelChunk) + { + return BlockVec3.chunkCached.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + else + { + final ChunkAccess chunk = world.getChunk(chunkx, chunkz); + BlockVec3.chunkCached = chunk; + BlockVec3.chunkCacheDim = world.dimension(); + BlockVec3.chunkCacheX = chunkx; + BlockVec3.chunkCacheZ = chunkz; + return chunk.getBlockState(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + } + } + //Chunk doesn't exist - meaning, it is not loaded + return Blocks.BEDROCK.defaultBlockState(); + } + catch (Throwable throwable) + { + CrashReport crashreport = CrashReport.forThrowable(throwable, "Oxygen Sealer thread: Exception getting block type in world"); + CrashReportCategory crashreportcategory = crashreport.addCategory("Requested block coordinates"); + crashreportcategory.setDetail("Location", CrashReportCategory.formatLocation(world, new BlockPos(this.x, this.y, this.z))); + throw new ReportedException(crashreport); + } + } + + public BlockVec3 translate(BlockVec3 par1) + { + this.x += par1.x; + this.y += par1.y; + this.z += par1.z; + return this; + } + + public BlockVec3 translate(int par1x, int par1y, int par1z) + { + this.x += par1x; + this.y += par1y; + this.z += par1z; + return this; + } + + public static BlockVec3 add(BlockVec3 par1, BlockVec3 a) + { + return new BlockVec3(par1.x + a.x, par1.y + a.y, par1.z + a.z); + } + + public BlockVec3 subtract(BlockVec3 par1) + { + this.x -= par1.x; + this.y -= par1.y; + this.z -= par1.z; + + return this; + } + + public BlockVec3 scale(int par1) + { + this.x *= par1; + this.y *= par1; + this.z *= par1; + + return this; + } + + public BlockVec3 modifyPositionFromSide(Direction side, int amount) + { + switch (side.ordinal()) + { + case 0: + this.y -= amount; + break; + case 1: + this.y += amount; + break; + case 2: + this.z -= amount; + break; + case 3: + this.z += amount; + break; + case 4: + this.x -= amount; + break; + case 5: + this.x += amount; + break; + } + return this; + } + + public BlockVec3 newVecSide(int side) + { + final BlockVec3 vec = new BlockVec3(this.x, this.y, this.z); + vec.sideDoneBits = (1 << (side ^ 1)) + (side << 6); + switch (side) + { + case 0: + vec.y--; + return vec; + case 1: + vec.y++; + return vec; + case 2: + vec.z--; + return vec; + case 3: + vec.z++; + return vec; + case 4: + vec.x--; + return vec; + case 5: + vec.x++; + return vec; + } + return vec; + } + + public BlockVec3 modifyPositionFromSide(Direction side) + { + return this.modifyPositionFromSide(side, 1); + } + + @Override + public int hashCode() + { + // Upgraded hashCode calculation from the one in VecDirPair to something + // a bit stronger and faster + return ((this.y * 379 + this.x) * 373 + this.z) * 7; + } + + @Override + public boolean equals(Object o) + { + if (o instanceof BlockVec3) + { + final BlockVec3 vector = (BlockVec3) o; + return this.x == vector.x && this.y == vector.y && this.z == vector.z; + } + + return false; + } + + @Override + public String toString() + { + return "[" + this.x + "," + this.y + "," + this.z + "]"; + } + + /** + * This will load the chunk. + */ + public BlockEntity getTileEntity(BlockGetter world) + { + return world.getBlockEntity(new BlockPos(this.x, this.y, this.z)); + } + + /** + * No chunk load: returns null if chunk to side is unloaded + */ + public BlockEntity getTileEntityOnSide(Level world, Direction side) + { + if (side == null) + { + return null; + } + + int x = this.x; + int y = this.y; + int z = this.z; + switch (side.ordinal()) + { + case 0: + y--; + break; + case 1: + y++; + break; + case 2: + z--; + break; + case 3: + z++; + break; + case 4: + x--; + break; + case 5: + x++; + break; + default: + return null; + } + final BlockPos pos = new BlockPos(x, y, z); + return world.isLoaded(pos) ? world.getBlockEntity(pos) : null; + } + + /** + * No chunk load: returns null if chunk to side is unloaded + */ + public BlockEntity getTileEntityOnSide(Level world, int side) + { + int x = this.x; + int y = this.y; + int z = this.z; + switch (side) + { + case 0: + y--; + break; + case 1: + y++; + break; + case 2: + z--; + break; + case 3: + z++; + break; + case 4: + x--; + break; + case 5: + x++; + break; + default: + return null; + } + final BlockPos pos = new BlockPos(x, y, z); + return world.isLoaded(pos) ? world.getBlockEntity(pos) : null; + } + + /** + * This will load the chunk to the side. + */ + public boolean blockOnSideHasSolidFace(Level world, int side) + { + int x = this.x; + int y = this.y; + int z = this.z; + switch (side) + { + case 0: + y--; + break; + case 1: + y++; + break; + case 2: + z--; + break; + case 3: + z++; + break; + case 4: + x--; + break; + case 5: + x++; + break; + default: + return false; + } + final BlockPos pos = new BlockPos(x, y, z); + return world.getBlockState(pos).isFaceSturdy(world.getChunkForCollisions(pos.getX(), pos.getZ()), pos, Direction.from3DDataValue(side ^ 1)); + } + + /** + * No chunk load: returns null if chunk is unloaded + */ + public Block getBlockOnSide(Level world, int side) + { + int x = this.x; + int y = this.y; + int z = this.z; + switch (side) + { + case 0: + y--; + break; + case 1: + y++; + break; + case 2: + z--; + break; + case 3: + z++; + break; + case 4: + x--; + break; + case 5: + x++; + break; + default: + return null; + } + final BlockPos pos = new BlockPos(x, y, z); + return world.isLoaded(pos) ? world.getBlockState(pos).getBlock() : null; + } + + public static BlockVec3 readFromNBT(CompoundTag nbtCompound) + { + final BlockVec3 tempVector = new BlockVec3(); + tempVector.x = nbtCompound.getInt("x"); + tempVector.y = nbtCompound.getInt("y"); + tempVector.z = nbtCompound.getInt("z"); + return tempVector; + } + + public int distanceTo(BlockVec3 vector) + { + int var2 = vector.x - this.x; + int var4 = vector.y - this.y; + int var6 = vector.z - this.z; + return floor(Math.sqrt(var2 * var2 + var4 * var4 + var6 * var6)); + } + + public int distanceSquared(BlockVec3 vector) + { + int var2 = vector.x - this.x; + int var4 = vector.y - this.y; + int var6 = vector.z - this.z; + return var2 * var2 + var4 * var4 + var6 * var6; + } + + public CompoundTag writeToNBT(CompoundTag par1NBTTagCompound) + { + par1NBTTagCompound.putInt("x", this.x); + par1NBTTagCompound.putInt("y", this.y); + par1NBTTagCompound.putInt("z", this.z); + return par1NBTTagCompound; + } + + public BlockVec3(CompoundTag par1NBTTagCompound) + { + this.x = par1NBTTagCompound.getInt("x"); + this.y = par1NBTTagCompound.getInt("y"); + this.z = par1NBTTagCompound.getInt("z"); + } + + public CompoundTag writeToNBT(CompoundTag par1NBTTagCompound, String prefix) + { + par1NBTTagCompound.putInt(prefix + "_x", this.x); + par1NBTTagCompound.putInt(prefix + "_y", this.y); + par1NBTTagCompound.putInt(prefix + "_z", this.z); + return par1NBTTagCompound; + } + + public static BlockVec3 readFromNBT(CompoundTag par1NBTTagCompound, String prefix) + { + Integer readX = par1NBTTagCompound.getInt(prefix + "_x"); + if (readX == null) return null; + Integer readY = par1NBTTagCompound.getInt(prefix + "_y"); + if (readY == null) return null; + Integer readZ = par1NBTTagCompound.getInt(prefix + "_z"); + if (readZ == null) return null; + return new BlockVec3(readX, readY, readZ); + } + + public double getMagnitude() + { + return Math.sqrt(this.getMagnitudeSquared()); + } + + public int getMagnitudeSquared() + { + return this.x * this.x + this.y * this.y + this.z * this.z; + } + + public void setBlock(Level worldObj, BlockState block) + { + worldObj.setBlock(new BlockPos(x, y, z), block, 3); + } + + public boolean blockExists(Level world) + { + return world.isLoaded(new BlockPos(this.x, this.y, this.z)); + } + + public void setSideDone(int side) + { + this.sideDoneBits |= 1 << side; + } + + public BlockEntity getTileEntityForce(Level world) + { + int chunkx = this.x >> 4; + int chunkz = this.z >> 4; + + ChunkAccess chunk = world.getChunk(chunkx, chunkz); + return chunk.getBlockEntity(new BlockPos(this.x & 15, this.y, this.z & 15)); + } + + public Vector3d midPoint() + { + return new Vector3d(this.x + 0.5, this.y + 0.5, this.z + 0.5); + } +} diff --git a/src/main/java/dev/galacticraft/impl/internal/fabric/GalacticraftAPI.java b/src/main/java/dev/galacticraft/impl/internal/fabric/GalacticraftAPI.java index dbcca64cb..3b213f83f 100644 --- a/src/main/java/dev/galacticraft/impl/internal/fabric/GalacticraftAPI.java +++ b/src/main/java/dev/galacticraft/impl/internal/fabric/GalacticraftAPI.java @@ -26,21 +26,35 @@ import dev.galacticraft.api.entity.attribute.GcApiEntityAttributes; import dev.galacticraft.api.gas.Gases; import dev.galacticraft.api.registry.BuiltInRocketRegistries; +import dev.galacticraft.dynamicdimensions.api.DynamicDimensionRegistry; import dev.galacticraft.dynamicdimensions.api.event.DynamicDimensionLoadCallback; import dev.galacticraft.impl.internal.command.GCApiCommands; import dev.galacticraft.impl.universe.BuiltinObjects; import dev.galacticraft.mod.Constant; import dev.galacticraft.mod.data.gen.SatelliteChunkGenerator; import net.fabricmc.api.ModInitializer; +import net.fabricmc.fabric.api.event.lifecycle.v1.ServerLifecycleEvents; import net.fabricmc.fabric.api.networking.v1.ServerPlayNetworking; +import net.minecraft.client.Minecraft; import net.minecraft.core.Registry; import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.server.level.ServerPlayer; import net.minecraft.world.SimpleContainer; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.storage.LevelStorageSource; import org.jetbrains.annotations.ApiStatus; +import javax.swing.event.ChangeEvent; +import java.io.File; +import java.nio.file.Path; + @ApiStatus.Internal public class GalacticraftAPI implements ModInitializer { public static final SimpleContainer EMPTY_INV = new SimpleContainer(0); + //don't know if this is the best way to get file path, but it works + public static Path currentWorldSaveDirectory; @Override public void onInitialize() { @@ -69,6 +83,7 @@ public void onInitialize() { BuiltinObjects.register(); BuiltInRocketRegistries.initialize(); GcApiEntityAttributes.init(); + ServerLifecycleEvents.SERVER_STARTED.register(this::onServerStarted); DynamicDimensionLoadCallback.register((minecraftServer, dynamicDimensionLoader) -> { ((SatelliteAccessor) minecraftServer).galacticraft$loadSatellites(dynamicDimensionLoader); @@ -76,4 +91,14 @@ public void onInitialize() { Gases.init(); Constant.LOGGER.info("API Initialization Complete. (Took {}ms).", System.currentTimeMillis() - startInitTime); } + + private void onServerStarted(MinecraftServer server) { + // Update the directory when the server starts + updateWorldSaveDirectory(server); + } + + private void updateWorldSaveDirectory(MinecraftServer server) { + currentWorldSaveDirectory = Path.of(Minecraft.getInstance().getLevelSource().getBaseDir().toString(), server.getWorldData().getLevelName()); + System.out.println("World Save Directory: " + currentWorldSaveDirectory.toString()); + } } diff --git a/src/main/java/dev/galacticraft/mod/Constant.java b/src/main/java/dev/galacticraft/mod/Constant.java index 6dd6efa1a..f8683f0ef 100644 --- a/src/main/java/dev/galacticraft/mod/Constant.java +++ b/src/main/java/dev/galacticraft/mod/Constant.java @@ -40,6 +40,7 @@ public interface Constant { String MOD_ID = "galacticraft"; + public static final String GCDATAFOLDER = "../galacticraft/"; String COMMON_NAMESPACE = "c"; Logger LOGGER = LogManager.getLogger("Galacticraft"); @@ -117,6 +118,9 @@ interface Block { String VAPOR_SPOUT = "vapor_spout"; // Ore + String MARS_IRON_ORE = "mars_iron_ore"; + String MARS_TIN_ORE = "mars_tin_ore"; + String MARS_COPPER_ORE = "mars_copper_ore"; String MOON_COPPER_ORE = "moon_copper_ore"; String LUNASLATE_COPPER_ORE = "lunaslate_copper_ore"; String DESH_ORE = "desh_ore"; @@ -302,7 +306,10 @@ static ResourceLocation getId(String s) { } interface Item { + String ITEM_GROUP_CANS = "cans"; String ITEM_GROUP = "items"; + String CANNED_FOOD = "canned_food"; + String EMPTY_CANNED_FOOD = "empty_can"; String RAW_SILICON = "raw_silicon"; String RAW_METEORIC_IRON = "raw_meteoric_iron"; String METEORIC_IRON_INGOT = "meteoric_iron_ingot"; @@ -367,12 +374,6 @@ interface Item { String GROUND_BEEF = "ground_beef"; String BEEF_PATTY = "beef_patty"; String CHEESEBURGER = "cheeseburger"; - //CANNED FOOD - String CANNED_DEHYDRATED_APPLE = "canned_dehydrated_apple"; - String CANNED_DEHYDRATED_CARROT = "canned_dehydrated_carrot"; - String CANNED_DEHYDRATED_MELON = "canned_dehydrated_melon"; - String CANNED_DEHYDRATED_POTATO = "canned_dehydrated_potato"; - String CANNED_BEEF = "canned_beef"; //ROCKET PARTS String TIER_1_HEAVY_DUTY_PLATE = "heavy_plating"; String TIER_2_HEAVY_DUTY_PLATE = "heavy_plating_t2"; diff --git a/src/main/java/dev/galacticraft/mod/Galacticraft.java b/src/main/java/dev/galacticraft/mod/Galacticraft.java index 31e5ef4ac..3f4a451c1 100644 --- a/src/main/java/dev/galacticraft/mod/Galacticraft.java +++ b/src/main/java/dev/galacticraft/mod/Galacticraft.java @@ -51,7 +51,12 @@ import dev.galacticraft.mod.world.gen.surfacebuilder.MoonSurfaceRules; import dev.galacticraft.mod.world.poi.GCPointOfInterestTypes; import net.fabricmc.api.ModInitializer; +import net.fabricmc.fabric.api.event.registry.RegistryEntryAddedCallback; import net.fabricmc.loader.api.FabricLoader; +import net.minecraft.core.Registry; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.core.registries.Registries; +import net.minecraft.world.item.Item; public class Galacticraft implements ModInitializer { public static final Config CONFIG = new ConfigImpl(FabricLoader.getInstance().getConfigDir().resolve("galacticraft.json").toFile()); @@ -60,6 +65,7 @@ public class Galacticraft implements ModInitializer { public void onInitialize() { long startInitTime = System.currentTimeMillis(); Constant.LOGGER.info("Starting initialization."); + GCChunkGenerator.register(); GCTags.register(); GCFluids.register(); GCBlocks.register(); diff --git a/src/main/java/dev/galacticraft/mod/GalacticraftClient.java b/src/main/java/dev/galacticraft/mod/GalacticraftClient.java index 169783ca9..1b956c5e1 100644 --- a/src/main/java/dev/galacticraft/mod/GalacticraftClient.java +++ b/src/main/java/dev/galacticraft/mod/GalacticraftClient.java @@ -45,6 +45,7 @@ import dev.galacticraft.mod.content.GCEntityTypes; import dev.galacticraft.mod.content.block.environment.FallenMeteorBlock; import dev.galacticraft.mod.content.entity.orbital.RocketEntity; +import dev.galacticraft.mod.content.item.CannedFoodItem; import dev.galacticraft.mod.content.item.GCItems; import dev.galacticraft.mod.events.ClientEventHandler; import dev.galacticraft.mod.misc.cape.CapesLoader; @@ -52,11 +53,13 @@ import dev.galacticraft.mod.screen.GCMenuTypes; import dev.galacticraft.mod.screen.GCPlayerInventoryMenu; import dev.galacticraft.mod.screen.RocketMenu; +import dev.galacticraft.mod.util.TextureUtils; import io.netty.buffer.Unpooled; import net.fabricmc.api.ClientModInitializer; import net.fabricmc.api.EnvType; import net.fabricmc.api.Environment; import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap; +import net.fabricmc.fabric.api.client.event.lifecycle.v1.ClientTickEvents; import net.fabricmc.fabric.api.client.model.loading.v1.ModelLoadingPlugin; import net.fabricmc.fabric.api.client.networking.v1.ClientPlayNetworking; import net.fabricmc.fabric.api.client.particle.v1.ParticleFactoryRegistry; @@ -66,15 +69,34 @@ import net.fabricmc.fabric.api.client.rendering.v1.EntityRendererRegistry; import net.fabricmc.fabric.api.client.rendering.v1.LivingEntityFeatureRendererRegistrationCallback; import net.fabricmc.fabric.api.resource.ResourceManagerHelper; +import net.fabricmc.fabric.mixin.registry.sync.RegistriesAccessor; import net.minecraft.client.gui.screens.MenuScreens; import net.minecraft.client.renderer.RenderType; import net.minecraft.client.renderer.entity.ThrownItemRenderer; +import net.minecraft.core.Registry; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.core.registries.Registries; import net.minecraft.network.FriendlyByteBuf; +import net.minecraft.resources.ResourceLocation; import net.minecraft.server.packs.PackType; +import net.minecraft.server.packs.resources.Resource; +import net.minecraft.world.item.Item; +import net.minecraft.world.item.ItemStack; +import net.minecraft.world.item.Items; import net.minecraft.world.level.material.Fluids; +import java.util.*; +import java.util.List; + +import static dev.galacticraft.mod.content.item.CannedFoodItem.registerCan; +import static dev.galacticraft.mod.content.item.GCItems.CANNED_FOOD_ITEMS; +import static dev.galacticraft.mod.util.TextureUtils.getAverageColor; + @Environment(EnvType.CLIENT) public class GalacticraftClient implements ClientModInitializer { + + private boolean colorsInitialized = false; + @Override public void onInitializeClient() { long startInitTime = System.currentTimeMillis(); @@ -180,9 +202,52 @@ public void onInitializeClient() { LivingEntityFeatureRendererRegistrationCallback.EVENT.register((entityType, entityRenderer, registrationHelper, context) -> { }); - + //couldn't be bothered finding a better way to get the texture of the items so overrides exists now + List nameOverride = new ArrayList<>(); + nameOverride.add(new String[]{"enchanted_golden_apple", "golden_apple"}); + nameOverride.add(new String[]{"air", "lime_dye"}); ModelLoadingPlugin.register(GCModelLoader.INSTANCE); - + ClientTickEvents.END_CLIENT_TICK.register(client -> { + if (!colorsInitialized) + { + if (client.player != null && client.level != null) + { + CANNED_FOOD_ITEMS.forEach(cannedFoodItem -> { + Optional cannedItem = CannedFoodItem.getContents(cannedFoodItem.getDefaultInstance()).findFirst(); + if (cannedItem.isPresent()) { + String nameComponent = cannedItem.toString(); + String itemName = extractInsideBrackets(nameComponent); + assert itemName != null; + String[] parts = itemName.split(":"); + String namespace = parts[0]; + String item = parts[1]; + for (String[] element: nameOverride) + { + if (parts[1].equals(element[0])) + { + item = element[1]; + } + } + ResourceLocation textureLocation = new ResourceLocation(namespace, "textures/item/" + item + ".png"); + int avgColor = getAverageColor(textureLocation); + cannedFoodItem.setColor(avgColor); + } + }); + colorsInitialized = true; + } + } + }); + //For every edible food create a creative item of that canned food type + for (Item item : BuiltInRegistries.ITEM) + { + if (item.getFoodProperties() != null) + { + if (!(item instanceof CannedFoodItem)) + { + registerCan(item.getDefaultInstance()); + } + } + } Constant.LOGGER.info("Client initialization complete. (Took {}ms.)", System.currentTimeMillis() - startInitTime); } @@ -200,4 +265,13 @@ public static void init() { GCDimensionEffects.register(); } + + public static String extractInsideBrackets(String input) { + int startIndex = input.indexOf('{'); + int endIndex = input.indexOf('}'); + if (startIndex != -1 && endIndex != -1 && startIndex < endIndex) { + return input.substring(startIndex + 1, endIndex); + } + return null; + } } diff --git a/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidDimensionEffects.java b/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidDimensionEffects.java new file mode 100644 index 000000000..bc29be7d7 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidDimensionEffects.java @@ -0,0 +1,78 @@ +/* + * Copyright (c) 2019-2024 Team Galacticraft + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package dev.galacticraft.mod.client.render.dimension; + +import dev.galacticraft.mod.api.dimension.GalacticDimensionEffects; +import dev.galacticraft.mod.particle.ScaleParticleType; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.Camera; +import net.minecraft.client.Minecraft; +import net.minecraft.client.ParticleStatus; +import net.minecraft.client.multiplayer.ClientLevel; +import net.minecraft.client.renderer.DimensionSpecialEffects; +import net.minecraft.client.renderer.LevelRenderer; +import net.minecraft.core.BlockPos; +import net.minecraft.core.Direction; +import net.minecraft.core.particles.ParticleOptions; +import net.minecraft.core.particles.ParticleTypes; +import net.minecraft.sounds.SoundEvents; +import net.minecraft.sounds.SoundSource; +import net.minecraft.tags.FluidTags; +import net.minecraft.util.CubicSampler; +import net.minecraft.util.Mth; +import net.minecraft.util.RandomSource; +import net.minecraft.world.level.biome.Biome; +import net.minecraft.world.level.block.Blocks; +import net.minecraft.world.level.block.CampfireBlock; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.levelgen.Heightmap; +import net.minecraft.world.level.material.FluidState; +import net.minecraft.world.phys.Vec3; +import net.minecraft.world.phys.shapes.VoxelShape; +import org.jetbrains.annotations.NotNull; + +@Environment(EnvType.CLIENT) +public class AsteroidDimensionEffects extends DimensionSpecialEffects { + private static final float[] FOG_COLOR = {0.0F, 0.0F, 0.0F, 0.0F}; + public static final AsteroidDimensionEffects INSTANCE = new AsteroidDimensionEffects(); + + private AsteroidDimensionEffects() { + super(Float.NaN, false, SkyType.NORMAL, true, true); + } + + @Override + public Vec3 getBrightnessDependentFogColor(Vec3 color, float sunHeight) { + return Vec3.ZERO; + } + + @Override + public boolean isFoggyAt(int camX, int camY) { + return false; + } + + @Override + public float[] getSunriseColor(float skyAngle, float tickDelta) { + return FOG_COLOR; + } +} diff --git a/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidSkyRenderer.java b/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidSkyRenderer.java new file mode 100644 index 000000000..9755148fe --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/client/render/dimension/AsteroidSkyRenderer.java @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2019-2024 Team Galacticraft + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package dev.galacticraft.mod.client.render.dimension; + +import com.mojang.blaze3d.platform.GlStateManager; +import com.mojang.blaze3d.systems.RenderSystem; +import com.mojang.blaze3d.vertex.*; +import com.mojang.math.Axis; +import dev.galacticraft.mod.Constant; +import net.fabricmc.fabric.api.client.rendering.v1.DimensionRenderingRegistry; +import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderContext; +import net.minecraft.client.Minecraft; +import net.minecraft.client.multiplayer.ClientLevel; +import net.minecraft.client.renderer.FogRenderer; +import net.minecraft.client.renderer.GameRenderer; +import net.minecraft.client.renderer.ShaderInstance; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.util.RandomSource; +import net.minecraft.world.phys.Vec3; +import org.joml.Matrix4f; +import org.lwjgl.opengl.GL11; + +public class AsteroidSkyRenderer extends SpaceSkyRenderer { + public static final AsteroidSkyRenderer INSTANCE = new AsteroidSkyRenderer(); + private static final ResourceLocation EARTH_TEXTURE = Constant.id("textures/gui/celestialbodies/earth.png"); + private static final ResourceLocation SUN_TEXTURE = Constant.id("textures/gui/celestialbodies/sun.png"); + + @Override + public void render(WorldRenderContext context) { + context.profiler().push("asteroid_sky_renderer"); + RenderSystem.disableBlend(); + RenderSystem.depthMask(false); + + final PoseStack matrices = context.matrixStack(); + final BufferBuilder buffer = Tesselator.getInstance().getBuilder(); + + context.profiler().push("stars"); + matrices.pushPose(); + matrices.mulPose(Axis.YP.rotationDegrees((context.world().getTimeOfDay(context.tickDelta()) * 360.0f) - 90F)); + matrices.mulPose(Axis.XP.rotationDegrees(context.world().getTimeOfDay(context.tickDelta()) * 360.0f)); + matrices.mulPose(Axis.YP.rotationDegrees(-19.0F)); + + this.starManager.render(context.matrixStack(), context.projectionMatrix(), context.world(), context.tickDelta()); + + matrices.popPose(); + context.profiler().pop(); + + context.profiler().push("sun"); + matrices.pushPose(); + + matrices.mulPose(Axis.YP.rotationDegrees(-90.0F)); + matrices.mulPose(Axis.XP.rotationDegrees(context.world().getTimeOfDay(context.tickDelta()) * 360.0f)); + + Matrix4f matrix = matrices.last().pose(); + RenderSystem.setShaderColor(1.0F, 1.0F, 1.0F, 1.0F); + float size = 20.0F; + RenderSystem.setShader(GameRenderer::getPositionTexShader); + RenderSystem.setShaderTexture(0, SUN_TEXTURE); + buffer.begin(VertexFormat.Mode.QUADS, DefaultVertexFormat.POSITION_TEX); + buffer.vertex(matrix, -size, 100.0F, -size).uv(0.0F, 0.0F).endVertex(); + buffer.vertex(matrix, size, 100.0F, -size).uv(1.0F, 0.0F).endVertex(); + buffer.vertex(matrix, size, 100.0F, size).uv(1.0F, 1.0F).endVertex(); + buffer.vertex(matrix, -size, 100.0F, size).uv(0.0F, 1.0F).endVertex(); + BufferUploader.drawWithShader(buffer.end()); + + matrices.popPose(); + context.profiler().pop(); + + context.profiler().push("earth"); + matrices.pushPose(); + matrix = matrices.last().pose(); + + size = 10.0F; + assert Minecraft.getInstance().player != null; + float earthRotation = (float) (context.world().getSharedSpawnPos().getZ() - Minecraft.getInstance().player.getZ()) * 0.01F; + matrices.scale(0.6F, 0.6F, 0.6F); + matrices.mulPose(Axis.XP.rotationDegrees((context.world().getTimeOfDay(context.tickDelta()) * 360.0F) * 0.001F)); + matrices.mulPose(Axis.XP.rotationDegrees(earthRotation + 200.0F)); + + RenderSystem.setShaderTexture(0, EARTH_TEXTURE); + + buffer.begin(VertexFormat.Mode.QUADS, DefaultVertexFormat.POSITION_TEX); + buffer.vertex(matrix, -size, -100.0F, size).uv(0.0F, 1.0F).endVertex(); + buffer.vertex(matrix, size, -100.0F, size).uv(1.0F, 1.0F).endVertex(); + buffer.vertex(matrix, size, -100.0F, -size).uv(1.0F, 0.0F).endVertex(); + buffer.vertex(matrix, -size, -100.0F, -size).uv(0.0F, 0.0F).endVertex(); + BufferUploader.drawWithShader(buffer.end()); + + context.profiler().pop(); + matrices.popPose(); + + RenderSystem.depthMask(true); + context.profiler().pop(); + } +} diff --git a/src/main/java/dev/galacticraft/mod/client/render/dimension/GCDimensionEffects.java b/src/main/java/dev/galacticraft/mod/client/render/dimension/GCDimensionEffects.java index d94269393..773b02f93 100644 --- a/src/main/java/dev/galacticraft/mod/client/render/dimension/GCDimensionEffects.java +++ b/src/main/java/dev/galacticraft/mod/client/render/dimension/GCDimensionEffects.java @@ -30,6 +30,7 @@ public class GCDimensionEffects { public static final ResourceLocation MOON = Constant.id("moon"); public static final ResourceLocation VENUS = Constant.id("venus"); + public static final ResourceLocation ASTEROID = Constant.id("asteroid"); public static void register() { DimensionRenderingRegistry.registerDimensionEffects(MOON, MoonDimensionEffects.INSTANCE); @@ -41,5 +42,10 @@ public static void register() { DimensionRenderingRegistry.registerCloudRenderer(GCDimensions.VENUS, EmptyCloudRenderer.INSTANCE); DimensionRenderingRegistry.registerWeatherRenderer(GCDimensions.VENUS, VenusWeatherRenderer.INSTANCE); DimensionRenderingRegistry.registerSkyRenderer(GCDimensions.VENUS, VenusSkyRenderer.INSTANCE); + + DimensionRenderingRegistry.registerDimensionEffects(ASTEROID, AsteroidDimensionEffects.INSTANCE); + DimensionRenderingRegistry.registerCloudRenderer(GCDimensions.ASTEROID, EmptyCloudRenderer.INSTANCE); + DimensionRenderingRegistry.registerWeatherRenderer(GCDimensions.ASTEROID, EmptyWeatherRenderer.INSTANCE); + DimensionRenderingRegistry.registerSkyRenderer(GCDimensions.ASTEROID, AsteroidSkyRenderer.INSTANCE); } } diff --git a/src/main/java/dev/galacticraft/mod/compat/AppleSkinEventHandler.java b/src/main/java/dev/galacticraft/mod/compat/AppleSkinEventHandler.java new file mode 100644 index 000000000..c71cbdf0c --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/compat/AppleSkinEventHandler.java @@ -0,0 +1,27 @@ +package dev.galacticraft.mod.compat; + +import net.minecraft.world.food.FoodProperties; +import squeek.appleskin.api.AppleSkinApi; +import squeek.appleskin.api.event.FoodValuesEvent; +import squeek.appleskin.api.food.FoodValues; + +import static dev.galacticraft.mod.content.item.CannedFoodItem.getCanFoodProperties; +import static dev.galacticraft.mod.content.item.CannedFoodItem.isCannedFoodItem; + +public class AppleSkinEventHandler implements AppleSkinApi +{ + + @Override + public void registerEvents() { + FoodValuesEvent.EVENT.register(foodValuesEvent -> { + if (isCannedFoodItem(foodValuesEvent.itemStack)) + { + FoodProperties foodProperties = getCanFoodProperties(foodValuesEvent.itemStack); + if (foodProperties != null) + { + foodValuesEvent.modifiedFoodValues = new FoodValues(foodProperties.getNutrition(), foodProperties.getSaturationModifier()); + } + } + }); + } +} diff --git a/src/main/java/dev/galacticraft/mod/content/CannedFoodTooltip.java b/src/main/java/dev/galacticraft/mod/content/CannedFoodTooltip.java new file mode 100644 index 000000000..15c4a90d2 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/CannedFoodTooltip.java @@ -0,0 +1,18 @@ +package dev.galacticraft.mod.content; + +import net.minecraft.core.NonNullList; +import net.minecraft.world.inventory.tooltip.TooltipComponent; +import net.minecraft.world.item.ItemStack; + +public class CannedFoodTooltip implements TooltipComponent { + private final NonNullList items; + + public CannedFoodTooltip(NonNullList nonNullList) + { + this.items = nonNullList; + } + + public NonNullList getItems() { + return this.items; + } +} diff --git a/src/main/java/dev/galacticraft/mod/content/ClientCannedFoodTooltip.java b/src/main/java/dev/galacticraft/mod/content/ClientCannedFoodTooltip.java new file mode 100644 index 000000000..ec3b78ad0 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/ClientCannedFoodTooltip.java @@ -0,0 +1,109 @@ +package dev.galacticraft.mod.content; + +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.gui.Font; +import net.minecraft.client.gui.GuiGraphics; +import net.minecraft.client.gui.screens.inventory.AbstractContainerScreen; +import net.minecraft.client.gui.screens.inventory.tooltip.ClientBundleTooltip; +import net.minecraft.client.gui.screens.inventory.tooltip.ClientTooltipComponent; +import net.minecraft.core.NonNullList; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.world.inventory.tooltip.BundleTooltip; +import net.minecraft.world.inventory.tooltip.TooltipComponent; +import net.minecraft.world.item.ItemStack; + +@Environment(EnvType.CLIENT) +public class ClientCannedFoodTooltip implements ClientTooltipComponent { + private static final ResourceLocation BACKGROUND_SPRITE = new ResourceLocation("container/bundle/background"); + private static final int MARGIN_Y = 4; + private static final int BORDER_WIDTH = 1; + private static final int SLOT_SIZE_X = 18; + private static final int SLOT_SIZE_Y = 20; + private final NonNullList items; + + public ClientCannedFoodTooltip(CannedFoodTooltip cannedFoodTooltip) { + this.items = cannedFoodTooltip.getItems(); + } + + public int getHeight() { + return this.backgroundHeight() + 4; + } + + public int getWidth(Font textRenderer) { + return this.backgroundWidth(); + } + + private int backgroundWidth() { + return this.gridSizeX() * 18 + 2; + } + + private int backgroundHeight() { + return this.gridSizeY() * 20 + 2; + } + + public void renderImage(Font textRenderer, int x, int y, GuiGraphics context) { + int i = this.gridSizeX(); + int j = this.gridSizeY(); + //creates a background panel over the items + //context.blitSprite(BACKGROUND_SPRITE, x, y, this.backgroundWidth(), this.backgroundHeight()); + int weight = 1; + boolean bl = weight >= 64; + int k = 0; + + for(int l = 0; l < j; ++l) { + for(int m = 0; m < i; ++m) { + int n = x + m * 18 + 1; + int o = y + l * 20 + 1; + this.renderSlot(n, o, k++, bl, context, textRenderer); + } + } + + } + + private void renderSlot(int x, int y, int index, boolean shouldBlock, GuiGraphics context, Font textRenderer) { + if (index >= this.items.size()) { + //creates a ending slot used for bundle not items contained + //this.blit(context, x, y, shouldBlock ? ClientCannedFoodTooltip.Texture.BLOCKED_SLOT : ClientCannedFoodTooltip.Texture.SLOT); + } else { + ItemStack itemStack = (ItemStack)this.items.get(index); + this.blit(context, x, y, ClientCannedFoodTooltip.Texture.SLOT); + context.renderItem(itemStack, x + 1, y + 1, index); + context.renderItemDecorations(textRenderer, itemStack, x + 1, y + 1); + //used to highlight the item slot + //not needed +// if (index == 0) { +// AbstractContainerScreen.renderSlotHighlight(context, x + 1, y + 1, 0); +// } + + } + } + + private void blit(GuiGraphics context, int x, int y, ClientCannedFoodTooltip.Texture sprite) { + context.blitSprite(sprite.sprite, x, y, 0, sprite.w, sprite.h); + } + + private int gridSizeX() { + return Math.max(2, (int)Math.ceil(Math.sqrt((double)this.items.size() + 1.0))); + } + + private int gridSizeY() { + return (int)Math.ceil(((double)this.items.size() + 1.0) / (double)this.gridSizeX()); + } + + @Environment(EnvType.CLIENT) + private static enum Texture { + BLOCKED_SLOT(new ResourceLocation("container/bundle/blocked_slot"), 18, 20), + SLOT(new ResourceLocation("container/bundle/slot"), 18, 20); + + public final ResourceLocation sprite; + public final int w; + public final int h; + + private Texture(ResourceLocation resourceLocation, int j, int k) { + this.sprite = resourceLocation; + this.w = j; + this.h = k; + } + } +} diff --git a/src/main/java/dev/galacticraft/mod/content/GCBlocks.java b/src/main/java/dev/galacticraft/mod/content/GCBlocks.java index fcae3dd5b..150097925 100644 --- a/src/main/java/dev/galacticraft/mod/content/GCBlocks.java +++ b/src/main/java/dev/galacticraft/mod/content/GCBlocks.java @@ -220,6 +220,10 @@ public class GCBlocks { public static final Block DESH_ORE = BLOCKS.register(Constant.Block.DESH_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 5.0F, false))); + public static final Block MARS_IRON_ORE = BLOCKS.register(Constant.Block.MARS_IRON_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 3.0F, false))); + public static final Block MARS_TIN_ORE = BLOCKS.register(Constant.Block.MARS_TIN_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 3.0F, false))); + public static final Block MARS_COPPER_ORE = BLOCKS.register(Constant.Block.MARS_COPPER_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 3.0F, false))); + public static final Block ILMENITE_ORE = BLOCKS.register(Constant.Block.ILMENITE_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 5.0F, false))); public static final Block GALENA_ORE = BLOCKS.register(Constant.Block.GALENA_ORE, new DropExperienceBlock(ConstantInt.of(0), oreSettings(3.0F, 5.0F, false))); @@ -290,7 +294,7 @@ public class GCBlocks { public static final AirlockBlock AIR_LOCK_FRAME = BLOCKS.register(Constant.Block.AIR_LOCK_FRAME, new AirlockBlock(false, BlockBehaviour.Properties.ofFullCopy(Blocks.IRON_BLOCK))); public static final AirlockBlock AIR_LOCK_CONTROLLER = BLOCKS.register(Constant.Block.AIR_LOCK_CONTROLLER, new AirlockBlock(true, BlockBehaviour.Properties.ofFullCopy(Blocks.IRON_BLOCK))); - public static final Block AIR_LOCK_SEAL = BLOCKS.register(Constant.Block.AIR_LOCK_SEAL, new Block(BlockBehaviour.Properties.ofFullCopy(AIR_LOCK_FRAME))); + public static final Block AIR_LOCK_SEAL = BLOCKS.register(Constant.Block.AIR_LOCK_SEAL, new AirlockSealBlock(BlockBehaviour.Properties.ofFullCopy(AIR_LOCK_FRAME))); public static Block register(String id, Block block) { return Registry.register(BuiltInRegistries.BLOCK, Constant.id(id), block); diff --git a/src/main/java/dev/galacticraft/mod/content/GCCelestialBodies.java b/src/main/java/dev/galacticraft/mod/content/GCCelestialBodies.java index 2b1ef7471..ce3e7c43e 100644 --- a/src/main/java/dev/galacticraft/mod/content/GCCelestialBodies.java +++ b/src/main/java/dev/galacticraft/mod/content/GCCelestialBodies.java @@ -219,8 +219,8 @@ public static void bootstrapRegistries(BootstapContext> cont ))); context.register(ASTEROIDS, DecorativePlanet.INSTANCE.configure(new DecorativePlanetConfig( - Component.translatable(Translations.CelestialBody.ASTEROIDS), - Component.translatable(Translations.CelestialBody.ASTEROIDS_DESC), + Component.translatable(Translations.CelestialBody.ASTEROID), + Component.translatable(Translations.CelestialBody.ASTEROID_DESC), sol, OrbitalCelestialPositionType.INSTANCE.configure(new OrbitalCelestialPositionConfig(45.0F, 1.375F, 0.0F, true)), SpinningIconCelestialDisplayType.INSTANCE.configure(new IconCelestialDisplayConfig(Constant.id("textures/gui/celestialbodies/asteroid.png"), 0, 0, 16, 16)), diff --git a/src/main/java/dev/galacticraft/mod/content/GCChunkGenerator.java b/src/main/java/dev/galacticraft/mod/content/GCChunkGenerator.java new file mode 100644 index 000000000..48362a4e8 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/GCChunkGenerator.java @@ -0,0 +1,26 @@ +package dev.galacticraft.mod.content; + +import com.mojang.serialization.Codec; +import dev.galacticraft.mod.Constant; +import dev.galacticraft.mod.world.gen.custom.AsteroidChunkGenerator; +import net.minecraft.core.Registry; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.world.level.chunk.ChunkGenerator; +import net.minecraft.world.level.storage.DimensionDataStorage; + + +public class GCChunkGenerator { + public static final GCChunkGeneratorRegistry CHUNK_GENERATOR = new GCChunkGeneratorRegistry(); + + + public static final Codec ASTEROIDS = CHUNK_GENERATOR.register("asteroid_chunk_generator", AsteroidChunkGenerator.CODEC); + + public static Codec register(String id, Codec codec) { + return Registry.register(BuiltInRegistries.CHUNK_GENERATOR, Constant.id(id), codec); + } + + public static void register() { + + } + +} diff --git a/src/main/java/dev/galacticraft/mod/content/GCChunkGeneratorRegistry.java b/src/main/java/dev/galacticraft/mod/content/GCChunkGeneratorRegistry.java new file mode 100644 index 000000000..3f894837b --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/GCChunkGeneratorRegistry.java @@ -0,0 +1,11 @@ +package dev.galacticraft.mod.content; + +import com.mojang.serialization.Codec; +import net.minecraft.core.registries.BuiltInRegistries; +import net.minecraft.world.level.chunk.ChunkGenerator; + +public class GCChunkGeneratorRegistry extends GCRegistry> { + public GCChunkGeneratorRegistry() { + super(BuiltInRegistries.CHUNK_GENERATOR); + } +} diff --git a/src/main/java/dev/galacticraft/mod/content/block/entity/AirlockControllerBlockEntity.java b/src/main/java/dev/galacticraft/mod/content/block/entity/AirlockControllerBlockEntity.java index 108249638..4f3b8ff83 100644 --- a/src/main/java/dev/galacticraft/mod/content/block/entity/AirlockControllerBlockEntity.java +++ b/src/main/java/dev/galacticraft/mod/content/block/entity/AirlockControllerBlockEntity.java @@ -26,6 +26,7 @@ import dev.galacticraft.mod.content.GCBlocks; import dev.galacticraft.mod.screen.AirlockControllerMenu; import net.minecraft.core.BlockPos; +import net.minecraft.core.Direction; import net.minecraft.network.chat.Component; import net.minecraft.world.MenuProvider; import net.minecraft.world.entity.player.Inventory; @@ -40,6 +41,8 @@ import java.util.List; +import static dev.galacticraft.mod.content.block.special.AirlockSealBlock.FACING; + public class AirlockControllerBlockEntity extends BlockEntity implements MenuProvider { public boolean redstoneActivation; public boolean playerDistanceActivation = true; @@ -63,7 +66,7 @@ public AirlockControllerBlockEntity(BlockPos blockPos, BlockState blockState) { super(GCBlockEntityTypes.AIRLOCK_CONTROLLER, blockPos, blockState); } - + public static void tick(Level level, BlockPos blockPos, BlockState blockState, AirlockControllerBlockEntity blockEntity) { blockEntity.tick(); } @@ -170,6 +173,8 @@ private void sealAirLock() int y = (this.lastProtocol.maxY + this.lastProtocol.minY) / 2; int z = (this.lastProtocol.maxZ + this.lastProtocol.minZ) / 2; + boolean facingNorth = (this.lastProtocol.maxX - this.lastProtocol.minX) == 0; + if (!this.getLevel().getBlockState(new BlockPos(x, y, z)).is(GCBlocks.AIR_LOCK_SEAL)) { // this.getLevel().playSound(null, x, y, z, GCSounds.openAirLock, SoundSource.BLOCKS, 1.0F, 1.0F); @@ -186,7 +191,13 @@ private void sealAirLock() BlockPos pos = new BlockPos(x, y, z); if (this.getLevel().getBlockState(pos).isAir()) { - this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState(), 3); + if (facingNorth) + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.EAST), 3); + }else + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.NORTH), 3); + } } } } @@ -202,7 +213,13 @@ private void sealAirLock() BlockPos pos = new BlockPos(x, y, z); if (this.getLevel().getBlockState(pos).isAir()) { - this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState(), 3); + if (facingNorth) + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.EAST), 3); + }else + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.NORTH), 3); + } } } } @@ -215,7 +232,13 @@ private void sealAirLock() BlockPos pos = new BlockPos(x, y, z); if (this.getLevel().getBlockState(pos).isAir()) { - this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState(), 3); + if (facingNorth) + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.EAST), 3); + }else + { + this.getLevel().setBlock(pos, GCBlocks.AIR_LOCK_SEAL.defaultBlockState().setValue(FACING, Direction.NORTH), 3); + } } } } diff --git a/src/main/java/dev/galacticraft/mod/content/block/special/AirlockSealBlock.java b/src/main/java/dev/galacticraft/mod/content/block/special/AirlockSealBlock.java new file mode 100644 index 000000000..9af7ea0e1 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/block/special/AirlockSealBlock.java @@ -0,0 +1,64 @@ +package dev.galacticraft.mod.content.block.special; + +import com.mojang.serialization.MapCodec; +import net.minecraft.core.BlockPos; +import net.minecraft.core.Direction; +import net.minecraft.world.item.context.BlockPlaceContext; +import net.minecraft.world.level.BlockGetter; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.HorizontalDirectionalBlock; +import net.minecraft.world.level.block.RotatedPillarBlock; +import net.minecraft.world.level.block.Rotation; +import net.minecraft.world.level.block.state.BlockBehaviour; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.block.state.StateDefinition; +import net.minecraft.world.level.block.state.properties.*; +import net.minecraft.world.phys.shapes.CollisionContext; +import net.minecraft.world.phys.shapes.VoxelShape; + +public class AirlockSealBlock extends Block { + public static final MapCodec CODEC = simpleCodec(AirlockSealBlock::new); + public static final DirectionProperty FACING = BlockStateProperties.HORIZONTAL_FACING; + + + @Override + public MapCodec codec() { + return CODEC; + } + public AirlockSealBlock(Properties properties) { + super(properties); + this.registerDefaultState(this.defaultBlockState().setValue(FACING, Direction.NORTH)); + } + + + + protected static final VoxelShape SHAPE_NORTH = Block.box(0.0, 0.0, 4.0, 16.0, 16.0, 12.0); + protected static final VoxelShape SHAPE_EAST = Block.box(4.0, 0.0, 0.0, 12.0, 16.0, 16.0); + + @Override + public VoxelShape getShape(BlockState state, BlockGetter world, BlockPos pos, CollisionContext context) { + if (state.getValue(FACING) == Direction.NORTH || state.getValue(FACING) == Direction.SOUTH) + { + return SHAPE_NORTH; + }else + { + return SHAPE_EAST; + } + } + + @Override + public BlockState rotate(BlockState blockState, Rotation rotation) { + return blockState.setValue(FACING, rotation.rotate(blockState.getValue(FACING))); + } + + @Override + protected void createBlockStateDefinition(StateDefinition.Builder builder) { + builder.add(FACING); + } + + @Override + public BlockState getStateForPlacement(BlockPlaceContext blockPlaceContext) { + return this.defaultBlockState().setValue(FACING, blockPlaceContext.getHorizontalDirection().getOpposite()); + } + +} \ No newline at end of file diff --git a/src/main/java/dev/galacticraft/mod/content/entity/SmallAsteroid.java b/src/main/java/dev/galacticraft/mod/content/entity/SmallAsteroid.java new file mode 100644 index 000000000..dd9353e3f --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/content/entity/SmallAsteroid.java @@ -0,0 +1,35 @@ +package dev.galacticraft.mod.content.entity; + +import net.minecraft.nbt.CompoundTag; +import net.minecraft.world.entity.Entity; +import net.minecraft.world.entity.EntityType; +import net.minecraft.world.level.Level; + +public class SmallAsteroid extends Entity { + + //private static final DataParameter SPIN_PITCH = EntityDataManager.createKey(EntitySmallAsteroid.class, DataSerializers.FLOAT); + //private static final DataParameter SPIN_YAW = EntityDataManager.createKey(EntitySmallAsteroid.class, DataSerializers.FLOAT); + //private static final DataParameter ASTEROID_TYPE = EntityDataManager.createKey(EntitySmallAsteroid.class, DataSerializers.VARINT); + public float spinPitch; + public float spinYaw; + public int type; + private boolean firstUpdate = true; + public SmallAsteroid(EntityType entityType, Level level) { + super(entityType, level); + } + + @Override + protected void defineSynchedData() { + + } + + @Override + protected void readAdditionalSaveData(CompoundTag nbt) { + + } + + @Override + protected void addAdditionalSaveData(CompoundTag nbt) { + + } +} diff --git a/src/main/java/dev/galacticraft/mod/content/item/CannedFoodItem.java b/src/main/java/dev/galacticraft/mod/content/item/CannedFoodItem.java index 381b36c94..6e2c9e0d7 100644 --- a/src/main/java/dev/galacticraft/mod/content/item/CannedFoodItem.java +++ b/src/main/java/dev/galacticraft/mod/content/item/CannedFoodItem.java @@ -22,32 +22,371 @@ package dev.galacticraft.mod.content.item; +import dev.galacticraft.mod.Constant; +import dev.galacticraft.mod.content.CannedFoodTooltip; +import net.fabricmc.fabric.api.item.v1.FabricItemStack; +import net.fabricmc.fabric.api.itemgroup.v1.ItemGroupEvents; +import net.minecraft.ChatFormatting; +import net.minecraft.advancements.CriteriaTriggers; +import net.minecraft.client.Minecraft; +import net.minecraft.core.NonNullList; +import net.minecraft.core.registries.Registries; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.ListTag; +import net.minecraft.nbt.Tag; +import net.minecraft.network.chat.Component; +import net.minecraft.resources.ResourceKey; +import net.minecraft.server.level.ServerPlayer; +import net.minecraft.stats.Stats; import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.player.Player; +import net.minecraft.world.food.FoodProperties; +import net.minecraft.world.inventory.tooltip.TooltipComponent; import net.minecraft.world.item.Item; import net.minecraft.world.item.ItemStack; +import net.minecraft.world.item.TooltipFlag; import net.minecraft.world.level.Level; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.awt.*; +import java.util.*; +import java.util.List; +import java.util.function.BiConsumer; +import java.util.function.BinaryOperator; +import java.util.function.Function; +import java.util.function.Supplier; +import java.util.stream.Collector; +import java.util.stream.Stream; + +import static dev.galacticraft.mod.content.item.GCItems.CANNED_FOOD; +import static dev.galacticraft.mod.content.item.GCItems.EMPTY_CANNED_FOOD; + +public class CannedFoodItem extends Item implements FabricItemStack { + private int color; + + + @Override + public @NotNull ItemStack finishUsingItem(ItemStack itemStack, Level level, LivingEntity livingEntity) { + if (!level.isClientSide) + { + int consumingItems = getItemsToBeConsumed(itemStack); + assert itemStack.getTag() != null; + CompoundTag copyTag = itemStack.getTag().copy(); + super.finishUsingItem(itemStack, level, livingEntity); + if (livingEntity instanceof ServerPlayer serverPlayer) { + CriteriaTriggers.CONSUME_ITEM.trigger(serverPlayer, itemStack); + serverPlayer.awardStat(Stats.ITEM_USED.get(this)); + } + ItemStack can = new ItemStack(CANNED_FOOD); + can.setTag(copyTag.copy()); + for (int i = 0; i < consumingItems; i++) { + removeOne(can); + System.out.println("removed item"); + System.out.println(can.getTag()); + } + if (itemStack.isEmpty()) { + if (getContents(can).findAny().isEmpty()) + { + can = new ItemStack(EMPTY_CANNED_FOOD); + } + return can; + }else + { + if (livingEntity instanceof Player player) { + if (!player.getAbilities().instabuild) { + + if (getContents(can).findAny().isEmpty()) + { + can = new ItemStack(EMPTY_CANNED_FOOD); + } + if (!player.getInventory().add(can)) { + player.drop(can, false); + } + } + } + } + } + return itemStack; + } -public class CannedFoodItem extends Item { public CannedFoodItem(Properties settings) { super(settings); + this.color = 0; } @Override - public ItemStack finishUsingItem(ItemStack itemStack, Level level, LivingEntity livingEntity) { - super.finishUsingItem(itemStack, level, livingEntity); - if (itemStack.isEmpty()) { - return new ItemStack(GCItems.TIN_CANISTER); + public void onCraftedBy(ItemStack stack, Level world, Player player) { + super.onCraftedBy(stack, world, player); + // Add functionality when the item is crafted (optional) + } + + public static void registerCan(ItemStack cannedFoodType) + { + ItemGroupEvents.modifyEntriesEvent(ResourceKey.create(Registries.CREATIVE_MODE_TAB, Constant.id(Constant.Item.ITEM_GROUP_CANS))).register(entries -> { + ItemStack cannedFoodItem = CANNED_FOOD.getDefaultInstance(); + add(cannedFoodItem, cannedFoodType); + entries.accept(cannedFoodItem); + }); + } + + @Override + public @NotNull Component getName(ItemStack stack) { + if (getContents(stack).findAny().isEmpty()) + { + return Component.literal("Empty Food Can"); + }else + { + String result = getContents(stack) + .map(CannedFoodItem::getItemDisplayName) + .collect(new TopNCollector<>(3)); + return Component.literal("Canned " + result); } + } - if (livingEntity instanceof Player player) { - if (!player.getAbilities().instabuild) { - ItemStack canStack = new ItemStack(GCItems.TIN_CANISTER); - if (!player.getInventory().add(canStack)) { - player.drop(canStack, false); + public void setColor(int color) + { + this.color = color; + } + + public int getColor(int layer) { + // Specify color for each layer, you can add more layers and their colors + if (layer == 1) { + return this.color; + } else { + return 0xFFFFFF; // Default color (no tint) + } + } + + @Override + public @NotNull Optional getTooltipImage(ItemStack stack) + { + if (getContents(stack).findAny().isPresent()) + { + NonNullList nonNullList = NonNullList.create(); + Stream stream = getContents(stack); + Objects.requireNonNull(nonNullList); + stream.forEach(nonNullList::add); + return Optional.of(new CannedFoodTooltip(nonNullList)); + }else + { + return Optional.empty(); + } + } + + @Override + public void appendHoverText(ItemStack stack, @Nullable Level world, List tooltip, TooltipFlag context) { + if (getContents(stack).findAny().isPresent()) { + tooltip.add(Component.literal("Total Nutrition: " + getTotalNutrition(stack)).withColor(ChatFormatting.DARK_GRAY.getColor())); + } + } + + public static Stream getContents(ItemStack stack) { + CompoundTag compoundTag = stack.getTag(); + if (compoundTag == null) { + return Stream.empty(); + } else { + ListTag listTag = compoundTag.getList("Items", 10); + Stream stream = listTag.stream(); + Objects.requireNonNull(CompoundTag.class); + return stream.map(CompoundTag.class::cast).map(ItemStack::of); + } + } + + public static boolean isCannedFoodItem(ItemStack stack) { + return stack.getItem() instanceof CannedFoodItem; + } + + private static void removeOne(ItemStack stack) { + CompoundTag compoundTag = stack.getOrCreateTag(); + if (compoundTag.contains("Items")) + { + ListTag listTag = compoundTag.getList("Items", 10); + if (!listTag.isEmpty()) + { + Tag tag = listTag.get(0); + if (tag instanceof CompoundTag tagCompound) { + ItemStack itemStack = ItemStack.of(tagCompound); + int itemCount = itemStack.getCount(); + if (itemCount != 1) + { + itemStack.shrink(1); + CompoundTag compoundNew = new CompoundTag(); + itemStack.save(compoundNew); + listTag.set(0, compoundNew); + }else + { + listTag.remove(0); + } + } + if (listTag.isEmpty()) { + stack.removeTagKey("Items"); } } } - return itemStack; + } + + private static void add(ItemStack cannedFood, ItemStack stack) { + if (!stack.isEmpty() && stack.getItem().canFitInsideContainerItems()) { + CompoundTag compoundTag = cannedFood.getOrCreateTag(); + if (!compoundTag.contains("Items")) { + compoundTag.put("Items", new ListTag()); + } + + //the max that the canned food item can hold + int k = Math.min(stack.getCount(), 16); + if (k != 0) + { + ListTag listTag = compoundTag.getList("Items", 10); + ItemStack itemStack2 = stack.copyWithCount(k); + CompoundTag compoundTag3 = new CompoundTag(); + itemStack2.save(compoundTag3); + listTag.add(0, compoundTag3); + } + } + } + + private static String getItemDisplayName(ItemStack itemStack) { + Component displayName = itemStack.getDisplayName(); + return stripControlCodes(displayName.getString()); + } + + private static String stripControlCodes(String input) { + return input.replaceAll("]", "").replaceAll("\\[", ""); + } + + public static class TopNCollector implements Collector, String> { + private final int n; + + public TopNCollector(int n) { + this.n = n; + } + + @Override + public Supplier> supplier() { + return ArrayList::new; + } + + @Override + public BiConsumer, T> accumulator() { + return (list, item) -> { + if (list.size() < n) { + list.add(item); + } else if (list.size() == n) { + list.add((T)"..."); + } + }; + } + + @Override + public BinaryOperator> combiner() { + return (list1, list2) -> { + list1.addAll(list2); + if (list1.size() > n) { + list1 = list1.subList(0, n); + list1.add((T) "..."); + } + return list1; + }; + } + + @Override + public Function, String> finisher() { + return list -> { + boolean greaterThanN = false; + if (list.size() > n) { + greaterThanN = true; + list.remove(3); + } + String string = String.join(", ", list.toArray(new String[0])); + if (greaterThanN) + { + string = string + "..."; + } + return string; + }; + } + + @Override + public Set characteristics() { + return new HashSet<>(); + } + } + + public static FoodProperties getCanFoodProperties(ItemStack stack) { + int playerHunger = 0; + if (Minecraft.getInstance().player != null) { + playerHunger = Minecraft.getInstance().player.getFoodData().getFoodLevel(); + } + int nutritionRequired = 20 - playerHunger; + int canNutrition = 0; + float canSaturation = 0f; + if (nutritionRequired != 0) + { + Stream stream = getContents(stack); + for (ItemStack foodItem : stream.toList()) + { + int itemCount = foodItem.getCount(); + for (int i = 0; i < itemCount; i++) + { + canNutrition += Objects.requireNonNull(foodItem.getFoodComponent()).getNutrition(); + canSaturation += foodItem.getFoodComponent().getSaturationModifier(); + if (canNutrition >= nutritionRequired) + { + return new FoodProperties.Builder().nutrition(canNutrition).saturationMod(canSaturation).build(); + } + } + } + if (canNutrition == 0) + { + return null; + }else + { + return new FoodProperties.Builder().nutrition(canNutrition).saturationMod(canSaturation).build(); + } + } + return null; + } + + public static int getTotalNutrition(ItemStack stack) { + int canNutrition = 0; + Stream stream = getContents(stack); + for (ItemStack foodItem : stream.toList()) + { + int itemCount = foodItem.getCount(); + for (int i = 0; i < itemCount; i++) + { + canNutrition += Objects.requireNonNull(foodItem.getFoodComponent()).getNutrition(); + } + } + return canNutrition; + } + + public static int getItemsToBeConsumed(ItemStack stack) { + int playerHunger = 0; + if (Minecraft.getInstance().player != null) { + playerHunger = Minecraft.getInstance().player.getFoodData().getFoodLevel(); + } + int nutritionRequired = 20 - playerHunger; + int canNutrition = 0; + int itemsToBeConsumed = 0; + if (nutritionRequired != 0) + { + Stream stream = getContents(stack); + for (ItemStack foodItem : stream.toList()) + { + int itemCount = foodItem.getCount(); + for (int i = 0; i < itemCount; i++) + { + itemsToBeConsumed += 1; + canNutrition += Objects.requireNonNull(foodItem.getFoodComponent()).getNutrition(); + if (canNutrition >= nutritionRequired) + { + return itemsToBeConsumed; + } + } + } + } + return itemsToBeConsumed; } } \ No newline at end of file diff --git a/src/main/java/dev/galacticraft/mod/content/item/GCCreativeModeTabs.java b/src/main/java/dev/galacticraft/mod/content/item/GCCreativeModeTabs.java index eff54f9a4..ac0c2d3d5 100644 --- a/src/main/java/dev/galacticraft/mod/content/item/GCCreativeModeTabs.java +++ b/src/main/java/dev/galacticraft/mod/content/item/GCCreativeModeTabs.java @@ -164,11 +164,7 @@ public class GCCreativeModeTabs { output.accept(BEEF_PATTY); output.accept(CHEESEBURGER); - output.accept(CANNED_DEHYDRATED_APPLE); - output.accept(CANNED_DEHYDRATED_CARROT); - output.accept(CANNED_DEHYDRATED_MELON); - output.accept(CANNED_DEHYDRATED_POTATO); - output.accept(CANNED_BEEF); + output.accept(THROWABLE_METEOR_CHUNK); output.accept(HOT_THROWABLE_METEOR_CHUNK); @@ -413,6 +409,15 @@ public class GCCreativeModeTabs { // MACHINES }).build(); + //Todo: fix up my bad programming to be translatable + public static final CreativeModeTab CANNED_FOOD_GROUP = FabricItemGroup + .builder() + .icon(() -> new ItemStack(CANNED_FOOD)) + .title(Component.literal("Galacticraft Cans")) + .displayItems((parameters, output) -> { + output.accept(EMPTY_CANNED_FOOD); + }).build(); + public static final CreativeModeTab MACHINES_GROUP = FabricItemGroup .builder() .icon(() -> new ItemStack(GCItems.COAL_GENERATOR)) @@ -441,5 +446,6 @@ public static void register() { Registry.register(BuiltInRegistries.CREATIVE_MODE_TAB, Constant.id(Constant.Item.ITEM_GROUP), ITEMS_GROUP); Registry.register(BuiltInRegistries.CREATIVE_MODE_TAB, Constant.id(Constant.Block.ITEM_GROUP_BLOCKS), BLOCKS_GROUP); Registry.register(BuiltInRegistries.CREATIVE_MODE_TAB, Constant.id(Constant.Block.ITEM_GROUP_MACHINES), MACHINES_GROUP); + Registry.register(BuiltInRegistries.CREATIVE_MODE_TAB, Constant.id(Constant.Item.ITEM_GROUP_CANS), CANNED_FOOD_GROUP); } } \ No newline at end of file diff --git a/src/main/java/dev/galacticraft/mod/content/item/GCFoodComponent.java b/src/main/java/dev/galacticraft/mod/content/item/GCFoodComponent.java index 8eca03177..0e1f4bf3f 100644 --- a/src/main/java/dev/galacticraft/mod/content/item/GCFoodComponent.java +++ b/src/main/java/dev/galacticraft/mod/content/item/GCFoodComponent.java @@ -33,9 +33,5 @@ public class GCFoodComponent { public static final FoodProperties BEEF_PATTY = new FoodProperties.Builder().nutrition(4).saturationMod(0.8F).meat().build(); public static final FoodProperties CHEESEBURGER = new FoodProperties.Builder().nutrition(14).saturationMod(4.0F).build(); - public static final FoodProperties DEHYDRATED_APPLE = new FoodProperties.Builder().nutrition(8).saturationMod(0.3F).build(); - public static final FoodProperties DEHYDRATED_CARROT = new FoodProperties.Builder().nutrition(8).saturationMod(0.6F).build(); - public static final FoodProperties DEHYDRATED_MELON = new FoodProperties.Builder().nutrition(4).saturationMod(0.3F).build(); - public static final FoodProperties DEHYDRATED_POTATO = new FoodProperties.Builder().nutrition(2).saturationMod(0.3F).build(); - public static final FoodProperties CANNED_BEEF = new FoodProperties.Builder().nutrition(8).saturationMod(0.6F).build(); + } diff --git a/src/main/java/dev/galacticraft/mod/content/item/GCItems.java b/src/main/java/dev/galacticraft/mod/content/item/GCItems.java index a79d0cfe9..79c677549 100644 --- a/src/main/java/dev/galacticraft/mod/content/item/GCItems.java +++ b/src/main/java/dev/galacticraft/mod/content/item/GCItems.java @@ -27,25 +27,35 @@ import dev.galacticraft.mod.content.GCFluids; import dev.galacticraft.mod.content.GCRegistry; import dev.galacticraft.mod.content.GCRocketParts; +import dev.galacticraft.mod.util.TextureUtils; import dev.galacticraft.mod.util.Translations; +import net.fabricmc.fabric.api.client.model.loading.v1.ModelLoadingPlugin; import net.fabricmc.fabric.api.item.v1.FabricItemSettings; +import net.minecraft.client.Minecraft; +import net.minecraft.client.resources.model.ModelManager; import net.minecraft.core.Direction; import net.minecraft.core.Registry; import net.minecraft.core.registries.BuiltInRegistries; import net.minecraft.network.chat.Component; import net.minecraft.resources.ResourceLocation; +import net.minecraft.world.food.FoodProperties; import net.minecraft.world.item.*; import net.minecraft.world.level.ItemLike; import net.minecraft.world.level.block.DispenserBlock; +import org.intellij.lang.annotations.Identifier; import java.util.ArrayList; import java.util.List; +import static dev.galacticraft.mod.Constant.MOD_ID; + @SuppressWarnings("unused") public class GCItems { public static final GCRegistry ITEMS = new GCRegistry<>(BuiltInRegistries.ITEM); public static final List HIDDEN_ITEMS = new ArrayList<>(1); + public static final List CANNED_FOOD_ITEMS = new ArrayList<>(); + // === START BLOCKS === // TORCHES public static final Item GLOWSTONE_TORCH = ITEMS.register(Constant.Block.GLOWSTONE_TORCH, new StandingAndWallBlockItem(GCBlocks.GLOWSTONE_TORCH, GCBlocks.GLOWSTONE_WALL_TORCH, new Item.Properties(), Direction.DOWN)); @@ -163,6 +173,9 @@ public class GCItems { public static final Item LUNASLATE_TIN_ORE = new BlockItem(GCBlocks.LUNASLATE_TIN_ORE, new Item.Properties()); public static final Item ALUMINUM_ORE = new BlockItem(GCBlocks.ALUMINUM_ORE, new Item.Properties()); + public static final Item MARS_TIN_ORE = new BlockItem(GCBlocks.MARS_TIN_ORE, new Item.Properties()); + public static final Item MARS_IRON_ORE = new BlockItem(GCBlocks.MARS_IRON_ORE, new Item.Properties()); + public static final Item MARS_COPPER_ORE = new BlockItem(GCBlocks.MARS_COPPER_ORE, new Item.Properties()); public static final Item DEEPSLATE_ALUMINUM_ORE = new BlockItem(GCBlocks.DEEPSLATE_ALUMINUM_ORE, new Item.Properties()); public static final Item DESH_ORE = new BlockItem(GCBlocks.DESH_ORE, new Item.Properties()); @@ -290,13 +303,7 @@ public class GCItems { public static final Item GROUND_BEEF = ITEMS.register(Constant.Item.GROUND_BEEF, new Item(new Item.Properties().food(GCFoodComponent.GROUND_BEEF))); public static final Item BEEF_PATTY = ITEMS.register(Constant.Item.BEEF_PATTY, new Item(new Item.Properties().food(GCFoodComponent.BEEF_PATTY))); public static final Item CHEESEBURGER = ITEMS.register(Constant.Item.CHEESEBURGER, new Item(new Item.Properties().food(GCFoodComponent.CHEESEBURGER))); - - public static final Item CANNED_DEHYDRATED_APPLE = new CannedFoodItem(new Item.Properties().food(GCFoodComponent.DEHYDRATED_APPLE)); - public static final Item CANNED_DEHYDRATED_CARROT = new CannedFoodItem(new Item.Properties().food(GCFoodComponent.DEHYDRATED_CARROT)); - public static final Item CANNED_DEHYDRATED_MELON = new CannedFoodItem(new Item.Properties().food(GCFoodComponent.DEHYDRATED_MELON)); - public static final Item CANNED_DEHYDRATED_POTATO = new CannedFoodItem(new Item.Properties().food(GCFoodComponent.DEHYDRATED_POTATO)); - public static final Item CANNED_BEEF = new CannedFoodItem(new Item.Properties().food(GCFoodComponent.CANNED_BEEF)); - + // ROCKET PLATES public static final Item TIER_1_HEAVY_DUTY_PLATE = ITEMS.register(Constant.Item.TIER_1_HEAVY_DUTY_PLATE, new Item(new Item.Properties())); public static final Item TIER_2_HEAVY_DUTY_PLATE = ITEMS.register(Constant.Item.TIER_2_HEAVY_DUTY_PLATE, new Item(new Item.Properties())); @@ -417,9 +424,15 @@ public class GCItems { public static final Item MOON_BUGGY_SCHEMATIC = new SchematicItem(new Item.Properties()); public static final Item TIER_3_ROCKET_SCHEMATIC = new SchematicItem(new Item.Properties()); public static final Item ASTRO_MINER_SCHEMATIC = new SchematicItem(new Item.Properties()); + + public static final CannedFoodItem CANNED_FOOD = new CannedFoodItem(new Item.Properties().food(new FoodProperties.Builder().nutrition(0).saturationMod(0).build())); + public static final CannedFoodItem EMPTY_CANNED_FOOD = new CannedFoodItem(new Item.Properties().food(null)); + public static void register() { // === START BLOCKS === + Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.EMPTY_CANNED_FOOD), EMPTY_CANNED_FOOD); + Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_FOOD), CANNED_FOOD); // MOON NATURAL Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.MOON_TURF), MOON_TURF); @@ -529,6 +542,9 @@ public static void register() { Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.ALUMINUM_ORE), ALUMINUM_ORE); Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.DEEPSLATE_ALUMINUM_ORE), DEEPSLATE_ALUMINUM_ORE); + Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.MARS_IRON_ORE), MARS_IRON_ORE); + Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.MARS_TIN_ORE), MARS_TIN_ORE); + Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.MARS_COPPER_ORE), MARS_COPPER_ORE); Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.DESH_ORE), DESH_ORE); Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Block.ILMENITE_ORE), ILMENITE_ORE); @@ -645,12 +661,6 @@ public static void register() { Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.MOON_BERRIES), MOON_BERRIES); Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CHEESE_CURD), CHEESE_CURD); - Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_DEHYDRATED_APPLE), CANNED_DEHYDRATED_APPLE); - Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_DEHYDRATED_CARROT), CANNED_DEHYDRATED_CARROT); - Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_DEHYDRATED_MELON), CANNED_DEHYDRATED_MELON); - Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_DEHYDRATED_POTATO), CANNED_DEHYDRATED_POTATO); - Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.CANNED_BEEF), CANNED_BEEF); - // THROWABLE METEOR CHUNKS Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.THROWABLE_METEOR_CHUNK), THROWABLE_METEOR_CHUNK); Registry.register(BuiltInRegistries.ITEM, Constant.id(Constant.Item.HOT_THROWABLE_METEOR_CHUNK), HOT_THROWABLE_METEOR_CHUNK); diff --git a/src/main/java/dev/galacticraft/mod/data/GCTranslationProvider.java b/src/main/java/dev/galacticraft/mod/data/GCTranslationProvider.java index 4e2960c26..9af55d20f 100644 --- a/src/main/java/dev/galacticraft/mod/data/GCTranslationProvider.java +++ b/src/main/java/dev/galacticraft/mod/data/GCTranslationProvider.java @@ -189,8 +189,8 @@ protected void generateTranslations(HolderLookup.@NotNull Provider registries) { this.add(CelestialBody.SOL_DESC, ""); this.add(CelestialBody.SOL, "Sol"); - this.add(CelestialBody.ASTEROIDS_DESC, ""); - this.add(CelestialBody.ASTEROIDS, "Asteroids"); + this.add(CelestialBody.ASTEROID_DESC, ""); + this.add(CelestialBody.ASTEROID, "Asteroid"); this.add(CelestialBody.EARTH_DESC, "The Overworld"); this.add(CelestialBody.EARTH, "Earth"); this.add(CelestialBody.JUPITER_DESC, ""); diff --git a/src/main/java/dev/galacticraft/mod/data/model/GCModelProvider.java b/src/main/java/dev/galacticraft/mod/data/model/GCModelProvider.java index 3bac097d3..1e66ef759 100644 --- a/src/main/java/dev/galacticraft/mod/data/model/GCModelProvider.java +++ b/src/main/java/dev/galacticraft/mod/data/model/GCModelProvider.java @@ -407,12 +407,6 @@ public void generateItemModels(ItemModelGenerators generator) { generator.generateFlatItem(GCItems.BEEF_PATTY, ModelTemplates.FLAT_ITEM); generator.generateFlatItem(GCItems.CHEESEBURGER, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.CANNED_DEHYDRATED_APPLE, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.CANNED_DEHYDRATED_CARROT, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.CANNED_DEHYDRATED_MELON, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.CANNED_DEHYDRATED_POTATO, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.CANNED_BEEF, ModelTemplates.FLAT_ITEM); - generator.generateFlatItem(GCItems.NOSE_CONE, ModelTemplates.FLAT_ITEM); generator.generateFlatItem(GCItems.HEAVY_NOSE_CONE, "_joined", ModelTemplates.FLAT_ITEM); @@ -434,6 +428,7 @@ public void generateItemModels(ItemModelGenerators generator) { } } + generator.generateFlatItem(GCItems.SENSOR_GLASSES, ModelTemplates.FLAT_ITEM); // TOOLS + WEAPONS diff --git a/src/main/java/dev/galacticraft/mod/data/recipes/GCMiscRecipeProvider.java b/src/main/java/dev/galacticraft/mod/data/recipes/GCMiscRecipeProvider.java index fa6e10fb1..33e47c1fa 100644 --- a/src/main/java/dev/galacticraft/mod/data/recipes/GCMiscRecipeProvider.java +++ b/src/main/java/dev/galacticraft/mod/data/recipes/GCMiscRecipeProvider.java @@ -373,41 +373,6 @@ public void buildRecipes(RecipeOutput output) { .pattern("CCC") .unlockedBy(getHasName(GCItems.CHEESE_CURD), has(GCItems.CHEESE_CURD)) .save(output); - - ShapelessRecipeBuilder.shapeless(RecipeCategory.FOOD, GCItems.CANNED_DEHYDRATED_APPLE) - .requires(GCItems.TIN_CANISTER) - .requires(Items.APPLE) - .requires(Items.APPLE) - .unlockedBy(getHasName(GCItems.TIN_CANISTER), has(GCItems.TIN_CANISTER)) - .save(output); - - ShapelessRecipeBuilder.shapeless(RecipeCategory.FOOD, GCItems.CANNED_DEHYDRATED_POTATO) - .requires(GCItems.TIN_CANISTER) - .requires(Items.POTATO) - .requires(Items.POTATO) - .unlockedBy(getHasName(GCItems.TIN_CANISTER), has(GCItems.TIN_CANISTER)) - .save(output); - - ShapelessRecipeBuilder.shapeless(RecipeCategory.FOOD, GCItems.CANNED_DEHYDRATED_CARROT) - .requires(GCItems.TIN_CANISTER) - .requires(Items.CARROT) - .requires(Items.CARROT) - .unlockedBy(getHasName(GCItems.TIN_CANISTER), has(GCItems.TIN_CANISTER)) - .save(output); - - ShapelessRecipeBuilder.shapeless(RecipeCategory.FOOD, GCItems.CANNED_DEHYDRATED_MELON) - .requires(GCItems.TIN_CANISTER) - .requires(Items.MELON_SLICE) - .requires(Items.MELON_SLICE) - .unlockedBy(getHasName(GCItems.TIN_CANISTER), has(GCItems.TIN_CANISTER)) - .save(output); - - ShapelessRecipeBuilder.shapeless(RecipeCategory.FOOD, GCItems.CANNED_BEEF) - .requires(GCItems.TIN_CANISTER) - .requires(GCItems.GROUND_BEEF) - .requires(GCItems.GROUND_BEEF) - .unlockedBy(getHasName(GCItems.TIN_CANISTER), has(GCItems.TIN_CANISTER)) - .save(output); } @Override diff --git a/src/main/java/dev/galacticraft/mod/data/tag/GCBiomeTagProvider.java b/src/main/java/dev/galacticraft/mod/data/tag/GCBiomeTagProvider.java index c3c5903c4..b671d5404 100644 --- a/src/main/java/dev/galacticraft/mod/data/tag/GCBiomeTagProvider.java +++ b/src/main/java/dev/galacticraft/mod/data/tag/GCBiomeTagProvider.java @@ -39,25 +39,26 @@ public GCBiomeTagProvider(FabricDataOutput output, CompletableFuture INFINIBURN_MOON = TagKey.create(Registries.BLOCK, Constant.id("infiniburn_moon")); public static final TagKey INFINIBURN_VENUS = TagKey.create(Registries.BLOCK, Constant.id("infiniburn_venus")); + public static final TagKey INFINIBURN_ASTEROID = TagKey.create(Registries.BLOCK, Constant.id("infiniburn_asteroid")); public static final TagKey BASE_STONE_MOON = TagKey.create(Registries.BLOCK, Constant.id("base_stone_moon")); public static final TagKey MOON_CARVER_REPLACEABLES = TagKey.create(Registries.BLOCK, Constant.id("moon_carver_replaceables")); public static final TagKey MOON_CRATER_CARVER_REPLACEABLES = TagKey.create(Registries.BLOCK, Constant.id("moon_crater_carver_replaceables")); @@ -53,6 +54,7 @@ public class GCTags { public static final TagKey MOON = TagKey.create(Registries.BIOME, Constant.id("moon")); public static final TagKey VENUS = TagKey.create(Registries.BIOME, Constant.id("venus")); + public static final TagKey ASTEROID = TagKey.create(Registries.BIOME, Constant.id("asteroid")); public static final TagKey MOON_PILLAGER_BASE_HAS_STRUCTURE = TagKey.create(Registries.BIOME, Constant.id("has_structure/moon_pillager_base")); public static final TagKey MOON_VILLAGE_HIGHLANDS_HAS_STRUCTURE = TagKey.create(Registries.BIOME, Constant.id("has_structure/moon_village_highlands")); diff --git a/src/main/java/dev/galacticraft/mod/util/TextureUtils.java b/src/main/java/dev/galacticraft/mod/util/TextureUtils.java new file mode 100644 index 000000000..654c22e92 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/util/TextureUtils.java @@ -0,0 +1,69 @@ +package dev.galacticraft.mod.util; + +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.texture.TextureAtlasSprite; +import net.minecraft.client.resources.model.BakedModel; +import net.minecraft.client.resources.model.Material; +import net.minecraft.client.resources.model.ModelManager; +import net.minecraft.client.resources.model.ModelResourceLocation; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.server.packs.resources.Resource; +import net.minecraft.server.packs.resources.ResourceManager; +import net.minecraft.world.item.Item; +import net.minecraft.world.item.ItemStack; + +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; +import java.io.File; +import java.io.IOException; +import java.io.InputStream; +import java.util.Objects; +import java.util.Optional; + +public class TextureUtils { + public static int getAverageColor(ResourceLocation textureLocation) { + Optional resourceOptional = Minecraft.getInstance().getResourceManager().getResource(textureLocation); + if (resourceOptional.isEmpty()) { + throw new RuntimeException("Failed to find resource: " + textureLocation); + } + + try (InputStream is = resourceOptional.get().open()) { + BufferedImage image = ImageIO.read(is); + return calculateAverageColor(image); + } catch (IOException e) { + throw new RuntimeException("Failed to load image: " + textureLocation, e); + } + } + + private static int calculateAverageColor(BufferedImage image) { + long sumRed = 0; + long sumGreen = 0; + long sumBlue = 0; + int pixelCount = 0; + + for (int y = 0; y < image.getHeight(); y++) { + for (int x = 0; x < image.getWidth(); x++) { + + int rgb = image.getRGB(x, y); + if (rgb != 0) + { + int red = (rgb >> 16) & 0xFF; + int green = (rgb >> 8) & 0xFF; + int blue = rgb & 0xFF; + + sumRed += red; + sumGreen += green; + sumBlue += blue; + pixelCount++; + } + } + } + + int avgRed = (int) (sumRed / pixelCount); + int avgGreen = (int) (sumGreen / pixelCount); + int avgBlue = (int) (sumBlue / pixelCount); + + return (avgRed << 16) | (avgGreen << 8) | avgBlue; + } +} + diff --git a/src/main/java/dev/galacticraft/mod/util/Translations.java b/src/main/java/dev/galacticraft/mod/util/Translations.java index d5bc983ee..5d074e158 100644 --- a/src/main/java/dev/galacticraft/mod/util/Translations.java +++ b/src/main/java/dev/galacticraft/mod/util/Translations.java @@ -120,8 +120,8 @@ interface CelestialBody { String SOL_DESC = "star.galacticraft.sol.description"; String SOL = "star.galacticraft.sol"; - String ASTEROIDS_DESC = "planet.galacticraft.asteroids.description"; - String ASTEROIDS = "planet.galacticraft.asteroids"; + String ASTEROID_DESC = "planet.galacticraft.asteroid.description"; + String ASTEROID = "planet.galacticraft.asteroid"; String EARTH_DESC = "planet.galacticraft.earth.description"; String EARTH = "planet.galacticraft.earth"; String JUPITER_DESC = "planet.galacticraft.jupiter.description"; diff --git a/src/main/java/dev/galacticraft/mod/world/biome/AsteroidBiomes.java b/src/main/java/dev/galacticraft/mod/world/biome/AsteroidBiomes.java new file mode 100644 index 000000000..e3c5d26c7 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/biome/AsteroidBiomes.java @@ -0,0 +1,85 @@ +/* + * Copyright (c) 2019-2024 Team Galacticraft + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package dev.galacticraft.mod.world.biome; + +import dev.galacticraft.mod.content.GCEntityTypes; +import dev.galacticraft.mod.content.GCSounds; +import dev.galacticraft.mod.world.gen.feature.GCOrePlacedFeatures; +import net.minecraft.core.HolderGetter; +import net.minecraft.sounds.Musics; +import net.minecraft.world.entity.MobCategory; +import net.minecraft.world.level.biome.*; +import net.minecraft.world.level.levelgen.GenerationStep; +import net.minecraft.world.level.levelgen.carver.ConfiguredWorldCarver; +import net.minecraft.world.level.levelgen.placement.PlacedFeature; + +import java.awt.*; + +public class AsteroidBiomes { + public static void monsters(MobSpawnSettings.Builder builder, int zombieWeight, int zombieVillagerWeight, int selektonWeight) { + builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_SPIDER, 100, 4, 4)); + builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_ZOMBIE, zombieWeight, 4, 4)); +// builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_ZOMBIE_VILLAGER, zombieVillagerWeight, 1, 1)); + builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_SKELETON, selektonWeight, 4, 4)); + builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_CREEPER, 100, 4, 4)); +// builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_SLIME, 100, 4, 4)); +// builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_ENDERMAN, 10, 1, 4)); +// builder.addSpawn(MobCategory.MONSTER, new MobSpawnSettings.SpawnerData(GCEntityTypes.EVOLVED_WITCH, 5, 1, 1)); + } + + public static void addDefaultAsteroidOres(BiomeGenerationSettings.Builder builder) { +// builder.addFeature(GenerationStep.Decoration.UNDERGROUND_ORES, GCOrePlacedFeatures.ORE_COPPER_MOON); +// builder.addFeature(GenerationStep.Decoration.UNDERGROUND_ORES, GCOrePlacedFeatures.ORE_COPPER_LARGE_MOON); +// +// builder.addFeature(GenerationStep.Decoration.UNDERGROUND_ORES, GCOrePlacedFeatures.ORE_TIN_SMALL_MOON); +// builder.addFeature(GenerationStep.Decoration.UNDERGROUND_ORES, GCOrePlacedFeatures.ORE_TIN_MIDDLE_MOON); +// builder.addFeature(GenerationStep.Decoration.UNDERGROUND_ORES, GCOrePlacedFeatures.ORE_TIN_UPPER_MOON); + } + + public static Biome asteroid( + HolderGetter featureGetter, HolderGetter> carverGetter + ) { + MobSpawnSettings.Builder spawnBuilder = new MobSpawnSettings.Builder(); + BiomeGenerationSettings.Builder generation = new BiomeGenerationSettings.Builder(featureGetter, carverGetter); + BiomeSpecialEffects.Builder specialEffects = new BiomeSpecialEffects.Builder(); + specialEffects.waterColor(0) + .waterFogColor(0) + .fogColor(0) + .skyColor(new Color(0, 0, 0).getRGB()) + .ambientMoodSound(AmbientMoodSettings.LEGACY_CAVE_SETTINGS) + .backgroundMusic(Musics.createGameMusic(GCSounds.MUSIC_MOON)); + + AsteroidBiomes.addDefaultAsteroidOres(generation); +// AsteroidBiomes.addDefaultSoftDisks(generation); + AsteroidBiomes.monsters(spawnBuilder, 95, 5, 100); + + return new Biome.BiomeBuilder() + .mobSpawnSettings(spawnBuilder.build()) + .hasPrecipitation(true) + .temperature(-2F) // temp is hot to prevent snow + .downfall(0.5F) + .specialEffects(specialEffects.build()) + .generationSettings(generation.build()) + .build(); + } +} diff --git a/src/main/java/dev/galacticraft/mod/world/biome/GCBiomes.java b/src/main/java/dev/galacticraft/mod/world/biome/GCBiomes.java index ef8505213..523eaf239 100644 --- a/src/main/java/dev/galacticraft/mod/world/biome/GCBiomes.java +++ b/src/main/java/dev/galacticraft/mod/world/biome/GCBiomes.java @@ -51,6 +51,10 @@ public static final class Venus { public static final ResourceKey VENUS_MOUNTAIN = key("venus_mountain"); } + public static final class Asteroid { + public static final ResourceKey ASTEROID_FIELD = key("asteroid_field"); + } + public static final ResourceKey SPACE = ResourceKey.create(Registries.BIOME, Constant.id("space")); public static Biome createSpaceBiome(HolderGetter holderGetter, HolderGetter> holderGetter2) { @@ -82,6 +86,8 @@ public static void bootstrapRegistries(BootstapContext context) { // moj- context.register(Venus.VENUS_VALLEY, VenusBiomes.venus(featureLookup, carverLookup)); context.register(Venus.VENUS_FLAT, VenusBiomes.venus(featureLookup, carverLookup)); context.register(Venus.VENUS_MOUNTAIN, VenusBiomes.venus(featureLookup, carverLookup)); + + context.register(Asteroid.ASTEROID_FIELD, AsteroidBiomes.asteroid(featureLookup, carverLookup)); } @Contract(pure = true) diff --git a/src/main/java/dev/galacticraft/mod/world/biome/source/GCMultiNoiseBiomeSourceParameterLists.java b/src/main/java/dev/galacticraft/mod/world/biome/source/GCMultiNoiseBiomeSourceParameterLists.java index c314971ef..525d6f8f7 100644 --- a/src/main/java/dev/galacticraft/mod/world/biome/source/GCMultiNoiseBiomeSourceParameterLists.java +++ b/src/main/java/dev/galacticraft/mod/world/biome/source/GCMultiNoiseBiomeSourceParameterLists.java @@ -86,15 +86,20 @@ public class GCMultiNoiseBiomeSourceParameterLists { public static final ResourceLocation MOON_PRESET_ID = Constant.id("moon"); public static final ResourceLocation VENUS_PRESET_ID = Constant.id("venus"); + public static final ResourceLocation ASTEROID_PRESET_ID = Constant.id("asteroid"); public static final MultiNoiseBiomeSourceParameterList.Preset MOON_PRESET = new MultiNoiseBiomeSourceParameterList.Preset( MOON_PRESET_ID, GCMultiNoiseBiomeSourceParameterLists::generateMoon ); public static final MultiNoiseBiomeSourceParameterList.Preset VENUS_PRESET = new MultiNoiseBiomeSourceParameterList.Preset( VENUS_PRESET_ID, GCMultiNoiseBiomeSourceParameterLists::generateVenus ); + public static final MultiNoiseBiomeSourceParameterList.Preset ASTEROID_PRESET = new MultiNoiseBiomeSourceParameterList.Preset( + ASTEROID_PRESET_ID, GCMultiNoiseBiomeSourceParameterLists::generateAsteroid + ); public static final ResourceKey MOON = Constant.key(Registries.MULTI_NOISE_BIOME_SOURCE_PARAMETER_LIST, "moon"); public static final ResourceKey VENUS = Constant.key(Registries.MULTI_NOISE_BIOME_SOURCE_PARAMETER_LIST, "venus"); + public static final ResourceKey ASTEROID = Constant.key(Registries.MULTI_NOISE_BIOME_SOURCE_PARAMETER_LIST, "asteroid"); @Contract("_ -> new") private static Climate.@NotNull ParameterList generateMoon(Function, T> biomeRegistry) { @@ -167,6 +172,21 @@ public class GCMultiNoiseBiomeSourceParameterLists { return new Climate.ParameterList<>(builder.build()); } + @Contract("_ -> new") + private static Climate.@NotNull ParameterList generateAsteroid(Function, T> biomeRegistry) { + ImmutableList.Builder> builder = ImmutableList.builder(); + writeBiomeParameters(builder::add, + HOT, // hot to prevent snow + DRY,// , + Parameter.span(SHORE_CONTINENTALNESS, MID_INLAND_CONTINENTALNESS), + MIN_EROSION, + WEIRDNESS_H_MIXED, + 0.0F, + biomeRegistry.apply(GCBiomes.Asteroid.ASTEROID_FIELD)); + + return new Climate.ParameterList<>(builder.build()); + } + private static void writeBiomeParameters( Consumer> parameters, Parameter temperature, @@ -194,12 +214,15 @@ private static void writeBiomeParameters( public static void register() { MultiNoiseBiomeSourceParameterListPresetAccessor.getByName().put(MOON_PRESET_ID, MOON_PRESET); MultiNoiseBiomeSourceParameterListPresetAccessor.getByName().put(VENUS_PRESET_ID, VENUS_PRESET); + MultiNoiseBiomeSourceParameterListPresetAccessor.getByName().put(ASTEROID_PRESET_ID, ASTEROID_PRESET); + } public static void bootstrapRegistries(BootstapContext context) { HolderGetter lookup = context.lookup(Registries.BIOME); context.register(MOON, new MultiNoiseBiomeSourceParameterList(MOON_PRESET, lookup)); context.register(VENUS, new MultiNoiseBiomeSourceParameterList(VENUS_PRESET, lookup)); + context.register(ASTEROID, new MultiNoiseBiomeSourceParameterList(ASTEROID_PRESET, lookup)); } } diff --git a/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensionTypes.java b/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensionTypes.java index cc2808a09..d5b5c6c1e 100644 --- a/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensionTypes.java +++ b/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensionTypes.java @@ -37,6 +37,7 @@ public class GCDimensionTypes { public static final ResourceKey MOON = key("moon"); public static final ResourceKey VENUS = key("venus"); + public static final ResourceKey ASTEROID = key("asteroid"); public static void bootstrapRegistries(BootstapContext context) { context.register(MOON, new DimensionType( @@ -73,6 +74,23 @@ public static void bootstrapRegistries(BootstapContext context) { 0.1F, // ambientLight new DimensionType.MonsterSettings(false, false, UniformInt.of(0, 7), 0) )); + context.register(ASTEROID, new DimensionType( + OptionalLong.empty(), // fixedTime + true, // hasSkyLight + false, // hasCeiling + false, // ultraWarm + false, // natural + 1.0, // coordinateScale + false, // bedWorks + false, // respawnAnchorWorks + -64, // minY + 384, // height + 384, // logicalHeight + GCTags.INFINIBURN_ASTEROID, // infiniburn + Constant.id("asteroid"), // effectsLocation // fixme + 0.1F, // ambientLight + new DimensionType.MonsterSettings(false, false, UniformInt.of(0, 7), 0) + )); } @Contract(value = "_ -> new", pure = true) diff --git a/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensions.java b/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensions.java index ee30ea2e7..eafb8c6f5 100644 --- a/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensions.java +++ b/src/main/java/dev/galacticraft/mod/world/dimension/GCDimensions.java @@ -32,6 +32,7 @@ public class GCDimensions { public static final ResourceKey MOON = key("moon"); public static final ResourceKey VENUS = key("venus"); + public static final ResourceKey ASTEROID = key("asteroid"); @Contract(pure = true) private static @NotNull ResourceKey key(@NotNull String id) { diff --git a/src/main/java/dev/galacticraft/mod/world/dimension/GCLevelStems.java b/src/main/java/dev/galacticraft/mod/world/dimension/GCLevelStems.java index 89bc3328f..36bdce0da 100644 --- a/src/main/java/dev/galacticraft/mod/world/dimension/GCLevelStems.java +++ b/src/main/java/dev/galacticraft/mod/world/dimension/GCLevelStems.java @@ -42,6 +42,7 @@ public class GCLevelStems { public static final ResourceKey MOON = key("moon"); public static final ResourceKey VENUS = key("venus"); + public static final ResourceKey ASTEROID = key("asteroid"); public static void bootstrapRegistries(@NotNull BootstapContext context) { HolderGetter typeLookup = context.lookup(Registries.DIMENSION_TYPE); @@ -52,6 +53,7 @@ public static void bootstrapRegistries(@NotNull BootstapContext conte // the returned reference may be null // context.register(MOON, new LevelStem(typeLookup.getOrThrow(GCDimensionTypes.MOON), new NoiseBasedChunkGenerator(MultiNoiseBiomeSource.createFromPreset(biomeNoiseLookup.getOrThrow(GCMultiNoiseBiomeSourceParameterLists.MOON)), noiseLookup.getOrThrow(GCNoiseGeneratorSettings.MOON)))); context.register(VENUS, new LevelStem(typeLookup.getOrThrow(GCDimensionTypes.VENUS), new NoiseBasedChunkGenerator(MultiNoiseBiomeSource.createFromPreset(biomeNoiseLookup.getOrThrow(GCMultiNoiseBiomeSourceParameterLists.VENUS)), noiseLookup.getOrThrow(GCNoiseGeneratorSettings.VENUS)))); + context.register(ASTEROID, new LevelStem(typeLookup.getOrThrow(GCDimensionTypes.ASTEROID), new NoiseBasedChunkGenerator(MultiNoiseBiomeSource.createFromPreset(biomeNoiseLookup.getOrThrow(GCMultiNoiseBiomeSourceParameterLists.ASTEROID)), noiseLookup.getOrThrow(GCNoiseGeneratorSettings.ASTEROID)))); } @Contract(value = "_ -> new", pure = true) diff --git a/src/main/java/dev/galacticraft/mod/world/gen/GCDensityFunctions.java b/src/main/java/dev/galacticraft/mod/world/gen/GCDensityFunctions.java index 08cb76b74..b76b3e208 100644 --- a/src/main/java/dev/galacticraft/mod/world/gen/GCDensityFunctions.java +++ b/src/main/java/dev/galacticraft/mod/world/gen/GCDensityFunctions.java @@ -44,6 +44,10 @@ public static final class Venus { // Final Density handles overall terrain shape public static final ResourceKey FINAL_DENSITY = createKey("venus/final_density"); } + public static final class Asteroid { + // Final Density handles overall terrain shape + public static final ResourceKey FINAL_DENSITY = createKey("asteroid/final_density"); + } private static ResourceKey createKey(String id) { return ResourceKey.create(Registries.DENSITY_FUNCTION, Constant.id(id)); @@ -127,6 +131,11 @@ public static void bootstrapRegistries(BootstapContext context) DensityFunctions.yClampedGradient(0, 90, 1, -1), BlendedNoise.createUnseeded(0.25, 0.375, 80.0, 160.0, 8.0) )); + + context.register(Asteroid.FINAL_DENSITY, DensityFunctions.add( + DensityFunctions.yClampedGradient(0, 90, 1, -1), + BlendedNoise.createUnseeded(0.25, 0.375, 80.0, 160.0, 8.0) + )); } private static DensityFunction registerAndWrap(BootstapContext context, ResourceKey key, DensityFunction densityFunction) { diff --git a/src/main/java/dev/galacticraft/mod/world/gen/GCNoiseGeneratorSettings.java b/src/main/java/dev/galacticraft/mod/world/gen/GCNoiseGeneratorSettings.java index 105c190f3..3642742ff 100644 --- a/src/main/java/dev/galacticraft/mod/world/gen/GCNoiseGeneratorSettings.java +++ b/src/main/java/dev/galacticraft/mod/world/gen/GCNoiseGeneratorSettings.java @@ -26,6 +26,7 @@ import dev.galacticraft.mod.content.GCBlocks; import dev.galacticraft.mod.world.gen.surfacebuilder.MoonSurfaceRules; import dev.galacticraft.mod.world.gen.surfacebuilder.VenusSurfaceRules; +import dev.galacticraft.mod.world.gen.surfacebuilder.AsteroidSurfaceRules; import net.minecraft.core.HolderGetter; import net.minecraft.core.registries.Registries; import net.minecraft.data.worldgen.BootstapContext; @@ -43,6 +44,7 @@ public class GCNoiseGeneratorSettings { public static final ResourceKey MOON = key("moon"); public static final ResourceKey VENUS = key("venus"); + public static final ResourceKey ASTEROID = key("asteroid"); public static void bootstrapRegistries(BootstapContext context) { HolderGetter densityLookup = context.lookup(Registries.DENSITY_FUNCTION); @@ -75,6 +77,20 @@ public static void bootstrapRegistries(BootstapContext c true, false )); + + context.register(ASTEROID, new NoiseGeneratorSettings( + NoiseSettings.create(-32, 256, 1, 2), + GCBlocks.HARD_VENUS_ROCK.defaultBlockState(), + Blocks.AIR.defaultBlockState(), + GCNoiseGeneratorSettings.asteroid(densityLookup, noiseLookup), + AsteroidSurfaceRules.ASTEROID, + new OverworldBiomeBuilder().spawnTarget(), + -32, + false, + false, + true, + false + )); } public static NoiseRouter moon(HolderGetter densityLookup, HolderGetter noiseLookup) { @@ -179,6 +195,26 @@ public static NoiseRouter venus(HolderGetter densityLookup, Hol ); } + public static NoiseRouter asteroid(HolderGetter densityLookup, HolderGetter noiseLookup) { + return new NoiseRouter( + DensityFunctions.zero(), // barrierNoise + DensityFunctions.zero(), // fluidLevelFloodednessNoise + DensityFunctions.zero(), // fluidLevelSpreadNoise + DensityFunctions.zero(), // lavaNoise + DensityFunctions.zero(), // temperature + DensityFunctions.zero(), // vegetation + DensityFunctions.zero(), // continents + DensityFunctions.zero(), // erosion + DensityFunctions.zero(), // depth + DensityFunctions.zero(), // ridges + DensityFunctions.noise(noiseLookup.getOrThrow(Noises.SPAGHETTI_3D_1)), // initialDensityWithoutJaggedness + DensityFunctions.blendDensity(GCDensityFunctions.getFunction(densityLookup, GCDensityFunctions.Asteroid.FINAL_DENSITY)), // finalDensity + DensityFunctions.zero(), // veinToggle + DensityFunctions.zero(), // veinRidged + DensityFunctions.zero() // veinGap + ); + } + @Contract(value = "_ -> new", pure = true) private static @NotNull ResourceKey key(String id) { return Constant.key(Registries.NOISE_SETTINGS, id); diff --git a/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidChunkGenerator.java b/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidChunkGenerator.java new file mode 100644 index 000000000..6fa847799 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidChunkGenerator.java @@ -0,0 +1,1067 @@ +package dev.galacticraft.mod.world.gen.custom; + +import com.mojang.serialization.Codec; +import com.mojang.serialization.codecs.RecordCodecBuilder; +import dev.galacticraft.api.perlin.NoiseModule; +import dev.galacticraft.api.perlin.generator.Billowed; +import dev.galacticraft.api.perlin.generator.Gradient; +import dev.galacticraft.api.vector.BlockVec3; +import dev.galacticraft.mod.content.GCBlocks; +import net.minecraft.core.BlockPos; +import net.minecraft.core.Holder; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.ListTag; +import net.minecraft.nbt.NbtIo; +import net.minecraft.resources.ResourceKey; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.server.level.WorldGenRegion; +import net.minecraft.world.level.*; +import net.minecraft.world.level.biome.BiomeManager; +import net.minecraft.world.level.biome.BiomeSource; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.Blocks; +import net.minecraft.world.level.block.state.BlockState; +import net.minecraft.world.level.chunk.*; +import net.minecraft.world.level.levelgen.*; +import net.minecraft.world.level.levelgen.blending.Blender; +import net.minecraft.world.level.storage.*; + +import java.io.*; +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.*; +import java.util.concurrent.CompletableFuture; +import java.util.concurrent.Executor; + +import static dev.galacticraft.impl.internal.fabric.GalacticraftAPI.currentWorldSaveDirectory; +import static dev.galacticraft.mod.world.gen.custom.AsteroidSaveData.saveDataID; + + +public class AsteroidChunkGenerator extends ChunkGenerator { + + //from WorldAsteroidProvider + private HashSet asteroids = new HashSet<>(); + private boolean dataNotLoaded = true; + private AsteroidSaveData datafile; + private double solarMultiplier = -1D; + + private int largeCount = 0; + private final Random rand; + private final NoiseModule asteroidDensity; + private final NoiseModule asteroidTurbulance; + private final ResourceKey dimensionKey; + + private final NoiseModule asteroidSkewX; + private final NoiseModule asteroidSkewY; + private final NoiseModule asteroidSkewZ; + + private final SpecialAsteroidBlockHandler coreHandler; + private final SpecialAsteroidBlockHandler shellHandler; + //micdoodle8 says do not change but I did :) + private static final int CHUNK_SIZE_X = 16; + private static final int CHUNK_SIZE_Y = 384; + private static final int CHUNK_SIZE_Z = 16; + + private static final int MAX_ASTEROID_RADIUS = 25; + private static final int MIN_ASTEROID_RADIUS = 5; + + private static final int MAX_ASTEROID_SKEW = 8; + + //MIN_ASTEROID_Y is -64 + 48 + private static final int MIN_ASTEROID_Y = -16; + //MAX_ASTEROID_Y is 384 - 64 - 48 + private static final int MAX_ASTEROID_Y = AsteroidChunkGenerator.CHUNK_SIZE_Y - 64 - 48; + //default is 800 + private static final int ASTEROID_CHANCE = 800; + private static final int ASTEROID_CORE_CHANCE = 2; //1 / n chance per asteroid + private static final int ASTEROID_SHELL_CHANCE = 2; //1 / n chance per asteroid + + private static final int MIN_BLOCKS_PER_CHUNK = 50; + private static final int MAX_BLOCKS_PER_CHUNK = 200; + + private static final int ILMENITE_CHANCE = 400; + private static final int IRON_CHANCE = 300; + private static final int ALUMINUM_CHANCE = 250; + + private static final int RANDOM_BLOCK_FADE_SIZE = 32; + private static final int FADE_BLOCK_CHANCE = 5; //1 / n chance of a block being in the fade zone + + private static final int NOISE_OFFSET_SIZE = 256; + + private static final float MIN_HOLLOW_SIZE = .6F; + private static final float MAX_HOLLOW_SIZE = .8F; + private static final int HOLLOW_CHANCE = 10; //1 / n chance per asteroid + private static final int MIN_RADIUS_FOR_HOLLOW = 15; + private static final float HOLLOW_LAVA_SIZE = .12F; + + //Per chunk per asteroid + private static final int TREE_CHANCE = 2; + private static final int TALL_GRASS_CHANCE = 2; + private static final int FLOWER_CHANCE = 2; + private static final int WATER_CHANCE = 2; + private static final int LAVA_CHANCE = 2; + private static final int GLOWSTONE_CHANCE = 20; + + private LinkedList largeAsteroids = new LinkedList(); + private static HashSet chunksDone = new HashSet(); + private int largeAsteroidsLastChunkX; + private int largeAsteroidsLastChunkZ; + + public static final Codec CODEC = RecordCodecBuilder.create(instance -> + instance.group( + BiomeSource.CODEC.fieldOf("biomeSource").forGetter(generator -> generator.biomeSource), + ServerLevel.RESOURCE_KEY_CODEC.fieldOf("dimensionKey").forGetter(generator -> generator.dimensionKey), + Codec.LONG.fieldOf("par2").forGetter(generator -> 1000L) + ).apply(instance, AsteroidChunkGenerator::new)); + private final Holder settings = null; + public AsteroidChunkGenerator(BiomeSource biomeSource, ResourceKey dimensionKey, long par2) { + super(biomeSource); + this.dimensionKey = dimensionKey; + this.rand = new Random(par2); + + this.asteroidDensity = new Billowed(this.rand.nextLong(), 2, .25F); + this.asteroidDensity.setFrequency(.009F); + this.asteroidDensity.amplitude = .6F; + + this.asteroidTurbulance = new Gradient(this.rand.nextLong(), 1, .2F); + this.asteroidTurbulance.setFrequency(.08F); + this.asteroidTurbulance.amplitude = .5F; + + this.asteroidSkewX = new Gradient(this.rand.nextLong(), 1, 1); + this.asteroidSkewX.amplitude = AsteroidChunkGenerator.MAX_ASTEROID_SKEW; + this.asteroidSkewX.frequencyX = 0.005F; + + this.asteroidSkewY = new Gradient(this.rand.nextLong(), 1, 1); + this.asteroidSkewY.amplitude = AsteroidChunkGenerator.MAX_ASTEROID_SKEW; + this.asteroidSkewY.frequencyY = 0.005F; + + this.asteroidSkewZ = new Gradient(this.rand.nextLong(), 1, 1); + this.asteroidSkewZ.amplitude = AsteroidChunkGenerator.MAX_ASTEROID_SKEW; + this.asteroidSkewZ.frequencyZ = 0.005F; + + this.coreHandler = new SpecialAsteroidBlockHandler(); + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK_2, 5, .3)); + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK_1, 7, .3)); + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK, 11, .25)); + + //TODO: FIX ORE TYPES ASTEROID DOESNT HAVE ORES + //!ConfigManagerAst.disableAluminumGen + if (true) + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ALUMINUM_ORE, 5, .2)); + //!ConfigManagerAsteroids.disableIlmeniteGen + if (true) + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ILMENITE_ORE, 4, .15)); + //!ConfigManagerAsteroids.disableIronGen + if (true) + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.MARS_IRON_ORE, 3, .2)); + //ConfigManagerCore.enableSiliconOreGen + if (true) + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.SILICON_ORE,2, .15)); + //Solid Meteoric Iron - has no config to disable + this.coreHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.METEORIC_IRON_BLOCK, 2, .13)); + //Diamond ore - has no config to disable + this.coreHandler.addBlock(new SpecialAsteroidBlock(Blocks.DIAMOND_ORE, 1, .1)); + + this.shellHandler = new SpecialAsteroidBlockHandler(); + this.shellHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK, 1, .15)); + this.shellHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK_1, 3, .15)); + this.shellHandler.addBlock(new SpecialAsteroidBlock(GCBlocks.ASTEROID_ROCK_2, 1, .15)); + this.shellHandler.addBlock(new SpecialAsteroidBlock(Blocks.PACKED_ICE, 1, .15)); //TODO: REPLACE WITH DENSE ICE + } + + private ChunkAccess generateChunkData(Blender blender, RandomState randomState, StructureManager structureManager, ChunkAccess chunkAccess) { + int heightLimit = chunkAccess.getHeight(); + int chunkX = chunkAccess.getPos().x; + int chunkZ = chunkAccess.getPos().z; + + this.largeAsteroids.clear(); + this.largeCount = 0; + final Random random = new Random(); + final int asteroidChance = AsteroidChunkGenerator.ASTEROID_CHANCE; + final int rangeY = AsteroidChunkGenerator.MAX_ASTEROID_Y - AsteroidChunkGenerator.MIN_ASTEROID_Y; + final int rangeSize = AsteroidChunkGenerator.MAX_ASTEROID_RADIUS - AsteroidChunkGenerator.MIN_ASTEROID_RADIUS; + + //If asteroid centre is nearby might need to generate some asteroid parts in this chunk + for (int i = chunkX - 3; i < chunkX + 3; i++) + { + int minX = i * 16; + int maxX = minX + AsteroidChunkGenerator.CHUNK_SIZE_X; + for (int k = chunkZ - 3; k < chunkZ + 3; k++) + { + int minZ = k * 16; + int maxZ = minZ + AsteroidChunkGenerator.CHUNK_SIZE_Z; + + //something about redundant code in gc4's code + for (int x = minX; x < maxX; x += 2) + { + for (int z = minZ; z < maxZ; z += 2) + { + //the next line is called 3136 times per chunk generated apparently? saying something about slow getNoise + if (this.randFromPointPos(x, z) < (this.asteroidDensity.getNoise(x, z) + .4) / asteroidChance) + { + random.setSeed(x + z * 3067); + int y = random.nextInt(rangeY) + AsteroidChunkGenerator.MIN_ASTEROID_Y; + int size = random.nextInt(rangeSize) + AsteroidChunkGenerator.MIN_ASTEROID_RADIUS; + + //generate the parts of the asteroid which are in this chunk + this.generateAsteroid(random, x, y, z, chunkX << 4, chunkZ << 4, size, chunkAccess); + this.largeCount++; + } + } + } + } + } + + return chunkAccess; + } + + public DimensionDataStorage getDimensionDataStorage(MinecraftServer server) { + ServerLevel level = server.getLevel(dimensionKey); + if (level == null) { + throw new IllegalStateException("ServerLevel for the given dimensionKey does not exist."); + } + return level.getDataStorage(); + } + + private void generateAsteroid(Random rand, int asteroidX, int asteroidY, int asteroidZ, int chunkX, int chunkZ, int size, ChunkAccess primer) + { + SpecialAsteroidBlock core = this.coreHandler.getBlock(rand, size); + + SpecialAsteroidBlock shell = null; + if (rand.nextInt(AsteroidChunkGenerator.ASTEROID_SHELL_CHANCE) == 0) + { + shell = this.shellHandler.getBlock(rand, size); + } + + boolean isHollow = false; + final float hollowSize = rand.nextFloat() * (AsteroidChunkGenerator.MAX_HOLLOW_SIZE - AsteroidChunkGenerator.MIN_HOLLOW_SIZE) + AsteroidChunkGenerator.MIN_HOLLOW_SIZE; + if (rand.nextInt(AsteroidChunkGenerator.HOLLOW_CHANCE) == 0 && size >= AsteroidChunkGenerator.MIN_RADIUS_FOR_HOLLOW) + { + isHollow = true; + //TODO: set to dense ice + shell = new SpecialAsteroidBlock(Blocks.PACKED_ICE, 1, .15); + } + + //Add to the list of asteroids for external use + ((AsteroidChunkGenerator) this).addAsteroid(asteroidX, asteroidY, asteroidZ, size, isHollow ? -1 : core.index); + + final int xMin = this.clamp(Math.max(chunkX, asteroidX - size - AsteroidChunkGenerator.MAX_ASTEROID_SKEW - 2) - chunkX, 0, 16); + final int zMin = this.clamp(Math.max(chunkZ, asteroidZ - size - AsteroidChunkGenerator.MAX_ASTEROID_SKEW - 2) - chunkZ, 0, 16); + final int yMin = asteroidY - size - AsteroidChunkGenerator.MAX_ASTEROID_SKEW - 2; + final int yMax = asteroidY + size + AsteroidChunkGenerator.MAX_ASTEROID_SKEW + 2; + final int xMax = this.clamp(Math.min(chunkX + 16, asteroidX + size + AsteroidChunkGenerator.MAX_ASTEROID_SKEW + 2) - chunkX, 0, 16); + final int zMax = this.clamp(Math.min(chunkZ + 16, asteroidZ + size + AsteroidChunkGenerator.MAX_ASTEROID_SKEW + 2) - chunkZ, 0, 16); + final int xSize = xMax - xMin; + final int ySize = yMax - yMin; + final int zSize = zMax - zMin; + + if (xSize <= 0 || ySize <= 0 || zSize <= 0) + { + return; + } + + final float noiseOffsetX = this.randFromPoint(asteroidX, asteroidY, asteroidZ) * AsteroidChunkGenerator.NOISE_OFFSET_SIZE + chunkX; + final float noiseOffsetY = this.randFromPoint(asteroidX * 7, asteroidY * 11, asteroidZ * 13) * AsteroidChunkGenerator.NOISE_OFFSET_SIZE; + final float noiseOffsetZ = this.randFromPoint(asteroidX * 17, asteroidY * 23, asteroidZ * 29) * AsteroidChunkGenerator.NOISE_OFFSET_SIZE + chunkZ; + this.setOtherAxisFrequency(1F / (size * 2F / 2F)); + + float[] sizeXArray = new float[ySize * zSize]; + float[] sizeZArray = new float[xSize * ySize]; + float[] sizeYArray = new float[xSize * zSize]; + + for (int x = 0; x < xSize; x++) + { + int xx = x * zSize; + float xxx = x + noiseOffsetX; + for (int z = 0; z < zSize; z++) + { + sizeYArray[xx + z] = this.asteroidSkewY.getNoise(xxx, z + noiseOffsetZ); + } + } + + AsteroidData asteroidData = new AsteroidData(isHollow, sizeYArray, xMin, zMin, xMax, zMax, zSize, size, asteroidX, asteroidY, asteroidZ); + this.largeAsteroids.add(asteroidData); + this.largeAsteroidsLastChunkX = chunkX; + this.largeAsteroidsLastChunkZ = chunkZ; + + for (int y = 0; y < ySize; y++) + { + int yy = y * zSize; + float yyy = y + noiseOffsetY; + for (int z = 0; z < zSize; z++) + { + sizeXArray[yy + z] = this.asteroidSkewX.getNoise(yyy, z + noiseOffsetZ); + } + } + + for (int x = 0; x < xSize; x++) + { + int xx = x * ySize; + float xxx = x + noiseOffsetX; + for (int y = 0; y < ySize; y++) + { + sizeZArray[xx + y] = this.asteroidSkewZ.getNoise(xxx, y + noiseOffsetY); + } + } + + double shellThickness = 0; + int terrainY = 0; + int terrainYY = 0; + + BlockState asteroidShell = null; + if (shell != null) + { + asteroidShell = shell.block.defaultBlockState(); + shellThickness = 1.0 - shell.thickness; + } + + BlockState asteroidCore = core.block.defaultBlockState(); + BlockState asteroidRock0 = GCBlocks.ASTEROID_ROCK.defaultBlockState(); + BlockState asteroidRock1 = GCBlocks.ASTEROID_ROCK_1.defaultBlockState(); + + for (int x = xMax - 1; x >= xMin; x--) { + int indexXY = (x - xMin) * ySize - yMin; + int indexXZ = (x - xMin) * zSize - zMin; + int distanceX = asteroidX - (x + chunkX); + int indexBaseX = x * AsteroidChunkGenerator.CHUNK_SIZE_Y << 4; + float xx = x + chunkX; + + for (int z = zMin; z < zMax; z++) { + if (isHollow) { + float sizeModY = sizeYArray[indexXZ + z]; + terrainY = this.getTerrainHeightFor(sizeModY, asteroidY, size); + terrainYY = this.getTerrainHeightFor(sizeModY, asteroidY - 1, size); + } + + float sizeY = size + sizeYArray[indexXZ + z]; + sizeY *= sizeY; + int distanceZ = asteroidZ - (z + chunkZ); + int indexBase = indexBaseX | z * AsteroidChunkGenerator.CHUNK_SIZE_Y; + float zz = z + chunkZ; + + for (int y = yMin; y < yMax; y++) { + float dSizeX = distanceX / (size + sizeXArray[(y - yMin) * zSize + z - zMin]); + float dSizeZ = distanceZ / (size + sizeZArray[indexXY + y]); + dSizeX *= dSizeX; + dSizeZ *= dSizeZ; + int distanceY = asteroidY - y; + distanceY *= distanceY; + float distance = dSizeX + distanceY / sizeY + dSizeZ; + float distanceAbove = distance; + distance += this.asteroidTurbulance.getNoise(xx, y, zz); + + if (isHollow && distance <= hollowSize) { + distanceAbove += this.asteroidTurbulance.getNoise(xx, y + 1, zz); + if (distanceAbove <= 1) { + if ((y - 1) == terrainYY) { + int index = indexBase | (y + 1); + primer.setBlockState(new BlockPos(x, y + 1, z), Blocks.GLOWSTONE.defaultBlockState(), false); +// blockArray[index] = this.LIGHT; +// metaArray[index] = this.LIGHT_META; + } + } + } + + if (distance <= 1) { + int index = indexBase | y; + if (isHollow && distance <= hollowSize) { + if (y == terrainY) { + primer.setBlockState(new BlockPos(x, y, z), Blocks.GRASS_BLOCK.defaultBlockState(), false); +// blockArray[index] = this.GRASS; +// metaArray[index] = this.GRASS_META; + } else if (y < terrainY) { + primer.setBlockState(new BlockPos(x, y, z), Blocks.DIRT.defaultBlockState(), false); +// blockArray[index] = this.DIRT; +// metaArray[index] = this.DIRT_META; + } else { + primer.setBlockState(new BlockPos(x, y, z), Blocks.AIR.defaultBlockState(), false); +// blockArray[index] = Blocks.air; +// metaArray[index] = 0; + } + } else if (distance <= core.thickness) { + if (rand.nextBoolean()) { + primer.setBlockState(new BlockPos(x, y, z), asteroidCore, false); +// blockArray[index] = core.block; +// metaArray[index] = core.meta; + } else { + primer.setBlockState(new BlockPos(x, y, z), asteroidRock0, false); +// blockArray[index] = this.ASTEROID_STONE; +// metaArray[index] = this.ASTEROID_STONE_META_0; + } + } else if (shell != null && distance >= shellThickness) { + primer.setBlockState(new BlockPos(x, y, z), asteroidShell, false); +// blockArray[index] = shell.block; +// metaArray[index] = shell.meta; + } else { + primer.setBlockState(new BlockPos(x, y, z), asteroidRock1, false); +// blockArray[index] = this.ASTEROID_STONE; +// metaArray[index] = this.ASTEROID_STONE_META_1; + } + } + } + } + } + + if (isHollow) + { + shellThickness = 0; + if (shell != null) + { + shellThickness = 1.0 - shell.thickness; + } + for (int x = xMin; x < xMax; x++) + { + int indexXY = (x - xMin) * ySize - yMin; + int indexXZ = (x - xMin) * zSize - zMin; + int distanceX = asteroidX - (x + chunkX); + distanceX *= distanceX; + + for (int z = zMin; z < zMax; z++) + { + float sizeModY = sizeYArray[indexXZ + z]; + float sizeY = size + sizeYArray[indexXZ + z]; + sizeY *= sizeY; + int distanceZ = asteroidZ - (z + chunkZ); + distanceZ *= distanceZ; + + for (int y = yMin; y < yMax; y++) + { + float sizeX = size + sizeXArray[(y - yMin) * zSize + z - zMin]; + float sizeZ = size + sizeZArray[indexXY + y]; + sizeX *= sizeX; + sizeZ *= sizeZ; + int distanceY = asteroidY - y; + distanceY *= distanceY; + float distance = distanceX / sizeX + distanceY / sizeY + distanceZ / sizeZ; + distance += this.asteroidTurbulance.getNoise(x + chunkX, y, z + chunkZ); + + if (distance <= 1) + { + BlockState state = primer.getBlockState(new BlockPos(x, y, z)); + BlockState stateAbove = primer.getBlockState(new BlockPos(x, y + 1, z)); + if (Blocks.AIR == stateAbove.getBlock() && (state.getBlock() == GCBlocks.ASTEROID_ROCK || state.getBlock() == GCBlocks.ASTEROID_ROCK_1 || state.getBlock() == GCBlocks.ASTEROID_ROCK_2 || state.getBlock() == Blocks.GRASS_BLOCK)) + { + if (this.rand.nextInt(GLOWSTONE_CHANCE) == 0) + { + primer.setBlockState(new BlockPos(x, y, z), Blocks.GLOWSTONE.defaultBlockState(), false); +// blockArray[index] = this.LIGHT; +// metaArray[index] = this.LIGHT_META; + } + } + } + } + } + } + } + } + + private final int getTerrainHeightFor(float yMod, int asteroidY, int asteroidSize) + { + return (int) (asteroidY - asteroidSize / 4 + yMod * 1.5F); + } + + private final int getTerrainHeightAt(int x, int z, float[] yModArray, int xMin, int zMin, int zSize, int asteroidY, int asteroidSize) + { + final int index = (x - xMin) * zSize - zMin; + if (index < yModArray.length && index >= 0) + { + final float yMod = yModArray[index]; + return this.getTerrainHeightFor(yMod, asteroidY, asteroidSize); + } + return 1; + } + + @Override + protected Codec codec() { + return CODEC; + } + + @Override + public void applyCarvers(WorldGenRegion region, long seed, RandomState randomState, BiomeManager biomeManager, StructureManager structureManager, ChunkAccess chunkAccess, GenerationStep.Carving carving) { + int chunkX = chunkAccess.getPos().x; + int chunkZ = chunkAccess.getPos().z; + + int x = chunkX << 4; + int z = chunkZ << 4; + if (!AsteroidChunkGenerator.chunksDone.add(new BlockVec3(x, 0, z))) + { + return; + } + +// BlockFalling.fallInstantly = true; +// this.world.getBiome(new BlockPos(x + 16, 0, z + 16)); +// BlockFalling.fallInstantly = false; + + this.rand.setSeed(seed); + long var7 = this.rand.nextLong() / 2L * 2L + 1L; + long var9 = this.rand.nextLong() / 2L * 2L + 1L; + this.rand.setSeed(chunkX * var7 + chunkZ * var9 ^ seed); + + //50:50 chance to include small blocks each chunk + if (this.rand.nextBoolean()) { + double density = this.asteroidDensity.getNoise(chunkX * 16, chunkZ * 16) * 0.54; + double numOfBlocks = this.clamp(this.randFromPoint(chunkX, chunkZ), .4, 1) * AsteroidChunkGenerator.MAX_BLOCKS_PER_CHUNK * density + AsteroidChunkGenerator.MIN_BLOCKS_PER_CHUNK; + int y0 = this.rand.nextInt(2); + Block block; + int yRange = AsteroidChunkGenerator.MAX_ASTEROID_Y - AsteroidChunkGenerator.MIN_ASTEROID_Y; + x += 4; + z += 4; + + for (int i = 0; i < numOfBlocks; i++) { + int y = this.rand.nextInt(yRange) + AsteroidChunkGenerator.MIN_ASTEROID_Y; + + //50:50 chance vertically as well + if (y0 == (y / 16) % 2) { + int px = x + this.rand.nextInt(AsteroidChunkGenerator.CHUNK_SIZE_X); + int pz = z + this.rand.nextInt(AsteroidChunkGenerator.CHUNK_SIZE_Z); + + block = GCBlocks.ASTEROID_ROCK; + + if (this.rand.nextInt(ILMENITE_CHANCE) == 0) { + block = GCBlocks.ILMENITE_ORE; + } else if (this.rand.nextInt(IRON_CHANCE) == 0) { + block = GCBlocks.MARS_IRON_ORE; + } else if (this.rand.nextInt(ALUMINUM_CHANCE) == 0) { + block = GCBlocks.ALUMINUM_ORE; + } + + chunkAccess.setBlockState(new BlockPos(px, y, pz), block.defaultBlockState(), false); + int count = 9; + if (!(chunkAccess.getBlockState(new BlockPos(px - 1, y, pz)).isAir())) { + count = 1; + } else if (!(chunkAccess.getBlockState(new BlockPos(px - 2, y, pz)).isAir())) { + count = 3; + } else if (!(chunkAccess.getBlockState(new BlockPos(px - 3, y, pz)).isAir())) { + count = 5; + } else if (!(chunkAccess.getBlockState(new BlockPos(px - 4, y, pz)).isAir())) { + count = 7; + } +//LIGHTEMP world.setLightFor(EnumSkyBlock.BLOCK, new BlockPos(px - (count > 1 ? 1 : 0), y, pz), count); + } + } + } + + if (this.largeAsteroidsLastChunkX != chunkX || this.largeAsteroidsLastChunkZ != chunkZ) + { + this.generateChunkData(null, null, null, chunkAccess); + } + + this.rand.setSeed(chunkX * var7 + chunkZ * var9 ^ seed); + + //Look for hollow asteroids to populate + if (!this.largeAsteroids.isEmpty()) + { + for (AsteroidData asteroidIndex : new ArrayList(this.largeAsteroids)) + { + if (!asteroidIndex.isHollow) + { + continue; + } + + float[] sizeYArray = asteroidIndex.sizeYArray; + int xMin = asteroidIndex.xMinArray; + int zMin = asteroidIndex.zMinArray; + int zSize = asteroidIndex.zSizeArray; + int asteroidY = asteroidIndex.asteroidYArray; + int asteroidSize = asteroidIndex.asteroidSizeArray; + boolean treesdone = false; + + if (rand.nextInt(AsteroidChunkGenerator.TREE_CHANCE) == 0) + { + int treeType = rand.nextInt(3); + if (treeType == 1) + { + treeType = 0; + } + BlockState log = Blocks.OAK_LOG.defaultBlockState(); + BlockState leaves = Blocks.OAK_LEAVES.defaultBlockState(); + /**WorldGenTrees wg = new WorldGenTrees(false, 2, log, leaves, false); + for (int tries = 0; tries < 5; tries++) + { + int i = rand.nextInt(16) + x + 8; + int k = rand.nextInt(16) + z + 8; + if (wg.generate(world, rand, new BlockPos(i, this.getTerrainHeightAt(i - x, k - z, sizeYArray, xMin, zMin, zSize, asteroidY, asteroidSize), k))) + { + break; + } + }**/ + treesdone = true; + } + if (!treesdone || rand.nextInt(AsteroidChunkGenerator.TALL_GRASS_CHANCE) == 0) + { + int i = rand.nextInt(16) + x + 8; + int k = rand.nextInt(16) + z + 8; + //new WorldGenTallGrass(GRASS_TYPE).generate(world, rand, new BlockPos(i, this.getTerrainHeightAt(i - x, k - z, sizeYArray, xMin, zMin, zSize, asteroidY, asteroidSize), k)); + } + if (rand.nextInt(AsteroidChunkGenerator.FLOWER_CHANCE) == 0) + { + int i = rand.nextInt(16) + x + 8; + int k = rand.nextInt(16) + z + 8; + int[] types = new int[]{2, 4, 5, 7}; + //new WorldGenFlowers(this.FLOWER, Blocks.POPPY).generate(world, rand, new BlockPos(i, this.getTerrainHeightAt(i - x, k - z, sizeYArray, xMin, zMin, zSize, asteroidY, asteroidSize), k)); + } + if (rand.nextInt(AsteroidChunkGenerator.LAVA_CHANCE) == 0) + { + int i = rand.nextInt(16) + x + 8; + int k = rand.nextInt(16) + z + 8; + //new WorldGenLakes(this.LAVA).generate(world, rand, new BlockPos(i, this.getTerrainHeightAt(i - x, k - z, sizeYArray, xMin, zMin, zSize, asteroidY, asteroidSize), k)); + } + if (rand.nextInt(AsteroidChunkGenerator.WATER_CHANCE) == 0) + { + int i = rand.nextInt(16) + x + 8; + int k = rand.nextInt(16) + z + 8; + //new WorldGenLakes(this.WATER).generate(world, rand, new BlockPos(i, this.getTerrainHeightAt(i - x, k - z, sizeYArray, xMin, zMin, zSize, asteroidY, asteroidSize), k)); + } + } + } + + //Update all block lighting + for (int xx = 0; xx < 16; xx++) + { + int xPos = x + xx; + for (int zz = 0; zz < 16; zz++) + { + int zPos = z + zz; + + //Asteroid at min height 48, size 20, can't have lit blocks below 16 + for (int y = 16; y < 240; y++) + { +//LIGHTTEMP world.checkLightFor(EnumSkyBlock.BLOCK, new BlockPos(xPos, y, zPos)); + } + } + } + + //this.dungeonGenerator.generate(this.world, this.rand, new ChunkPos(chunkX, chunkZ)); + } + + @Override + public void buildSurface(WorldGenRegion region, StructureManager structureManager, RandomState randomState, ChunkAccess chunkAccess) { + + } + + @Override + public void spawnOriginalMobs(WorldGenRegion region) { + + } + + @Override + public int getGenDepth() { + return 0; + } + + @Override + public CompletableFuture fillFromNoise(Executor executor, Blender blender, RandomState randomState, StructureManager structureManager, ChunkAccess chunkAccess) { + + CompletableFuture future = new CompletableFuture<>(); + + executor.execute(() -> { + try { + // Example asynchronous operation (replace with your actual logic) + ChunkAccess result = generateChunkData(blender, randomState, structureManager, chunkAccess); + future.complete(result); + } catch (Exception e) { + future.completeExceptionally(e); + } + }); + + return future; + } + + public void resetBase() + { + //this.dungeonGenerator.reset(); + } + + + + @Override + public int getSeaLevel() { + return 0; + } + + @Override + public int getMinY() { + return 0; + } + + @Override + public int getBaseHeight(int i, int j, Heightmap.Types types, LevelHeightAccessor levelHeightAccessor, RandomState randomState) { + return 0; + } + + @Override + public NoiseColumn getBaseColumn(int i, int j, LevelHeightAccessor levelHeightAccessor, RandomState randomState) { + return null; + } + + @Override + public void addDebugScreenInfo(List list, RandomState randomState, BlockPos blockPos) { + + } + + private float randFromPointPos(int x, int z) + { + int n = x + z * 57; + n ^= n << 13; + n = n * (n * n * 15731 + 789221) + 1376312589 & 0x3fffffff; + return 1.0F - n / 1073741824.0F; + } + + private final void setOtherAxisFrequency(float frequency) + { + this.asteroidSkewX.frequencyY = frequency; + this.asteroidSkewX.frequencyZ = frequency; + + this.asteroidSkewY.frequencyX = frequency; + this.asteroidSkewY.frequencyZ = frequency; + + this.asteroidSkewZ.frequencyX = frequency; + this.asteroidSkewZ.frequencyY = frequency; + } + + private final int clamp(int x, int min, int max) + { + if (x < min) + { + x = min; + } + else if (x > max) + { + x = max; + } + return x; + } + + private final double clamp(double x, double min, double max) + { + if (x < min) + { + x = min; + } + else if (x > max) + { + x = max; + } + return x; + } + private float randFromPoint(int x, int y, int z) + { + int n = x + z * 57 + y * 571; + n ^= n << 13; + n = n * (n * n * 15731 + 789221) + 1376312589 & 0x7fffffff; + return 1.0F - n / 1073741824.0F; + } + + private float randFromPoint(int x, int z) + { + int n = x + z * 57; + n ^= n << 13; + n = n * (n * n * 15731 + 789221) + 1376312589 & 0x7fffffff; + return 1.0F - n / 1073741824.0F; + } + + public void addAsteroid(int x, int y, int z, int size, int core) + { + AsteroidData coords = new AsteroidData(x, y, z, size, core); + if (!this.asteroids.contains(coords)) + { + if (this.dataNotLoaded) + { + this.loadAsteroidSavedData(); + } + if (!this.asteroids.contains(coords)) + { + this.addToNBT(this.datafile.datacompound, coords); + this.asteroids.add(coords); + } + } + } + + private void addToNBT(CompoundTag nbt, AsteroidData coords) + { + ListTag coordList = nbt.getList("coords", 10); + CompoundTag tag = new CompoundTag(); + coords.writeToNBT(tag); + coordList.add(tag); + nbt.put("coords", coordList); + this.datafile.setDirty(); + Path dataPath = Path.of(currentWorldSaveDirectory.toString(), saveDataID); + Path dataFile = dataPath.resolve("data.dat"); + this.setData(dataFile, datafile); + } + + private void writeToNBT(CompoundTag nbt) + { + ListTag coordList = new ListTag(); + for (AsteroidData coords : this.asteroids) + { + CompoundTag tag = new CompoundTag(); + coords.writeToNBT(tag); + coordList.add(tag); + } + nbt.put("coords", coordList); + this.datafile.setDirty(); + Path dataPath = Path.of(currentWorldSaveDirectory.toString(), saveDataID); + Path dataFile = dataPath.resolve("data.dat"); + this.setData(dataFile, datafile); + } + + private static class AsteroidData + { + public boolean isHollow; + public float[] sizeYArray; + public int xMinArray; + public int zMinArray; + public int xMax; + public int zMax; + public int zSizeArray; + public int asteroidSizeArray; + public int asteroidXArray; + public int asteroidYArray; + public int asteroidZArray; + + public AsteroidData(boolean hollow, float[] sizeYArray2, int xMin, int zMin, int xmax, int zmax, int zSize, int size, int asteroidX, int asteroidY, int asteroidZ) + { + this.isHollow = hollow; + this.sizeYArray = sizeYArray2.clone(); + this.xMinArray = xMin; + this.zMinArray = zMin; + this.xMax = xmax; + this.zMax = zmax; + this.zSizeArray = zSize; + this.asteroidSizeArray = size; + this.asteroidXArray = asteroidX; + this.asteroidYArray = asteroidY; + this.asteroidZArray = asteroidZ; + } + protected BlockVec3 centre; + protected int sizeAndLandedFlag = 15; + protected int coreAndSpawnedFlag = -2; + + public AsteroidData(int x, int y, int z) + { + this.centre = new BlockVec3(x, y, z); + } + + public AsteroidData(int x, int y, int z, int size, int core) + { + this.centre = new BlockVec3(x, y, z); + this.sizeAndLandedFlag = size; + this.coreAndSpawnedFlag = core; + } + + public AsteroidData(BlockVec3 bv) + { + this.centre = bv; + } + + @Override + public int hashCode() + { + if (this.centre != null) + { + return this.centre.hashCode(); + } + else + { + return 0; + } + } + + @Override + public boolean equals(Object o) + { + if (o instanceof AsteroidData) + { + BlockVec3 vector = ((AsteroidData) o).centre; + return this.centre.x == vector.x && this.centre.y == vector.y && this.centre.z == vector.z; + } + + if (o instanceof BlockVec3) + { + BlockVec3 vector = (BlockVec3) o; + return this.centre.x == vector.x && this.centre.y == vector.y && this.centre.z == vector.z; + } + + return false; + } + + public CompoundTag writeToNBT(CompoundTag tag) + { + tag.putInt("x", this.centre.x); + tag.putInt("y", this.centre.y); + tag.putInt("z", this.centre.z); + tag.putInt("coreAndFlag", this.coreAndSpawnedFlag); + tag.putInt("sizeAndFlag", this.sizeAndLandedFlag); + + return tag; + } + + public static AsteroidData readFromNBT(CompoundTag tag) + { + BlockVec3 tempVector = new BlockVec3(); + tempVector.x = tag.getInt("x"); + tempVector.y = tag.getInt("y"); + tempVector.z = tag.getInt("z"); + + AsteroidData roid = new AsteroidData(tempVector); + if (tag.hasUUID("coreAndFlag")) + { + roid.coreAndSpawnedFlag = tag.getInt("coreAndFlag"); + } + if (tag.hasUUID("sizeAndFlag")) + { + roid.sizeAndLandedFlag = tag.getInt("sizeAndFlag"); + } + + return roid; + } + } + + private int getIndex(int x, int y, int z) + { + return x * AsteroidChunkGenerator.CHUNK_SIZE_Y * 16 | z * AsteroidChunkGenerator.CHUNK_SIZE_Y | y; + } + + public void loadAsteroidSavedData() { + Path dataPath = Path.of(currentWorldSaveDirectory.toString(), saveDataID); + Path dataFile = dataPath.resolve("data.dat"); + + this.datafile = this.loadData(dataFile); + + if (this.datafile == null) + { + if (!Files.exists(dataFile)) + { + try { + Files.createDirectories(dataPath); + } catch (IOException e) { + throw new RuntimeException(e); + } + try { + Files.createFile(dataFile); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + this.datafile = new AsteroidSaveData(""); + this.writeToNBT(this.datafile.datacompound); + this.setData(dataFile, this.datafile); + } + else + { + this.readFromNBT(this.datafile.datacompound); + } + + this.dataNotLoaded = false; + + } + + public void setData(Path filePath, AsteroidSaveData data) { + try { + NbtIo.write(data.datacompound, filePath); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + public AsteroidSaveData loadData(Path filePath) { + if (Files.exists(filePath)) + { + CompoundTag tag; + try { + tag = NbtIo.read(filePath); + } catch (IOException e) { + throw new RuntimeException(e); + } + AsteroidSaveData saveData = new AsteroidSaveData(""); + saveData.datacompound = tag; + return saveData; + } + else + { + return null; + } + } + + + private void readFromNBT(CompoundTag nbt) + { + ListTag coordList = nbt.getList("coords", 10); + if (coordList.size() > 0) + { + for (int j = 0; j < coordList.size(); j++) + { + CompoundTag tag1 = coordList.getCompound(j); + + if (tag1 != null) + { + this.asteroids.add(AsteroidData.readFromNBT(tag1)); + } + } + } + } + + public BlockVec3 isLargeAsteroidAt(int x0, int z0) + { + int xToCheck; + int zToCheck; + for (int i0 = 0; i0 <= 32; i0++) + { + for (int i1 = -i0; i1 <= i0; i1++) + { + xToCheck = (x0 >> 4) + i0; + zToCheck = (z0 >> 4) + i1; + + if (isLargeAsteroidAt0(xToCheck * 16, zToCheck * 16)) + { + return new BlockVec3(xToCheck * 16, 0, zToCheck * 16); + } + + xToCheck = (x0 >> 4) + i0; + zToCheck = (z0 >> 4) - i1; + + if (isLargeAsteroidAt0(xToCheck * 16, zToCheck * 16)) + { + return new BlockVec3(xToCheck * 16, 0, zToCheck * 16); + } + + xToCheck = (x0 >> 4) - i0; + zToCheck = (z0 >> 4) + i1; + + if (isLargeAsteroidAt0(xToCheck * 16, zToCheck * 16)) + { + return new BlockVec3(xToCheck * 16, 0, zToCheck * 16); + } + + xToCheck = (x0 >> 4) - i0; + zToCheck = (z0 >> 4) - i1; + + if (isLargeAsteroidAt0(xToCheck * 16, zToCheck * 16)) + { + return new BlockVec3(xToCheck * 16, 0, zToCheck * 16); + } + } + } + + return null; + } + + private boolean isLargeAsteroidAt0(int x0, int z0) + { + for (int x = x0; x < x0 + AsteroidChunkGenerator.CHUNK_SIZE_X; x += 2) + { + for (int z = z0; z < z0 + AsteroidChunkGenerator.CHUNK_SIZE_Z; z += 2) + { + if ((Math.abs(this.randFromPoint(x, z)) < (this.asteroidDensity.getNoise(x, z) + .4) / AsteroidChunkGenerator.ASTEROID_CHANCE)) + { + return true; + } + } + } + + return false; + } + +} diff --git a/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidSaveData.java b/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidSaveData.java new file mode 100644 index 000000000..bf0ef9471 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/gen/custom/AsteroidSaveData.java @@ -0,0 +1,51 @@ +package dev.galacticraft.mod.world.gen.custom; + +import dev.galacticraft.mod.Constant; +import dev.galacticraft.mod.data.GCDataGenerator; +import net.fabricmc.fabric.api.event.lifecycle.v1.ServerLifecycleEvents; +import net.minecraft.data.CachedOutput; +import net.minecraft.data.DataProvider; +import net.minecraft.nbt.CompoundTag; +import net.minecraft.nbt.NbtIo; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.server.MinecraftServer; +import net.minecraft.server.dedicated.DedicatedServer; +import net.minecraft.server.level.ServerLevel; +import net.minecraft.util.datafix.DataFixTypes; +import net.minecraft.world.level.saveddata.SavedData; +import net.minecraft.world.level.storage.DimensionDataStorage; +import net.minecraft.world.level.storage.LevelStorageSource; + +import java.io.*; +import java.nio.file.Path; +import java.util.concurrent.CompletableFuture; + +public class AsteroidSaveData extends SavedData{ + + public static final String saveDataID = "dimensions/galacticraft/asteroid/data"; + + public CompoundTag datacompound; + + public AsteroidSaveData(String s) + { + super(); + this.datacompound = new CompoundTag(); + } + + public void readFromNBT(CompoundTag nbt) + { + this.datacompound = nbt.getCompound("asteroids"); + } + + @Override + public CompoundTag save(CompoundTag nbt) + { + nbt.put("asteroids", this.datacompound); + return nbt; + } + + public static AsteroidSaveData load(CompoundTag compound) { + String value = compound.getString("someValue"); + return new AsteroidSaveData(value); + } +} diff --git a/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlock.java b/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlock.java new file mode 100644 index 000000000..7c24f90bb --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlock.java @@ -0,0 +1,22 @@ +package dev.galacticraft.mod.world.gen.custom; + +import net.minecraft.world.level.block.Block; + +import java.util.ArrayList; +public class SpecialAsteroidBlock +{ + public Block block; + public int probability; + public double thickness; //Arbitrary scale from 0 to 1; + public int index; + public static ArrayList register = new ArrayList<>(); + + public SpecialAsteroidBlock(Block block, int probability, double thickness) + { + this.block = block; + this.probability = probability; + this.thickness = thickness; + this.index = register.size(); + register.add(this); + } +} diff --git a/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlockHandler.java b/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlockHandler.java new file mode 100644 index 000000000..5a2f1b437 --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/gen/custom/SpecialAsteroidBlockHandler.java @@ -0,0 +1,46 @@ +package dev.galacticraft.mod.world.gen.custom; + +import java.util.ArrayList; +import java.util.Random; +public class SpecialAsteroidBlockHandler +{ + ArrayList asteroidBlocks; + + public SpecialAsteroidBlockHandler(SpecialAsteroidBlock... asteroidBlocks) + { + this.asteroidBlocks = new ArrayList(); + for (SpecialAsteroidBlock asteroidBlock : this.asteroidBlocks) + { + for (int i = 0; i < asteroidBlock.probability; i++) + { + this.asteroidBlocks.add(asteroidBlock); + } + } + } + + public SpecialAsteroidBlockHandler() + { + this.asteroidBlocks = new ArrayList(); + } + + public void addBlock(SpecialAsteroidBlock asteroidBlock) + { + for (int i = 0; i < asteroidBlock.probability; i++) + { + this.asteroidBlocks.add(asteroidBlock); + } + } + + public SpecialAsteroidBlock getBlock(Random rand, int size) + { + int s = this.asteroidBlocks.size(); + if (s < 10) + { + return this.asteroidBlocks.get(rand.nextInt(s)); + } + + Double r = rand.nextDouble(); + int index = (int) (s * Math.pow(r, (size + 5) * 0.05D)); + return this.asteroidBlocks.get(index); + } +} diff --git a/src/main/java/dev/galacticraft/mod/world/gen/surfacebuilder/AsteroidSurfaceRules.java b/src/main/java/dev/galacticraft/mod/world/gen/surfacebuilder/AsteroidSurfaceRules.java new file mode 100644 index 000000000..32740f57c --- /dev/null +++ b/src/main/java/dev/galacticraft/mod/world/gen/surfacebuilder/AsteroidSurfaceRules.java @@ -0,0 +1,54 @@ +/* + * Copyright (c) 2019-2024 Team Galacticraft + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package dev.galacticraft.mod.world.gen.surfacebuilder; + +import dev.galacticraft.mod.content.GCBlocks; +import dev.galacticraft.mod.world.biome.GCBiomes; +import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.block.Blocks; +import net.minecraft.world.level.levelgen.SurfaceRules; +import net.minecraft.world.level.levelgen.VerticalAnchor; +import org.jetbrains.annotations.Contract; +import org.jetbrains.annotations.NotNull; + +public class AsteroidSurfaceRules { + private static final SurfaceRules.RuleSource BEDROCK = block(Blocks.BEDROCK); + public static final SurfaceRules.RuleSource HARD_ROCK = block(GCBlocks.HARD_VENUS_ROCK); + + public static final SurfaceRules.RuleSource ASTEROID = createDefaultRule(); + + public static @NotNull SurfaceRules.RuleSource createDefaultRule() { + return SurfaceRules.sequence( + SurfaceRules.ifTrue( + SurfaceRules.isBiome(GCBiomes.Asteroid.ASTEROID_FIELD), + HARD_ROCK + ), + SurfaceRules.ifTrue(SurfaceRules.verticalGradient("bedrock_floor", VerticalAnchor.bottom(), VerticalAnchor.aboveBottom(5)), BEDROCK) + ); + } + + @Contract("_ -> new") + private static @NotNull SurfaceRules.RuleSource block(@NotNull Block block) { + return SurfaceRules.state(block.defaultBlockState()); + } +} diff --git a/src/main/resources/assets/galacticraft/models/block/air_lock_seal.json b/src/main/resources/assets/galacticraft/models/block/air_lock_seal.json new file mode 100644 index 000000000..81fcd308e --- /dev/null +++ b/src/main/resources/assets/galacticraft/models/block/air_lock_seal.json @@ -0,0 +1,21 @@ +{ + "textures": { + "particle": "galacticraft:block/tin_decoration", + "top": "galacticraft:block/tin_decoration", + "side": "galacticraft:block/tin_decoration", + "bottom": "galacticraft:block/tin_decoration" + }, + "elements": [ + { "from": [ 4, 0, 0 ], + "to": [ 12, 16, 16 ], + "faces": { + "down": {"texture": "#top"}, + "up": {"texture": "#bottom"}, + "north": {"texture": "#side"}, + "east": {"texture": "#side"}, + "south": {"texture": "#side"}, + "west": {"texture": "#side"} + } + } + ] +} diff --git a/src/main/resources/assets/galacticraft/textures/block/cobbled_lunaslate.png b/src/main/resources/assets/galacticraft/textures/block/cobbled_lunaslate.png new file mode 100644 index 000000000..b4c155f58 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/cobbled_lunaslate.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/deepslate_aluminum_ore.png b/src/main/resources/assets/galacticraft/textures/block/deepslate_aluminum_ore.png new file mode 100644 index 000000000..8a3ca9bfb Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/deepslate_aluminum_ore.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/deepslate_silicon_ore.png b/src/main/resources/assets/galacticraft/textures/block/deepslate_silicon_ore.png new file mode 100644 index 000000000..7259ae700 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/deepslate_silicon_ore.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/deepslate_tin_ore.png b/src/main/resources/assets/galacticraft/textures/block/deepslate_tin_ore.png new file mode 100644 index 000000000..e4e0d31a3 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/deepslate_tin_ore.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_side.png b/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_side.png new file mode 100644 index 000000000..3690b66ef Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_side.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_top.png b/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_top.png new file mode 100644 index 000000000..10411fe1d Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/detailed_dark_decoration_top.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/lunaslate_copper_ore.png b/src/main/resources/assets/galacticraft/textures/block/lunaslate_copper_ore.png new file mode 100644 index 000000000..cbe069ee6 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/lunaslate_copper_ore.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/lunaslate_tin_ore.png b/src/main/resources/assets/galacticraft/textures/block/lunaslate_tin_ore.png new file mode 100644 index 000000000..a9f47fc04 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/lunaslate_tin_ore.png differ diff --git a/src/main/resources/assets/galacticraft/textures/block/lunaslate_top.png b/src/main/resources/assets/galacticraft/textures/block/lunaslate_top.png new file mode 100644 index 000000000..46f07be0f Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/block/lunaslate_top.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_beef.png b/src/main/resources/assets/galacticraft/textures/item/canned_beef.png deleted file mode 100644 index 0152403b1..000000000 Binary files a/src/main/resources/assets/galacticraft/textures/item/canned_beef.png and /dev/null differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_apple.png b/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_apple.png deleted file mode 100644 index c9df0297b..000000000 Binary files a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_apple.png and /dev/null differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_carrot.png b/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_carrot.png deleted file mode 100644 index 12299d94d..000000000 Binary files a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_carrot.png and /dev/null differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_melon.png b/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_melon.png deleted file mode 100644 index 4ad74b814..000000000 Binary files a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_melon.png and /dev/null differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_potato.png b/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_potato.png deleted file mode 100644 index 503db6df6..000000000 Binary files a/src/main/resources/assets/galacticraft/textures/item/canned_dehydrated_potato.png and /dev/null differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_food_label.png b/src/main/resources/assets/galacticraft/textures/item/canned_food_label.png new file mode 100644 index 000000000..ffe7eab93 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/canned_food_label.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/canned_food_template.png b/src/main/resources/assets/galacticraft/textures/item/canned_food_template.png new file mode 100644 index 000000000..f7a7745a5 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/canned_food_template.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/raw_aluminum.png b/src/main/resources/assets/galacticraft/textures/item/raw_aluminum.png new file mode 100644 index 000000000..1a23e1ea4 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/raw_aluminum.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/raw_lead.png b/src/main/resources/assets/galacticraft/textures/item/raw_lead.png new file mode 100644 index 000000000..59b75dfb9 Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/raw_lead.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/raw_tin.png b/src/main/resources/assets/galacticraft/textures/item/raw_tin.png new file mode 100644 index 000000000..745b1497f Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/raw_tin.png differ diff --git a/src/main/resources/assets/galacticraft/textures/item/raw_titanium.png b/src/main/resources/assets/galacticraft/textures/item/raw_titanium.png new file mode 100644 index 000000000..aa28c329a Binary files /dev/null and b/src/main/resources/assets/galacticraft/textures/item/raw_titanium.png differ diff --git a/src/main/resources/fabric.mod.json b/src/main/resources/fabric.mod.json index eee30c83b..e5c6f4b7d 100644 --- a/src/main/resources/fabric.mod.json +++ b/src/main/resources/fabric.mod.json @@ -139,6 +139,9 @@ ], "jei_mod_plugin": [ "dev.galacticraft.mod.compat.jei.GCJEIPlugin" + ], + "appleskin": [ + "dev.galacticraft.mod.compat.AppleSkinEventHandler" ] }, "mixins": [ diff --git a/src/main/resources/galacticraft.mixins.json b/src/main/resources/galacticraft.mixins.json index 66514a244..d9ecfe67e 100644 --- a/src/main/resources/galacticraft.mixins.json +++ b/src/main/resources/galacticraft.mixins.json @@ -28,6 +28,8 @@ "client.ClientPacketListenerMixin" ], "client": [ + "client.ClientTooltipMixin", + "client.FabricItemMixin", "client.AbstractClientPlayerMixin", "client.AlphaWarningTitleScreenMixin", "client.AnimalModelAgeableListModel",