[HL2:DM] Flaregun

Please post any questions about developing your plugin here. Please use the search function before posting!
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

[HL2:DM] Flaregun

Postby Painkiller » Sat Mar 30, 2019 8:13 pm

If I shoot a Flargun from the pistol come currently these error messages

Code: Select all

2019-03-30 16:08:29 - sp   -   EXCEPTION   
[SP] Caught an Exception:
Traceback (most recent call last):
  File "../addons/source-python/packages/source-python/listeners/tick.py", line 80, in _tick
    self.pop(0).execute()
  File "../addons/source-python/packages/source-python/listeners/tick.py", line 161, in execute
    return self.callback(*self.args, **self.kwargs)
  File "../addons/source-python/packages/source-python/listeners/tick.py", line 606, in _execute
    self.callback(*self.args, **self.kwargs)
  File "../addons/source-python/plugins/supermod/modules/flaregun.py", line 54, in check_buttons
    if player.active_weapon.classname == "weapon_pistol":

AttributeError: 'NoneType' object has no attribute 'classname'
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Dec 20, 2021 11:16 am

Hi guys, I noticed that when the opponents are hit by a flare no longer burn (no HP loss).
(Player and NPC not burn)
Could someone look where drann that is?
I use this script.

There are also no errors in the log

Syntax: Select all

# ../addons/source-python/plugins/supermod/modules/flaregun.py

# ============================================================================
# >> IMPORTS
# ============================================================================
from engines.precache import Model
from entities.entity import Entity
from events import Event
from players.entity import Player
from filters.players import PlayerIter
from listeners.tick import Repeat
from players.constants import PlayerButtons
from mathlib import Vector
from colors import Color

from listeners.tick import Delay, Repeat
import core
from entities.constants import SolidFlags
from entities.constants import CollisionGroup
from entities.hooks import EntityPreHook
from entities.hooks import EntityCondition
from memory import make_object
from messages.base import HintText
from messages import SayText2
from engines.sound import Attenuation
from listeners import OnEntityOutput

model = Model("models/weapons/flare.mdl")
sound_shoot = "weapons/flaregun/fire.wav"
sound_empty = "weapons/pistol/pistol_empty.wav"
throw_force = 1000
flare_scale = 4.5
flare_delay = 0.1
ignite_time = 2.0
core.console_message("\n[Supermod] Flaregun loaded!")
max_ammo = 15
ammo = {}
can_shoot = {}


def init_player(userid):
ammo[userid] = max_ammo
can_shoot[userid] = 1


@Event('player_connect')
def connect(ev):
init_player(ev['userid'])



@Event('player_spawn')
def spawn(ev):
ammo[ev['userid']] = max_ammo
can_shoot[ev['userid']] = 1


def check_buttons():
for player in PlayerIter('all'):
if player.buttons & PlayerButtons.ATTACK2:
userid = player.userid
_weapon = player.active_weapon
if _weapon is not None and userid in can_shoot:
if _weapon.weapon_name == "weapon_pistol":
if can_shoot[player.userid] == 1:
throwFlare(player.index)

if userid not in can_shoot:
init_player(userid)



def throwFlare(index):
player = Player(index)
if ammo[player.userid] == 0:
player.play_sound(sound_empty, 1.0, Attenuation.NONE, download=True)
else:
player.play_sound(sound_shoot, 1.0, Attenuation.NONE, download=True)
entity = Entity.create("env_flare")
entity.scale = flare_scale
entity.spawn()
entity.solid_flags = SolidFlags(entity.solid_flags | SolidFlags.NOT_SOLID)
entity.owner_handle = player.inthandle
pos = player.eye_location
view = player.view_coordinates
vel = player.velocity.length_2D/10
forward = player.view_vector * (25 + vel)
pos.x += forward.x
pos.y += forward.y
pos.z += forward.z
ang = player.view_angle
null_vec = Vector(0, 0, 0)
entity.teleport(pos, ang, null_vec)
entity.call_input('Launch', 0.0)
entity.base_velocity = player.view_vector * throw_force
ammo[player.userid] -= 1
can_shoot[player.userid] = 0
entity.collision_group = CollisionGroup.NONE
entity.delay(flare_delay, reset_shot, (player.userid,))


