Jump to content

[LE] Quick question about Objectreference


Recommended Posts

Is there any different between these three scripts?

 

Script 1:

Actor Caster

ObjectReference CasterRef

 

Event OnEffectStart(Actor akTarget, Actor akCaster)

 

Caster = akCaster

CasterRef = Caster

 

EndEvent

 

Script 2:

Actor Caster

ObjectReference CasterRef

 

Event OnEffectStart(Actor akTarget, Actor akCaster)

 

Caster = akCaster

CasterRef = Caster as ObjectReference

 

EndEvent

 

Script 3:

Actor Caster

ObjectReference CasterRef

 

Event OnEffectStart(Actor akTarget, Actor akCaster)

 

Caster = akCaster

CasterRef = (Caster as ObjectReference)

 

EndEvent

 

Thank you

Link to comment
Share on other sites

No. Casting is only required if you're going from a general type to a more specific one (for example, ObjectReference -> Actor). Actor already extends ObjectReference, so it can be supplied without casting to anything that expects an ObjectReference, because all actors *are* ObjectReferences.

 

Which also makes me wonder why you're bothering to store it twice.

Link to comment
Share on other sites

No. Casting is only required if you're going from a general type to a more specific one (for example, ObjectReference -> Actor). Actor already extends ObjectReference, so it can be supplied without casting to anything that expects an ObjectReference, because all actors *are* ObjectReferences.

 

Which also makes me wonder why you're bothering to store it twice.

Just to add to that, here is a comprehensive script objects map that shows the hierarchy of extensions.

 

https://www.creationkit.com/index.php?title=Category:Script_Objects

 

This is probably one of the most useful pages in the whole wiki.

 

EDIT 1: If he stores akCaster as Caster out of a function, like at the top with the properties, he can use that in other functions with Caster as the value.

 

Thats all I could see it be useful for.

 

EDIT 2: OH, I see... he only needs Caster instead of CasterRef, not both.

Edited by smashballsx88
Link to comment
Share on other sites

Thank you for both your answer, so the "as" only use for transferring one general type to one more specific one ( foamyesque). Could you give me some examples when I should do that? Also, smashballsx88 you also mention about the function. I intend to learn how to use function in my script from creation kit wiki, but I'm stuck. Especially, the parameter of a function and also I don't if there is any different between a function and an event. Could they replace each other? For example,

 

Event OnEffectStart(.......)

 

AFunction() // Can this be replaced with an Event? Like example 2

 

EndEvent

 

Function AFunction()

 

EndFunction

 

Example 2

AEvent()

 

Event AEvent()

 

EndEvent

Link to comment
Share on other sites

Thank you for both your answer, so the "as" only use for transferring one general type to one more specific one ( foamyesque). Could you give me some examples when I should do that?

 

Generally, it happens when a function returns a general class (e.g., a Form) when you know what you're after is a particular subtype (e.g. Armor) and you want to use functions specific to Armor on it.

Link to comment
Share on other sites

I don't if there is any different between a function and an event. Could they replace each other?

There is some pretty big differences. https://www.creationkit.com/index.php?title=Events_Reference

 

You can't just make events like you can functions. Example 1 is the way to go, besides why would you want launch an event from an event? If it has to initiate through 1 event, then any functions it runs are all based on the event anyways.

 

You can add multiple events to the script though.

 

Event OnInit()

EndEvent

 

Event OnActivate()

EndEvent

Link to comment
Share on other sites

You can absolutely custom define new events and there's no difference whatsoever script-wise between the two. All events are functions, and you can convert a function to an event just by changing its declaration. Nothing will care. The distinction is purely a meta one for the programmer, to highlight things that are triggered by the game doing something.

Link to comment
Share on other sites

Thank you for both your answering. For smashballsx88, I did this because I saw the Orchedo teleport script seem doing that way. The Event Teleport() is obvious a new event. I just wonder why they use event teleport() instead function teleport().

