Jump to content

[1.8.9] Raytrace or EntityBullet?


XFactHD

Recommended Posts

I am in the process of creating a gun mod. I have guns with a fire rate of over one bullet per tick. Now I am debating if I want to use raytraces or actual flying objects to determine if a player or any other entity/block was hit. Why I am thinking of using a raytrace is that I want to prevent a phenomenon that I encountered multiple while playing with FlansMod, especially when using a sniper, even though the bullet would definitely have hit the player, he didn't take damage because he could more or less run away from the flying bullet. My main problems now are:

  • Can I make an entity fast enough to counter this behaviour without needing enormous amounts of CPU time?

  • Can I make a raytrace with MovingObjectPosition with a vector with a length of 500 blocks or similar and how would I handle the damage applied to an entity when I have a gun that fires multiple bullets per tick?

Link to comment
Share on other sites

You can make an entity travel quickly enough to be impractical to dodge.

 

You can use a ray trace over a long distance, but keep in mind that the typical amount of loaded chunks is not going to be that far. 1 chunk = 16 blocks, and in most cases you will have 8-12 chunks loaded in any given direction, giving you 128 to 192 blocks worth of viable distance at most.

 

Whether you choose an entity or a ray trace, entities can only be damaged once per 20 ticks or so; once damaged, any other attacks during that grace period do not inflict any damage unless the amount is greater than the previous damage amount.

 

E.g. you get hit for 2 damage from a zombie and a few ticks later a creeper blows up next to you for 20 damage - even though you are immune to damage, you will still be hit for 20 damage because it is greater than 2. If you had been hit by a skeleton's arrow for 3 damage, however, the horde of zombies trying to attack you would be impotent until you once again become vulnerable to damage.

 

Minecraft purposefully does not allow multiple attacks to stack damage, and I don't recommend trying to circumvent that. You may was well make one bullet kill rather than making damage stack.

Link to comment
Share on other sites

Would it kill the game if 10 people at the same time fire with guns that fire multiple bullets per tick if the bullets are that fast?

 

Is it possible to get the amount of loaded chunks with a vector to calculate how far I can do the raytrace?

 

The problem with the damage immunity is that it for example makes shotguns useless against assault rifles.

Link to comment
Share on other sites

1 bullet a tick is a lot of bullets.  There's literally no need to be doing it that often.

 

(By the way: there are ways around the damage immunity time, as your custom projectile--or the raytrace--can just set the damage immunity time to zero prior to inflicting damage; but it means that those weapons would simply bypass the immunity time entirely).

Apparently I'm a complete and utter jerk and come to this forum just like to make fun of people, be confrontational, and make your personal life miserable.  If you think this is the case, JUST REPORT ME.  Otherwise you're just going to get reported when you reply to my posts and point it out, because odds are, I was trying to be nice.

 

Exception: If you do not understand Java, I WILL NOT HELP YOU and your thread will get locked.

 

DO NOT PM ME WITH PROBLEMS. No help will be given.

Link to comment
Share on other sites

I know that one or more bullets per tick is a lot but if you want to replicate an FPS in Minecraft, you need to do such things  ;D

 

Also, I know that trick with the damage immunity, I just wasn't sure if this field in EntityLivingBase is accesible without an AccessTransformer.

Link to comment
Share on other sites

the two things can be done

 

actualy in mi mod on 1.8 i made the bullets froom a custom arrow, but in mi mod the max fire rate is one bullet every two ticks

like 600 bpm  and mi shotgun shoots 25 bullets in in a single tick but in needs a leats 6 ticks to fire again

 

in 1.9 im trying the ray trace thing actully have funtin¡onal guns but not tested enought and still need to make the guns compatible whith mi entityes

 

if you mess  whith the on update method from the arrow an doo something like

 

@Override

public void onUpdate() {

super.onUpdate();

World worldIn = this.worldObj;

 

 

 

if ((onUpdateTick % 2) == 0) {

 

                      //Do stufff

}

onUpdateTick++;

}

 

then the arrow/bullet will travel two times faster

 

 

Link to comment
Share on other sites

do your really need guns that shoot faster than 1200 bpm, there are very few hand held guns that fire faster 1000. If you do plan on making your guns shoot that fast or faster I recommend you not use actual entities. 10 people firing at the same time for 1 second would spawn 200+ entities.

I would recommend that you make a handler class that implements ITickable and then have each bullet get added to a list for updates.

 

something like this:

class Manager implements ITickable{
   private static List<Bullet> bullets = new ArrayList<Bullet>();

