Jump to content

Photo

Scripting Assistance

summoning item array target help multiple

  • Please log in to reply
12 replies to this topic

#1
Someone1

Someone1

    Journeyman

  • Members
  • Pip
  • 31 posts

Hello all, I was hoping to get steered in the right direction so that I can be on my way to develop a mod that I've been wanting to create for a while now.

 

To get to the point, I would like to summon a certain number of objects (10 for example) at the target location of a spell. These items can be base items for all I care, I am just looking for framework here.

 

Now, I was able to get one item to summon (A door in this case, but it can obviouslly be changed to anything) using this method http://forums.nexusm...mmoning-a-door/

 

My issue is trying to adopt this to summon multiple items, preferable in a circle around the target (I can work on that later though), for now I just want to know what I'm doing wrong.

 

Incorperating a array in the matter is what's most troubling to me at the moment. I'm not sure if this method is the right direction or not but its something I tried to combined from another script

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door Property TeleportDoor Auto
Activator Property EffectSummonBanishFX Auto
ObjectReference[] Doors	

Event OnInit(Actor Target)
Doors = new ObjectReference[10]
int i = 0
While i < 10
    Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90 + i)
    Self.PlaceAtMe(EffectSummonBanishFX)
    Doors[i]=Self.PlaceAtMe(TeleportDoor)
	Doors[i].Enable()
	i+= 1
EndWhile
EndEvent

I also tried something like below to no avail.

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door[] Property TeleportDoor Auto
Activator Property EffectSummonBanishFX Auto

Event OnInit(Actor Target)
int i = 0
While i < 10
    Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90 + i)
    Self.PlaceAtMe(EffectSummonBanishFX)
    Self.PlaceAtMe(TeleportDoor[i])
	i+= 1
EndWhile
EndEvent

Again, super rough code but I'm just trying to get the point across. (I honestly don't think a .Enable should even be necessary). I think the Self. portion is what's throwing me off the most.

 

So again, main idea is to shoot a spell at a target (could be the ground or a person) and it will summon 10 items of whatever.

 

Even if you can point me to a thread remotely close to what I'm looking for would be helpfull because I sure can't find one other than maybe this one. http://forums.nexusm...-summons-spell/

 

I'm not entirely sure how to adopt that to what I'm looking for as I don't know if NPC vs objects differ at all.

 

Anyways, if you could help I would appreciate it, if not, no worries. I'll be happy to clear anything up that I can.



#2
Mattiewagg

Mattiewagg

    Is Female?!

  • Supporter
  • PipPipPipPipPip
  • 5,544 posts
The event you're looking to use is NOT onInit - OnInit shouldn't have a ton of stuff in it and it doesn't take parameters anyway. You want to use the OnEffectStart http://www.creationk...tiveMagicEffect on a script on the magic effect attached to the spell. You'll place your objects at akTarget, make sure your magic effect has a target location.

#3
Someone1

Someone1

    Journeyman

  • Members
  • Pip
  • 31 posts

The event you're looking to use is NOT onInit - OnInit shouldn't have a ton of stuff in it and it doesn't take parameters anyway. You want to use the OnEffectStart http://www.creationk...tiveMagicEffect on a script on the magic effect attached to the spell. You'll place your objects at akTarget, make sure your magic effect has a target location.

 

Ah, ok I'll take that into consideration and try it out. Now out of curiosity, why does the script below work just fine? (That is the original teleporting door marker script.) I know there's a 1000 ways to skin a cat and I was just curious on why the method below works just fine?

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door Property TeleportDoor Auto
Activator Property EffectSummonBanishFX Auto

Event OnInit()
    Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90)
    Self.PlaceAtMe(EffectSummonBanishFX)
    Self.PlaceAtMe(TeleportDoor)
    Self.DeleteWhenAble()
EndEvent

Moving on, how do place more that one object at the target location script wise, using the array?

Is it something like below

Target.PlaceAtMe(TeleportDoor[i])

Or something a little different?

 

Thanks for the help thus far!


Edited by Someone1, 18 December 2015 - 07:48 PM.


#4
BigBizkit

BigBizkit

    Community Manager

  • Admin
  • 6,338 posts

The event you're looking to use is NOT onInit - OnInit shouldn't have a ton of stuff in it and it doesn't take parameters anyway. You want to use the OnEffectStart http://www.creationk...tiveMagicEffect on a script on the magic effect attached to the spell. You'll place your objects at akTarget, make sure your magic effect has a target location.

