require 'lib.moonloader'

math.randomseed(os.time())

local events = require 'lib.samp.events'

-- Константы
local liftAmount = 0.01 -- Количество смещения по оси Y
local returnSpeed = 0.001 -- Скорость возврата

-- Переменные
local currentLift = 0 -- Текущий подъём камеры
local isLifting = false -- Флаг для состояния подъёма
local originalCameraY = 0 -- Исходное положение камеры по оси Y

function main()
    repeat wait(0) until isSampAvailable()
    wait(-1) -- Ждение завершения работы
end

function fix(angle)
    if angle > math.pi then
        angle = angle - (math.pi * 2)
    elseif angle < -math.pi then
        angle = angle + (math.pi * 2)
    end
    return angle
end

function events.onSendBulletSync() 
    -- Устанавливаем флаг подъёма камеры только при каждом выстреле
    if not isLifting then
        isLifting = true
    end
end

function onD3DPresent()
    local view = {
        fix(representIntAsFloat(readMemory(0xB6F258, 4, false))), 
        fix(representIntAsFloat(readMemory(0xB6F248, 4, false)))
    }

    -- Инициализируем исходное положение камеры (Y) при первом использовании
    if currentLift == 0 then
        originalCameraY = view[2] -- Сохраняем начальное значение Y
    end

    -- Плавный подъём
    if isLifting then
        currentLift = math.min(currentLift + returnSpeed, liftAmount)
        
        -- Устанавливаем новую позицию камеры при подъёме
        setCameraPositionUnfixed(view[1], originalCameraY + currentLift)

        -- Если достигнут целевой подъём, прекращаем подъём
        if currentLift >= liftAmount then
            isLifting = false
        end
    else
        -- Плавный возврат обратно
        if currentLift > 0 then
            currentLift = math.max(currentLift - returnSpeed, 0) -- Уменьшаем поднятие
        end
        
        -- Устанавливаем камеру на исходное положение (Y) с текущим смещением
        setCameraPositionUnfixed(originalCameraY + currentLift, view[1])
    end
end

тут чего-то перепутано с осями. 

в коде ниже есть правильное использование функций, так что почини код выше.

require 'lib.moonloader'

local imgui      = require('imgui')
local vkeys      = require('vkeys')
local ffi        = require('ffi')

local getbonePosition = ffi.cast("int (__thiscall*)(void*, float*, int, bool)", 0x5E4280)

local stun_anims = {'DAM_armL_frmBK', 'DAM_armL_frmFT', 'DAM_armL_frmLT', 'DAM_armR_frmBK', 'DAM_armR_frmFT', 'DAM_armR_frmRT', 'DAM_LegL_frmBK', 'DAM_LegL_frmFT', 'DAM_LegL_frmLT', 'DAM_LegR_frmBK', 'DAM_LegR_frmFT', 'DAM_LegR_frmRT', 'DAM_stomach_frmBK', 'DAM_stomach_frmFT', 'DAM_stomach_frmLT', 'DAM_stomach_frmRT'}

local mainWindowState = imgui.ImBool(false)
local smooth = imgui.ImFloat(0.0)
local radius = imgui.ImFloat(0.6)
local enable = imgui.ImBool(false)
local clistFilter = imgui.ImBool(false)
local visibleCheck = imgui.ImBool(false)
local checkStuned = imgui.ImBool(false)
local checkPause = imgui.ImBool(false)

function main()
    repeat wait(0) until isSampAvailable()
    lua_thread.create(smooth_aimbot)
    while true do
        wait(0)
        if wasKeyPressed(vkeys.VK_INSERT) then
            mainWindowState.v = not mainWindowState.v
        end
        imgui.Process = mainWindowState.v
    end
end

function imgui.OnDrawFrame()
    local posX, posY = getScreenResolution()
    if mainWindowState.v then
        imgui.SetNextWindowPos(imgui.ImVec2(posX / 2, posY / 2), imgui.Cond.FirstUseEver, imgui.ImVec2(0.5, 0.5))
        imgui.SetNextWindowSize(imgui.ImVec2(350, 200), imgui.Cond.FirstUseEver)
        imgui.Begin('Smooth aimbot', mainWindowState)

        imgui.SliderFloat('Radius', radius, 0.0, 100.0, '%.1f')
        imgui.SliderFloat('Smooth', smooth, 0.0, 50.0, '%.1f')

        imgui.Checkbox('Enable', enable)
        imgui.Checkbox('VisibleCheck', visibleCheck)
        imgui.Checkbox('CheckStuned', checkStuned)
        imgui.Checkbox('ClistFilter', clistFilter)
        imgui.Checkbox('CheckPause', checkPause)

        imgui.End()
    end
end

function fix(angle)
    if angle > math.pi then
        angle = angle - (math.pi * 2)
    elseif angle < -math.pi then
        angle = angle + (math.pi * 2)
    end
    return angle
end