   public void shoot(Bullet b){bullets.add(b);}

   @Override (I don't recall the exact method name and params)
   public void onUpdate(){
      List<Bullet> toRemove = new ArrayList<Bullet>();
      for(Bullet b : bullets)
      {
         MovingObjectPosition result = customRayTrace((vec3d)b.travel(), b.currentLocation());
         if(result hit entity)
           //do damage
           //add b to toRemove list
         else if(result hit block)
          //add b to toRemove list
         else
            b.updateLocation()
      }
      for(Bullet b : toRemove)
         bullets.remove(b);
   }
}

 

 

Edit: Entities are effectively using raytrace to detect collision anyways and they have a lot of overhead so if you are going to be making that many you should NOT use entities.

Current Project: Armerger 

Planned mods: Light Drafter  | Ore Swords

Looking for help getting a mod off the ground? Coding  | Textures

Link to comment
Share on other sites

I am amazed that till this post noone even mentioned using particles.

 

This is a simple game-design choice! You can achieve any kind of BPM using FPS-based rendering. Sure, it's not gonna be straight one method solution, but still - a nice-looking one.

 

entities can only be damaged once per 20 ticks or so; once damaged, any other attacks during that grace period do not inflict any damage unless the amount is greater than the previous damage amount.

 

Generally speaking - you don't need more than about 2 bullets per second. 4 or 5 AT MOST! Bullet per tick is literally ridonculous - Entity with speed as high as bullets will never hit 2 different targets if shoot in 1 tick intervals. Too "streamy". And if they will hit same target - target still won't be hurt unless you handle it properly (it is possible).

 

Anyway - if you are after LOOKS - it is possible to hide easy-on-CPU logics behind good looking effects that will be cheap client-based.

 

Simply shoot few Entities (server side) and lots of Particles (client side).

Previously I mentioned "hacky" ways - yeah, it will be if you want to achieve smooth animations.

Shooting (using items) happen on logical side of things, meaning - 20 calls per sec. FPS is on rendering side of game.

If you want your bullet-particles to be shot more than 20/sec you will need to use "partialTicks". You can do that by using Client/Rendering events which are called on FPS-basis (meaning - even houndreds of times per second).

One way to achieve it is to set boolean when starting shooting (boolean will be client-sided, per-entity/player, saved in IEEP/Capability of player/entity)

and false it when stopped. Then use that boolean in RenderTickEvent to spawn particles on client side based on that gun held. (make some nice abstraction call to some IGun interface).

 

Any questions?

1.7.10 is no longer supported by forge, you are on your own.

Link to comment
Share on other sites

I need to use particles anyway because a flash hider without any kind of flash is useless :D

 

Generally speaking - you don't need more than about 2 bullets per second.

 

Normally that is most likely true but if you want to replicate another game as good as possble, you need more (in my case up to almost one bullet per tick).

 

I decided that I am gonna use the raytracing method for hit detection (one vector per bullet from the shooter to the target on eye height of the shooter)

 

I have one question: How can I achieve smooth firing, if I can't divide 20 by the amount of bullets per second (for example I have an MP that fires 800 RMP, that's about 13 bullets per second)?

Link to comment
Share on other sites

Two approaches:

 

Logical:

* Hold 20 tick-based interval starting at 0.

13 / 20 = 0.65

Each tick you will be adding 0.65 to that counter. At every full number you will spawn new Entity and offset (move it in firing direction) by "rest" of movement factor (for 1.3, will be 0.3 * distance, where distance is bulletSpeed * time).

 

Other way would be rendering way, but apparently you don't like it.

1.7.10 is no longer supported by forge, you are on your own.

Link to comment
Share on other sites

if you mess  whith the on update method from the arrow an doo something like

 

	@Override
public void onUpdate() {
	super.onUpdate();
	World worldIn = this.worldObj;

	if ((onUpdateTick % 2) == 0) {
                       //Do stufff
	}
	onUpdateTick++;
}

 

then the arrow/bullet will travel two times faster

 

That's half as fast. You're an idiot.

And what's this

worldIn

nonsense?  Seriously,

this.worldObj

is already an accessible field property of

this

class!

And for fuck's sake, use the god damn [code ] tag.

 

Now I remember why I have you on ignore. :V

Apparently I'm a complete and utter jerk and come to this forum just like to make fun of people, be confrontational, and make your personal life miserable.  If you think this is the case, JUST REPORT ME.  Otherwise you're just going to get reported when you reply to my posts and point it out, because odds are, I was trying to be nice.

 