def set_collision(entity):
entity.collision_group = 5


def reset_shot(userid):
can_shoot[userid] = 1


@EntityPreHook(EntityCondition.equals_entity_classname('env_flare'), 'touch')
def pre_start_touch(stack):
entity = make_object(Entity, stack[0])
if entity.classname == "env_flare":
other = make_object(Entity, stack[1])
if other.classname == "player":
other_player = Player(other.index)
if other_player != entity.owner_handle:
other.ignite_lifetime(ignite_time)
handle = entity.get_property_int('m_pParent')
if handle != -1:
return False


repeat_check = Repeat(check_buttons)
repeat_check.start(0.1)
Last edited by Painkiller on Thu Jan 27, 2022 1:35 pm, edited 1 time in total.
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Thu Jan 27, 2022 1:34 pm

anybody can help ?
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 1:01 pm

Hi Painkiller, I've made some adjustments to the plugin that should fix the issues you're having:

Syntax: Select all

# ../addons/source-python/plugins/supermod/modules/flaregun.py

# Python
from random import uniform

# Source.Python
import core
from core import PLATFORM
from engines.sound import Attenuation
from entities.constants import CollisionGroup, SolidFlags
from entities.entity import Entity
from entities.helpers import index_from_pointer
from entities.hooks import EntityCondition, EntityPreHook
from events import Event
from listeners import (
ButtonStatus, OnButtonStateChanged, get_button_combination_status
)
from mathlib import QAngle
from memory import Convention, DataType, find_binary
from players.constants import PlayerButtons
from players.entity import Player


# Burn duration (in seconds) applied to entities that touch the flare.
IGNITE_TIME = 2
# How much flaregun ammo should the players spawn with?
MAX_FLARE_AMMO = 15
# Seconds until the player can fire another flare.
FLAREGUN_FIRE_RATE = 0.1
# Speed at which the flare is fired.
FLARE_THROW_FORCE = 1000
# Size of the flare.
FLARE_SCALE = 4.5
# Size of the signal particle effects.
FLARE_PARTICLES_SCALE = 4.5
# Should the flare only ignite players?
ONLY_IGNITE_PLAYERS = False
# Should the flare ignite the player that fired it?
IGNITE_OWNER = False
# Should the flare go through players?
PASS_THROUGH_PLAYERS = False
# Should the player's view shake/wobble when they fire a flare?
VIEW_PUNCH = True


# Message that will be displayed when the plugin gets loaded.
core.console_message("\n[Supermod] Flaregun loaded!")

# Condition used for the 'start_touch' hook.
is_flare = EntityCondition.equals_entity_classname('env_flare')


# =============================================================================
# >> CBasePlayer::ViewPunch
# =============================================================================
if PLATFORM == 'windows':
signature = \
b'\x55\x8B\xEC\xA1\x2A\x2A\x2A\x2A\x83\xEC\x0C\x83\x78\x30\x00\x56\x8B'
else:
signature = '_ZN11CBasePlayer9ViewPunchERK6QAngle'


view_punch = find_binary('server')[signature].make_function(
Convention.THISCALL,
(DataType.POINTER, DataType.POINTER),
DataType.VOID
)


# =============================================================================
# >> FLARE CLASS
# =============================================================================
class Flare(Entity):
"""Flare class."""
caching = True

@classmethod
def create(cls, owner_handle=None):
"""Creates a flare.

Args:
owner_handle (int): Inthandle of the entity that created the flare.
"""
flare = super().create('env_flare')
flare.set_key_value_float('scale', FLARE_PARTICLES_SCALE)
flare.spawn()
flare.model_scale = FLARE_SCALE

if owner_handle is not None:
flare.owner_handle = owner_handle

flare.solid_flags = SolidFlags.TRIGGER

