[RELEASE][FREE] RY-RENT | Vehicle Rental with UI, Timer and more

Hello everyone,
Today I present a very simple script but a lot of people like it!
A clean and beautiful vehicle rental with NUI. With the ability to customize any image of any vehicle.

preview

Config
RY = {}

RY.Options = {
    FrameWork = 'esx', -- esx or qb

    enableRentTimer = true, 
    rentTime = 120,

    priceMaxPerformance = 1000,
    refundMoneyWhenDelivered = true,
    deleteVehicleWhenFinished = true, -- delete vehicle when rent time is finished and not delivered? Default true
    deleteTime = 25000, -- time in MS that vehicle will be deleted if 'deleteVehicleWhenFinished' is active and after rent time is finished. 
    -- Default 25000MS | 25Seconds. 
    
    oxTarget = {
        enable = true, -- if false it will enable markers/3dtext
        icons = {
            menu = 'fa-solid fa-cube',
            returnMenu = 'fa-solid fa-cube'
        } ,
        labels = {
            menu = 'Vehicle Rental',
            returnMenu = 'Return Vehicle'
        }
    }
}

RY.Messages = {
    returnSuccess = "Successfully returned the vehicle, thank you!",
    returnError  = "You need to be in the vehicle you rented.",
    noMoney = "You don't have enought money to rent the vehicle.",
    refund = "Received refund of",
    rentFinished = "Your rental time is up, thank you.",
    alreadyRented = "You already rented a vehicle."
}

RY.Locations = {
    ['rent1'] = {
        menuCoords = vector3(-1028.55, -2740.08, 20.16),
        returnVehicleCoords = vector3(-1032.65,-2732.00,20.16),
        vehicleSpawnCoords = {x =-1024.80, y =-2734.81, z=20.09, h=243.77},

        -- Markers
        markersConfig = {
            markerMenu = {
                useKey = 38, -- E
                markerType = 2,
                markerSize  = {x = 0.3, y = 0.3, z = 0.3}, 
                markerColor = {r = 255, g = 255, b = 255},
                markerText = '[ ~g~E~w~ ] Rent Vehicle'
            },
            markerReturnMenu = {
                useKey = 47, -- G
                markerType = 2,
                markerSize  = {x = 0.3, y = 0.3, z = 0.3}, 
                markerColor = {r = 255, g = 0, b = 0},
                markerText = '[ ~g~G~w~ ] Return Vehicle'
            }
        },

        -- Blips
        blipsConfig = {
            blipMenu = {
                blipName = 'Rent Vehicle',
                blipSprite = 523,
                blipScale = 0.8,
                blipColor = 2
            },
            blipReturnMenu = {
                blipName = 'Return rented Vehicle',
                blipSprite = 523,
                blipScale = 0.8,
                blipColor = 4
            }
        },

        -- Vehicles
        vehiclesConfig = {
            [1] = {
                vehicleModel = 'zentorno',
                vehicleLabel = 'Mercedes AMG',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'car',
                vehicleImageName = 'amg.png'
                -- IMAGE RESOLUTION --
                -- 310x250 Pixels --
                -- IMAGE RESOLUTION --
            },
            [2] = {
                vehicleModel = 'bati',
                vehicleLabel = 'BMW',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 999,
                vehicleType = 'car',
                vehicleImageName = 'bmw.png'
            },
            [3] = {
                vehicleModel = 'feltzer2',
                vehicleLabel = 'Nissan GTR',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'car',
                vehicleImageName = 'gtr.png'
            },
            [4] = {
                vehicleModel = 'cruiser',
                vehicleLabel = 'Bicycle',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 100,
                vehicleType = 'bicycle',
                vehicleImageName = 'bike.png'
            },
            --[[[5] = {
                vehicleModel = 'cruiser',
                vehicleLabel = 'Bicycle',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 100,
                vehicleType = 'bicycle',
                vehicleImageName = 'bike.png'
            },]]--
        }
    },
    -- MORE EXAMPLES --
    --[['rent2'] = {
        menuCoords = vector3(-1028.55, -2740.08, 20.16),
        returnVehicleCoords = vector3(-1032.65,-2732.00,20.16),
        vehicleSpawnCoords = {x =-1024.80, y =-2734.81, z=20.09, h=243.77},

        markersConfig = {
            markerMenu = {
                useKey = 38, -- E
                markerType = 2,
                markerSize  = {x = 0.3, y = 0.3, z = 0.3}, 
                markerColor = {r = 255, g = 255, b = 255},
                markerText = '[ ~g~E~w~ ] Rent Vehicle'
            },
            markerReturnMenu = {
                useKey = 47, -- E
                markerType = 2,
                markerSize  = {x = 0.3, y = 0.3, z = 0.3}, 
                markerColor = {r = 255, g = 0, b = 0},
                markerText = '[ ~g~E~w~ ] Return Vehicle'
            }
        },

        blipsConfig = {
            blipMenu = {
                blipName = 'Rent Vehicle',
                blipSprite = 523,
                blipScale = 0.8,
                blipColor = 2
            },
            blipReturnMenu = {
                blipName = 'Return rented Vehicle',
                blipSprite = 523,
                blipScale = 0.8,
                blipColor = 4
            }
        },

        vehiclesConfig = {
            [1] = {
                vehicleModel = 'zentorno',
                vehicleLabel = 'Mercedes AMG',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'car',
                vehicleImageName = 'amg.png'
                -- IMAGE RESOLUTION --
                -- 310x250 Pixels --
                -- IMAGE RESOLUTION --
            },
            [2] = {
                vehicleModel = 't20',
                vehicleLabel = 'BMW',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'car',
                vehicleImageName = 'bmw.png'
            },
            [3] = {
                vehicleModel = 'zentorno',
                vehicleLabel = 'Nissan GTR',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'car',
                vehicleImageName = 'gtr.png'
            },
            [4] = {
                vehicleModel = 'cruiser',
                vehicleLabel = 'Bicycle',
                vehicleDescription = 'description example',
                vehicleRentalPrice = 1000,
                vehicleType = 'bicycle',
                vehicleImageName = 'amg.png'
            },
        }
    }, ]]--
}