The target in OnEffectStart has to be an actor. Therefore it cannot be used to get the target location of a target location spell. I am also quite certain that OnEffectStart is useless in this situation to begin with.

 

You will have to utilize a more convoluted way:

 

1. Place a dummy object (empty mesh) at a location via spell. There are several ways to do that. Having a dummy explosion place it at the spells impact point works best imo,

 

2. Put an OnLoad script on that dummy object that runs your code. You can have it place multiple objects via placeatme.

 

3. Make sure to put a timer on the object that at its end will disable and delete it.



#5
Someone1

Someone1

    Journeyman

  • Members
  • Pip
  • 31 posts

 

The event you're looking to use is NOT onInit - OnInit shouldn't have a ton of stuff in it and it doesn't take parameters anyway. You want to use the OnEffectStart http://www.creationk...tiveMagicEffect on a script on the magic effect attached to the spell. You'll place your objects at akTarget, make sure your magic effect has a target location.

The target in OnEffectStart has to be an actor. Therefore it cannot be used to get the target location of a target location spell. I am also quite certain that OnEffectStart is useless in this situation to begin with.

 

You will have to utilize a more convoluted way:

 

1. Place a dummy object (empty mesh) at a location via spell. There are several ways to do that. Having a dummy explosion place it at the spells impact point works best imo,

 

2. Put an OnLoad script on that dummy object that runs your code. You can have it place multiple objects via placeatme.

 

3. Make sure to put a timer on the object that at its end will disable and delete it.

 

 

Oddly enough I just got to try the on OnEffectStart suggestion and like you said, it only works on the actor so the original idea of placing a dummy object via the explosion seems to be the best way (as you stated).

 

First question though is why OnLoad as opposed to OnInt?

Second question, how would multiple objects be placed code wise? (i.e. will the code look like target.placeatme or self.placeatme or something else.)

Also using multiple objects, will I need to use ObjectReferences? Like will it be similar to below

Scriptname MultipleObjects extends ObjectReference

Door Property Stuff Auto

ObjectReference object2
ObjectReference object1

Event OnLoad()
	object1 = self.PlaceAtMe(Stuff)
	object2 = self.PlaceAtMe(Stuff)

EndEvent

Or will it be more like something below

Scriptname MultipleObjects extends ObjectReference

Door[] Property Stuff Auto

ObjectReference object2
ObjectReference object1

Event OnLoad()
	self.PlaceAtMe(Stuff[1])
	self.PlaceAtMe(Stuff[2])

EndEvent

Hopefully that all makes sense, I can try and further explain what I'm saying if it's unclear



#6
BigBizkit

BigBizkit

    Community Manager

  • Admin
  • 6,338 posts

It depends on what you want to do. Without more info, I cannot tell you which event would be preferable.

 

A way to use arrays would be e.g. 

 

referencealias[] property CrewAlias auto      <- this is how to define an array property

 

 

int indexCrow = 0
while indexCrow < 9
if CrewAlias[indexCrow].GetActorRef().ISInFaction(aaShipCrewCrowFaction)
CrewAlias[indexCrow].GetActorRef().MoveTo(XCrow)
endif
indexCrow+= 1
endwhile
 
This is copy pasta from one of my scripts. What it does is move CrewAlias 1-8 to XCrow, if that alias is in the aaShipCrewCrowFaction.
 
So in the same way you would use Self.Placeatme(Stuff[indexIntWhichYouNeedToDefineFirst]) followed by indexIntWhichYouNeedToDefineFirst+= 1, nested in a while loop.


#7
Someone1

Someone1

    Journeyman

  • Members
  • Pip
  • 31 posts


 

It depends on what you want to do. Without more info, I cannot tell you which event would be preferable.

 

A way to use arrays would be e.g. 

 

referencealias[] property CrewAlias auto      <- this is how to define an array property

 

 

int indexCrow = 0
while indexCrow < 9
if CrewAlias[indexCrow].GetActorRef().ISInFaction(aaShipCrewCrowFaction)
CrewAlias[indexCrow].GetActorRef().MoveTo(XCrow)
endif
indexCrow+= 1
endwhile
 
This is copy pasta from one of my scripts. What it does is move CrewAlias 1-8 to XCrow, if that alias is in the aaShipCrewCrowFaction.
 
