Skrypty systemu paliwa FiveM: Realistyczne tankowanie pojazdów
Dodaj działający system paliwa do swojego serwera FiveM. Stacje benzynowe, kanistry, pojazdy elektryczne i najlepsze skrypty paliwa dla konfiguracji QBCore, ESX oraz standalone.
Agency Scripts
Założyciel i główny deweloper w Agency Scripts
Mechanika zużycia paliwa
Realistyczny system paliwa dodaje kluczową warstwę immersji i tworzy naturalny pochłaniacz pieniędzy, pomagający zrównoważyć ekonomię twojego serwera. Główna mechanika polega na śledzeniu poziomu paliwa każdego pojazdu jako wartości zmiennoprzecinkowej od 0 do 100, zmniejszając go na podstawie pracy silnika i stylu jazdy. Zapisuj poziom paliwa za pomocą entity state bags z Entity(vehicle).state.fuel dzięki czemu wartość utrzymuje się u wszystkich klientów i przetrwa zmiany network ownership. Obliczaj zużycie na tick na podstawie aktualnego RPM pojazdu uzyskanego przez GetVehicleCurrentRpm, pozycja przepustnicy z GetControlNormal, oraz mnożnik zużycia właściwy dla klasy pojazdu. Samochody sportowe i supersamochody powinny zużywać paliwo znacznie szybciej niż pojazdy ekonomiczne, podczas gdy ciężarówki i SUV-y plasują się gdzieś pośrodku. Zastosuj dodatkowe modyfikatory zużycia dla agresywnej jazdy, takiej jak gwałtowne przyspieszanie, utrzymywanie wysokich prędkości i hamowanie silnikiem. Gdy paliwo spadnie do zera, stopniowo redukuj maksymalną prędkość pojazdu za pomocą SetVehicleMaxSpeed aby symulować dławienie się silnika zamiast natychmiastowego gaszenia go, dając graczowi kilka cennych sekund na bezpieczne zjechanie na pobocze.
-- Client-side fuel consumption thread
local fuelConsumptionRate = 0.0
CreateThread(function()
while true do
local ped = PlayerPedId()
local vehicle = GetVehiclePedIsIn(ped, false)
if vehicle ~= 0 and GetPedInVehicleSeat(vehicle, -1) == ped then
local engineOn = GetIsVehicleEngineRunning(vehicle)
if engineOn then
local rpm = GetVehicleCurrentRpm(vehicle)
local speed = GetEntitySpeed(vehicle) * 3.6 -- km/h
local classMultiplier = Config.ClassConsumption[GetVehicleClass(vehicle)] or 1.0
-- Base consumption + RPM factor + speed factor
fuelConsumptionRate = (Config.BaseConsumption
+ (rpm * Config.RpmFactor)
+ (speed * Config.SpeedFactor)
) * classMultiplier
local currentFuel = Entity(vehicle).state.fuel or 100.0
local newFuel = math.max(0.0, currentFuel - fuelConsumptionRate)
Entity(vehicle).state:set('fuel', newFuel, true)
-- Engine stall when empty
if newFuel <= 0 then
SetVehicleUndriveable(vehicle, true)
SetVehicleEngineOn(vehicle, false, true, true)
elseif newFuel <= 5.0 then
-- Sputtering effect
SetVehicleMaxSpeed(vehicle, 30.0 * (newFuel / 5.0))
end
end
end
Wait(1000) -- Update every second
end
end)
UI stacji paliw i tankowanie
Obsługa stacji benzynowej powinna być dopracowana i intuicyjna dzięki dobrze zaprojektowanemu interfejsowi NUI. Gdy gracz zaparkuje w pobliżu dystrybutora paliwa w określonym promieniu, wyświetl monit o interakcję. Po wejściu w interakcję otwórz UI tankowania, które pokazuje aktualny poziom paliwa jako wskaźnik lub pasek postępu, pojemność baku pojazdu, cenę za litr na podstawie aktualnego typu paliwa oraz opcje zatankowania do pełna lub za określoną kwotę. Animacja tankowania powinna być odtwarzana na postaci gracza, która stoi obok pojazdu, trzymając prop pistoletu paliwowego przy użyciu TaskPlayAnim, oraz sam dystrybutor paliwa, jeśli używasz niestandardowej konfiguracji propów. Paliwo powinno napełniać się stopniowo w czasie rzeczywistym zamiast natychmiastowego uzupełnienia do pełna, co tworzy krótkie oczekiwanie dodające realizmu i uniemożliwia graczom błyskawiczne tankowanie podczas pościgów. Pokazuj bieżący koszt aktualizowany na żywo w trakcie tankowania i pobieraj opłatę dopiero, gdy gracz przestanie tankować lub zbiornik będzie pełny. Zapewnij obsługę wielu rodzajów paliwa na stacjach premium: zwykłą bezołowiową w standardowej cenie, paliwo premium dające niewielki wzrost osiągów i kosztujące więcej oraz diesel dla ciężarówek i pojazdów przemysłowych z osobnymi dystrybutorami.
Kanister i tankowanie awaryjne
Brak paliwa na autostradzie to realistyczny scenariusz, z którym Twój system powinien radzić sobie płynnie, nie zmuszając gracza do porzucenia pojazdu. Wprowadź kanister jako przedmiot, który można kupić na stacjach benzynowych lub w marketach budowlanych i napełnić paliwem przy dowolnym dystrybutorze. Kanister powinien działać jako używalny przedmiot w ekwipunku z metadanymi śledzącymi aktualny poziom napełnienia, mieszcząc zazwyczaj 10-20 litrów. Gdy gracz użyje kanistra w pobliżu pustego pojazdu, uruchom animację nalewania i przelej paliwo z kanistra do baku. Kanister powinien mieć wagę w systemie ekwipunku proporcjonalną do ilości zawartego paliwa, dzięki czemu pełny kanister jest cięższy niż pusty. Dodaj mechanikę umożliwiającą wezwanie pomocy drogowej przez telefon w grze, wysyłającą lawetę prowadzoną przez NPC lub gracza ze świadczeniem usługi dowozu paliwa za opłatą. Dla większej immersji gracze powinni mieć możliwość spuszczania paliwa z innych pojazdów za pomocą wężyka, przelewając paliwo między pojazdami kosztem czasu i ryzykiem przyłapania na gorącym uczynku.
-- Jerry can usage handler
RegisterNetEvent('fuel:useJerryCan')
AddEventHandler('fuel:useJerryCan', function(slot)
local src = source
local ped = GetPlayerPed(src)
local coords = GetEntityCoords(ped)
-- Find nearest vehicle
local nearbyVehicle = GetClosestVehicle(coords, 3.0)
if not nearbyVehicle or nearbyVehicle == 0 then
return notify(src, 'No vehicle nearby.', 'error')
end
-- Get jerry can metadata
local canData = exports.ox_inventory:GetSlot(src, slot)
if not canData or not canData.metadata or not canData.metadata.fuel then
return notify(src, 'Jerry can is empty.', 'error')
end
local canFuel = canData.metadata.fuel
local vehicleFuel = Entity(nearbyVehicle).state.fuel or 0.0
local maxTransfer = math.min(canFuel, 100.0 - vehicleFuel)
if maxTransfer <= 0 then
return notify(src, 'Vehicle tank is already full.', 'error')
end
-- Transfer fuel
Entity(nearbyVehicle).state:set('fuel', vehicleFuel + maxTransfer, true)
-- Update jerry can metadata
local remainingFuel = canFuel - maxTransfer
if remainingFuel <= 0 then
exports.ox_inventory:SetMetadata(src, slot, { fuel = 0, label = 'Empty Jerry Can' })
else
exports.ox_inventory:SetMetadata(src, slot, { fuel = remainingFuel })
end
notify(src, ('Transferred %.1f liters to the vehicle.'):format(maxTransfer), 'success')
end)
Obsługa pojazdów elektrycznych
Nowoczesne serwery roleplay coraz częściej wprowadzają pojazdy elektryczne, które wymagają równoległej infrastruktury ładowania. Pojazdy elektryczne nie powinny zużywać benzyny, lecz rozładowywać akumulator, co działa identycznie jak wskaźnik paliwa, ale w innym tempie. Zużycie energii przez pojazdy elektryczne powinno być niższe w przeliczeniu na kilometr niż w autach spalinowych, co odzwierciedla ich rzeczywistą przewagę wydajności, jednak ładowanie powinno trwać dłużej niż tankowanie, tworząc inny rytm rozgrywki. Rozmieść stacje ładowania w wybranych miejscach na mapie, niekoniecznie na tradycyjnych stacjach benzynowych, aby stworzyć odrębne trasy dla właścicieli aut elektrycznych. Zaimplementuj UI ładowania, które pokazuje aktualny procent naładowania, szacowany czas do pełnego naładowania oraz koszt za kilowatogodzinę. Dodaj opcję szybkiego ładowania na stacjach premium, która napełnia baterię w dwa razy krótszym czasie przy podwójnej cenie za jednostkę. W konfiguracji pojazdów sklasyfikuj auta elektryczne według ich hasha modelu i zapisz typ pojazdu w configu, aby system automatycznie wykrywał, czy pojazd potrzebuje benzyny, czy prądu. Obsługuj pojazdy hybrydowe, które mogą korzystać z obu rodzajów napędu, przełączając się na tryb elektryczny przy niskich prędkościach i benzynowy przy prędkościach autostradowych, zużywając oba zasoby w mniejszym stopniu.
Ekonomia dynamicznych cen paliwa
Dynamiczny system cen ożywia gospodarkę paliwową i stawia graczy przed ciekawymi decyzjami ekonomicznymi. Oprzyj ceny paliw na konfigurowalnej stawce, która waha się w oparciu o mechanikę popytu i podaży. Śledź całkowitą ilość paliwa kupowanego na wszystkich stacjach w określonych oknach czasowych: gdy zużycie jest wysokie, ceny stopniowo rosną. Gdy zużycie spada, ceny maleją, aby przyciągnąć więcej klientów. Wdróż zróżnicowanie cen według stacji, gdzie oddalone stacje w Blaine County pobierają wyższe opłaty ze względu na koszty transportu, podczas gdy stacje miejskie konkurują niższymi marżami. Pozwól graczom na posiadanie stacji benzynowych, gdzie właściciel może ustalać własne ceny paliw w minimalnym i maksymalnym zakresie określonym w konfiguracji serwera, co tworzy prawdziwą konkurencję cenową między operatorami stacji. Właściciel stacji kupuje paliwo hurtowo od NPC dostawcy po cenie hurtowej i narzuca marżę do ceny detalicznej, przy czym marża stanowi jego dochód. Dodaj sezonowe lub okolicznościowe skoki cen, w których koszty paliwa gwałtownie rosną podczas wydarzeń serwerowych z dużym ruchem pojazdów, takich jak wyścigi lub napady, co wywołuje fale ekonomiczne wpływające na wszystkich graczy i zachęca do oszczędzania lub strategicznego tankowania przed przewidywanymi podwyżkami cen.
Stacja paliw jako biznes
Przekształcenie stacji paliw w biznesy prowadzone przez graczy dodaje pełną pętlę ekonomiczną do systemu paliw. Właściciel stacji zarządza zapasami, zamawiając dostawy paliwa od hurtowego dostawcy, dba o sprzęt, płacąc za naprawy i ulepszenia dystrybutorów, oraz zarządza personelem, zatrudniając innych graczy jako pracowników stacji zarabiających stawkę godzinową. Wdróż panel zarządzania stacją dostępny wyłącznie dla właściciela, który wyświetla dzienny wolumen sprzedaży, przychody, marże zysku, aktualny stan paliwa w zbiornikach podziemnych oraz ewidencję obecności pracowników. Stacja powinna posiadać fizyczny zbiornik podziemny o ograniczonej pojemności, który opróżnia się w miarę tankowania przez klientów, co wymaga od właściciela planowania przyjazdów cystern, które wymagają czasu na dojazd i kosztują z góry. Dodaj komponent sklepu wewnątrz stacji, w którym właściciel może wystawiać artykuły codziennego użytku, takie jak przekąski, napoje i podstawowe zaopatrzenie, które klienci mogą kupić razem z paliwem, tworząc dodatkowe źródło przychodów. Zezwól na ulepszenia samej stacji, takie jak dodawanie kolejnych stanowisk dystrybutorów do jednoczesnej obsługi większej liczby klientów, instalacja myjni samochodowej za dodatkową opłatą lub dodanie stacji ładowania pojazdów elektrycznych, aby wejść na rynek aut elektrycznych. Śledź reputację stacji na podstawie uczciwości cen, dostępności paliwa i zadowolenia klientów, aby stacje z lepszą reputacją były wyróżnione na mapie i przyciągały większy ruch.
Integracja HUD i wskaźnik paliwa
Wskaźnik paliwa to stały element HUD, który gracze widzą nieustannie, dlatego musi być przejrzysty wizualnie i nieinwazyjny, a jednocześnie przekazywać najważniejsze informacje na pierwszy rzut oka. Zaprojektuj minimalistyczny wskaźnik paliwa umieszczony w pobliżu prędkościomierza lub w rogu ekranu, pokazujący aktualny poziom paliwa w formie półkolistego wskaźnika, pionowego paska lub prostego odczytu procentowego. Zastosuj oznaczenie kolorystyczne, w którym zielony wskazuje optymalny poziom paliwa powyżej 50%, żółty sygnalizuje umiarkowany poziom między 20 a 50%, a czerwony ostrzega przed krytycznie niskim poziomem poniżej 20%. Gdy poziom paliwa spadnie poniżej 15%, uruchamiaj okresowy dźwięk ostrzegawczy i spraw, by wskaźnik migał, aby gracz przypadkowo nie opróżnił baku. Wyświetlaj szacowany pozostały dystans na podstawie aktualnego zużycia, obliczany przez podzielenie pozostałego paliwa przez średnie zużycie na kilometr z ostatnich kilku minut jazdy. Ukrywaj wskaźnik paliwa całkowicie, gdy gracz porusza się pieszo, aby ograniczyć natłok elementów na ekranie, i płynnie go wyświetlaj po wejściu do pojazdu. Dla graczy preferujących minimalistyczny HUD udostępnij opcję całkowitego ukrycia wskaźnika paliwa i pokazywania go jedynie jako tymczasowe powiadomienie, gdy poziom paliwa spadnie poniżej konfigurowalnego progu. Zintegruj wskaźnik z innymi elementami HUD pojazdu, takimi jak prędkościomierz i stan silnika, aby stworzyć spójną deskę rozdzielczą pojazdu.
Wydajność i synchronizacja
System paliwa działa nieprzerwanie na każdym kliencie prowadzącym pojazd, dlatego optymalizacja wydajności jest kluczowa. Zastosuj interwał aktualizacji zużycia wynoszący 1000 milisekund zamiast wykonywania kodu w każdej klatce, ponieważ zmiany poziomu paliwa są na tyle stopniowe, że aktualizacje co sekundę są wizualnie nie do odróżnienia od aktualizacji klatka po klatce, zużywając przy tym około 60 razy mniej mocy obliczeniowej. Przechowuj wartości paliwa w state bags jednostek zamiast w niestandardowych eventach sieciowych, ponieważ state bags są zoptymalizowane pod kątem często zmieniających się wartości i synchronizują się tylko wtedy, gdy wartość faktycznie ulega zmianie. Przy zapisywaniu paliwa do bazy danych w celu zachowania stanu po restartach serwera grupuj wszystkie aktualizacje paliwa pojazdów w jedno zapytanie wykonywane co 60 sekund, zamiast zapisywać każde z osobna przy każdej zmianie paliwa. Używaj network ID pojazdu jako klucza do śledzenia paliwa i usuwaj zapisane dane paliwa dla pojazdów, które już nie istnieją, aby zapobiec rozrostowi bazy danych. Obsłuż przypadek brzegowy, w którym pojazd zmienia właściciela sieciowego podczas tankowania, sprawdzając własność przed zastosowaniem zmian paliwa i stosując walidację po stronie serwera dla wszystkich transakcji płatniczych. W przypadku stacji z wieloma klientami jednocześnie wdróż system kolejkowy, który zapobiega korzystaniu z tego samego dystrybutora przez dwóch graczy naraz, pokazując jednocześnie wizualny wskaźnik informujący, że dystrybutor jest zajęty.