Targettable Projectiles, and Multiple projectiles from the s

Post » Tue Jun 19, 2012 3:17 am

OK, It's taken me a week and a couple days to get this working (semi) perfectly, so here goes.

Problem: You can't get a reference to a projectile that you can use to do...well...anything with it. You can't even find it's location.

Solution: Make your own projectile.

Procedure:

First, you will need to create an object to represent your projectile. I used an Activator because I could easily attach a script directly to it, and not have to attach an effect to it to do so like you would with lots of other objects.

Next, you want the projectile to be visible. Use a BSM unpacker to unpack the Nif files so you can pick a model, or you can learn how to use a program like Blender (I haven't used a modelling program since version 2 of 3D Studio Max, I'd need to take a class or something to learn how again...) and make your own model. Click on "Edit" on the model slot of your activator and pick the model you want.

Now you'll need global variables. Create a dummy quest and put a script in it containing properties you can access in other scripts. Such a script would look like this:
Spoiler
Scriptname NodeVariableScript extends Quest  {Variables used by the Node Based spells}NodeGlow property NodeMote AutoObjectReference property Missile auto ; Tvar.Missile = The Pseudo-Projectile. For more than one you can use an Array.ObjectReference property Target auto ; Tvar.Target = Storing the destination target of the Node, which it will follow.float property Speed=2000.0 Auto; Tvar.Speed = How fast the Projectile moves.bool property UsingTargetType Auto; Tvar.UsingTargetType = Is the current target a Target object? If not there is none or it's an actor.; To access these variables and functions in a script, place the following line in the script:; NodeVariableScript Property TVar Auto