if PASS_THROUGH_PLAYERS:
flare.collision_group = CollisionGroup.DEBRIS
else:
flare.collision_group = CollisionGroup.NONE

return flare


# =============================================================================
# >> PLAYER CLASS
# =============================================================================
class PlayerF(Player):
"""Extended Player class.

Args:
index (int): A valid player index.
caching (bool): Check for a cached instance?

Attributes:
flare_ammo (int): Current amount of ammo for the flare gun.
flare_ready (bool): Can the player shoot a flare?
flare_cooldown (Delay): Instance of Delay() used for reloading the
flaregun.
"""
sound_flare_empty = {
'sample': 'weapons/pistol/pistol_empty.wav',
'attenuation': Attenuation.NONE,
'volume': 1.0,
'download': True
}
sound_flare_shoot = {
'sample': 'weapons/flaregun/fire.wav',
'attenuation': Attenuation.NONE,
'volume': 1.0,
'download': True
}

def __init__(self, index, caching=True):
"""Initializes the object."""
super().__init__(index, caching)
self.flare_ammo = 0
self.flare_ready = False
self.flare_cooldown = None

def initialize_flares(self, ammo):
"""Gives the player ammo for the flaregun, and lets them use it."""
self.flare_ammo = ammo
self.flare_ready = True

def disable_flares(self):
"""Makes the player unable to use the flaregun."""
try:
# Stop the delay responsible for reloading the flaregun.
self.flare_cooldown.cancel()
except (AttributeError, ValueError):
# AttributeError: Missing Delay() instance.
# ValueError: Delay() already executed the callback.
pass

self.flare_ready = False

def shoot_flare(self):
"""Shoots a flare."""
if not self.flare_ready:
return

try:
# Try to get the name of the weapon the player is holding.
weapon_name = self.active_weapon.classname
except AttributeError:
# Player might be dead or missing their weapons.
return

# Is the player not holding a pistol?
if weapon_name != 'weapon_pistol':
return

# Is the player out of ammo?
if self.flare_ammo < 1:
self.play_sound(**PlayerF.sound_flare_empty)
return

flare = Flare.create(owner_handle=self.inthandle)

origin = self.eye_location
view_vector = self.view_vector
velocity = self.velocity.length_2D / 10

forward = view_vector * (25 + velocity)
origin += forward

flare.teleport(origin, self.view_angle)
flare.call_input('Launch', 0.0)
flare.base_velocity = view_vector * FLARE_THROW_FORCE

# Reduce the amount of ammo.
self.flare_ammo -= 1
self.flare_ready = False
self.flare_cooldown = self.delay(FLAREGUN_FIRE_RATE, setattr, (
self, 'flare_ready', True))

self.play_sound(**PlayerF.sound_flare_shoot)

if VIEW_PUNCH:
view_punch(self, QAngle(uniform(0.7, 1.1), uniform(-1.4, 1.4), 0))


# =============================================================================
# >> EVENTS AND LISTENERS
# =============================================================================
@Event('player_spawn')
def player_spawn(event):
"""Called when a player spawns."""
PlayerF.from_userid(event['userid']).initialize_flares(ammo=MAX_FLARE_AMMO)


@Event('player_death')
def player_death(event):
"""Called when a player dies."""
PlayerF.from_userid(event['userid']).disable_flares()


@OnButtonStateChanged
def on_button_state_changed(player, old_buttons, new_buttons):
"""Called when the button state of a player changed."""
status = get_button_combination_status(
old_buttons, new_buttons, PlayerButtons.ATTACK2)

# Did the player just press right click (+attack2)?
if status == ButtonStatus.PRESSED:
PlayerF(player.index).shoot_flare()


# =============================================================================
# >> HOOKS
# =============================================================================
@EntityPreHook(is_flare, 'start_touch')
def start_touch_pre(stack_data):
"""Called when an 'env_flare' entity touches another entity."""
try:
flare = Flare.cache[index_from_pointer(stack_data[0])]
except KeyError:
return