For foamyesque, if so, I can replace the Event teleport() with function teleport() without any influence to trigger it, right?

 

As I show below

scriptName defaultTeleportAbility extends activeMagicEffect
{Attempt at a generic script for NPCs to teleport to XXX markers when threatened by melee}

import game
import utility

;VFX
Activator property SummonFX Auto

;Summon parameters
activator property teleportBase auto
{Base object to search for as a teleport point}
float property fSearchRadius = 1600.0 auto
{How far near me to search for teleport points? DEFAULT = 768u}
int property iMinToTeleport = 2 auto
{Min # of hits I'll take before teleporting.  DEFAULT = 2}
int property iMaxToTeleport = 4 auto
{Max # of hits I'll take before teleporting.  DEFAULT = 4}
effectShader property fadeOutFX auto
effectShader property fadeInFX auto
visualEffect property TrailFX auto
;{Let's try some trailing FX to show where I'm going to pop out}

;Internal variables.
bool combatStarted
int hitCount
ObjectReference teleportGoal 
ObjectReference player
actor caster
objectReference casterRef
bool inBleedout
objectReference opponent

Event OnEffectStart(Actor akTarget, Actor akCaster)
	player = game.getPlayer()
	caster = akCaster
	casterRef = (caster as ObjectReference)
endEVENT

;Every 2 hits, the Caller teleports.
Event OnHit(ObjectReference akAggressor, Form weap, Projectile proj, bool abPowerAttack, bool abSneakAttack, bool abBashAttack, bool abHitBlocked)
	opponent = akAggressor
	int hitTolerance = RandomInt(iMinToTeleport, iMaxToTeleport)
	hitCount = hitCount + 1
	if (hitCount > hitTolerance && !caster.IsDead())
		hitCount = 0
		if inBleedout == FALSE && caster.isDead() == FALSE
			Teleport()
		endif
	EndIf
	
	; additional check - seen instances where NPC with this ability would not die!
	if Caster.getActorValue("Health") < 0
		caster.kill()
; 		debug.trace("teleport NPC killed by self (HP<0 safety net): "+caster)
	endif
	
EndEvent

Event Teleport()
		
	;Where's the Caller going?
	int i = 0					; incrementer for while
	int maxSearch = 10		; limit number of while recursions
	while i < maxSearch
		teleportGoal = FindRandomReferenceOfTypeFromRef(teleportBase, casterRef, fSearchRadius)
		if teleportGoal.getDistance(opponent) < 512 || (player as actor).hasLoS(teleportGoal) == FALSE
; 			;debug.trace(caster.getActorBase()+" found but doesn't prefer "+teleportGoal)
			; this teleport marker isn't the best, but hold onto it as a backup option
			; therefore don't kick out of the loop just yet
		elseif teleportGoal.getDistance(opponent) > 512 || (player as actor).hasLoS(teleportGoal) == TRUE
			; if we found a teleport marker that works, just use it!
; 			;debug.trace(caster.getActorBase()+" found a good goal and kicking out of while loop "+teleportGoal)
			i = maxSearch
		endif
		i += 1
; 		;debug.trace("While Recursion #"+i+" on "+self)
	endWhile
			

	;Perform the swap.
	;casterRef.Disable()
	fadeOutFX.play(casterRef)
	caster.setGhost(TRUE)
	objectReference previousLoc = casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	TrailFX.Play(previousLoc, 0.5, teleportGoal)
	
	casterRef.MoveTo(teleportGoal)
	casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	;casterRef.Enable()
	fadeOutFX.stop(casterRef)
	caster.setGhost(FALSE)
	caster.evaluatePackage()
	caster.startCombat(opponent as actor)
EndEvent

EVENT onEnterBleedout()
	inBleedout = TRUE
	; For now never reset this boolean.  Considering it part of the flow that bleeding out turns the ability off
endEVENT
Link to comment
Share on other sites

The replaced one Event to Function:

scriptName defaultTeleportAbility extends activeMagicEffect
{Attempt at a generic script for NPCs to teleport to XXX markers when threatened by melee}

import game
import utility

;VFX
Activator property SummonFX Auto

;Summon parameters
activator property teleportBase auto
{Base object to search for as a teleport point}
float property fSearchRadius = 1600.0 auto
{How far near me to search for teleport points? DEFAULT = 768u}
int property iMinToTeleport = 2 auto
{Min # of hits I'll take before teleporting.  DEFAULT = 2}
int property iMaxToTeleport = 4 auto
{Max # of hits I'll take before teleporting.  DEFAULT = 4}
effectShader property fadeOutFX auto
effectShader property fadeInFX auto
visualEffect property TrailFX auto
;{Let's try some trailing FX to show where I'm going to pop out}

;Internal variables.
bool combatStarted
int hitCount
ObjectReference teleportGoal 
ObjectReference player
actor caster
objectReference casterRef
bool inBleedout
objectReference opponent

Event OnEffectStart(Actor akTarget, Actor akCaster)
	player = game.getPlayer()
	caster = akCaster
	casterRef = (caster as ObjectReference)
endEVENT

;Every 2 hits, the Caller teleports.
Event OnHit(ObjectReference akAggressor, Form weap, Projectile proj, bool abPowerAttack, bool abSneakAttack, bool abBashAttack, bool abHitBlocked)
	opponent = akAggressor
	int hitTolerance = RandomInt(iMinToTeleport, iMaxToTeleport)
	hitCount = hitCount + 1
	if (hitCount > hitTolerance && !caster.IsDead())
		hitCount = 0
		if inBleedout == FALSE && caster.isDead() == FALSE
			Teleport()
		endif
	EndIf
	
	; additional check - seen instances where NPC with this ability would not die!
	if Caster.getActorValue("Health") < 0
		caster.kill()
; 		debug.trace("teleport NPC killed by self (HP<0 safety net): "+caster)
	endif
	
EndEvent

Function Teleport()
		
	;Where's the Caller going?
	int i = 0					; incrementer for while
	int maxSearch = 10		; limit number of while recursions
	while i < maxSearch
		teleportGoal = FindRandomReferenceOfTypeFromRef(teleportBase, casterRef, fSearchRadius)
		if teleportGoal.getDistance(opponent) < 512 || (player as actor).hasLoS(teleportGoal) == FALSE
; 			;debug.trace(caster.getActorBase()+" found but doesn't prefer "+teleportGoal)
			; this teleport marker isn't the best, but hold onto it as a backup option
			; therefore don't kick out of the loop just yet
		elseif teleportGoal.getDistance(opponent) > 512 || (player as actor).hasLoS(teleportGoal) == TRUE
			; if we found a teleport marker that works, just use it!
; 			;debug.trace(caster.getActorBase()+" found a good goal and kicking out of while loop "+teleportGoal)
			i = maxSearch
		endif
		i += 1
; 		;debug.trace("While Recursion #"+i+" on "+self)
	endWhile
			

	;Perform the swap.
	;casterRef.Disable()
	fadeOutFX.play(casterRef)
	caster.setGhost(TRUE)
	objectReference previousLoc = casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	TrailFX.Play(previousLoc, 0.5, teleportGoal)
	
	casterRef.MoveTo(teleportGoal)
	casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	;casterRef.Enable()
	fadeOutFX.stop(casterRef)
	caster.setGhost(FALSE)
	caster.evaluatePackage()
	caster.startCombat(opponent as actor)
EndEvent

EVENT onEnterBleedout()
	inBleedout = TRUE
	; For now never reset this boolean.  Considering it part of the flow that bleeding out turns the ability off
endEVENT
Link to comment
Share on other sites

 

The replaced one Event to Function:

scriptName defaultTeleportAbility extends activeMagicEffect
{Attempt at a generic script for NPCs to teleport to XXX markers when threatened by melee}

import game
import utility

;VFX
Activator property SummonFX Auto

;Summon parameters
activator property teleportBase auto
{Base object to search for as a teleport point}
float property fSearchRadius = 1600.0 auto
{How far near me to search for teleport points? DEFAULT = 768u}
int property iMinToTeleport = 2 auto
{Min # of hits I'll take before teleporting.  DEFAULT = 2}
int property iMaxToTeleport = 4 auto
{Max # of hits I'll take before teleporting.  DEFAULT = 4}
effectShader property fadeOutFX auto
effectShader property fadeInFX auto
visualEffect property TrailFX auto
;{Let's try some trailing FX to show where I'm going to pop out}

;Internal variables.
bool combatStarted
int hitCount
ObjectReference teleportGoal 
ObjectReference player
actor caster
objectReference casterRef
bool inBleedout
objectReference opponent

Event OnEffectStart(Actor akTarget, Actor akCaster)
	player = game.getPlayer()
	caster = akCaster
	casterRef = (caster as ObjectReference)
endEVENT

;Every 2 hits, the Caller teleports.
Event OnHit(ObjectReference akAggressor, Form weap, Projectile proj, bool abPowerAttack, bool abSneakAttack, bool abBashAttack, bool abHitBlocked)
	opponent = akAggressor
	int hitTolerance = RandomInt(iMinToTeleport, iMaxToTeleport)
	hitCount = hitCount + 1
	if (hitCount > hitTolerance && !caster.IsDead())
		hitCount = 0
		if inBleedout == FALSE && caster.isDead() == FALSE
			Teleport()
		endif
	EndIf
	
	; additional check - seen instances where NPC with this ability would not die!
	if Caster.getActorValue("Health") < 0
		caster.kill()
; 		debug.trace("teleport NPC killed by self (HP<0 safety net): "+caster)
	endif
	
EndEvent

Function Teleport()
		
	;Where's the Caller going?
	int i = 0					; incrementer for while
	int maxSearch = 10		; limit number of while recursions
	while i < maxSearch
		teleportGoal = FindRandomReferenceOfTypeFromRef(teleportBase, casterRef, fSearchRadius)
		if teleportGoal.getDistance(opponent) < 512 || (player as actor).hasLoS(teleportGoal) == FALSE
; 			;debug.trace(caster.getActorBase()+" found but doesn't prefer "+teleportGoal)
			; this teleport marker isn't the best, but hold onto it as a backup option
			; therefore don't kick out of the loop just yet
		elseif teleportGoal.getDistance(opponent) > 512 || (player as actor).hasLoS(teleportGoal) == TRUE
			; if we found a teleport marker that works, just use it!
; 			;debug.trace(caster.getActorBase()+" found a good goal and kicking out of while loop "+teleportGoal)
			i = maxSearch
		endif
		i += 1
; 		;debug.trace("While Recursion #"+i+" on "+self)
	endWhile
			

	;Perform the swap.
	;casterRef.Disable()
	fadeOutFX.play(casterRef)
	caster.setGhost(TRUE)
	objectReference previousLoc = casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	TrailFX.Play(previousLoc, 0.5, teleportGoal)
	
	casterRef.MoveTo(teleportGoal)
	casterRef.PlaceAtMe(SummonFX)
	Utility.Wait(0.5)
	
	;casterRef.Enable()
	fadeOutFX.stop(casterRef)
	caster.setGhost(FALSE)
	caster.evaluatePackage()
	caster.startCombat(opponent as actor)
EndEvent

EVENT onEnterBleedout()
	inBleedout = TRUE
	; For now never reset this boolean.  Considering it part of the flow that bleeding out turns the ability off
endEVENT

 

I misspoke slightly: You also need to change the "EndEvent" to "EndFunction" to match the declaration :v

Link to comment
Share on other sites

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...