diff --git a/rainbow.svg b/rainbow.svg
new file mode 100644
index 00000000..4f03bf9e
--- /dev/null
+++ b/rainbow.svg
@@ -0,0 +1,128 @@
+
+
+
+
diff --git a/src/main/java/com/minelittlepony/unicopia/UEntities.java b/src/main/java/com/minelittlepony/unicopia/UEntities.java
index 908a35ff..424e9fd5 100644
--- a/src/main/java/com/minelittlepony/unicopia/UEntities.java
+++ b/src/main/java/com/minelittlepony/unicopia/UEntities.java
@@ -1,23 +1,23 @@
package com.minelittlepony.unicopia;
-import java.util.List;
-
import com.minelittlepony.unicopia.entity.EntityCloud;
import com.minelittlepony.unicopia.entity.EntityConstructionCloud;
import com.minelittlepony.unicopia.entity.EntityRacingCloud;
+import com.minelittlepony.unicopia.entity.EntityRainbow;
import com.minelittlepony.unicopia.entity.EntitySpell;
import com.minelittlepony.unicopia.entity.EntitySpellbook;
import com.minelittlepony.unicopia.entity.EntityProjectile;
import com.minelittlepony.unicopia.entity.EntityWildCloud;
+import com.minelittlepony.unicopia.forgebullshit.BiomeBS;
import com.minelittlepony.unicopia.forgebullshit.EntityType;
import com.minelittlepony.unicopia.render.RenderCloud;
import com.minelittlepony.unicopia.render.RenderGem;
import com.minelittlepony.unicopia.render.RenderProjectile;
+import com.minelittlepony.unicopia.render.RenderRainbow;
import com.minelittlepony.unicopia.render.RenderSpellbook;
import net.minecraft.entity.EnumCreatureType;
import net.minecraft.world.biome.Biome;
-import net.minecraft.world.biome.Biome.SpawnListEntry;
import net.minecraft.world.biome.BiomeEnd;
import net.minecraft.world.biome.BiomeHell;
import net.minecraftforge.common.BiomeManager;
@@ -38,6 +38,8 @@ public class UEntities {
builder.creature(EntityConstructionCloud.class, "construction_cloud"),
builder.creature(EntitySpell.class, "magic_spell"),
builder.creature(EntitySpellbook.class, "spellbook"),
+ builder.creature(EntityRainbow.Spawner.class, "rainbow_spawner"),
+ builder.projectile(EntityRainbow.class, "rainbow", 500, 5),
builder.projectile(EntityProjectile.class, "thrown_item", 10, 5)
);
}
@@ -47,19 +49,18 @@ public class UEntities {
RenderingRegistry.registerEntityRenderingHandler(EntitySpell.class, RenderGem::new);
RenderingRegistry.registerEntityRenderingHandler(EntityProjectile.class, RenderProjectile::new);
RenderingRegistry.registerEntityRenderingHandler(EntitySpellbook.class, RenderSpellbook::new);
+ RenderingRegistry.registerEntityRenderingHandler(EntityRainbow.class, RenderRainbow::new);
}
static void registerSpawnEntries(Biome biome) {
-
if (!(biome instanceof BiomeHell || biome instanceof BiomeEnd)) {
- List entries = biome.getSpawnableList(EnumCreatureType.AMBIENT);
- entries.stream().filter(p -> p.entityClass == EntityWildCloud.class).findFirst().orElseGet(() -> {
- entries.add(
- BiomeManager.oceanBiomes.contains(biome) ?
- EntityWildCloud.SPAWN_ENTRY_LAND : EntityWildCloud.SPAWN_ENTRY_OCEAN
- );
- return null;
- });
+
+ BiomeBS.addSpawnEntry(biome, EnumCreatureType.AMBIENT, EntityWildCloud.class, b ->
+ BiomeManager.oceanBiomes.contains(b) ? EntityWildCloud.SPAWN_ENTRY_LAND : EntityWildCloud.SPAWN_ENTRY_OCEAN
+ );
+ BiomeBS.addSpawnEntry(biome, EnumCreatureType.CREATURE, EntityRainbow.Spawner.class, b -> EntityRainbow.SPAWN_ENTRY);
}
}
+
+
}
diff --git a/src/main/java/com/minelittlepony/unicopia/entity/EntityRainbow.java b/src/main/java/com/minelittlepony/unicopia/entity/EntityRainbow.java
new file mode 100644
index 00000000..28385c11
--- /dev/null
+++ b/src/main/java/com/minelittlepony/unicopia/entity/EntityRainbow.java
@@ -0,0 +1,128 @@
+package com.minelittlepony.unicopia.entity;
+
+import net.minecraft.entity.EntityLiving;
+import net.minecraft.entity.effect.EntityWeatherEffect;
+import net.minecraft.nbt.NBTTagCompound;
+import net.minecraft.util.SoundCategory;
+import net.minecraft.util.math.AxisAlignedBB;
+import net.minecraft.util.math.MathHelper;
+import net.minecraft.world.World;
+import net.minecraft.world.biome.Biome.SpawnListEntry;
+
+public class EntityRainbow extends EntityWeatherEffect {
+
+ public static final SpawnListEntry SPAWN_ENTRY = new SpawnListEntry(EntityRainbow.Spawner.class, 1, 1, 1);
+
+ private int ticksAlive;
+
+ private double radius;
+
+ public static final int RAINBOW_MAX_SIZE = 180;
+ public static final int RAINBOW_MIN_SIZE = 50;
+
+ public EntityRainbow(World world) {
+ this(world, 0, 0, 0);
+ }
+
+ public EntityRainbow(World world, double x, double y, double z) {
+ super(world);
+
+ float yaw = (int)MathHelper.nextDouble((world == null ? rand : world.rand), 0, 360);
+
+ setLocationAndAngles(x, y, z, yaw, 0);
+
+ radius = MathHelper.nextDouble(world == null ? rand : world.rand, RAINBOW_MIN_SIZE, RAINBOW_MAX_SIZE);
+ ticksAlive = 10000;
+
+ ignoreFrustumCheck = true;
+
+ width = (float)radius;
+ height = width;
+ }
+
+ @Override
+ public void setPosition(double x, double y, double z) {
+ posX = x;
+ posY = y;
+ posZ = z;
+
+ setEntityBoundingBox(new AxisAlignedBB(
+ x - width, y - radius/2, z,
+ x + width, y + radius/2, z
+ ));
+ }
+
+ @Override
+ public AxisAlignedBB getRenderBoundingBox() {
+ return super.getRenderBoundingBox();
+ }
+
+ @Override
+ public SoundCategory getSoundCategory() {
+ return SoundCategory.WEATHER;
+ }
+
+ @Override
+ public boolean isInRangeToRenderDist(double distance) {
+ return true;
+ }
+
+ public double getRadius() {
+ return radius;
+ }
+
+ @Override
+ public void onUpdate() {
+ super.onUpdate();
+
+ if (ticksAlive-- <= 0) {
+ setDead();
+ }
+ }
+
+ @Override
+ protected void entityInit() {
+ }
+
+ @Override
+ protected void readEntityFromNBT(NBTTagCompound compound) {
+ }
+
+ @Override
+ protected void writeEntityToNBT(NBTTagCompound compound) {
+ }
+
+ public static class Spawner extends EntityLiving {
+
+ public static final AxisAlignedBB SPAWN_COLLISSION_RADIUS = new AxisAlignedBB(0, 0, 0, RAINBOW_MAX_SIZE, RAINBOW_MAX_SIZE, RAINBOW_MAX_SIZE);
+
+ public Spawner(World worldIn) {
+ super(worldIn);
+ this.setInvisible(true);
+ }
+
+ @Override
+ public boolean getCanSpawnHere() {
+ if (super.getCanSpawnHere()) {
+ return world.getEntitiesWithinAABB(EntityRainbow.class, SPAWN_COLLISSION_RADIUS.offset(getPosition())).size() == 0;
+ }
+
+ return false;
+ }
+
+ @Override
+ public int getMaxSpawnedInChunk() {
+ return 1;
+ }
+
+ @Override
+ public void onUpdate() {
+ super.onUpdate();
+ setDead();
+
+ EntityRainbow rainbow = new EntityRainbow(world);
+ rainbow.setPosition(posX, posY, posZ);
+ world.spawnEntity(rainbow);
+ }
+ }
+}
diff --git a/src/main/java/com/minelittlepony/unicopia/forgebullshit/BiomeBS.java b/src/main/java/com/minelittlepony/unicopia/forgebullshit/BiomeBS.java
index ff933eca..c04a0cb9 100644
--- a/src/main/java/com/minelittlepony/unicopia/forgebullshit/BiomeBS.java
+++ b/src/main/java/com/minelittlepony/unicopia/forgebullshit/BiomeBS.java
@@ -1,10 +1,15 @@
package com.minelittlepony.unicopia.forgebullshit;
+import java.util.List;
import java.util.Optional;
+import java.util.function.Function;
import com.google.common.collect.Lists;
+import net.minecraft.entity.EntityLivingBase;
+import net.minecraft.entity.EnumCreatureType;
import net.minecraft.world.biome.Biome;
+import net.minecraft.world.biome.Biome.SpawnListEntry;
import net.minecraftforge.common.BiomeManager;
import net.minecraftforge.common.BiomeManager.BiomeType;
@@ -24,4 +29,16 @@ public class BiomeBS {
.isPresent()
).findFirst();
}
+
+ /**
+ * Adds a spawn entry for the specified entity if one does not already exist.
+ */
+ public static void addSpawnEntry(Biome biome, EnumCreatureType list, Class extends EntityLivingBase> type, Function func) {
+ List entries = biome.getSpawnableList(list);
+
+ entries.stream().filter(p -> p.entityClass == type).findFirst().orElseGet(() -> {
+ entries.add(func.apply(biome));
+ return null;
+ });
+ }
}
diff --git a/src/main/java/com/minelittlepony/unicopia/render/RenderRainbow.java b/src/main/java/com/minelittlepony/unicopia/render/RenderRainbow.java
new file mode 100644
index 00000000..82624b13
--- /dev/null
+++ b/src/main/java/com/minelittlepony/unicopia/render/RenderRainbow.java
@@ -0,0 +1,67 @@
+package com.minelittlepony.unicopia.render;
+
+import org.lwjgl.opengl.GL11;
+
+import com.minelittlepony.unicopia.entity.EntityRainbow;
+
+import net.minecraft.client.Minecraft;
+import net.minecraft.client.renderer.BufferBuilder;
+import net.minecraft.client.renderer.GlStateManager;
+import net.minecraft.client.renderer.Tessellator;
+import net.minecraft.client.renderer.entity.Render;
+import net.minecraft.client.renderer.entity.RenderManager;
+import net.minecraft.client.renderer.vertex.DefaultVertexFormats;
+import net.minecraft.util.ResourceLocation;
+
+public class RenderRainbow extends Render {
+
+ public RenderRainbow(RenderManager renderManager) {
+ super(renderManager);
+ }
+
+ private static final ResourceLocation TEXTURE = new ResourceLocation("unicopia", "textures/environment/rainbow.png");
+
+ public void doRender(EntityRainbow entity, double x, double y, double z, float entityYaw, float partialTicks) {
+ bindEntityTexture(entity);
+
+ GlStateManager.pushMatrix();
+ GlStateManager.disableLighting();
+ GlStateManager.disableCull();
+ GlStateManager.enableBlend();
+ GlStateManager.blendFunc(GlStateManager.SourceFactor.SRC_ALPHA, GlStateManager.DestFactor.ONE_MINUS_SRC_ALPHA);
+
+ GlStateManager.translate(x, y, z);
+ GlStateManager.rotate(entityYaw, 0, 1, 0);
+
+ float distance = Minecraft.getMinecraft().getRenderViewEntity().getDistance(entity);
+
+
+ float maxDistance = 16 * Minecraft.getMinecraft().gameSettings.renderDistanceChunks;
+
+ GlStateManager.color(1, 1, 1, ((maxDistance - distance) / maxDistance) * 0.9f);
+
+ Tessellator tessellator = Tessellator.getInstance();
+ BufferBuilder bufferbuilder = tessellator.getBuffer();
+
+ double r = entity.getRadius();
+
+ bufferbuilder.begin(GL11.GL_QUADS, DefaultVertexFormats.POSITION_TEX);
+ bufferbuilder.pos(-r, r, 0).tex(1, 0).endVertex();
+ bufferbuilder.pos( r, r, 0).tex(0, 0).endVertex();
+ bufferbuilder.pos( r, 0, 0).tex(0, 1).endVertex();
+ bufferbuilder.pos(-r, 0, 0).tex(1, 1).endVertex();
+
+ tessellator.draw();
+
+ GlStateManager.disableBlend();
+ GlStateManager.enableCull();
+ GlStateManager.enableLighting();
+ GlStateManager.popMatrix();
+ }
+
+ @Override
+ protected ResourceLocation getEntityTexture(EntityRainbow entity) {
+ return TEXTURE;
+ }
+
+}
diff --git a/src/main/resources/assets/unicopia/textures/environment/rainbow.png b/src/main/resources/assets/unicopia/textures/environment/rainbow.png
new file mode 100644
index 00000000..018f310c
Binary files /dev/null and b/src/main/resources/assets/unicopia/textures/environment/rainbow.png differ