Exception: If you do not understand Java, I WILL NOT HELP YOU and your thread will get locked.

 

DO NOT PM ME WITH PROBLEMS. No help will be given.

Link to comment
Share on other sites

@Ernio

You are not completely wrong with that one, I hate rendering, especially entity rendering, it just never works for me  :-\

 

Another problem with the entities is that the amount of entities spawned per second is ernormous, worst case is almost 200 per second if all ten players shoot at the same time with the MP I mentioned before.

 

Your example makes sense when I use entities but if I use a vector (which means instant hit when firing, distance doesn't make any difference), how would I go about doing it then?

Link to comment
Share on other sites

I still recommend setting up something like I mentioned where the bullets are tracked in code and only do raytraces on the distance they would have traveled in 1 tick as an entity. If you find that you there are too many checks happening per tick and the game slows down you can split up the bullets into multiple queues and only update/check 1 queue per tick. You could probably get away with updating a bullet once every 4 ticks without it looking laggy

Current Project: Armerger 

Planned mods: Light Drafter  | Ore Swords

Looking for help getting a mod off the ground? Coding  | Textures

Link to comment
Share on other sites

As for when to fire it also happens to work out that if you have a counter like this

count = 0;
if(count == 0 || count == 2)
   //fire bullet
count = (count + 1)%3;

it will fire 13 bullets every second as long as they are shooting.

Current Project: Armerger 

Planned mods: Light Drafter  | Ore Swords

Looking for help getting a mod off the ground? Coding  | Textures

Link to comment
Share on other sites

If you want to emulate rapid fire and/or shotguns, Ernio's suggestion of using particles is spot on. In order to manage the attacking aspect of it, rather than spawning an entity, you can ray trace each tick while the item is in use for the semi-autos and hit whatever that is (giving you ~1200 bpm, but realistically, a typical rifle magazine holds 30 before needing to swap out). Even if you get 'crazy', max magazine size is still 100 at best unless you have a feeder instead of a magazine. So sure, you can fire 30-100 shots at a rate of 1200 bmp, taking all of about 1.5 to 5 seconds before needing to reload, a process that likely takes 5-20 seconds or more depending on training, stress, etc.

 

Just be sure to flag entities struck in this manner so that if they get shot again, you can stack the damage. Alternatively, just always allow firearms to cause damage, and forget about setting a flag. I'm sure you're aware, but doing so goes against a specific design choice of Minecraft to limit damage, and it could have serious playability consequences; of course, you'll have to try it to find out what those may be, and it could turn out to be awesome fun.

 

For the shotgun, I'd recommend spawning a single entity per shot, and override the #onUpdate method so you can make a custom hit-detection algorithm. The projectiles ticksExisted field gives you the perfect input for calculating spread, and you'd simply damage every entity within the current spread. If you wanted to get fancy, you could estimate how many pellets you'd expect to hit that entity as a function of the current spread compared to the entity's height * width, and subtract that many pellets from the 'total'. Once the number of pellets is 0, the shotgun shell 'entity' is 'dead'.

Link to comment
Share on other sites

My guns have a capability and the capability's implementation has access to the player who is holding the gun. Because I want the guns to have multiple purposes, for one they will be craftable for survival use and also for my implementations of the game modes from the game I want to replicate. If I go with raytracing, the capability is doing all the work. To make the games work properly, I will have to make a game manager. This means that I can set a boolean in the gun capability to tell it to circumvent the damage cool down as long as the player is in a match and if the player is just using the gun in survival or whatever, the gun won't circumvent the damage cool down. The biggest mag I have at the moment is 100 bullets on a belt for a russian MG, the biggest SMG mag is 52 for the P90. All other fast firing weapons have 30 bullets in their mag.

 

Also, I am kinda understanding the modulo operator but why modulo 3 and not any other number?

Link to comment
Share on other sites

Also, I am kinda understanding the modulo operator but why modulo 3 and not any other number?

Because in his example, he wants to limit 'count' to a value between 0 and 2.

int count = 0;

#someTickingMethod:
if (count != 1) {
  // fire bullet
}
count = (count + 1) % 3;

Tick  Count  Modulo
  0        0      (0 + 1) % 3 = 1
  1        1      (1 + 1) % 3 = 2
  2        2      (2 + 1) % 3 = 0
  3        0      (0 + 1) % 3 = 1
  4        1      (1 + 1) % 3 = 2
  5        2      (2 + 1) % 3 = 0

Make sense now?

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Announcements



×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use.