So in the same way you would use Self.Placeatme(Stuff[indexIntWhichYouNeedToDefineFirst]) followed by indexIntWhichYouNeedToDefineFirst+= 1, nested in a while loop.

 

 

I can give you any info you need, just let me know what needs clarifed and I'll be happy to do so! But I'll try the code below and see if that works out, although I have my doubts.

 

Edit: I'll try to further explain what I'm trying to do. Basically I want to cast a spell on a target (it'll eventually be actor only but for now the ground is just fine) Then whenever the projectile hits the target a ring of objects appears, say 10 or so, around the target point (all aiming at the target.) Then the items will each shoot a spell out, or the objects will launch at the target, whatever is better (I still haven't decided.)  Hopefully that all makes sense.

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door[] Property TeleportDoor Auto
Activator[] Property EffectSummonBanishFX Auto


Event OnInit()
int i = 0
While i <10
Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90+i*2)
Self.PlaceAtMe(EffectSummonBanishFX[i])
Self.PlaceAtMe(TeleportDoor[i])
Self.DeleteWhenAble()
    i+=1
EndWhile
EndEvent

Edit 2: Using the code below has resulted in a success (atleast to me) as shown in the video here: https://www.youtube....eature=youtu.be

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door[] Property TeleportDoor Auto
Activator[] Property EffectSummonBanishFX Auto


Event OnInit()
int i = 0
While i <10
    Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90 + (i*5))
    Self.PlaceAtMe(EffectSummonBanishFX[i])
    Self.PlaceAtMe(TeleportDoor[i])
    ;Self.DeleteWhenAble()
	i+=1
EndWhile
EndEvent

So progress has been made, now if there a better way to do it, I'm all ears but this is a solid foundation. The next step is the circle portion in which I'm trying to figure out the best way to do that section. If you have any helpful hints I would greatly appreciate it.

 

Edit 3: Thanks for the help thus far, by the way, its very much appreciated!


Edited by Someone1, 20 December 2015 - 07:28 AM.


#8
Someone1

Someone1

    Journeyman

  • Members
  • Pip
  • 31 posts

Ok new post because the edit keeps severley messing up on me. Now that I/we got the multiple object to spawn, my goal is for them to spawn in a circle around the target location. I added to the script below to what I think makes the most sense to me but of course it doesn't work. The script below only spawns them from the target location and then goes down to the ground. I'm not sure if it's my math or my scripting so any help would be appreciated.

Scriptname _TeleportDoorMarkerScript extends ObjectReference

Door[] Property TeleportDoor Auto
Activator[] Property EffectSummonBanishFX Auto


Event OnInit()
int i = 0
int orbit_angle = 360;
int orbit_radius = 128;

While i <10
    Self.SetAngle(0.0,0.0, Game.GetPlayer().GetAngleZ() + 90 + (i*5))
    Self.PlaceAtMe(EffectSummonBanishFX[i])
    Self.PlaceAtMe(TeleportDoor[i])
	orbit_angle += i
	float x = Self.GetPositionX() + orbit_radius * math.cos(math.degreestoradians(orbit_angle));
	float y = Self.GetPositionY() + orbit_radius * math.sin(math.degreestoradians(orbit_angle));
	Self.TranslateTo(x,y,0.0,0.0,0.0,0.0,50.0)
    ;Self.DeleteWhenAble()
	i+=1
EndWhile
EndEvent

Edited by Someone1, 21 December 2015 - 08:23 AM.


#9
BigBizkit

BigBizkit

    Community Manager

  • Admin
  • 6,338 posts

Sinus and cosinus are my old archnemeses from math class, so I cannot help you with that.

 

It depends on what you want to do, obviously, but personally once I have more than 2-3 objects that need to be placed in a specific relative position, I'd rather combine them all into one nif. Makes positioning easier.



#10
Mattiewagg

Mattiewagg

    Is Female?!

  • Supporter
  • PipPipPipPipPip
  • 5,544 posts
OnLoad on the explosion placed marker would be best. It will place the marker as an explosion invisibly where the spell lands, and as soon as it is placed/enabled/loaded, you can just move the object to it quite easily. As for the circle, you can just look up coding a circle around an object. Should be easily convertible to Papyrus.

Edited by Mattiewagg, 21 December 2015 - 10:11 PM.






Also tagged with one or more of these keywords: summoning, item, array, target, help, multiple

IPB skins by Skinbox
Page loaded in: 1.091 seconds