From 5c08de449c38b825c3948e840a0d5788566e6b4e Mon Sep 17 00:00:00 2001 From: haru315 Date: Sat, 14 May 2022 09:47:37 +0900 Subject: [PATCH 1/3] use generalized spiral points algorithm --- .../com/hbm/explosion/ExplosionNukeRay.java | 168 +++++++++--------- 1 file changed, 86 insertions(+), 82 deletions(-) diff --git a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java index 4131b4852..1e9cdaf3b 100644 --- a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java +++ b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java @@ -11,7 +11,7 @@ import net.minecraft.util.Vec3; import net.minecraft.world.World; public class ExplosionNukeRay { - + List affectedBlocks = new ArrayList(); int posX; int posY; @@ -28,6 +28,11 @@ public class ExplosionNukeRay { public boolean isAusf3Complete = false; private double overrideRange = 0; + + int gss_num_max; + int gss_num; + double gss_x; + double gss_y; public ExplosionNukeRay(World world, int x, int y, int z, int strength, int count, int speed, int length) { this.world = world; @@ -46,6 +51,39 @@ public class ExplosionNukeRay { //starts at around 80, becomes 8 at length 500 this.overrideRange = Math.max((Math.log(length) * 4 - 2.5D) * 10, 0); + + // Total number of points + this.gss_num_max = (int)(2.5 * Math.PI * Math.pow(this.strength,2)); + this.gss_num = 1; + + // The beginning of the generalized spiral points + this.gss_x = Math.PI; + this.gss_y = 0.0; + + } + // Raise one generalized spiral points + private void generateGssUp(){ + if (this.gss_num < this.gss_num_max) { + int k = this.gss_num + 1; + double hk = -1.0 + 2.0 * (k - 1.0) / (this.gss_num_max - 1.0); + this.gss_x = Math.acos(hk); + + double prev_lon = this.gss_y; + double lon = prev_lon + 3.6 / Math.sqrt(this.gss_num_max) / Math.sqrt(1.0 - hk * hk); + this.gss_y = lon % (Math.PI * 2); + } else { + this.gss_x = 0.0; + this.gss_y = 0.0; + } + this.gss_num++; + } + + // Get Cartesian coordinates for spherical coordinates + private Vec3 getSpherical2cartesian(){ + double dx = Math.sin(this.gss_x) * Math.cos(this.gss_y); + double dz = Math.sin(this.gss_x) * Math.sin(this.gss_y); + double dy = Math.cos(this.gss_x); + return Vec3.createVectorHelper(dx, dy, dz); } /*public void processBunch(int count) { @@ -104,7 +142,7 @@ public class ExplosionNukeRay { }*/ public void processTip(int count) { - + int processedBlocks = 0; int braker = 0; @@ -169,7 +207,7 @@ public class ExplosionNukeRay { int length = (int)Math.ceil(strength); float res = strength; - + FloatTriplet lastPos = null; for(int i = 0; i < length; i ++) { @@ -223,7 +261,7 @@ public class ExplosionNukeRay { int length = (int)Math.ceil(strength); float res = strength; - + FloatTriplet lastPos = null; for(int i = 0; i < length; i ++) { @@ -246,7 +284,7 @@ public class ExplosionNukeRay { if(res > 0 && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { lastPos = new FloatTriplet(x0, y0, z0); } - + if(res <= 0 || i + 1 >= this.length) { if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) affectedBlocks.add(new FloatTriplet(lastPos.xCoord, lastPos.yCoord, lastPos.zCoord)); @@ -333,87 +371,53 @@ public class ExplosionNukeRay { public void collectTipMk4_5(int count) { int amountProcessed = 0; - - double bow = Math.PI * this.strength; - double bowCount = Math.ceil(bow); - - //Axial - //StartY starts at this.length - for(int v = startY; v <= bowCount; v++) { - - float part = (float) (Math.PI/bow); - float rot = part * -v; - - Vec3 heightVec = Vec3.createVectorHelper(0, -strength, 0); - heightVec.rotateAroundZ(rot); - - double y = heightVec.yCoord; - - double sectionRad = Math.sqrt(Math.pow(strength, 2) - Math.pow(y, 2)); - double circumference = 2 * Math.PI * sectionRad; - - //if(y < 2 && y > -2) - // circumference *= 1.25D; - - //circumference = Math.ceil(circumference); - - //Radial - //StartCir starts at circumference - for(int r = startCir; r < circumference; r ++) { - - Vec3 vec = Vec3.createVectorHelper(sectionRad, y, 0); - vec = vec.normalize(); - /*if(y > 0) - vec.rotateAroundZ((float) (y / sectionRad) * 0.15F);*/ - /*if(y < 0) - vec.rotateAroundZ((float) (y / sectionRad) * 0.15F);*/ - vec.rotateAroundY((float) (360 / circumference * r)); - - int length = (int)Math.ceil(strength); - - float res = strength; - - FloatTriplet lastPos = null; - - for(int i = 0; i < length; i ++) { - - if(i > this.length) - break; - - float x0 = (float) (posX + (vec.xCoord * i)); - float y0 = (float) (posY + (vec.yCoord * i)); - float z0 = (float) (posZ + (vec.zCoord * i)); - - double fac = 100 - ((double) i) / ((double) length) * 100; - fac *= 0.07D; - - if(!world.getBlock((int)x0, (int)y0, (int)z0).getMaterial().isLiquid()) - res -= Math.pow(world.getBlock((int)x0, (int)y0, (int)z0).getExplosionResistance(null), 7.5D - fac); - else - res -= Math.pow(Blocks.air.getExplosionResistance(null), 7.5D - fac); - - if(res > 0 && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { - lastPos = new FloatTriplet(x0, y0, z0); - } - - if(res <= 0 || i + 1 >= this.length) { - if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) { - affectedBlocks.add(new FloatTriplet(lastPos.xCoord, lastPos.yCoord, lastPos.zCoord)); - } - break; - } + + while (this.gss_num_max >= this.gss_num){ + // 一般化螺旋集合を 一個上げる + this.generateGssUp(); + + //球面座標を直交座標を取得 + Vec3 vec = this.getSpherical2cartesian(); + + int length = (int)Math.ceil(strength); + + float res = strength; + + FloatTriplet lastPos = null; + + for(int i = 0; i < length; i ++) { + + if(i > this.length) + break; + + float x0 = (float) (posX + (vec.xCoord * i)); + float y0 = (float) (posY + (vec.yCoord * i)); + float z0 = (float) (posZ + (vec.zCoord * i)); + + double fac = 100 - ((double) i) / ((double) length) * 100; + fac *= 0.07D; + + if(!world.getBlock((int)x0, (int)y0, (int)z0).getMaterial().isLiquid()) + res -= Math.pow(world.getBlock((int)x0, (int)y0, (int)z0).getExplosionResistance(null), 7.5D - fac); + else + res -= Math.pow(Blocks.air.getExplosionResistance(null), 7.5D - fac); + + if(res > 0 && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { + lastPos = new FloatTriplet(x0, y0, z0); } - - amountProcessed++; - - if(amountProcessed >= count) { - startY = v; - startCir = startCir + 1; - return; + + if(res <= 0 || i + 1 >= this.length) { + if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) { + affectedBlocks.add(new FloatTriplet(lastPos.xCoord, lastPos.yCoord, lastPos.zCoord)); + } + break; } } + amountProcessed++; + if(amountProcessed >= count) { + return; + } } - isAusf3Complete = true; } From 17c742416fe346cb4e0404b5eba5d69e79af9f70 Mon Sep 17 00:00:00 2001 From: haru315 Date: Sat, 14 May 2022 10:46:10 +0900 Subject: [PATCH 2/3] use generalized spiral points algorithm --- src/main/java/com/hbm/explosion/ExplosionNukeRay.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java index 1e9cdaf3b..fbcec5d42 100644 --- a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java +++ b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java @@ -373,10 +373,11 @@ public class ExplosionNukeRay { int amountProcessed = 0; while (this.gss_num_max >= this.gss_num){ - // 一般化螺旋集合を 一個上げる + + // Raise one generalized spiral points this.generateGssUp(); - //球面座標を直交座標を取得 + // Get Cartesian coordinates for spherical coordinates Vec3 vec = this.getSpherical2cartesian(); int length = (int)Math.ceil(strength); From d65c2a7505afbab401debd0f81dec20dad19710d Mon Sep 17 00:00:00 2001 From: haru315 Date: Sat, 14 May 2022 23:08:22 +0900 Subject: [PATCH 3/3] Minor corrections and moving code around, commenting out unused portions --- .../com/hbm/explosion/ExplosionNukeRay.java | 320 +++++++++--------- 1 file changed, 161 insertions(+), 159 deletions(-) diff --git a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java index fbcec5d42..a36975d17 100644 --- a/src/main/java/com/hbm/explosion/ExplosionNukeRay.java +++ b/src/main/java/com/hbm/explosion/ExplosionNukeRay.java @@ -2,9 +2,6 @@ package com.hbm.explosion; import java.util.ArrayList; import java.util.List; -import java.util.Random; - -import com.hbm.interfaces.Untested; import net.minecraft.init.Blocks; import net.minecraft.util.Vec3; @@ -12,79 +9,191 @@ import net.minecraft.world.World; public class ExplosionNukeRay { - List affectedBlocks = new ArrayList(); + List affectedBlocks = new ArrayList<>(); int posX; int posY; int posZ; - Random rand = new Random(); World world; + int strength; + int length; + int processed; + + int gspNumMax; + int gspNum; + double gspX; + double gspY; + + public boolean isAusf3Complete = false; + + /*[[unused]] int count; int speed; - int processed; - int length; int startY; int startCir; - public boolean isAusf3Complete = false; - + Random rand = new Random(); private double overrideRange = 0; + */ - int gss_num_max; - int gss_num; - double gss_x; - double gss_y; - public ExplosionNukeRay(World world, int x, int y, int z, int strength, int count, int speed, int length) { this.world = world; this.posX = x; this.posY = y; this.posZ = z; this.strength = strength; - this.count = count; - this.speed = speed; this.length = length; //Ausf3, must be double - //this.startY = strength; //Mk 4.5, must be int32 + + // Total number of points + this.gspNumMax = (int)(2.5 * Math.PI * Math.pow(this.strength,2)); + this.gspNum = 1; + + // The beginning of the generalized spiral points + this.gspX = Math.PI; + this.gspY = 0.0; + + + /*[[unused]] + // this.startY = strength; this.startY = 0; this.startCir = 0; + + this.count = count; + this.speed = speed; //starts at around 80, becomes 8 at length 500 this.overrideRange = Math.max((Math.log(length) * 4 - 2.5D) * 10, 0); - - // Total number of points - this.gss_num_max = (int)(2.5 * Math.PI * Math.pow(this.strength,2)); - this.gss_num = 1; - - // The beginning of the generalized spiral points - this.gss_x = Math.PI; - this.gss_y = 0.0; - + */ } - // Raise one generalized spiral points - private void generateGssUp(){ - if (this.gss_num < this.gss_num_max) { - int k = this.gss_num + 1; - double hk = -1.0 + 2.0 * (k - 1.0) / (this.gss_num_max - 1.0); - this.gss_x = Math.acos(hk); - double prev_lon = this.gss_y; - double lon = prev_lon + 3.6 / Math.sqrt(this.gss_num_max) / Math.sqrt(1.0 - hk * hk); - this.gss_y = lon % (Math.PI * 2); + // Raise one generalized spiral points + private void generateGspUp(){ + if (this.gspNum < this.gspNumMax) { + int k = this.gspNum + 1; + double hk = -1.0 + 2.0 * (k - 1.0) / (this.gspNumMax - 1.0); + this.gspX = Math.acos(hk); + + double prev_lon = this.gspY; + double lon = prev_lon + 3.6 / Math.sqrt(this.gspNumMax) / Math.sqrt(1.0 - hk * hk); + this.gspY = lon % (Math.PI * 2); } else { - this.gss_x = 0.0; - this.gss_y = 0.0; + this.gspX = 0.0; + this.gspY = 0.0; } - this.gss_num++; + this.gspNum++; } // Get Cartesian coordinates for spherical coordinates private Vec3 getSpherical2cartesian(){ - double dx = Math.sin(this.gss_x) * Math.cos(this.gss_y); - double dz = Math.sin(this.gss_x) * Math.sin(this.gss_y); - double dy = Math.cos(this.gss_x); + double dx = Math.sin(this.gspX) * Math.cos(this.gspY); + double dz = Math.sin(this.gspX) * Math.sin(this.gspY); + double dy = Math.cos(this.gspX); return Vec3.createVectorHelper(dx, dy, dz); } + + //currently used by mk4 + public void collectTipMk4_5(int count) { + + int amountProcessed = 0; + + while (this.gspNumMax >= this.gspNum){ + // Get Cartesian coordinates for spherical coordinates + Vec3 vec = this.getSpherical2cartesian(); + + int length = (int)Math.ceil(strength); + float res = strength; + FloatTriplet lastPos = null; + + for(int i = 0; i < length; i ++) { + + if(i > this.length) + break; + + float x0 = (float) (posX + (vec.xCoord * i)); + float y0 = (float) (posY + (vec.yCoord * i)); + float z0 = (float) (posZ + (vec.zCoord * i)); + + double fac = 100 - ((double) i) / ((double) length) * 100; + fac *= 0.07D; + + if(!world.getBlock((int)x0, (int)y0, (int)z0).getMaterial().isLiquid()) + res -= Math.pow(world.getBlock((int)x0, (int)y0, (int)z0).getExplosionResistance(null), 7.5D - fac); + else + res -= Math.pow(Blocks.air.getExplosionResistance(null), 7.5D - fac); + + if(res > 0 && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { + lastPos = new FloatTriplet(x0, y0, z0); + } + + if(res <= 0 || i + 1 >= this.length) { + if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) { + affectedBlocks.add(lastPos); + } + break; + } + } + // Raise one generalized spiral points + this.generateGspUp(); + + amountProcessed++; + if(amountProcessed >= count) { + return; + } + } + isAusf3Complete = true; + } + + public void processTip(int count) { + + int processedBlocks = 0; + int braker = 0; + + for(int l = 0; l < Integer.MAX_VALUE; l++) { + + if(processedBlocks >= count) + return; + + if(braker >= count * 50) + return; + + if(l > affectedBlocks.size() - 1) + break; + + if(affectedBlocks.isEmpty()) + return; + + int in = affectedBlocks.size() - 1; + + float x = affectedBlocks.get(in).xCoord; + float y = affectedBlocks.get(in).yCoord; + float z = affectedBlocks.get(in).zCoord; + + world.setBlock((int)x, (int)y, (int)z, Blocks.air); + + Vec3 vec = Vec3.createVectorHelper(x - this.posX, y - this.posY, z - this.posZ); + double pX = vec.xCoord / vec.lengthVector(); + double pY = vec.yCoord / vec.lengthVector(); + double pZ = vec.zCoord / vec.lengthVector(); + + for(int i = 0; i < vec.lengthVector(); i ++) { + int x0 = (int)(posX + pX * i); + int y0 = (int)(posY + pY * i); + int z0 = (int)(posZ + pZ * i); + + if(!world.isAirBlock(x0, y0, z0)) { + world.setBlock(x0, y0, z0, Blocks.air); + processedBlocks++; + } + + braker++; + } + + affectedBlocks.remove(in); + } + + processed += count; + } /*public void processBunch(int count) { for(int l = processed; l < processed + count; l++) { @@ -140,58 +249,7 @@ public class ExplosionNukeRay { } } }*/ - - public void processTip(int count) { - - int processedBlocks = 0; - int braker = 0; - - for(int l = 0; l < Integer.MAX_VALUE; l++) { - - if(processedBlocks >= count) - return; - - if(braker >= count * 50) - return; - - if(l > affectedBlocks.size() - 1) - break; - - if(affectedBlocks.isEmpty()) - return; - - int in = affectedBlocks.size() - 1; - - float x = affectedBlocks.get(in).xCoord; - float y = affectedBlocks.get(in).yCoord; - float z = affectedBlocks.get(in).zCoord; - - world.setBlock((int)x, (int)y, (int)z, Blocks.air); - - Vec3 vec = Vec3.createVectorHelper(x - this.posX, y - this.posY, z - this.posZ); - double pX = vec.xCoord / vec.lengthVector(); - double pY = vec.yCoord / vec.lengthVector(); - double pZ = vec.zCoord / vec.lengthVector(); - - for(int i = 0; i < vec.lengthVector(); i ++) { - int x0 = (int)(posX + pX * i); - int y0 = (int)(posY + pY * i); - int z0 = (int)(posZ + pZ * i); - - if(!world.isAirBlock(x0, y0, z0)) { - world.setBlock(x0, y0, z0, Blocks.air); - processedBlocks++; - } - - braker++; - } - - affectedBlocks.remove(in); - } - - processed += count; - } - +/* @Untested //override range public void collectTip(int count) { @@ -223,21 +281,19 @@ public class ExplosionNukeRay { res -= Math.pow(world.getBlock((int)x0, (int)y0, (int)z0).getExplosionResistance(null), 1.25); else res -= Math.pow(Blocks.air.getExplosionResistance(null), 1.25); - - /* - * Blast resistance calculations are still done to preserve the general shape, - * but if the blast were to be stopped within this range we go through with it anyway. - * There is currently no blast resistance limit on this, could change in the future. - */ + + //Blast resistance calculations are still done to preserve the general shape, + //but if the blast were to be stopped within this range we go through with it anyway. + //There is currently no blast resistance limit on this, could change in the future. boolean inOverrideRange = this.overrideRange >= length; if((res > 0 || inOverrideRange) && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { lastPos = new FloatTriplet(x0, y0, z0); } - /* - * Only stop if we are either out of range or if the remaining strength is 0 while being outside the override range - */ + + // Only stop if we are either out of range or if the remaining strength is 0 while being outside the override range + if((res <= 0 && !inOverrideRange) || i + 1 >= this.length) { if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) affectedBlocks.add(new FloatTriplet(lastPos.xCoord, lastPos.yCoord, lastPos.zCoord)); @@ -246,7 +302,8 @@ public class ExplosionNukeRay { } } } - +*/ + /* public void collectTipExperimental(int count) { for(int k = 0; k < count; k++) { @@ -293,7 +350,7 @@ public class ExplosionNukeRay { } } } - + */ /*public void collectTipAusf3(int count) { int amountProcessed = 0; @@ -366,61 +423,6 @@ public class ExplosionNukeRay { isAusf3Complete = true; }*/ - - //currently used by mk4 - public void collectTipMk4_5(int count) { - - int amountProcessed = 0; - - while (this.gss_num_max >= this.gss_num){ - - // Raise one generalized spiral points - this.generateGssUp(); - - // Get Cartesian coordinates for spherical coordinates - Vec3 vec = this.getSpherical2cartesian(); - - int length = (int)Math.ceil(strength); - - float res = strength; - - FloatTriplet lastPos = null; - - for(int i = 0; i < length; i ++) { - - if(i > this.length) - break; - - float x0 = (float) (posX + (vec.xCoord * i)); - float y0 = (float) (posY + (vec.yCoord * i)); - float z0 = (float) (posZ + (vec.zCoord * i)); - - double fac = 100 - ((double) i) / ((double) length) * 100; - fac *= 0.07D; - - if(!world.getBlock((int)x0, (int)y0, (int)z0).getMaterial().isLiquid()) - res -= Math.pow(world.getBlock((int)x0, (int)y0, (int)z0).getExplosionResistance(null), 7.5D - fac); - else - res -= Math.pow(Blocks.air.getExplosionResistance(null), 7.5D - fac); - - if(res > 0 && world.getBlock((int)x0, (int)y0, (int)z0) != Blocks.air) { - lastPos = new FloatTriplet(x0, y0, z0); - } - - if(res <= 0 || i + 1 >= this.length) { - if(affectedBlocks.size() < Integer.MAX_VALUE - 100 && lastPos != null) { - affectedBlocks.add(new FloatTriplet(lastPos.xCoord, lastPos.yCoord, lastPos.zCoord)); - } - break; - } - } - amountProcessed++; - if(amountProcessed >= count) { - return; - } - } - isAusf3Complete = true; - } //Dysfunctional, punches hole into ground /*public void collectTipAusf3(int count) {