Вопрос Хуки для способностей

  • 14
  • 1
Хуки для способностей. Как их сделать?

Спросил у нейронки выдала такие вот хуки, но они не работают


sv_effects:
Развернуть Свернуть Копировать
if SERVER then

    -- Модификатор получаемого урона
    hook.Add("EntityTakeDamage", "UndergroundDamageModifiers", function(target, dmg)
        if target:IsPlayer() then
            local resist = target:GetNWFloat("UndmDamageResist", 1.0)
            dmg:ScaleDamage(resist)
            
            local taken = target:GetNWFloat("UndmDamageTaken", 1.0)
            dmg:ScaleDamage(taken)
        end
        
        local attacker = dmg:GetAttacker()
        if IsValid(attacker) and attacker:IsPlayer() then
            if dmg:IsDamageType(DMG_CLUB) or dmg:IsDamageType(DMG_SLASH) then
                local meleeBoost = attacker:GetNWFloat("UndmMeleeDamage", 1.0)
                dmg:ScaleDamage(meleeBoost)
            end
            
            local damageBoost = attacker:GetNWFloat("UndmDamageDealt", 1.0)
            dmg:ScaleDamage(damageBoost)
            
            if attacker:GetNWBool("UndmElectroStun", false) and target:IsPlayer() then
                target:SetVelocity(attacker:GetAimVector() * 500)
                target:ScreenFade(SCREENFADE.IN, Color(0, 150, 255, 100), 0.5, 0.5)
                target:ViewPunch(Angle(-10, 0, 0))
            end
        end
    end)
    
    -- Модификатор скорости атаки
    hook.Add("PlayerSwitchWeapon", "UndergroundAttackSpeed", function(ply, oldWeapon, newWeapon)
        local speedMulti = ply:GetNWFloat("UndmAttackSpeed", 1.0)
        if speedMulti ~= 1.0 and IsValid(newWeapon) then
            if newWeapon:GetClass() == "weapon_fists" and newWeapon.Primary then
                newWeapon.Primary.Delay = (newWeapon.Primary.Delay or 0.5) / speedMulti
                newWeapon:SetNextPrimaryFire(CurTime() + (newWeapon.Primary.Delay or 0.5) / speedMulti)
            end
        end
    end)

    hook.Add("WeaponReload", "UndergroundReloadSpeed", function(weapon)
        local ply = weapon:GetOwner()
        if not IsValid(ply) or not ply:IsPlayer() then return end
        
        local reloadMulti = ply:GetNWFloat("UndmReloadSpeed", 1.0)
        if reloadMulti ~= 1.0 and weapon.ReloadTime then
            weapon:SetNextPrimaryFire(CurTime() + weapon.ReloadTime / reloadMulti)
            return true
        end
    end)
    
    hook.Add("PlayerStartCommand", "UndergroundSpreadModifier", function(ply, cmd)
        local spreadMulti = ply:GetNWFloat("UndmSpreadMulti", 1.0)
        if spreadMulti ~= 1.0 then
            local wep = ply:GetActiveWeapon()
            if IsValid(wep) and wep.Primary and wep.Primary.Cone then
                wep.Primary.Cone = wep.Primary.Cone * spreadMulti
            end
        end
    end)
    
    hook.Add("SetupMove", "UndergroundRecoilModifier", function(ply, mv, cmd)
        local recoilMulti = ply:GetNWFloat("UndmRecoilMulti", 1.0)
        if recoilMulti ~= 1.0 and cmd:KeyDown(IN_ATTACK) then
            local ang = cmd:GetViewAngles()
            ang.p = ang.p - (recoilMulti - 1) * 0.5
            cmd:SetViewAngles(ang)
        end
    end)

    -- Очистка при смерти
    hook.Add("PlayerDeath", "UndergroundClearEffects", function(ply)
        ply.ActiveSubstances = {}
        net.Start("UM_ClearEffects")
        net.Send(ply)
        
        local steamID = string.gsub(ply:SteamID(), ":", "_")
        for _,v in pairs({"Biolink", "Spank", "DeathTouch", "Berserk", "ElectroCharge",
                         "QuickDraw", "BloodRage", "Steroids"}) do
            timer.Remove(v .. "Effect_" .. steamID)
            timer.Remove(v .. "AfterEffect_" .. steamID)
            timer.Remove(v .. "Overdose_" .. steamID)
            timer.Remove(v .. "Stun_" .. steamID)
        end
    end)
end
 
  • 11
  • 1
  • 2
Ну так она тебе их и сделала, если не работает то скорее всего просто тебе нужно будет переписывать под свой пак оружия добавлять всякие костыли
 
  • 14
  • 1