Updates

UPDATE - 22/11/2023

  • Code completely redone and some optimizations.
  • Added support for qbcore.
  • Added support for ox_target.
  • Added support for custom notification.
  • Some changes to the UI.

Other updates will be on the way, the most important thing now was to have a clean code where I can add more things easily.

Download - Github

Code is accessible Yes
Subscription-based No
Lines (approximately) 500
Requirements ESX or QB
Support Yes
15 Likes

Let me tell you ! Well done on the UI. Its smooth and easy adjustable. Is there a way I can change the Currency on the UI? I cant seem to find where I can change it. This is what I have done on my edit


4 Likes

Hello, thank you for your feedback! Yes you can adjust the currency in html/js/functions.js line 16

 <div class="footer-price">${vehicle.price}$</div>

Many thanks! Maybe you could also add a Return spot?

1 Like

Sure! in a few hours I will release some updates including that

Are you serious. My duuuuuuude… You are quick-fast hey :laughing:

1 Like

NEW UPDATE!

  • Added return spot
    – A blip will appear on the map for you to return the vehicle.
    – You can only return if the vehicle is really what you rented.
    – The blip will disappear if you don’t have a rented vehicle.
    – All of this fully configurable in the config for each location.

  • Added Currency Option in html/js/config.js:9 so you can change the currency more easily.

NEXT UPDATE’S

  • Timer to return the vehicle.
  • More options in NUI.

Download now in Github

Finally!!!

Thank you so so much!!! I hope to see more of your work!!

You’re welcome! Suggestions are open and if you find any bugs try to quickly let me know :smile:

That’s my boy ! <3

1 Like

Good job!

1 Like

nice bro but
not working with me i did change the cars but wont spawn and theres no error

Nice work, we all needed a more beautiful and new car rent, yours is perfect, if it weren’t for the code optimization, which I thought of.

Client.lua
ESX = exports.es_extended:getSharedObject()
InMenu = false
sleep = true

Options = {
    vehicle = {
        hash = 0,
    },
    last_location = '',
    have_rented = false,
    blips = {}
}

for k, v in pairs(Config.Locations) do
    rent = AddBlipForCoord(v.coords.x, v.coords.y, v.coords.z)

    SetBlipSprite (rent, v.blips.spawn.sprite)
    SetBlipDisplay(rent, 4)
    SetBlipScale  (rent, 0.65)
    SetBlipAsShortRange(rent, true)
    SetBlipColour(rent, v.blips.spawn.color)

    BeginTextCommandSetBlipName("STRING")
    AddTextComponentSubstringPlayerName(v.blips.spawn.name)
    EndTextCommandSetBlipName(rent)