function GetNearestPed(fov)
    local maxDistance = 35
    local nearestPED = -1
    for i = 0, sampGetMaxPlayerId(true) do
        if sampIsPlayerConnected(i) then
            local find, handle = sampGetCharHandleBySampPlayerId(i)
            if find then
                if isCharOnScreen(handle) then
                    if not isCharDead(handle) then
                        local _, currentID = sampGetPlayerIdByCharHandle(PLAYER_PED)
                        local enPos = {GetBodyPartCoordinates(GetNearestBone(handle), handle)}
                        local myPos = {getActiveCameraCoordinates()}
                        local vector = {myPos[1] - enPos[1], myPos[2] - enPos[2], myPos[3] - enPos[3]}
                        if isWidescreenOnInOptions() then coefficentZ = 0.0778 else coefficentZ = 0.103 end
                        local angle = {(math.atan2(vector[2], vector[1]) + 0.04253), (math.atan2((math.sqrt((math.pow(vector[1], 2) + math.pow(vector[2], 2)))), vector[3]) - math.pi / 2 - coefficentZ)}
                        local view = {fix(representIntAsFloat(readMemory(0xB6F258, 4, false))), fix(representIntAsFloat(readMemory(0xB6F248, 4, false)))}
                        local distance = math.sqrt((math.pow(angle[1] - view[1], 2) + math.pow(angle[2] - view[2], 2))) * 57.2957795131
                        if distance > fov then check = true else check = false end
                        if not check then
                            local myPos = {getCharCoordinates(PLAYER_PED)}
                            local distance = math.sqrt((math.pow((enPos[1] - myPos[1]), 2) + math.pow((enPos[2] - myPos[2]), 2) + math.pow((enPos[3] - myPos[3]), 2)))
                            if (distance < maxDistance) then
                                nearestPED = handle
                                maxDistance = distance
                            end
                        end
                    end
                end
            end
        end
    end
    return nearestPED
end

function GetNearestBone(handle)
    local maxDist = 20000    
    local nearestBone = -1
    bone = {42, 52, 23, 33, 3, 22, 32, 8}
    for n = 1, 8 do
        local crosshairPos = {convertGameScreenCoordsToWindowScreenCoords(339.1, 179.1)}
        local bonePos = {GetBodyPartCoordinates(bone[n], handle)}
        local enPos = {convert3DCoordsToScreen(bonePos[1], bonePos[2], bonePos[3])}
        local distance = math.sqrt((math.pow((enPos[1] - crosshairPos[1]), 2) + math.pow((enPos[2] - crosshairPos[2]), 2)))
        if (distance < maxDist) then
            nearestBone = bone[n]
            maxDist = distance
        end 
    end
    return nearestBone
end

function GetBodyPartCoordinates(id, handle)
    if doesCharExist(handle) then
        local pedptr = getCharPointer(handle)
        local vec = ffi.new("float[3]")
        getbonePosition(ffi.cast("void*", pedptr), vec, id, true)
        return vec[0], vec[1], vec[2]
    end
end

function CheckStuned()
	for k, v in pairs(stun_anims) do
		if isCharPlayingAnim(PLAYER_PED, v) then
			return false
		end
	end
	return true
end

function smooth_aimbot()
    if enable.v and isKeyDown(vkeys.VK_RBUTTON) then
        local handle = GetNearestPed(radius.v)
        if handle ~= -1 then
            local _, myID = sampGetPlayerIdByCharHandle(PLAYER_PED)
            local result, playerID = sampGetPlayerIdByCharHandle(handle)
            if result then
                if (checkStuned.v and not CheckStuned()) then return false end
                if (clistFilter.v and sampGetPlayerColor(myID) == sampGetPlayerColor(playerID)) then return false end
                if (checkPause.v and sampIsPlayerPaused(playerID)) then return false end
                local myPos = {getActiveCameraCoordinates()}
                local enPos = {GetBodyPartCoordinates(GetNearestBone(handle), handle)}
                if not visibleCheck.v or (visibleCheck.v and isLineOfSightClear(myPos[1], myPos[2], myPos[3], enPos[1], enPos[2], enPos[3], true, true, false, true, true)) then
                    local vector = {myPos[1] - enPos[1], myPos[2] - enPos[2], myPos[3] - enPos[3]}
                    if isWidescreenOnInOptions() then coefficentZ = 0.0778 else coefficentZ = 0.103 end
                    local angle = {(math.atan2(vector[2], vector[1]) + 0.04253), (math.atan2((math.sqrt((math.pow(vector[1], 2) + math.pow(vector[2], 2)))), vector[3]) - math.pi / 2 - coefficentZ)}
                    local view = {fix(representIntAsFloat(readMemory(0xB6F258, 4, false))), fix(representIntAsFloat(readMemory(0xB6F248, 4, false)))}
                    local difference = {angle[1] - view[1], angle[2] - view[2]}
                    local smooth = {difference[1] / smooth.v, difference[2] / smooth.v}
                    setCameraPositionUnfixed((view[2] + smooth[2]), (view[1] + smooth[1]))
                end
            end
        end
    end
    return false
end