Ну так она тебе их и сделала, если не работает то скорее всего просто тебе нужно будет переписывать под свой пак оружия добавлять всякие костыли
оно не работает даже с HL2 и стандартным оружием darkrp

Также скорость атаки на кулаках не работает, модификатор получаемого урона не работает
 
  • 14
  • 1
target:SetNWFloat("UndmDamageTaken", 0.5)
у тебя вообще ставиться это где-то?
if modifiers.damage_taken then
ply:SetNWFloat("UndmDamageTaken", modifiers.damage_taken)
end

в SH файле.

сам файл:

sh_effects:
Развернуть Свернуть Копировать
local EFFECTS = {}

function EFFECTS.ApplyModifiers(ply, modifiers)
    -- Применение голода
    if modifiers.hunger then
        if not ply.OriginalHungerMod then
            ply.OriginalHungerMod = ply:GetTable().HungerMod or 1
        end
        ply:GetTable().HungerMod = ply.OriginalHungerMod * modifiers.hunger
    end

    -- Применение скорости
    if modifiers.speed then
        ply:SetWalkSpeed(ply:GetWalkSpeed() * modifiers.speed)
        ply:SetRunSpeed(ply:GetRunSpeed() * modifiers.speed)
    end

    -- Применение бонуса здоровья
    if modifiers.health_bonus then
        ply:SetHealth(math.min(ply:Health() + modifiers.health_bonus, ply:GetMaxHealth()))
    end

    -- Применение сопротивления урону
    if modifiers.damage_resist then
        ply:SetNWFloat("UndmDamageResist", modifiers.damage_resist)
    end

    -- Применение урона в ближнем бою
    if modifiers.melee_damage then
        ply:SetNWFloat("UndmMeleeDamage", modifiers.melee_damage)
    end

    -- Применение скорости атаки
        if modifiers.attack_speed then
        ply:SetNWFloat("UndmAttackSpeed", modifiers.attack_speed)
       
        -- Немедленно применяем к кулакам, если они в руках
        local wep = ply:GetActiveWeapon()
        if IsValid(wep) and wep:GetClass() == "weapon_fists" then
            wep.Primary.Delay = wep.Primary.Delay / modifiers.attack_speed
        end
    end

    -- Применение бонуса урона
    if modifiers.damage_bonus then
        ply:SetNWFloat("UndmDamageDealt", modifiers.damage_bonus)
    end

    -- Применение получаемого урона
    if modifiers.damage_taken then
        ply:SetNWFloat("UndmDamageTaken", modifiers.damage_taken)
    end

    -- Применение электрошока
    if modifiers.electro_stun then
        ply:SetNWBool("UndmElectroStun", true)
    end

    -- Применение модификатора отдачи
    if modifiers.recoil then
        ply:SetNWFloat("UndmRecoilMulti", modifiers.recoil)
    end

    -- Применение скорости перезарядки
    if modifiers.reload_speed then
        ply:SetNWFloat("UndmReloadSpeed", modifiers.reload_speed)
    end

    -- Применение модификатора разброса
    if modifiers.after_spread then
        ply:SetNWFloat("UndmSpreadMulti", modifiers.after_spread)
    end

    -- Применение модификатора опыта
    if modifiers.xp_bonus then
        ply:SetNWFloat("UndmStrengthXP", modifiers.xp_bonus)
    end

    -- Применение модификатора выносливости
    if modifiers.after_stamina then
        ply:SetNWFloat("UndmStamina", modifiers.after_stamina)
    end
end