entity = Entity._obj(stack_data[1])
# Is this entity not a player (and do we only want to ignite players)?
if not entity.is_player() and ONLY_IGNITE_PLAYERS:
# Don't go further.
return

# Is this the entity that fired the flare (and do we want to avoid igniting
# the owner of the flare)?
if entity.inthandle == flare.owner_handle and not IGNITE_OWNER:
return

try:
# Try to set the entity on fire.
entity.ignite_lifetime(IGNITE_TIME)
except AttributeError:
# This entity can't be set on fire.
pass
And I've added a couple of features you can play around with. :wink:
Last edited by VinciT on Mon Jan 31, 2022 10:52 pm, edited 3 times in total.
ImageImageImageImageImage
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Jan 31, 2022 1:20 pm

This is great thank you.
Works great.

I noticed that I can not put the size of the flare. Nothing changed.

( The color would still be intressant ;)
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 1:55 pm

Should be working now, give it another shot.
Painkiller wrote:( The color would still be intressant ;)
You want the flare to be a different color?
ImageImageImageImageImage
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Jan 31, 2022 1:59 pm

Haha that's great with the size.
Now it works.

shake/wobble doesn't seem to work yet either.

Yes different colors would be great.
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 3:55 pm

Painkiller wrote:shake/wobble doesn't seem to work yet either.
I believe I fixed it, grab the updated plugin and tell me if it works.
Painkiller wrote:Yes different colors would be great.
It appears red is hardcoded/prebaked into the env_flare entity. We'd have to create a custom entity - most likely a prop_physics_override with particle effects and temporary entities (smoke, sparks, and so on) parented to it in order to support custom colors.
ImageImageImageImageImage
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Jan 31, 2022 4:02 pm

VinciT wrote:
Painkiller wrote:shake/wobble doesn't seem to work yet either.
I believe I fixed it, grab the updated plugin and tell me if it works.

Painkiller wrote:Yes different colors would be great.
It appears red is hardcoded/prebaked into the env_flare entity. We'd have to create a custom entity - most likely a prop_physics_override with particle effects and temporary entities (smoke, sparks, and so on) parented to it in order to support custom colors.


shake/wobble still does not work

Oh that does not have to be extra
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 4:31 pm

Painkiller wrote:shake/wobble still does not work
Huh, strange - works on my machine. I'll look into it and update the plugin when I find the solution.
ImageImageImageImageImage
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 10:53 pm

Updated the plugin with a possible solution for the view punch (screen shake/wobble).
ImageImageImageImageImage
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Jan 31, 2022 11:32 pm

Unfortunately, it does not work yet.
Probably it is because of my outdated SP version. But I'm too afraid to update it after half of it works again.

And no one has time and desire once to fix everything

an older shake when the grenade explodes nearby makes me shake
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 11:45 pm

It's as if view punch is disabled on your server. This is what it looks like for me:

I'll add a different type of screen shake later tonight, which will probably work for you.
ImageImageImageImageImage
User avatar
Painkiller
Senior Member
Posts: 725
Joined: Sun Mar 01, 2015 8:09 am
Location: Germany
Contact:

Re: [HL2:DM] Flaregun

Postby Painkiller » Mon Jan 31, 2022 11:49 pm

Oh my goodness, now I've noticed.

That is very weak and you do not get in the movement with gets

But yes it works.
I just did not notice it before.
User avatar
VinciT
Senior Member
Posts: 331
Joined: Thu Dec 18, 2014 2:41 am

Re: [HL2:DM] Flaregun

Postby VinciT » Mon Jan 31, 2022 11:56 pm

Hahahahahahaha, dang. We've been chasing a non-existent issue. :grin:
If you'd like to modify the shake to be stronger, go to line 198:

Syntax: Select all

view_punch(self, QAngle(uniform(0.7, 1.1), uniform(-1.4, 1.4), 0))
And play around with those values.
ImageImageImageImageImage

Return to “Plugin Development Support”

Who is online

Users browsing this forum: No registered users and 17 guests