Next, go back to your Projectile, and add a script like this:
Spoiler
Scriptname FollowObjectTracker extends ObjectReference  {Object will follow an object.}import gameimport utilityfloat Distance ; sure, we could pass the variable isntead.bool Moving = TrueObjectReference Following = Nonefloat Velocity = 0.0Float Function DistanceBetween(Objectreference A,ObjectReference B) global ; Returns the distance between 2 objectreferences	return A.GetDistance(B)endfunctionFunction Move()	ObjectReference Target = Following	float Speed = Velocity	Distance = DistanceBetween(Self,Target)	if Distance > 200.0		Self.TranslateTo(Target.X,Target.Y,Target.Z,0.0,0.0,0.0,Tvar.NodeSpeed,0.0)	else  ; If it's close enough, don't bother to move.; Insert "On reaching your target" code here...explosions, apply effects to nearby enemies, etc.; But only if it's a seeker type missile.; Be sure to include any Self-Destruction code so you don't have missiles running around forever.		Moving = False	endifEndFunctionFunction Follow(ObjectReference inTarget=None, float inSpeed=0.0) ; Function call is .Follow(FollowObject,Speed)	ObjectReference Target = Tvar.Target ; The "Destination" node set in the global variable.	float Speed = Tvar.Speed ; The "Speed" assigned in the global variable.	If inTarget != None ; If passed an object, use that object instead.		Target = inTarget	endif	If inSpeed != 0.0 ; If passed a speed, use that instead.		Speed = inSpeed	endif	Velocity = Speed	Following = Target ; Store values so the Events can tell what we're following.	While Target		if !Moving ; If we have stopped moving; If missile is NOT seeker type, put "on reaching your target" Code here and comment the Move out.			Move(Target,Speed) ; Get a wiggle on...or try to. (Seeking Missile option)		endif		;Move(Target,Speed) Non-Seeking weapon option.	endwhileendFunctionEvent OnTranslationComplete()	Moving = FalseEndEventEvent OnTranslationFailed() ; couldn't move	Debug.Notification("Unable to move: " + self)endeventEvent OnUpdate()	Self.Disable()	Self.Delete()EndEventEvent OnInit()	Follow(Tvar.Target) ; This is initialized before any Missiles are created.EndEventNodeVariableScript Property TVar Auto
(Heavily cut for generic missiles...but you can see more or less what it's supposed to do hopefully)

Be sure to assign the property Tvar to the global variables script.

OK, that's the projectile itself. Now we need to make a navigation system for it. I copied the Magelight spell, ramped the projectile speed up to around 10000, and the duration down to 1 second, made a custom explosion to occur when it strikes something (no damage, but drops a second type of activator, with the following script on it):

Spoiler
Scriptname NodeTargetScript extends ObjectReference  {An object whose purpose in life is to be followed by another object.}import gameimport utilityFunction FireMissile()	Tvar.Missile = Game.GetPlayer().PlaceAtMe(Node,1,false,false); Make a Missile	Tvar.Missile.Moveto(Game.GetPlayer(),0.0,0.0,60.0); Put it above the ground.EndFunctionEvent OnInit()	if Tvar.Target && Tvar.UsingTargetType; No killing NPCs just because they were being followed by a missile! Let the missiles' damage handle that part.		Tvar.Target.Delete() ; Gets rid of the last target if it was an invisible node.	endif		Tvar.Target = self	Tvar.UsingTargetType = True	int Count = 0	while Count < NumberOfMissiles		 FireMissile()		 Count += 1	EndWhileEndEventint property NumberOfMissiles AutoActivator property Node AutoNodeVariableScript Property TVar Auto

OK, so once the Target is in place, IT launches the missiles essentially at itself.

One more script to add, to the Light-spell-launching Effect copy:

Spoiler
Scriptname LaunchMissileScript extends activemagiceffect  import gameimport utilityObjectReference TeleportHereEvent OnEffectStart(Actor Target, Actor Caster) ; Only fires when the Targetting projectile strikes an actor and "sticks"	If Tvar.UsingTargetType ; If the previous node was an invisible Target		Wait(2.0) ; Wait til the explosion dropped Target has spawned it's follow node and missiles.		Tvar.Target.Delete() ; Bye Bye, You mean old invisible Target!	endif	TVar.UsingTargetType = False ; Protects the NPC from deletion later.	TVar.Target = (Target  as ObjectReference); The missiles check this, and if they are seeker type, they will try to find the NPC after reaching initial point.EndEventNodeVariableScript Property TVar Auto

That's basically the guts of the solution. The global variable will keep track of the last missile you created, and you can search for the others, or make an array to store references to multiple missiles. Once the missiles are launched, they will pretty much do whatever you told them to with any code modifications you added.

http://www.youtube.com/watch?v=b_Tvl55fCoE(Sorry for the lousy resolution...wanted upload to be shorter than 3 hours or more...)
User avatar
Trish
 
Posts: 3332
Joined: Fri Feb 23, 2007 9:00 am

Post » Tue Jun 19, 2012 9:24 am

Oh, the one disadvantage here is, the projectiles this spell makes ignore collision unless you give them collision capable models, and I'm not sure they will be movable with translate even then, since I tried it using the model for the Yngol wisps for the node, and instead of tracking the target it just fell on the ground. So they're best used for spells that go straight to the target location and explode, or are fast if they're seekers so the target doesn't make them go through a wall. Of course you could make some pretty wacky spells using something like the wisps to bounce down the hall to the target location and then do whatever they do when they get close enough (and make the follow node invisible)
User avatar
Gen Daley
 
Posts: 3315
Joined: Sat Jul 08, 2006 3:36 pm

Post » Tue Jun 19, 2012 12:45 am

First Spell(Translocate - Mark) -> Projectile -> Explosion -> Placed Impact Object = Marker

Second Spell (Translocate - Recall)= MySelf.MoveTo(Marker)

The only thing that mine doesn't do that yours does it attach to actors though I did not want it to either, also Collision works.
User avatar
Jessica Nash
 
Posts: 3424
Joined: Tue Dec 19, 2006 10:18 pm

Post » Tue Jun 19, 2012 5:20 am

First Spell(Translocate - Mark) -> Projectile -> Explosion -> Placed Impact Object = Marker

Second Spell (Translocate - Recall)= MySelf.MoveTo(Marker)

The only thing that mine doesn't do that yours does it attach to actors though I did not want it to either, also Collision works.

OK, smarty...how did you get the teleport spell to move you to the position of the projectile while it was in transit (Before the explosion drops the marker)? Because I couldn't figure that one out.
User avatar
oliver klosoff
 
Posts: 3436
Joined: Sun Nov 25, 2007 1:02 am

Post » Tue Jun 19, 2012 11:50 am

This just stuck out to me:
		int Count = 0		while Count < NumberOfMissiles				 FireMissile()				 Count += Count		EndWhile
:shocking:
User avatar
Jason Wolf
 
Posts: 3390
Joined: Sun Jun 17, 2007 7:30 am

Post » Mon Jun 18, 2012 9:00 pm

This just stuck out to me:
		int Count = 0		while Count < NumberOfMissiles				 FireMissile()				 Count += Count		EndWhile
:shocking:

Oopsie...missed that one...fixed.

My version only fires one missile, but I wanted to show how to do more than one.
User avatar
evelina c
 
Posts: 3377
Joined: Tue Dec 19, 2006 4:28 pm

Post » Tue Jun 19, 2012 1:55 am

OK, smarty...how did you get the teleport spell to move you to the position of the projectile while it was in transit (Before the explosion drops the marker)? Because I couldn't figure that one out.

It doesn't there is no real projectile -> the projectile generated basically instantly hits whatever surface its pointed at -> far faster then the player ever could cast the second spell.

Explosions are cleaned up by the game engine. no script

And the PIO does exactly 2 things it moves the single reference Marker to itself and then it deletes itself. 3 lines of code -> I will probably add a few lines of code to prevent deletion before the Marker gets moved for slower computers mine does not have an issue with this but others might.
Marker.MoveTo(Self)
Self.Disable()
Self.Delete()

The Marker has no script as it does not need one.

and the Second spell I already game you its entire code up top.
User avatar
NAtIVe GOddess
 
Posts: 3348
Joined: Tue Aug 15, 2006 6:46 am

Post » Mon Jun 18, 2012 8:18 pm

It doesn't there is no real projectile -> the projectile generated basically instantly hits whatever surface its pointed at -> far faster then the player ever could cast the second spell.

Explosions are cleaned up by the game engine. no script

And the PIO does exactly 2 things it moves the single reference Marker to itself and then it deletes itself. 3 lines of code -> I will probably add a few lines of code to prevent deletion before the Marker gets moved for slower computers mine does not have an issue with this but others might.
Marker.MoveTo(Self)
Self.Disable()
Self.Delete()

The Marker has no script as it does not need one.

and the Second spell I already game you its entire code up top.

SO, basically, you were spectacularly incorrect when you said that yours does everything mine does "except following an actor" In my spell there is, in fact, a projectile you can target and teleport to.

DId you even watch the video? There's a lot more you can do with that spell than just teleport.
User avatar
matt white
 
Posts: 3444
Joined: Fri Jul 27, 2007 2:43 pm

Post » Tue Jun 19, 2012 11:57 am

Brilliant.
User avatar
Sam Parker
 
Posts: 3358
Joined: Sat May 12, 2007 3:10 am

Post » Tue Jun 19, 2012 11:49 am

very nice
User avatar
Michelle Serenity Boss
 
Posts: 3341
Joined: Tue Oct 17, 2006 10:49 am

Post » Tue Jun 19, 2012 12:04 am

wanted to know this :D
User avatar
roxanna matoorah
 
Posts: 3368
Joined: Fri Oct 13, 2006 6:01 am

Post » Tue Jun 19, 2012 1:51 am

Oh cool, you managed to get http://www.gamesas.com/topic/1348694-object-reference-to-a-spell-projectile/page__view__findpost__p__20324426 to work? Looks like it could end up being a very useful tool!

Cipscis
User avatar
KRistina Karlsson
 
Posts: 3383
Joined: Tue Jun 20, 2006 9:22 pm

Post » Tue Jun 19, 2012 8:40 am

Oh cool, you managed to get http://www.gamesas.com/topic/1348694-object-reference-to-a-spell-projectile/page__view__findpost__p__20324426 to work? Looks like it could end up being a very useful tool!

Cipscis

Unfortunately, papyrus is very slow for computing the "hext step" in a follow path..like I said in the video, while it's thinking about whree it needs to move on the next segment, it makes the projectile pause for like 3 seconds...and trying to use the event OnTranslationCompleted() to call the next movement doesn't seem to work right.
User avatar
JERMAINE VIDAURRI
 
Posts: 3382
Joined: Tue Dec 04, 2007 9:06 am

Post » Tue Jun 19, 2012 7:22 am

Yeah, I noticed that in your video. Sounds like homing projectiles aren't going to be as easy as we might have hoped. I guess if all you want to do is make this fake projectile go in a straight line from the source to the target, though, the only problem is that initial delay?

What happens if you try to use http://www.creationkit.com/OnTranslationComplete_-_ObjectReference? I'd have expected it would be just what you were looking for...

Cipscis
User avatar
leni
 
Posts: 3461
Joined: Tue Jul 17, 2007 3:58 pm

Post » Tue Jun 19, 2012 2:14 am

Yeah, I noticed that in your video. Sounds like homing projectiles aren't going to be as easy as we might have hoped. I guess if all you want to do is make this fake projectile go in a straight line from the source to the target, though, the only problem is that initial delay?

What happens if you try to use http://www.creationkit.com/OnTranslationComplete_-_ObjectReference? I'd have expected it would be just what you were looking for...

Cipscis

I tried that...even thoiugh the debug.notification I put in there comes up on the screen, the call to the move function in there never initializes...I wasn't able to determine why.
User avatar
Rhysa Hughes
 
Posts: 3438
Joined: Thu Nov 23, 2006 3:00 pm

Post » Tue Jun 19, 2012 9:00 am

Perhaps it would be worth checking if that causes an http://www.creationkit.com/OnTranslationFailed_-_ObjectReference event to be called. Also, have you tried a short http://www.creationkit.com/Wait_-_Utility before starting the new translation?

Cipscis
User avatar
Cassie Boyle
 
Posts: 3468
Joined: Sun Nov 05, 2006 9:33 am

Post » Tue Jun 19, 2012 12:10 pm

Perhaps it would be worth checking if that causes an http://www.creationkit.com/OnTranslationFailed_-_ObjectReference event to be called. Also, have you tried a short http://www.creationkit.com/Wait_-_Utility before starting the new translation?

Cipscis

Checked that first one, no fail.Tinkering with it a bit still, but I'm saving my working version of course...
User avatar
neen
 
Posts: 3517
Joined: Sun Nov 26, 2006 1:19 pm

Post » Tue Jun 19, 2012 8:13 am

Sounds like homing projectiles aren't going to be as easy as we might have hoped.

Don't be too sure about that. I copied the witchlight race and wisp actor and as long as you have a target you just tell them to http://www.creationkit.com/StartCombat_-_Actor and off they go. If the target changes course, so do they. They use the Navmesh for avoidance and everything.

I've been trying to get them to fly, but that doesn't seem to be working.
User avatar
ILy- Forver
 
Posts: 3459
Joined: Sun Feb 04, 2007 3:18 am

Post » Tue Jun 19, 2012 1:59 am

Don't be too sure about that. I copied the witchlight race and wisp actor and as long as you have a target you just tell them to http://www.creationkit.com/StartCombat_-_Actor and off they go. If the target changes course, so do they. They use the Navmesh for avoidance and everything.

I've been trying to get them to fly, but that doesn't seem to be working.

well I got the "Homemade" projectiles to follow a target, even minimized the "wait time" between movement segments...but the Roll/Pitch/Yaw problem is still bugging me (Can't get the projectile to face an object and tilt upward if the target is above, and downward if the target is below, due to the sequential Z>Y>X rotations the game uses for the setrotation and translate functions...working on cracking that problem, but it's a bear, since nobody at Bethesda thought to give Papyrus access to local object rotation functions, so we have to make our own.
User avatar
Michael Korkia
 
Posts: 3498
Joined: Mon Jul 23, 2007 7:58 pm

Post » Tue Jun 19, 2012 7:02 am

is there anyway i can get an esp file of this? im trying to make a spell that does exactly what you managed to do, but i am rather new to this so if i could see how you did it in the creation kit i am positive i could get a better understanding that way. I just really need to see an example of how the scripts are applied in the creation kit.
User avatar
aisha jamil
 
Posts: 3436
Joined: Sun Jul 02, 2006 11:54 am

Post » Tue Jun 19, 2012 11:53 am

I've been monkeying with something similar to this method and have created a beta magic missile spell:

http://www.youtube.com/watch?v=WtcVJhSfkso

Rough around the edges but the hard part is done. The only stuttering happens after the missile reaches its location and THEN the target moves, but of course if the missile explodes than this won't be an issue. Might be though if I want some other effect to happen.
User avatar
Damien Mulvenna
 
Posts: 3498
Joined: Wed Jun 27, 2007 3:33 pm

Post » Mon Jun 18, 2012 7:57 pm

is there anyway i can get an esp file of this? im trying to make a spell that does exactly what you managed to do, but i am rather new to this so if i could see how you did it in the creation kit i am positive i could get a better understanding that way. I just really need to see an example of how the scripts are applied in the creation kit.

Unfortunately, it's currently embedded very deep in a completely unfinished mod. I'll try to make a mini version for uploads...
User avatar
Andres Lechuga
 
Posts: 3406
Joined: Sun Aug 12, 2007 8:47 pm

Post » Tue Jun 19, 2012 11:33 am

Forgot to mention about my above video, one hard part I am working on is getting the missiles to curve a bit more towards their target. Spline functions work but I can't seem to get it to look decent.
User avatar
Damien Mulvenna
 
Posts: 3498
Joined: Wed Jun 27, 2007 3:33 pm

Post » Tue Jun 19, 2012 7:20 am

Forgot to mention about my above video, one hard part I am working on is getting the missiles to curve a bit more towards their target. Spline functions work but I can't seem to get it to look decent.

Maybe you could do computation on the fly as the target is moving. In the video it seems the projectiles spawn, and go "I need a target->found one->get position->go there->do something"

Maybe you could use a waypoint system that can be reconfigured, and at each waypoint the projectile runs logic "get position->go there" and modifies the array list of waypoints that have not been visited.

Papyrus' slowness shows with these time critical cases, so also you should try and estimate the position of the target by adding its (scaled) velocity vector in so you won't have to update your waypoints as much if the target is heading along the projected path (most targets do move in straight lines except dragons)
User avatar
cosmo valerga
 
Posts: 3477
Joined: Sat Oct 13, 2007 10:21 am

Post » Mon Jun 18, 2012 8:42 pm

Yeah, for aesthetics I considered a waypoint system to make it look like the projectiles "arc" towards the target but I think it would simply be too jerky to even attempt. Right now the projectiles will curve if the target starts to move before they arrive, but if they don't move its going to be a straight line. With waypoints I think you would get this jerky motion of moving straight line to the waypoint, stop, move straight line to next waypoint, stop, etc.

I think I'll muck with the Spline functions a bit more.
User avatar
Dean Ashcroft
 
Posts: 3566
Joined: Wed Jul 25, 2007 1:20 am


Return to V - Skyrim