function EFFECTS.ResetModifiers(ply, itemName, isOverdose)
    local effect = aquascriptsConfig.UndergroundMarket.Effects[itemName]
    if not effect then return end

    -- BIOLINK
    if itemName == "BIOLINK" then
        if ply.OriginalHungerMod then
            ply:GetTable().HungerMod = ply.OriginalHungerMod *
                (isOverdose and effect.modifiers.after_hunger or 1)
        end
        if isOverdose then
            ply:SetWalkSpeed(ply:GetWalkSpeed() / effect.modifiers.speed)
            ply:SetRunSpeed(ply:GetRunSpeed() / effect.modifiers.speed)
        end
   
    -- SPANK
    elseif itemName == "SPANK" then
        ply:SetNWFloat("UndmDamageResist", 1.0)
   
    -- DEATH TOUCH
    elseif itemName == "DEATH TOUCH" then
        ply:SetNWFloat("UndmMeleeDamage", 1.0)
        ply:SetHealth(math.max(1, ply:Health() * effect.modifiers.after_health))
        ply:SetNWFloat("UndmDamageTaken", effect.modifiers.after_damage_taken)
   
    -- BERSERK
    elseif itemName == "BERSERK" then
        ply:GodDisable()
        ply:SetNWFloat("UndmAttackSpeed", 5.6)
        ply:SetHealth(math.max(1, ply:Health() * effect.modifiers.after_health))
        ply:SetNWFloat("UndmDamageDealt", 1.0)
        ply:SetNWFloat("UndmStamina", effect.modifiers.after_stamina)
   
    -- ELECTRO CHARGE
    elseif itemName == "ELECTRO CHARGE" then
        ply:SetNWBool("UndmElectroStun", false)
        ply:SetNWFloat("UndmDamageDealt", 1.0)
        ply:SetNWFloat("UndmSpreadMulti", effect.modifiers.after_spread)
   
    -- QUICK DRAW
    elseif itemName == "QUICK DRAW" then
        ply:SetNWFloat("UndmRecoilMulti", isOverdose and effect.modifiers.overdose_recoil or effect.modifiers.after_recoil)
        ply:SetNWFloat("UndmReloadSpeed", 1.0)
   
    -- BLOOD RAGE
    elseif itemName == "BLOOD RAGE" then
        ply:SetNWFloat("UndmDamageDealt", 1.0)
        ply:SetNWFloat("UndmDamageTaken", 1.0)
        -- Кровотечение обрабатывается отдельным таймером
   
    -- STEROIDS
    elseif itemName == "STEROIDS" then
        ply:SetNWFloat("UndmDamageDealt", 1.0)
        ply:SetNWFloat("UndmStrengthXP", 1.0)
        ply:SetNWFloat("UndmStamina", effect.modifiers.after_stamina)
        if isOverdose then
            ply:SetNWFloat("UndmAttackSpeed", effect.modifiers.overdose_attack_speed)
        end
    end
end

function EFFECTS.ApplyItemEffects(ply, itemName)
    if not IsValid(ply) or not ply:IsPlayer() then return end
    if not aquascriptsConfig.UndergroundMarket.Effects[itemName] then return end

    local steamID = string.gsub(ply:SteamID(), ":", "_")
    ply.ActiveSubstances = ply.ActiveSubstances or {}

    -- Проверка на смешивание веществ
    local substanceCount = 0
    for k,_ in pairs(ply.ActiveSubstances) do
        if k ~= "BIOLINK" then substanceCount = substanceCount + 1 end
    end

    if substanceCount >= 1 and itemName ~= "BIOLINK" then
        ply:ChatPrint("ФАТАЛЬНАЯ ОШИБКА: Смешивание веществ привело к смерти!")
        timer.Simple(3, function() if IsValid(ply) then ply:Kill() end end)
        ply:ScreenFade(SCREENFADE.OUT, Color(255, 0, 0, 255), 3, 3)
        ply:SetHealth(1)
        return
    end

    local effect = aquascriptsConfig.UndergroundMarket.Effects[itemName]
    local uses = ply.ActiveSubstances[itemName] or 0
    ply.ActiveSubstances[itemName] = uses + 1
    local isOverdose = uses >= effect.overdose_limit

    -- Применение эффекта
    ply:ChatPrint(effect.messages.apply)
    EFFECTS.ApplyModifiers(ply, effect.modifiers)

    -- Обработка передозировки
    if isOverdose and effect.messages.overdose then
        ply:ChatPrint(effect.messages.overdose)
        if effect.modifiers.overdose_health then
            ply:SetHealth(math.max(1, ply:Health() + effect.modifiers.overdose_health))
        end
    end

    -- Таймер окончания эффекта
    timer.Create(itemName.."Effect_"..steamID, effect.duration, 1, function()
        if IsValid(ply) then
            ply:ChatPrint(effect.messages.aftereffect)
            EFFECTS.ResetModifiers(ply, itemName, isOverdose)
            ply.ActiveSubstances[itemName] = nil
           
            net.Start("UM_RemoveEffect")
                net.WriteString(itemName)
            net.Send(ply)
        end
    end)

    net.Start("UM_AddEffect")
        net.WriteString(itemName)
        net.WriteUInt(effect.duration, 32)
        net.WriteBool(isOverdose)
    net.Send(ply)
end

UndergroundMarketEffects = EFFECTS


cl_effects:
Развернуть Свернуть Копировать
local EFFECTS_PANEL = {
    effects = {},
    margin = 10,
    width = 300,
    itemHeight = 60,
    maxEffects = 5
}

function EFFECTS_PANEL:Init()
    self.panel = vgui.Create("DPanel")
    self.panel:SetSize(self.width, math.min(ScrH() * 0.7, self.itemHeight * self.maxEffects + 10))
    self.panel:SetPos(self.margin, ScrH() * 0.15)
    self.panel:SetVisible(false)
    self.panel.Paint = function(_, w, h)
        draw.RoundedBox(8, 0, 0, w, h, Color(17, 17, 17, 220))
    end
    
    self.scroll = vgui.Create("DScrollPanel", self.panel)
    self.scroll:Dock(FILL)
    
    local scrollBar = self.scroll:GetVBar()
    scrollBar:SetHideButtons(true)
    scrollBar.Paint = function(_, w, h) end
    scrollBar.btnGrip.Paint = function(_, w, h)
        draw.RoundedBox(4, w/2 - 2, 0, 4, h, Color(145, 145, 145, 200))
    end
end

net.Receive("UM_AddEffect", function()
    local name = net.ReadString()
    local duration = net.ReadUInt(32)
    local isOverdose = net.ReadBool()
    
    if not EFFECTS_PANEL.panel then EFFECTS_PANEL:Init() end
    
    -- Удаляем старый эффект с таким же именем
    for k,v in pairs(EFFECTS_PANEL.effects) do
        if v.name == name then
            table.remove(EFFECTS_PANEL.effects, k)
            break
        end
    end
    
    -- Добавляем новый эффект
    table.insert(EFFECTS_PANEL.effects, {
        name = name,
        startTime = RealTime(),
        endTime = RealTime() + duration,
        isOverdose = isOverdose
    })
    
    -- Обновляем высоту панели в зависимости от количества эффектов
    local effectCount = #EFFECTS_PANEL.effects
    local panelHeight = math.min(EFFECTS_PANEL.itemHeight * effectCount + 10,
                          EFFECTS_PANEL.itemHeight * EFFECTS_PANEL.maxEffects + 10)
    EFFECTS_PANEL.panel:SetSize(EFFECTS_PANEL.width, panelHeight)
    
    EFFECTS_PANEL.panel:SetVisible(true)
    EFFECTS_PANEL:UpdateEffects()
end)

net.Receive("UM_RemoveEffect", function()
    local name = net.ReadString()
    for k,v in pairs(EFFECTS_PANEL.effects) do
        if v.name == name then
            table.remove(EFFECTS_PANEL.effects, k)
            break
        end
    end
    EFFECTS_PANEL:UpdateEffects()
end)

net.Receive("UM_ClearEffects", function()
    EFFECTS_PANEL.effects = {}
    if EFFECTS_PANEL.panel then
        EFFECTS_PANEL.panel:SetVisible(false)
    end
end)

function EFFECTS_PANEL:UpdateEffects()
    if not IsValid(self.panel) or not IsValid(self.scroll) then return end
    
    self.scroll:Clear()
    
    for k, effect in pairs(self.effects) do
        local panel = vgui.Create("DPanel", self.scroll)
        panel:Dock(TOP)
        panel:SetHeight(self.itemHeight)
        panel:DockMargin(5, 5, 5, 0)
        panel.Paint = function(_, w, h)
            local progress = 1 - math.Clamp((effect.endTime - RealTime()) / (effect.endTime - effect.startTime), 0, 1)
            local col = effect.isOverdose and Color(255, 50, 50) or Color(50, 200, 50)
            
            draw.RoundedBox(6, 0, 0, w, h, Color(30, 30, 30, 200))
            draw.RoundedBox(6, 0, 0, w * progress, h, Color(col.r, col.g, col.b, 50))
            
            draw.SimpleText(effect.name, "MontserratSB16", 10, 15, color_white, TEXT_ALIGN_LEFT, TEXT_ALIGN_CENTER)
            
            local timeLeft = math.max(0, effect.endTime - RealTime())
            local minutes = math.floor(timeLeft / 60)
            local seconds = math.floor(timeLeft % 60)
            draw.SimpleText(string.format("%02d:%02d", minutes, seconds), "MontserratSB14", w - 10, 15, color_white, TEXT_ALIGN_RIGHT, TEXT_ALIGN_CENTER)
            
            if effect.isOverdose then
                draw.SimpleText("ПЕРЕДОЗ", "MontserratSB12", w/2, h - 15, Color(255, 50, 50), TEXT_ALIGN_CENTER, TEXT_ALIGN_CENTER)
            end
        end
    end
    
    if #self.effects == 0 and IsValid(self.panel) then
        self.panel:SetVisible(false)
    end
end

hook.Add("Think", "UpdateEffectsPanel", function()
    if EFFECTS_PANEL.panel and #EFFECTS_PANEL.effects > 0 then
        EFFECTS_PANEL:UpdateEffects()
    end
end)
 
Последнее редактирование:
Назад
Сверху Снизу