end


Citizen.CreateThread(function()
    while true do 
        Citizen.Wait(5)
        sleep = true
        local playerPed = PlayerPedId()
        local coords = GetEntityCoords(playerPed)
        for k,v in pairs(Config.Locations) do
            if not InMenu then
                local distance = #(coords - v.coords)
                local return_distance = #(coords - v.return_coords) 

                if distance < 1 then
                    sleep = false
                    DrawText3D(v.coords.x, v.coords.y, v.coords.z + 0.25, v.markers.spawn.text)
                    if IsControlJustReleased(0, v.markers.spawn.key) then
                        Options.last_location = k
                        open_ui(k)
                    end
                end

                if distance <= 15 then
                    sleep = false
                    DrawMarker(v.markers.spawn.type, v.coords.x, v.coords.y, v.coords.z, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, v.markers.spawn.size.x, v.markers.spawn.size.y, v.markers.spawn.size.z, v.markers.spawn.color.r, v.markers.spawn.color.g, v.markers.spawn.color.b, 50, false, true, 2, false, nil, nil, false)
                end

                if Options.have_rented then
                    if return_distance < 3 then
                        sleep = false
                        DrawText3D(v.return_coords.x, v.return_coords.y, v.return_coords.z + 0.25, v.markers.return_spot.text)
                        if IsControlJustReleased(0, v.markers.return_spot.key) then
                            return_vehicle()
                        end
                    end
                    sleep = false
                    if return_distance <= 15 then
                        DrawMarker(v.markers.return_spot.type, v.return_coords.x, v.return_coords.y, v.return_coords.z, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, v.markers.return_spot.size.x, v.markers.return_spot.size.y, v.markers.return_spot.size.z, v.markers.return_spot.color.r, v.markers.return_spot.color.g, v.markers.return_spot.color.b, 50, false, true, 2, false, nil, nil, false)
                    end
                end
            end
        end
        if sleep then
            Citizen.Wait(150)
        end
    end
end)

In this way the code is always 0.00 in idle and take ms only when the script is really called.
I have removed also a lot of useless stuff, if you want you can take this code and improve the script performace (all is already tested, blip, marker etc etc)

Resmon Preview

Enjoy!

1 Like

Hello NaShMiJo,
Can you show me the config?

Thank you so much for the feedback, and I will definitely use this code!

1 Like

This is working so amazing for my server. Thank you! One question, can there be no fix for the html to extend the amount of vehicles, as I want to use this as a “Car Rental” option at the Airport. Maybe that could be more of a variety, don’t you think? If that was possible
image

1 Like

Sure! In the next update we have that :smile:

UPDATE - 30/07/2022

  • Now you can add more then 4 vehicles. Video

Download - Github

1 Like

Since it seems like you ignore or dont understand the PRs i made:

With this in the fxmanifest:
image

You dont need those:
image
image

And for the Server.lua

replace this

RegisterServerEvent('ry_rent:pay')
AddEventHandler('ry_rent:pay', function(amount)
	local _source = source
  local xPlayer = ESX.GetPlayerFromId(_source)
	
  xPlayer.removeMoney(tonumber(amount))
  TriggerClientEvent('esx:showNotification', source, 'You paid ~g~' .. amount .. '~w~$ to rent the vehicle.')
end)

with this:

RegisterServerEvent('ry_rent:pay')
AddEventHandler('ry_rent:pay', function(amount)
    local _source = source
    local xPlayer = ESX.GetPlayerFromId(_source)
    local Money = xPlayer.getAccount('money').money

    if Money >= amount then 
        xPlayer.removeMoney(tonumber(amount))
        TriggerClientEvent('esx:showNotification', source, 'You paid ~g~' .. amount .. '~w~$ to rent the vehicle.')
    else
        TriggerClientEvent('esx:showNotification', source, 'You dont have enough Money to rent a vehicle.')
    end
end)

then you cant randomly spam cars and get your self in negative Money.

And you can add your Config.lua from

server_script and client_script to shared_script too.

Hello ofcShiro,
I didn’t ignore it, I just didn’t see ahah
But thanks a lot for the suggestion, I will definitely implement it :smile: