- Home /
Shotgun using array/list in Javascript
Sorry for the vague title, I wasn't sure what to call this.
Anyway, I am making a shotgun for an FPS and want it to be easy to modify it's properties from the editor, so I am planning to have a variable determining the number of pellets fired in each shot:
var pelletsPerShot : int=12;
and from that make an array or list of rays, with a length equal to the variable above, then, for every item on that array, assign a new direction to simulate spread. (I know how to do the bullet spread part of the script, I just don't know how to make/use arrays and lists, as I am relatively new to unity, and can't find an explanation for them anywhere.)
So, what I want is a script that makes an array of new rays with a length of x, then for all of them does y.
Also I don't know whether I should use arrays or lists, apparently arrays are obseletebut I have never seen a list used on this site so I am not sure.
Answer by robertbu · Jun 01, 2013 at 02:00 AM
When you read to not use Array(), the comments are talking about a specific Array() class. I typically use the build-in arrays for anything that is fixed in size. For most other things I used a Generic List. You can find out more about the various array classes here:
http://wiki.unity3d.com/index.php?title=Which_Kind_Of_Array_Or_Collection_Should_I_Use%3F
As for your problem, here is a bit of code to demonstrate using Debug.DrawRay(). The lines will visible in Scene view and in Game View if Gizmos is turned on.
#pragma strict
var maxPellets : int = 50;
var pelletsThisShot : int = 12;
var spreadAmount : float = 0.2; // This much spread at
var spreadDistance : float = 11.0; // this distance
private var arv3Shots : Vector3[];
function Start() {
arv3Shots = new Vector3[maxPellets];
CalcSpread();
}
function Update() {
if (Input.GetKeyDown(KeyCode.A)) {
pelletsThisShot = Random.Range(10, maxPellets);
CalcSpread();
}
for (var i = 0; i < pelletsThisShot; i++)
Debug.DrawRay(transform.position, arv3Shots[i]*20.0, Color.green);
}
function CalcSpread() {
pelletsThisShot = Mathf.Clamp(pelletsThisShot, 0, maxPellets);
for (var i = 0; i < pelletsThisShot; i++) {
var v3 : Vector3 = Random.insideUnitCircle * spreadAmount;
v3.z = spreadDistance;
v3.Normalize();
v3 = transform.TransformDirection(v3);
arv3Shots[i] = v3;
}
}
A few comments:
Rather than a variable using a list which I could add to and delete from, I'm using the build-in array and establishing a maximum number of pellets.
I use Random.insideUnitCircle and a spreadDistance to make the shots random. I felt this would be a good way of getting a uniform spread.
This script uses the forward of the game object it is attached to as the 0 point for the spread.
Thank you, this works. However because of the number of bulletholes it has to instantiate in one frame, the FPS drops to about 1 from 70 for a second or so. Is there a way to avoid this?
I cannot think of an easy way. Using a pool system would work, but then you'd lose old blasts. Using a single graphic or a set of graphics for the full blast would work, but then the blast zones would be uniform. The best solution I can think of is fairly complex. You would create a mesh where each quad on the mesh represents one bullet hole. That way a full blast would only represent a single game object, and all the bullet holes would as a single drawcall. You would need to research mesh creation to make this happen.
Your answer
Follow this Question
Related Questions
How to find the opposite variables list? 1 Answer
Inspector variable MonoScript, using for creating a List? 2 Answers
A node in a childnode? 1 Answer
How to put buttons in a list? 1 Answer
How to use an Array list of classes inside a class? 1 Answer