diff --git a/resources/[inventory]/nordi_bbq/config.lua b/resources/[inventory]/nordi_bbq/config.lua index fa5719d4d..51ab60de7 100644 --- a/resources/[inventory]/nordi_bbq/config.lua +++ b/resources/[inventory]/nordi_bbq/config.lua @@ -6,7 +6,10 @@ Config.GrillProps = { "prop_bbq_2", "prop_bbq_3", "prop_bbq_4", - "prop_bbq_5" + "prop_bbq_5", + "smallbbqtrailer", + "bigbbqtrailer" + } -- Zeit zum Grillen (in ms) @@ -22,7 +25,18 @@ Config.GrillRecipes = { requires = { {item = "rawmeat", amount = 1} } + }, + { + label = "Fisch", + description = "Ein perfekt gegrilltes Fischfilet", + item = "grilled_fish", + icon = "fas fa-drumstick-bite", + requires = { + {item = "fish_fillet", amount = 1} + } } + + -- Hier kannst du weitere Rezepte hinzufügen } diff --git a/resources/[inventory]/nordi_vending/client/main.lua b/resources/[inventory]/nordi_vending/client/main.lua deleted file mode 100644 index eba6357a9..000000000 --- a/resources/[inventory]/nordi_vending/client/main.lua +++ /dev/null @@ -1,238 +0,0 @@ -local QBCore = exports['qb-core']:GetCoreObject() -local inZone = false -local currentMachine = nil -local PlayerData = {} - -local function SetupTarget() - if not Config.UseQBTarget then return end - - -- Default 24/7 machines - for modelHash, machineData in pairs(Config.DefaultMachines.Models) do - exports['qb-target']:AddTargetModel(modelHash, { - options = { - { - type = 'client', - event = 'vendingmachines:client:openMenu', - icon = 'fas fa-cash-register', - label = 'Use Vending Machine', - machineModel = modelHash, - isPlayerOwned = false - }, - Config.EnableRobbery and { - type = 'client', - event = 'vendingmachines:client:startRobbery', - icon = 'fas fa-lock', - label = 'Rob Machine', - item = Config.RobberyItem, - machineModel = modelHash, - isPlayerOwned = false - } or nil - }, - distance = Config.TargetOptions.distance - }) - end - - -- Player owned machines will be added dynamically as they're loaded -end - -local function RefreshPlayerMachines() - local playerMachines = QBCore.Functions.TriggerRpc('vendingmachines:server:getPlayerMachines', PlayerData.citizenid) - - for _, machine in pairs(playerMachines) do - exports['qb-target']:AddBoxZone('vending_' .. machine.id, json.decode(machine.location), 0.5, 0.5, { - name = 'vending_' .. machine.id, - heading = 0, - debugPoly = false, - minZ = json.decode(machine.location).z - 0.5, - maxZ = json.decode(machine.location).z + 0.5 - }, { - options = { - { - type = 'client', - event = 'vendingmachines:client:openMenu', - icon = 'fas fa-cash-register', - label = 'Use Vending Machine', - machineId = machine.id, - isPlayerOwned = true, - machineModel = machine.model_hash - }, - Config.EnableRobbery and { - type = 'client', - event = 'vendingmachines:client:startRobbery', - icon = 'fas fa-lock', - label = 'Rob Machine', - item = Config.RobberyItem, - machineId = machine.id, - isPlayerOwned = true - } or nil, - table.contains(Config.PlayerOwnedMachines.AllowedJobs, PlayerData.job.name) and { - type = 'client', - event = 'vendingmachines:client:restockMenu', - icon = 'fas fa-boxes', - label = 'Restock Machine', - machineId = machine.id - } or nil, - table.contains(Config.PlayerOwnedMachines.AllowedJobs, PlayerData.job.name) and { - type = 'client', - event = 'vendingmachines:client:collectEarnings', - icon = 'fas fa-money-bill-wave', - label = 'Collect Earnings', - machineId = machine.id - } or nil - }, - distance = Config.TargetOptions.distance - }) - end -end - -local function OpenVendingMenu(machineInfo) - local menu = { - header = 'Vending Machine', - items = {} - } - - if machineInfo.isPlayerOwned then - menu.header = 'Player Vending Machine' - menu.items[#menu.items + 1] = { - title = 'Stock: ' .. (currentMachine and currentMachine.stock or '?'), - description = 'Available items for purchase', - disabled = true - } - else - menu.header = '24/7 Vending Machine' - end - - local items = Config.DefaultMachines.Models[machineInfo.machineModel].items - for _, item in pairs(items) do - menu.items[#menu.items + 1] = { - title = item.label, - description = 'Price: $' .. item.price, - onSelect = function() - local input = lib.inputDialog('Purchase Amount', { - { type = 'number', label = 'Amount', min = 1, max = 10, default = 1 } - }) - - if input and input[1] then - TriggerServerEvent('vendingmachines:server:processPurchase', - machineInfo.isPlayerOwned, - machineInfo.isPlayerOwned and machineInfo.machineId or machineInfo.machineModel, - item.name, - input[1]) - end - end - } - end - - lib.registerContext(menu) - lib.showContext('vending_menu') -end - -local function StartRobbery(machineInfo) - QBCore.Functions.TriggerCallback('vendingmachines:server:hasItem', function(hasItem) - if hasItem then - local success = lib.skillCheck({ 'easy', 'easy', { areaSize = 60, speedMultiplier = 1 } }, { 'w', 'a', 's', 'd' }) - - if success then - QBCore.Functions.Progressbar('robbing_machine', 'Robbing vending machine...', - Config.RobberyTime * 1000, false, true, { - disableMovement = true, - disableCarMovement = true, - disableMouse = false, - disableCombat = true, - }, { - animDict = 'mini@safe_cracking', - anim = 'idle_base', - flags = 16, - }, {}, {}, function() - TriggerServerEvent('vendingmachines:server:completeRobbery', - machineInfo.isPlayerOwned, - machineInfo.isPlayerOwned and machineInfo.machineId or nil) - end, function() - TriggerServerEvent('vendingmachines:server:robberyFailed', - machineInfo.isPlayerOwned, - machineInfo.isPlayerOwned and machineInfo.machineId or nil) - end) - else - QBCore.Functions.Notify('Robbery failed', 'error') - end - else - QBCore.Functions.Notify('You don\'t have the required item', 'error') - end - end, Config.RobberyItem) -end - --- Events -RegisterNetEvent('vendingmachines:client:openMenu', function(data) - OpenVendingMenu(data) -end) - -RegisterNetEvent('vendingmachines:client:registerMachine', function() - local playerPed = PlayerPedId() - local coords = GetEntityCoords(playerPed) - local obj = GetClosestObjectOfType(coords, 3.0, GetHashKey('prop_vend_soda_01'), false, false, false) - - if DoesEntityExist(obj) then - local modelHash = GetEntityModel(obj) - local validModel = false - - for _, model in pairs(Config.PlayerOwnedMachines.Models) do - if model == modelHash then - validModel = true - break - end - end - - if not validModel then - QBCore.Functions.Notify('This vending machine cannot be owned', 'error') - return - end - - local objCoords = GetEntityCoords(obj) - TriggerServerEvent('vendingmachines:server:registerMachine', modelHash, objCoords) - else - QBCore.Functions.Notify('No vending machine nearby', 'error') - end -end) - -RegisterNetEvent('vendingmachines:client:startRobbery', function(data) - StartRobbery(data) -end) - -RegisterNetEvent('vendingmachines:client:refreshPlayerMachines', function() - RefreshPlayerMachines() -end) - -RegisterNetEvent('vendingmachines:client:restockMenu', function(data) - local input = lib.inputDialog('Restock Amount', { - { type = 'number', label = 'Amount', min = 1, default = 1 } - }) - - if input and input[1] then - TriggerServerEvent('vendingmachines:server:restockMachine', data.machineId) - end -end) - -RegisterNetEvent('vendingmachines:client:collectEarnings', function(data) - TriggerServerEvent('vendingmachines:server:collectEarnings', data.machineId) -end) - --- Initialization -AddEventHandler('QBCore:Client:OnPlayerLoaded', function() - PlayerData = QBCore.Functions.GetPlayerData() - SetupTarget() - RefreshPlayerMachines() -end) - -AddEventHandler('QBCore:Client:OnJobUpdate', function(job) - PlayerData.job = job -end) - -AddEventHandler('onResourceStart', function(resource) - if GetCurrentResourceName() == resource then - PlayerData = QBCore.Functions.GetPlayerData() - SetupTarget() - Citizen.SetTimeout(5000, function() - RefreshPlayerMachines() - end) - end -end) diff --git a/resources/[inventory]/nordi_vending/fxmanifest.lua b/resources/[inventory]/nordi_vending/fxmanifest.lua deleted file mode 100644 index b99434fe7..000000000 --- a/resources/[inventory]/nordi_vending/fxmanifest.lua +++ /dev/null @@ -1,30 +0,0 @@ -fx_version 'cerulean' -game 'gta5' - -name 'QB-VendingMachines' -author 'Nordi' -description 'Advanced Vending Machine System for QB-Core' -version '1.0.0' - -shared_scripts { - 'shared/config.lua', - '@qb-core/shared/locale.lua', - 'locales/en.lua' -- add other locales as needed -} - -client_scripts { - '@qb-target/client.lua', - 'client/main.lua' -} - -server_scripts { - '@oxmysql/lib/MySQL.lua', - 'server/main.lua' -} - -dependencies { - 'qb-core', - 'qb-target', - 'qs-inventory', - 'ox_lib' -- or 'ox_lib' if using newer version -} diff --git a/resources/[inventory]/nordi_vending/server/main.lua b/resources/[inventory]/nordi_vending/server/main.lua deleted file mode 100644 index c130ad9e9..000000000 --- a/resources/[inventory]/nordi_vending/server/main.lua +++ /dev/null @@ -1,316 +0,0 @@ -local QBCore = exports['qb-core']:GetCoreObject() -local Config = require 'config' - --- SQL Setup -local function SetupDatabase() - local query = [[ - CREATE TABLE IF NOT EXISTS player_vending_machines ( - id INT AUTO_INCREMENT PRIMARY KEY, - owner VARCHAR(50) NOT NULL, - model_hash BIGINT NOT NULL, - location LONGTEXT NOT NULL, - stock INT DEFAULT 0, - earnings DECIMAL(10,2) DEFAULT 0, - last_collected BIGINT DEFAULT 0, - UNIQUE KEY unique_machine (owner, model_hash, location(255)) - ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; - ]] - MySQL.ready(function() - MySQL.query(query, {}, function(result) - print('^2[Vending Machines]^7 Database table initialized') - end) - end) -end - --- Global state for 24/7 machine robberies -local robberyCooldown = {} - --- Register usable items -QBCore.Functions.CreateUseableItem(Config.RobberyItem, function(source) - TriggerClientEvent('vendingmachines:client:startRobbery', source) -end) - -if Config.PlayerOwnedMachines.RestockItem then - QBCore.Functions.CreateUseableItem(Config.PlayerOwnedMachines.RestockItem, function(source) - TriggerClientEvent('vendingmachines:client:startRestock', source) - end) -end - --- Player-owned machine management -local function GetPlayerMachines(citizenid) - local result = MySQL.query.await('SELECT * FROM player_vending_machines WHERE owner = ?', { citizenid }) - return result -end - -local function GetMachineById(id) - local result = MySQL.query.await('SELECT * FROM player_vending_machines WHERE id = ?', { id }) - return result[1] -end - -local function RegisterPlayerMachine(source, modelHash, coords) - local Player = QBCore.Functions.GetPlayer(source) - if not Player then return false end - - local location = json.encode({ - x = coords.x, - y = coords.y, - z = coords.z - }) - - local result = MySQL.insert.await([[ - INSERT INTO player_vending_machines (owner, model_hash, location) - VALUES (?, ?, ?) - ]], { Player.PlayerData.citizenid, modelHash, location }) - - if result then - TriggerClientEvent('vendingmachines:client:refreshPlayerMachines', -1) - return true - end - return false -end - -local function RestockMachine(machineId, amount) - local machine = GetMachineById(machineId) - if not machine then return false end - - local newStock = math.min(machine.stock + amount, Config.PlayerOwnedMachines.MaxStock) - MySQL.update.await('UPDATE player_vending_machines SET stock = ? WHERE id = ?', { newStock, machineId }) - return true -end - -local function CollectEarnings(machineId) - local machine = GetMachineById(machineId) - if not machine or machine.earnings <= 0 then return 0 end - - local amount = machine.earnings - MySQL.update.await('UPDATE player_vending_machines SET earnings = 0, last_collected = ? WHERE id = ?', - { os.time(), machineId }) - return amount -end - --- Handle vending machine purchases -local function ProcessPurchase(source, isPlayerOwned, machineId, itemName, amount) - local Player = QBCore.Functions.GetPlayer(source) - if not Player then return false end - - if isPlayerOwned then - -- Player-owned machine purchase - local machine = GetMachineById(machineId) - if not machine or machine.stock < amount then return false end - - local itemData = nil - for _, item in pairs(Config.DefaultMachines.Models[machine.model_hash].items) do - if item.name == itemName then - itemData = item - break - end - end - - if not itemData then return false end - - local totalPrice = itemData.price * amount - if Player.Functions.RemoveMoney('cash', totalPrice) then - local earnings = totalPrice - local ownerCut = math.floor(earnings * Config.PlayerOwnedMachines.OwnerCut) - local businessCut = earnings - ownerCut - - MySQL.update.await('UPDATE player_vending_machines SET stock = stock - ?, earnings = earnings + ? WHERE id = ?', - { amount, businessCut, machineId }) - - -- Give item to player - Player.Functions.AddItem(itemName, amount) - return true - end - else - -- 24/7 machine purchase - local modelHash = tonumber(machineId) - local machineItems = Config.DefaultMachines.Models[modelHash] - if not machineItems then return false end - - local itemData = nil - for _, item in pairs(machineItems.items) do - if item.name == itemName then - itemData = item - break - end - end - - if not itemData then return false end - - local totalPrice = itemData.price * amount - if Player.Functions.RemoveMoney('cash', totalPrice) then - Player.Functions.AddItem(itemName, amount) - return true - end - end -end - --- Robbery functions -local function AlertPolice(machineCoords) - if Config.Dispatch == 'ps-dispatch' then - exports['ps-dispatch']:VendingMachineRobbery(machineCoords) - elseif Config.Dispatch == 'qb-dispatch' then - TriggerEvent('qb-dispatch:officerDistress', { - dispatchCode = '10-31', - firstStreet = GetStreetAndZone(machineCoords), - priority = 2, - origin = { - x = machineCoords.x, - y = machineCoords.y, - z = machineCoords.z - }, - blip = { - sprite = 52, - scale = 1.5, - color = 1, - flashes = true, - text = 'Vending Machine Robbery', - time = 5 - } - }) - end -end - -local function CompleteRobbery(source, isPlayerOwned, machineId) - local Player = QBCore.Functions.GetPlayer(source) - if not Player then return false end - - if robberyCooldown[source] and os.time() - robberyCooldown[source] < 300 then - TriggerClientEvent('QBCore:Notify', source, 'You need to wait before robbing again', 'error') - return false - end - - if Player.Functions.RemoveItem(Config.RobberyItem, 1) then - local reward = math.random(Config.MinRobberyCash, Config.MaxRobberyCash) - Player.Functions.AddMoney('cash', reward) - - if math.random(1, 100) <= Config.RobberyAlertChance then - local coords = GetEntityCoords(GetPlayerPed(source)) - AlertPolice(coords) - end - - robberyCooldown[source] = os.time() - - if isPlayerOwned then - local machine = GetMachineById(machineId) - if machine then - MySQL.update.await('UPDATE player_vending_machines SET stock = GREATEST(0, stock - ?) WHERE id = ?', - { math.random(5, 15), machineId }) - end - end - - return true - end - return false -end - --- Server Events -RegisterNetEvent('vendingmachines:server:registerMachine', function(modelHash, coords) - local src = source - if RegisterPlayerMachine(src, modelHash, coords) then - TriggerClientEvent('QBCore:Notify', src, 'Vending machine registered successfully', 'success') - else - TriggerClientEvent('QBCore:Notify', src, 'Failed to register vending machine', 'error') - end -end) - -RegisterNetEvent('vendingmachines:server:processPurchase', function(isPlayerOwned, machineId, itemName, amount) - local src = source - if ProcessPurchase(src, isPlayerOwned, machineId, itemName, amount) then - TriggerClientEvent('QBCore:Notify', src, 'Purchase successful', 'success') - else - TriggerClientEvent('QBCore:Notify', src, 'Purchase failed', 'error') - end -end) - -RegisterNetEvent('vendingmachines:server:restockMachine', function(machineId) - local src = source - local Player = QBCore.Functions.GetPlayer(src) - if not Player then return end - - local jobName = Player.PlayerData.job.name - local allowed = false - for _, job in pairs(Config.PlayerOwnedMachines.AllowedJobs) do - if job == jobName then - allowed = true - break - end - end - - if not allowed then - TriggerClientEvent('QBCore:Notify', src, 'You are not authorized to restock machines', 'error') - return - end - - if Player.Functions.RemoveItem(Config.PlayerOwnedMachines.RestockItem, 1) then - if RestockMachine(machineId, Config.PlayerOwnedMachines.StockAmount) then - TriggerClientEvent('QBCore:Notify', src, 'Machine restocked successfully', 'success') - else - Player.Functions.AddItem(Config.PlayerOwnedMachines.RestockItem, 1) - TriggerClientEvent('QBCore:Notify', src, 'Failed to restock machine', 'error') - end - else - TriggerClientEvent('QBCore:Notify', src, 'You don\'t have the restock item', 'error') - end -end) - -RegisterNetEvent('vendingmachines:server:collectEarnings', function(machineId) - local src = source - local Player = QBCore.Functions.GetPlayer(src) - if not Player then return end - - local jobName = Player.PlayerData.job.name - local allowed = false - for _, job in pairs(Config.PlayerOwnedMachines.AllowedJobs) do - if job == jobName then - allowed = true - break - end - end - - if not allowed then - TriggerClientEvent('QBCore:Notify', src, 'You are not authorized to collect earnings', 'error') - return - end - - local amount = CollectEarnings(machineId) - if amount > 0 then - Player.Functions.AddMoney('cash', amount) - TriggerClientEvent('QBCore:Notify', src, string.format('Collected $%d from the machine', amount), 'success') - else - TriggerClientEvent('QBCore:Notify', src, 'No earnings to collect', 'error') - end -end) - -RegisterNetEvent('vendingmachines:server:completeRobbery', function(isPlayerOwned, machineId) - local src = source - if CompleteRobbery(src, isPlayerOwned, machineId) then - TriggerClientEvent('QBCore:Notify', src, 'Robbery successful', 'success') - else - TriggerClientEvent('QBCore:Notify', src, 'Robbery failed', 'error') - end -end) - --- Commands -QBCore.Commands.Add('registermachine', 'Register a player-owned vending machine', {}, false, function(source) - TriggerClientEvent('vendingmachines:client:registerMachine', source) -end, 'admin') - -QBCore.Commands.Add('mymachines', 'View your owned vending machines', {}, false, function(source) - local Player = QBCore.Functions.GetPlayer(source) - if not Player then return end - - local machines = GetPlayerMachines(Player.PlayerData.citizenid) - if #machines > 0 then - local msg = "Your machines:\n" - for _, machine in pairs(machines) do - msg = msg .. string.format("ID: %d | Stock: %d | Earnings: $%.2f\n", machine.id, machine.stock, machine.earnings) - end - TriggerClientEvent('chat:addMessage', source, { args = { 'SYSTEM', msg } }) - else - TriggerClientEvent('QBCore:Notify', source, 'You don\'t own any machines', 'error') - end -end) - --- Initialize -SetupDatabase() diff --git a/resources/[inventory]/nordi_vending/shared/config.lua b/resources/[inventory]/nordi_vending/shared/config.lua deleted file mode 100644 index 614f4b397..000000000 --- a/resources/[inventory]/nordi_vending/shared/config.lua +++ /dev/null @@ -1,70 +0,0 @@ -Config = {} - --- General Settings -Config.UseQBTarget = true -Config.UseOxLib = true -Config.Inventory = 'qs-inventory' -- or 'qb-inventory' - --- Robbery Settings -Config.EnableRobbery = true -Config.RobberyItem = 'lockpick' -- item needed to rob -Config.MinRobberyCash = 50 -Config.MaxRobberyCash = 250 -Config.RobberyTime = 15 -- seconds -Config.PoliceJob = 'police' -Config.Dispatch = 'ps-dispatch' -- or 'qb-dispatch' -Config.RobberyAlertChance = 70 -- percentage chance police get alerted - --- Player-owned Vending Machines -Config.PlayerOwnedMachines = { - AllowedJobs = { -- jobs that can restock/collect money - 'vending', - 'delivery' - }, - Models = { - `prop_vend_soda_01`, - `prop_vend_soda_02`, - `prop_vend_water_01` - }, - RestockItem = 'sodasyrup', -- item needed to restock - StockAmount = 10, -- how much stock restock item provides - PricePerItem = 10, -- how much player earns per sale - MaxStock = 50, - OwnerCut = 0.7 -- percentage owner gets (30% goes to business) -} - --- 24/7 Vending Machines -Config.DefaultMachines = { - Models = { - [`prop_vend_soda_01`] = { - items = { - { name = 'water_bottle', price = 5, label = 'Water' }, - { name = 'kurkakola', price = 7, label = 'Cola' }, - { name = 'sprunk', price = 7, label = 'Sprunk' } - } - }, - [`prop_vend_soda_02`] = { - items = { - { name = 'water_bottle', price = 5, label = 'Water' }, - { name = 'ecola', price = 8, label = 'eCola' } - } - }, - [`prop_vend_coffe_01`] = { - items = { - { name = 'coffee', price = 10, label = 'Coffee' } - } - } - } -} - --- Target Options -Config.TargetOptions = { - useZones = true, -- create target zones for machines - distance = 2.0 -} - --- Notification Settings -Config.Notify = 'qb' -- or 'ox', 'okok', 'esx' -Config.Locale = 'en' -- if using locale files - -return Config diff --git a/resources/[jobs]/[civ]/wasabi_fishing/configuration/config.lua b/resources/[jobs]/[civ]/wasabi_fishing/configuration/config.lua index b1c166fc4..3ce109dc8 100644 --- a/resources/[jobs]/[civ]/wasabi_fishing/configuration/config.lua +++ b/resources/[jobs]/[civ]/wasabi_fishing/configuration/config.lua @@ -123,8 +123,8 @@ Config.fish = { -- Add prices for processed items Config.processedItems = { - { item = 'fish_fillet', label = 'Fish Fillet', price = {50, 100} }, - { item = 'caviar', label = 'Caviar', price = {300, 500} }, + { item = 'fish_fillet', label = 'Fish Fillet', price = {10, 40} }, + { item = 'caviar', label = 'Caviar', price = {60, 100} }, } RegisterNetEvent('wasabi_fishing:notify') diff --git a/resources/[jobs]/[civ]/wasabi_fishing/configuration/strings.lua b/resources/[jobs]/[civ]/wasabi_fishing/configuration/strings.lua index 5eea9f725..a7f84c9c3 100644 --- a/resources/[jobs]/[civ]/wasabi_fishing/configuration/strings.lua +++ b/resources/[jobs]/[civ]/wasabi_fishing/configuration/strings.lua @@ -18,7 +18,7 @@ Strings = { fish_success = 'Fisch im Kasten – das Abendessen ist gesichert.', fish_success_desc = 'Du hast eine/n %s!', sell_shop_blip = 'Fish Market', - sell_fish = '[E] - Fisch verkaufen.', + sell_fish = '[E] - Fisch verkaufen', kicked = 'Du kannst’s versuchen, aber das klappt hier nicht.', sold_for = 'Fisch verkauft.', sold_for_desc = 'Du hast %sx %s für $%s verkauft.', @@ -28,7 +28,7 @@ Strings = { waiting_bite_desc = 'Ein bisschen Geduld – der Fisch ist gleich da.', cannot_carry = 'Kein Platz!', cannot_carry_desc = 'Du schleppst schon genug – mehr passt nicht rein!', - no_knife = 'Kein Messer.', + no_knife = 'Kein Messer', no_knife_desc = 'Ohne Messer ist der Fisch nur Deko.', processing_success = 'Fang verarbeitet – nächster Schritt: Grill an!', processing_success_desc = '%d %s – frisch aus der Fischverarbeitung!',