mirror of
https://github.com/UltimateMenu/UltimateMenu.git
synced 2026-10-10 11:53:08 +08:00
Compare commits
136 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| cf2e354173 | |||
| 2c7b12720b | |||
| 034c9e4bef | |||
| e6d5d3a245 | |||
| b3ebc25a43 | |||
| b77c81bc48 | |||
| e8adcde6e2 | |||
| b54f4c48c5 | |||
| d868876d70 | |||
| e4a41668ee | |||
| 9ca89413c9 | |||
| c45c7f03fc | |||
| 624c607185 | |||
| a7120f68e7 | |||
| 4dd2ec689c | |||
| b7625dfbe1 | |||
| 5ff45873e2 | |||
| 720816f826 | |||
| c06a2ff411 | |||
| 96e20e98e1 | |||
| 2e74762235 | |||
| 307d6e07ca | |||
| 9583689be9 | |||
| c679209178 | |||
| c6ea3a97c0 | |||
| 306c771a78 | |||
| 11b079a49e | |||
| 335cf29d97 | |||
| a28c577c2a | |||
| 362e626393 | |||
| b6e598c4f7 | |||
| 150f423ed7 | |||
| 63f0ea1488 | |||
| ff7def525b | |||
| 29965eeb59 | |||
| c9fe45884c | |||
| b4f01c9771 | |||
| f3778a4b21 | |||
| ba45b292db | |||
| 859a682f92 | |||
| d14b42b08e | |||
| e030c7f3f4 | |||
| 5d5b8a6de0 | |||
| 2a2d655c96 | |||
| 8e72de2936 | |||
| cc1bbd0040 | |||
| bce5cca6cf | |||
| dc127f8e19 | |||
| 3ae957323f | |||
| 7f8468d4a3 | |||
| 4548f33290 | |||
| c9381be953 | |||
| ed8de348fa | |||
| ef159a8efc | |||
| db2b8ae936 | |||
| 5c5d95f84e | |||
| bb9ab6b081 | |||
| bb3b76951b | |||
| de2144259e | |||
| a83beadfc0 | |||
| fd1064ba80 | |||
| 4ccd511e2d | |||
| dbd70e2f0e | |||
| 9abe0ad3ab | |||
| a68053e489 | |||
| 6e287087f4 | |||
| bf71acc16c | |||
| 37e5774a4c | |||
| d635ed9866 | |||
| 129a4caa90 | |||
| 86a905d7dd | |||
| 9663c47911 | |||
| d566697e8d | |||
| 875dca2969 | |||
| 54832454ca | |||
| 2a9b4d51be | |||
| 6a6e0e2d50 | |||
| c107f0bf10 | |||
| f839fd2ee5 | |||
| ed828baf8b | |||
| ee142f4564 | |||
| 473c84ac69 | |||
| 8515113297 | |||
| 5cbdbb204d | |||
| 9972459de4 | |||
| cd1edbfa64 | |||
| 1730fb5bde | |||
| ff6052e2f4 | |||
| c5dbaea207 | |||
| 24bb44eb45 | |||
| d656cf578d | |||
| 6b592202ff | |||
| 503c1f2ba3 | |||
| 97c8e8df7c | |||
| 03844850ca | |||
| 57cff43f87 | |||
| ac6176f6c4 | |||
| a3606c6577 | |||
| 561837d5ef | |||
| e0aa8504c2 | |||
| b573a8f1b2 | |||
| a0dde9ffe8 | |||
| 80fad0a562 | |||
| 07ffefacdd | |||
| b66a28e547 | |||
| 8d899318b9 | |||
| 75652c055e | |||
| 92269eb9a2 | |||
| 540701e9e1 | |||
| af62aba2f3 | |||
| f6069a007f | |||
| 1830770813 | |||
| da306f00a8 | |||
| d3ae866674 | |||
| 146608dd9f | |||
| 4eec8e59e8 | |||
| 32335e27d8 | |||
| 5bd236b78e | |||
| cc0c040d71 | |||
| 73e1362d55 | |||
| 8053782438 | |||
| 0cb8d211b0 | |||
| 9e354e9bc8 | |||
| 9b6c9d8da3 | |||
| d74542e7db | |||
| 9aca683529 | |||
| 0dc7832b5f | |||
| 885a1c020b | |||
| 0937eb8d19 | |||
| 45c327b8cc | |||
| a987622320 | |||
| b00b2a9d3e | |||
| 788257d97c | |||
| 74961d14ad | |||
| 92c1832ebc | |||
| bc5d7ee305 |
@@ -0,0 +1,113 @@
|
||||
name: Bug report
|
||||
description: Create a report to help us improve
|
||||
title: "[Bug]: "
|
||||
labels: bug
|
||||
type: bug
|
||||
body:
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Describe the bug
|
||||
description: A clear and concise description of what the bug is.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Steps To Reproduce
|
||||
description: Steps to reproduce the behavior.
|
||||
placeholder: |
|
||||
1. Go to '...'
|
||||
2. Click on '...'
|
||||
3. Scroll down to '...'
|
||||
4. See error
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Expected Behavior
|
||||
description: A clear and concise description of what you expected to happen.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Logs
|
||||
description: |
|
||||
For a bug report to be valid, you need to include the logs for YimMenu.
|
||||
They can be found under `%appdata%/YimMenu/cout.log`, even if you think the log file is useless we'd still like for you to include it here.
|
||||
|
||||
Tip: To easily upload your log file rename the cout.log file to cout.txt, alternatively zip the cout.log file. You can then drag and drop the file here.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Screenshots / Video
|
||||
description: |
|
||||
If you think the issue can be better explained with screenshots or a video then consider adding these here.
|
||||
|
||||
Tip: You can attach images by clicking this area to highlight it and then dragging files in.
|
||||
value: |
|
||||
<!-- drag and drop your images or video(s) here -->
|
||||
validations:
|
||||
required: false
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Store
|
||||
description: Which launcher/store do you use to launch your game?
|
||||
multiple: false
|
||||
options:
|
||||
- Steam
|
||||
- Epic Games
|
||||
- Rockstar
|
||||
- Other (please mention in "Additional context")
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Language
|
||||
description: Which language do you have GTA 5 set to?
|
||||
multiple: false
|
||||
options:
|
||||
- English
|
||||
- French
|
||||
- Italian
|
||||
- German
|
||||
- Spanish
|
||||
- Japanese
|
||||
- Russian
|
||||
- Polish
|
||||
- Brazilian Portuguese
|
||||
- Traditional Chinese
|
||||
- Simplified Chinese
|
||||
- Latin American Spanish
|
||||
- Korean
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: YimMenu Language
|
||||
description: Which language do you use with YimMenu?
|
||||
multiple: false
|
||||
options:
|
||||
- English (US)
|
||||
- Español (España)
|
||||
- Français (FR)
|
||||
- Italiano (IT)
|
||||
- Portuguese (BR)
|
||||
- Русский (RU)
|
||||
- Chinese (CN)
|
||||
- Chinese (TW)
|
||||
- Korean (KR)
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add any other context about the problem here.
|
||||
validations:
|
||||
required: false
|
||||
- type: checkboxes
|
||||
attributes:
|
||||
label: Release
|
||||
description: We want to confirm that this issue exists on the latest **release** version of UltimateMenu, not a fork or your own version of UltimateMenu.
|
||||
options:
|
||||
- label: I've confirmed the issue exists on the latest **release** version of UltimateMenu
|
||||
required: true
|
||||
@@ -0,0 +1,17 @@
|
||||
blank_issues_enabled: false
|
||||
contact_links:
|
||||
- name: Website
|
||||
url: https://ultimatemenu.github.io
|
||||
about: Main website of UltimateMenu.
|
||||
- name: Docs | wiki
|
||||
url: https://github.com/UltimateMenu/UltimateMenu/wiki
|
||||
about: Maybe take a look a the docs in the main wiki of UltimateMenu?
|
||||
- name: Discord Server
|
||||
url: https://l7neg.uk.to/discord
|
||||
about: Main Discord Server of UltimateMenu.
|
||||
- name: UltimateMenu profile
|
||||
url: https://github.com/UltimateMenu
|
||||
about: Main github Orgnization profile of UltimateMenu for other sources.
|
||||
- name: UltimateMenu Org discussions
|
||||
url: https://github.com/orgs/UltimateMenu/discussions
|
||||
about: Main github Orgnization discussions of UltimateMenu.
|
||||
@@ -0,0 +1,29 @@
|
||||
name: Enhancement request
|
||||
description: Enhance an existing feature in UltimateMenu.
|
||||
title: "[Enhancement]: "
|
||||
labels: enhancement
|
||||
type: enhancement
|
||||
body:
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Which feature
|
||||
description: "Explain which feature you want to see enhanced/improved and what you'd like to be changed about it."
|
||||
placeholder: "ex: I'd like to enhance/improve .... because .... ."
|
||||
validations:
|
||||
required: false
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Reason
|
||||
description: Provide Reasoning
|
||||
placeholder: "Tell us why you'd want for us to improve this feature in UltimateMenu."
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: |
|
||||
Add any other context about the request here.
|
||||
|
||||
Tip: You can attach images or log files by clicking this area to highlight it and then dragging files in.
|
||||
validations:
|
||||
required: false
|
||||
@@ -0,0 +1,36 @@
|
||||
name: Feature request
|
||||
description: Suggest an idea for this project
|
||||
title: "[Request]: "
|
||||
labels: feature request
|
||||
type: feature request
|
||||
body:
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Problem
|
||||
description: "Is your feature request related to a problem? Please describe."
|
||||
placeholder: "A clear and concise description of what the problem is. Ex. I'm always frustrated when [...]"
|
||||
validations:
|
||||
required: false
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Solution
|
||||
description: "Describe the solution you'd like"
|
||||
placeholder: "A clear and concise description of what you want to happen."
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Reason
|
||||
description: Provide Reasoning
|
||||
placeholder: "Tell us why you'd want for us to add this to UltimateMenu."
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: |
|
||||
Add any other context about the request here.
|
||||
|
||||
Tip: You can attach images or log files by clicking this area to highlight it and then dragging files in.
|
||||
validations:
|
||||
required: false
|
||||
@@ -0,0 +1,42 @@
|
||||
name: Autolocker
|
||||
|
||||
on:
|
||||
pull_request_target:
|
||||
types: [closed]
|
||||
issues:
|
||||
types: [closed]
|
||||
|
||||
permissions: write-all
|
||||
|
||||
jobs:
|
||||
autolock-prs:
|
||||
if: ${{ github.event_name == 'pull_request_target' && github.event.pull_request.merged }}
|
||||
runs-on: ubuntu-latest
|
||||
name: Autolock merged PRs
|
||||
steps:
|
||||
- name: Autolock merged PRs
|
||||
uses: actions/github-script@v6
|
||||
with:
|
||||
script: |
|
||||
github.rest.issues.lock({
|
||||
issue_number: context.issue.number,
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
lock_reason: "resolved"
|
||||
});
|
||||
|
||||
autolock-issues:
|
||||
if: ${{ github.event_name == 'issues' }}
|
||||
runs-on: ubuntu-latest
|
||||
name: Autolock closed Issues
|
||||
steps:
|
||||
- name: Autolock closed Issues
|
||||
uses: actions/github-script@v6
|
||||
with:
|
||||
script: |
|
||||
github.rest.issues.lock({
|
||||
issue_number: context.issue.number,
|
||||
owner: context.repo.owner,
|
||||
repo: context.repo.repo,
|
||||
lock_reason: "resolved"
|
||||
});
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,21 @@
|
||||
# Ultimate Menu for Nenyoo
|
||||
|
||||
Ultimate Menu runs in Nenyoo on GTA V Legacy and Enhanced with the same menu structure and controls as the YimMenu edition.
|
||||
|
||||
## Install
|
||||
|
||||
1. Copy this folder to `%LOCALAPPDATA%\Nenyoo\Plus\Scripts\User\UltimateMenu\`.
|
||||
2. Keep `Ultimate_Menu.lua` and the `lib` folder together.
|
||||
3. In Nenyoo, open **Scripts** and select `Ultimate_Menu.lua`.
|
||||
|
||||
Online features become available after joining GTA Online.
|
||||
|
||||
## Supported builds
|
||||
|
||||
- GTA V Legacy 3889
|
||||
- GTA V Enhanced 1158.13
|
||||
|
||||
The correct offset catalog is selected automatically. Build-specific globals and locals are stored in:
|
||||
|
||||
- `lib/game_offsets_legacy.offsets`
|
||||
- `lib/game_offsets_enhanced.offsets`
|
||||
@@ -0,0 +1,49 @@
|
||||
-- @nenyoo-menu
|
||||
-- Ultimate Menu for Nenyoo (GTA V Legacy and Enhanced).
|
||||
-- Install this package under %LOCALAPPDATA%\Nenyoo\Plus\Scripts\User\UltimateMenu.
|
||||
|
||||
local source = debug.getinfo(1, "S").source
|
||||
assert(source:sub(1, 1) == "@", "Ultimate Menu must be loaded from a file")
|
||||
local directory = source:sub(2):match("^(.*[\\/])")
|
||||
assert(directory, "Could not locate the Ultimate Menu package")
|
||||
|
||||
-- The YimResupplier config belongs to this package, not the GTA working directory.
|
||||
local script_io = setmetatable({
|
||||
open = function(name, mode)
|
||||
if name == "YimResupplier.json" then name = directory .. name end
|
||||
return io.open(name, mode)
|
||||
end,
|
||||
}, {__index = io})
|
||||
|
||||
-- Keep compatibility overrides inside this package; other Nenyoo scripts use
|
||||
-- the original native, memory, network, and script tables.
|
||||
local environment = setmetatable({
|
||||
io = script_io,
|
||||
memory = setmetatable({}, {__index = memory}),
|
||||
network = setmetatable({}, {__index = network or {}}),
|
||||
script = setmetatable({}, {__index = script or {}}),
|
||||
NETSHOPPING = setmetatable({}, {__index = NETSHOPPING}),
|
||||
PAD = setmetatable({}, {__index = PAD}),
|
||||
HUD = setmetatable({}, {__index = HUD}),
|
||||
ENTITY = setmetatable({}, {__index = ENTITY}),
|
||||
CUTSCENE = setmetatable({}, {__index = CUTSCENE}),
|
||||
}, {__index = _ENV})
|
||||
local function run(path)
|
||||
local chunk, message = loadfile(path, "t", environment)
|
||||
assert(chunk, message)
|
||||
return chunk()
|
||||
end
|
||||
|
||||
local offsets = run(directory .. "lib\\game_offsets.offsets")
|
||||
for _, group in ipairs({offsets.globals, offsets.locals, offsets.scripts}) do
|
||||
for name, value in pairs(group) do environment[name] = value end
|
||||
end
|
||||
environment.ULTIMATE_MENU_OFFSETS = offsets
|
||||
environment.ULTIMATE_MENU_EDITION = offsets.edition
|
||||
environment.ULTIMATE_MENU_BUILD = offsets.build
|
||||
|
||||
local compatibility = run(directory .. "lib\\yim_compat.lua")
|
||||
run(directory .. "lib\\Ultimate_Menu_Legacy.lua")
|
||||
run(directory .. "lib\\info_panel.lua")(compatibility)
|
||||
compatibility.materialize_imgui()
|
||||
return compatibility
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,13 @@
|
||||
-- Select the build-specific GTA address catalog at runtime.
|
||||
local source = debug.getinfo(1, "S").source
|
||||
assert(source:sub(1, 1) == "@", "Offset catalog must be loaded from a file")
|
||||
local directory = assert(source:sub(2):match("^(.*[\\/])"), "Could not locate offset catalogs")
|
||||
|
||||
local edition = "Legacy"
|
||||
if ctx and type(ctx.edition) == "function" then
|
||||
local reported = tostring(ctx.edition())
|
||||
if reported:lower() == "enhanced" then edition = "Enhanced" end
|
||||
end
|
||||
|
||||
local filename = edition == "Enhanced" and "game_offsets_enhanced.offsets" or "game_offsets_legacy.offsets"
|
||||
return assert(loadfile(directory .. filename, "t", _ENV))()
|
||||
@@ -0,0 +1,278 @@
|
||||
-- GTA V Enhanced build 1158.13 globals and script locals used by Ultimate Menu.
|
||||
-- Update addresses here when a game build changes; feature code should not
|
||||
-- contain raw global or local addresses.
|
||||
|
||||
local FREEMODE_TUNABLES = 262145
|
||||
|
||||
local globals = {
|
||||
FMg = 262145, -- freemode tunables base
|
||||
CSg1 = 1575048, -- session type
|
||||
CSg2 = 1574589, -- session switch
|
||||
CSg3 = 1574591, -- session quit
|
||||
|
||||
ACg1 = 1936408, -- apartment cut: player 1
|
||||
ACg2 = 1936409, -- apartment cut: player 2
|
||||
ACg3 = 1936410, -- apartment cut: player 3
|
||||
ACg4 = 1936411, -- apartment cut: player 4
|
||||
ACg5 = 1941383, -- apartment local-player cut
|
||||
AUAJg1 = 271333, -- Fleeca job root hash
|
||||
AUAJg2 = 271338, -- Prison Break root hash
|
||||
AUAJg3 = 271345, -- Humane Labs root hash
|
||||
AUAJg4 = 271351, -- Series A root hash
|
||||
AUAJg5 = 271357, -- Pacific Standard root hash
|
||||
ACDg = 2686124, -- apartment cooldown/player-data base
|
||||
AHDg = 4722363, -- apartment heist difficulty
|
||||
|
||||
DCCg1 = 1976088, -- casino cut: player 1
|
||||
DCCg2 = 1976089, -- casino cut: player 2
|
||||
DCCg3 = 1976090, -- casino cut: player 3
|
||||
DCCg4 = 1976091, -- casino cut: player 4
|
||||
CPCg1 = 1981458, -- Cayo cut: player 1
|
||||
CPCg2 = 1981459, -- Cayo cut: player 2
|
||||
CPCg3 = 1981460, -- Cayo cut: player 3
|
||||
CPCg4 = 1981461, -- Cayo cut: player 4
|
||||
DCg1 = 1969934, -- Doomsday cut: player 1
|
||||
DCg2 = 1969935, -- Doomsday cut: player 2
|
||||
DCg3 = 1969936, -- Doomsday cut: player 3
|
||||
DCg4 = 1969937, -- Doomsday cut: player 4
|
||||
GCg = 2692915, -- generic heist cut multiplier
|
||||
|
||||
KCBGL = 300182, -- Kortz bag size
|
||||
KCWMG = 300344, -- Kortz weekly multiplier
|
||||
KCCDG = 300247, -- Kortz normal cooldown
|
||||
KCCD2G = 300248, -- Kortz hard cooldown
|
||||
KCLDG = 1935711, -- Kortz lasers disabled
|
||||
KCSECONDARY_BASE = 5009911, -- Kortz secondary-target array
|
||||
KCPAYOUT_BASE = 300149, -- Kortz primary-target payouts
|
||||
|
||||
HGLs1 = 4722361, -- heist launch state 1
|
||||
HGLs2 = 4722364, -- heist launch state 2
|
||||
HGLs3 = 4722365, -- heist launch state 3
|
||||
HGLs4 = 4915256, -- heist launch state 4
|
||||
|
||||
SNOW = 266558,
|
||||
halloweatherAddress = 294894,
|
||||
yetihuntAddress = 297763,
|
||||
TRICK_OR_TREAT = 294663,
|
||||
SNOWMEN_COLLECTIBLES = 295964,
|
||||
GVADg = 296039, -- Gun Van armour discount
|
||||
GVWDg = 296020, -- Gun Van weapon discount
|
||||
GVTDg = 296031, -- Gun Van throwable discount
|
||||
CCBL0 = 288788, -- casino chip buy limit 1
|
||||
CCBL1 = 288789, -- casino chip buy limit 2
|
||||
CPBg = 291483, -- Cayo bag size
|
||||
PSV = 291735, -- Panther Statue value
|
||||
PDIAMOND = 291733, -- Pink Diamond value
|
||||
BB = 291732, -- Bearer Bonds value
|
||||
RN = 291731, -- Ruby Necklace value
|
||||
TEQUILA = 291730, -- Tequila value
|
||||
|
||||
AG = 4525224, -- achievement unlock selector
|
||||
current_objectives_global = 2359296,
|
||||
weekly_objectives_global = 2732247,
|
||||
objectives_state_global = 1574746,
|
||||
CARGO1 = 284730,
|
||||
CARGO2 = 284731,
|
||||
CARGO3 = 284732,
|
||||
CARGO4 = 284733,
|
||||
CARGO5 = 284734,
|
||||
CARGO6 = 284735,
|
||||
CARGO7 = 284736,
|
||||
CARGO8 = 284737,
|
||||
CARGO9 = 284738,
|
||||
CEO1 = 277970, -- special cargo sale threshold
|
||||
CEO2 = 277737, -- special cargo buy cooldown
|
||||
CEO3 = 277738, -- special cargo sell cooldown
|
||||
SafeCapacity = 23773, -- nightclub safe capacity tunable offset
|
||||
IncomeStart = 23750, -- nightclub income range start
|
||||
IncomeEnd = 23769, -- nightclub income range end
|
||||
main_global = 1673814, -- YimResupplier business-state base
|
||||
|
||||
TRANSACTION_ERROR_GLOBAL_1 = 4516981,
|
||||
TRANSACTION_ERROR_GLOBAL_2 = 4516982,
|
||||
TRANSACTION_ERROR_GLOBAL_3 = 4516983,
|
||||
GUN_VAN_LOCATION_GLOBAL = 2655290,
|
||||
PLAYER_RP_MULTIPLIER_GLOBAL = 262146,
|
||||
AIR_CARGO_RP_MULTIPLIER_GLOBAL = 284713,
|
||||
NIGHTCLUB_CASH_BONUS_1 = 279564,
|
||||
NIGHTCLUB_CASH_BONUS_2 = 279570,
|
||||
NIGHTCLUB_CASH_BASE = 279558,
|
||||
NIGHTCLUB_COKE_BONUS_1 = 279565,
|
||||
NIGHTCLUB_COKE_BONUS_2 = 279571,
|
||||
NIGHTCLUB_COKE_BASE = 279559,
|
||||
NIGHTCLUB_METH_BONUS_1 = 279566,
|
||||
NIGHTCLUB_METH_BONUS_2 = 279572,
|
||||
NIGHTCLUB_METH_BASE = 279560,
|
||||
NIGHTCLUB_WEED_BONUS_1 = 279567,
|
||||
NIGHTCLUB_WEED_BONUS_2 = 279573,
|
||||
NIGHTCLUB_WEED_BASE = 279561,
|
||||
NIGHTCLUB_DOCUMENTS_BONUS_1 = 279563,
|
||||
NIGHTCLUB_DOCUMENTS_BONUS_2 = 279569,
|
||||
NIGHTCLUB_DOCUMENTS_BASE = 279557,
|
||||
NIGHTCLUB_BUNKER_BONUS_1 = 283494,
|
||||
NIGHTCLUB_BUNKER_BONUS_2 = 283493,
|
||||
NIGHTCLUB_BUNKER_BASE = 283492,
|
||||
NIGHTCLUB_ACID_BONUS = 279568,
|
||||
NIGHTCLUB_ACID_BASE = 279562,
|
||||
}
|
||||
|
||||
function globals.DAILY_OBJECTIVE_CURRENT(index)
|
||||
return globals.current_objectives_global + 1 + 681 + 4248 + 1 + (index * 3)
|
||||
end
|
||||
function globals.DAILY_OBJECTIVE_STATE(index)
|
||||
return globals.objectives_state_global + 1 + 1 + index
|
||||
end
|
||||
function globals.WEEKLY_OBJECTIVE_STATE()
|
||||
return globals.weekly_objectives_global + 1 + 1
|
||||
end
|
||||
function globals.WEEKLY_OBJECTIVE_CURRENT()
|
||||
return globals.weekly_objectives_global + 1 + 2
|
||||
end
|
||||
function globals.NIGHTCLUB_SAFE_VALUE(player_id)
|
||||
return 1845347 + player_id + 260 + 364 + 5
|
||||
end
|
||||
function globals.APARTMENT_COOLDOWN(player_id)
|
||||
return globals.ACDg + 1 + (player_id * 77) + 76
|
||||
end
|
||||
function globals.APARTMENT_HEIST_TYPE(player_id)
|
||||
return globals.ACDg + (player_id * 77) + 24 + 2
|
||||
end
|
||||
function globals.HEIST_SOLO_LAUNCH(heist_type)
|
||||
return 794989 + 4 + 1 + (heist_type * 95) + 75
|
||||
end
|
||||
function globals.APARTMENT_FORCE_READY(player_index)
|
||||
return 2658294 + 1 + ((player_index - 1) * 468) + 270
|
||||
end
|
||||
function globals.LEGACY_HEIST_FORCE_READY(player_index)
|
||||
return 1882717 + 1 + ((player_index - 1) * 315) + 43 + 11 + player_index
|
||||
end
|
||||
function globals.CAYO_FORCE_READY(player_index)
|
||||
return 1981147 + 1 + ((player_index - 1) * 27) + 7 + player_index
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_TARGET(player_index, offset)
|
||||
return globals.KCSECONDARY_BASE + (player_index * 333) + offset
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_PRIMARY(player_index)
|
||||
return globals.KORTZ_SECONDARY_TARGET(player_index, 68)
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_SECONDARY(player_index)
|
||||
return globals.KORTZ_SECONDARY_TARGET(player_index, 143)
|
||||
end
|
||||
function globals.KORTZ_PAYOUT(target_index)
|
||||
return globals.KCPAYOUT_BASE + target_index + 1
|
||||
end
|
||||
function globals.YIM_RESUPPLIER_SLOT(slot_index)
|
||||
return globals.main_global + slot_index + 1
|
||||
end
|
||||
|
||||
local locals = {
|
||||
AIFl1 = 20412, -- apartment instant finish 1
|
||||
AIFl2 = 21474,
|
||||
AIFl3 = 22153,
|
||||
AIFl4 = 23098,
|
||||
AIFl5 = 29327,
|
||||
AIFl6 = 32854,
|
||||
AFHl = 12263, -- Fleeca hack
|
||||
AFDl = 10538, -- Fleeca drill
|
||||
AFPl = 10233, -- Pacific hack
|
||||
AHSo = 20414, -- apartment checkpoint bitset
|
||||
AHLIVESL = 28164, -- apartment team lives
|
||||
|
||||
DCRBl = 219, -- casino planning reload
|
||||
DCAg = 10713, -- casino autograbber state
|
||||
DCAs = 10727, -- casino autograbber speed
|
||||
DCFHl = 55028, -- casino fingerprint hack
|
||||
DCKHl = 56098, -- casino keypad hack
|
||||
DCDVDl1 = 10534, -- casino vault drill result
|
||||
DCDVDl2 = 10564, -- casino vault drill progress
|
||||
DCLIVESL = 28164, -- casino team lives
|
||||
DCXf1 = 20412,
|
||||
DCXf2 = 21474,
|
||||
DCXf3 = 22153,
|
||||
DCXf4 = 23098,
|
||||
DCXf5 = 29327,
|
||||
DCXf6 = 32854,
|
||||
|
||||
CPRSl = 1580, -- Cayo planning reload
|
||||
CPFHl = 26619, -- Cayo fingerprint hack
|
||||
CPPCCl = 32754, -- Cayo plasma cutter
|
||||
CPSTCl = 31511, -- Cayo drainage pipe
|
||||
CPXf1 = 56504,
|
||||
CPXf2 = 58281,
|
||||
CPLIVESL = 64395, -- Cayo team lives
|
||||
|
||||
DDSHl = 1449, -- Doomsday scenario hack
|
||||
DDIF1 = 20412,
|
||||
DDIF2 = 22153,
|
||||
DDIF3 = 29327,
|
||||
DDIF4 = 32854,
|
||||
DDIF5 = 32882,
|
||||
DDLIVESL = 28164, -- Doomsday team lives
|
||||
|
||||
KCBRL = 599, -- Kortz planning reload
|
||||
KCDCL = 1388, -- Kortz data crack base
|
||||
KCFHL = 26866, -- Kortz fingerprint hack
|
||||
KCAC_BASE = 32819, -- Kortz access-code base
|
||||
KCLGL = 71006, -- Kortz lasers
|
||||
KCVLL = 27914, -- Kortz vault door
|
||||
KCCGL_BASE = 32856, -- Kortz cut-glass base
|
||||
KCCGL_OFFSET = 3,
|
||||
KCPT_STATE = 29366, -- Kortz primary target state
|
||||
KCST_STATE = 29366, -- Kortz secondary target state
|
||||
KCLIVESL = 65159, -- Kortz team lives
|
||||
KCIf1 = 57251,
|
||||
KCIf2 = 59027,
|
||||
|
||||
AGFl1 = 56505, -- Agency instant finish 1
|
||||
AGFl2 = 58281,
|
||||
ASIFl1 = 56505, -- Auto Shop instant finish 1
|
||||
ASIFl2 = 58281,
|
||||
ASRBl = 418, -- Auto Shop planning reload
|
||||
SYRl1 = 547, -- Salvage Yard planning reload
|
||||
HGGs1 = 20230, -- fmmc_launcher heist type
|
||||
HGGs2 = 20211, -- fmmc_launcher minimum players
|
||||
IHPB = 56504,
|
||||
IHPL = 58281,
|
||||
NLCl = 267, -- nightclub cutscene state
|
||||
|
||||
slots_random_results_table = 1381,
|
||||
prize_wheel_win_state = 311,
|
||||
prize_wheel_prize = 14,
|
||||
prize_wheel_prize_state = 45,
|
||||
SMC1 = 577,
|
||||
SMC2 = 583,
|
||||
SMC3 = 1160,
|
||||
SMC4 = 631,
|
||||
SMC5 = 1171,
|
||||
SMC6 = 591,
|
||||
SMC7 = 772,
|
||||
SMC8 = 773,
|
||||
SMC9 = 639,
|
||||
SMC10 = 635,
|
||||
SMC11 = 825,
|
||||
SMC12 = 826,
|
||||
SCRIPT_STATE = 2,
|
||||
GUNCLUB_LIVERY = 955,
|
||||
}
|
||||
|
||||
function locals.KORTZ_DATA_CRACK(index)
|
||||
return locals.KCDCL + 1 + (index * 4)
|
||||
end
|
||||
function locals.KORTZ_ACCESS_CODE(index)
|
||||
return locals.KCAC_BASE + (index * 2)
|
||||
end
|
||||
function locals.KORTZ_CUT_GLASS(index)
|
||||
return locals.KCCGL_BASE + (index * 13) + locals.KCCGL_OFFSET
|
||||
end
|
||||
|
||||
local scripts = {
|
||||
FMC = "fm_mission_controller",
|
||||
FMMCL = "fmmc_launcher",
|
||||
FMC2020 = "fm_mission_controller_2020",
|
||||
HIP = "heist_island_planning",
|
||||
CASINO_SLOTS = "casino_slots",
|
||||
CASINO_LUCKY_WHEEL = "casino_lucky_wheel",
|
||||
GUNCLUB_SHOP = "gunclub_shop",
|
||||
}
|
||||
|
||||
return {edition = "Enhanced", build = "1158.13", globals = globals, locals = locals, scripts = scripts}
|
||||
@@ -0,0 +1,303 @@
|
||||
-- GTA V Legacy build 3889 globals and script locals used by Ultimate Menu.
|
||||
-- Update addresses here when a game build changes; feature code should not
|
||||
-- contain raw global or local addresses.
|
||||
|
||||
local FREEMODE_TUNABLES = 262145
|
||||
|
||||
local globals = {
|
||||
FMg = FREEMODE_TUNABLES, -- freemode tunables base
|
||||
CSg1 = 1575046, -- session type
|
||||
CSg2 = 1574589, -- session switch
|
||||
CSg3 = 1574589 + 2, -- session quit
|
||||
|
||||
ACg1 = 1935929 + 1 + 1, -- apartment cut: player 1
|
||||
ACg2 = 1935929 + 1 + 2, -- apartment cut: player 2
|
||||
ACg3 = 1935929 + 1 + 3, -- apartment cut: player 3
|
||||
ACg4 = 1935929 + 1 + 4, -- apartment cut: player 4
|
||||
ACg5 = 1937897 + 3008 + 1, -- apartment local-player cut
|
||||
ACg6 = 1937897 + 3008 + 2, -- apartment cut: player 2 (actual)
|
||||
ACg7 = 1937897 + 3008 + 3, -- apartment cut: player 3 (actual)
|
||||
ACg8 = 1937897 + 3008 + 4, -- apartment cut: player 4 (actual)
|
||||
AUAJg1 = FREEMODE_TUNABLES + 9184, -- Fleeca job root hash
|
||||
AUAJg2 = FREEMODE_TUNABLES + 9189, -- Prison Break root hash
|
||||
AUAJg3 = FREEMODE_TUNABLES + 9196, -- Humane Labs root hash
|
||||
AUAJg4 = FREEMODE_TUNABLES + 9202, -- Series A root hash
|
||||
AUAJg5 = FREEMODE_TUNABLES + 9208, -- Pacific Standard root hash
|
||||
ACDg = 2686119, -- apartment cooldown/player-data base
|
||||
AFRg = 2658293, -- apartment force ready global
|
||||
AHDg = 4718592 + 3771, -- apartment heist difficulty
|
||||
|
||||
DCCg1 = 1972483 + 1497 + 736 + 92 + 1, -- casino cut: player 1
|
||||
DCCg2 = 1972483 + 1497 + 736 + 92 + 2, -- casino cut: player 2
|
||||
DCCg3 = 1972483 + 1497 + 736 + 92 + 3, -- casino cut: player 3
|
||||
DCCg4 = 1972483 + 1497 + 736 + 92 + 4, -- casino cut: player 4
|
||||
CFRg = 1976846, -- casino force ready global
|
||||
CPCg1 = 1979291 + 831 + 56 + 1, -- Cayo cut: player 1
|
||||
CPCg2 = 1979291 + 831 + 56 + 2, -- Cayo cut: player 2
|
||||
CPCg3 = 1979291 + 831 + 56 + 3, -- Cayo cut: player 3
|
||||
CPCg4 = 1979291 + 831 + 56 + 4, -- Cayo cut: player 4
|
||||
CYFRg = 1980404, -- Cayo force ready global
|
||||
DCg1 = 1968511 + 812 + 50 + 1, -- Doomsday cut: player 1
|
||||
DCg2 = 1968511 + 812 + 50 + 2, -- Doomsday cut: player 2
|
||||
DCg3 = 1968511 + 812 + 50 + 3, -- Doomsday cut: player 3
|
||||
DCg4 = 1968511 + 812 + 50 + 4, -- Doomsday cut: player 4
|
||||
DDFRg = 1882652, -- Doomsday force ready global
|
||||
GCg = 2686119 + 6791, -- generic heist cut multiplier
|
||||
|
||||
KCBGL = FREEMODE_TUNABLES + 37438, -- Kortz bag size
|
||||
KCWMG = FREEMODE_TUNABLES + 37600, -- Kortz weekly multiplier
|
||||
KCCDG = FREEMODE_TUNABLES + 37503, -- Kortz normal cooldown
|
||||
KCCD2G = FREEMODE_TUNABLES + 37504, -- Kortz hard cooldown
|
||||
KCLDG = 1935234, -- Kortz lasers disabled
|
||||
KCSECONDARY_BASE = 4980736 + 1 + 29174, -- Kortz secondary-target array
|
||||
KCPAYOUT_BASE = FREEMODE_TUNABLES + 37405, -- Kortz primary-target payouts
|
||||
|
||||
HGLs1 = 4718592 + 3769, -- heist launch state 1
|
||||
HGLs2 = 4718592 + 3772, -- heist launch state 2
|
||||
HGLs3 = 4718592 + 3773, -- heist launch state 3
|
||||
HGLs4 = 4718592 + 190163 + 1, -- heist launch state 4
|
||||
|
||||
SNOW = FREEMODE_TUNABLES + 4413,
|
||||
halloweatherAddress = FREEMODE_TUNABLES + 32247,
|
||||
yetihuntAddress = FREEMODE_TUNABLES + 35041,
|
||||
TRICK_OR_TREAT = FREEMODE_TUNABLES + 32173,
|
||||
SNOWMEN_COLLECTIBLES = FREEMODE_TUNABLES + 33317,
|
||||
GVADg = FREEMODE_TUNABLES + 33392, -- Gun Van armour discount
|
||||
GVWDg = FREEMODE_TUNABLES + 33373, -- Gun Van weapon discount
|
||||
GVTDg = FREEMODE_TUNABLES + 33384, -- Gun Van throwable discount
|
||||
CCBL0 = FREEMODE_TUNABLES + 26623, -- casino chip buy limit 1
|
||||
CCBL1 = FREEMODE_TUNABLES + 26624, -- casino chip buy limit 2
|
||||
CPBg = FREEMODE_TUNABLES + 29300, -- Cayo bag size
|
||||
PSV = FREEMODE_TUNABLES + 29552, -- Panther Statue value
|
||||
PDIAMOND = FREEMODE_TUNABLES + 29550, -- Pink Diamond value
|
||||
BB = FREEMODE_TUNABLES + 29549, -- Bearer Bonds value
|
||||
RN = FREEMODE_TUNABLES + 29548, -- Ruby Necklace value
|
||||
TEQUILA = FREEMODE_TUNABLES + 29547, -- Tequila value
|
||||
|
||||
AG = 4525223 + 1, -- achievement unlock selector
|
||||
current_objectives_global = 2359296,
|
||||
weekly_objectives_global = 2732111,
|
||||
objectives_state_global = 1574746,
|
||||
CARGO1 = FREEMODE_TUNABLES + 22581,
|
||||
CARGO2 = FREEMODE_TUNABLES + 22582,
|
||||
CARGO3 = FREEMODE_TUNABLES + 22583,
|
||||
CARGO4 = FREEMODE_TUNABLES + 22584,
|
||||
CARGO5 = FREEMODE_TUNABLES + 22585,
|
||||
CARGO6 = FREEMODE_TUNABLES + 22586,
|
||||
CARGO7 = FREEMODE_TUNABLES + 22587,
|
||||
CARGO8 = FREEMODE_TUNABLES + 22588,
|
||||
CARGO9 = FREEMODE_TUNABLES + 22589,
|
||||
CEO1 = FREEMODE_TUNABLES + 15821, -- special cargo sale threshold
|
||||
CEO2 = FREEMODE_TUNABLES + 15588, -- special cargo buy cooldown
|
||||
CEO3 = FREEMODE_TUNABLES + 15589, -- special cargo sell cooldown
|
||||
SafeCapacity = 23769, -- nightclub safe capacity tunable offset
|
||||
IncomeStart = 23746, -- nightclub income range start
|
||||
IncomeEnd = 23765, -- nightclub income range end
|
||||
main_global = 1673807, -- YimResupplier business-state base
|
||||
|
||||
TRANSACTION_ERROR_GLOBAL_1 = 4516981,
|
||||
TRANSACTION_ERROR_GLOBAL_2 = 4516982,
|
||||
TRANSACTION_ERROR_GLOBAL_3 = 4516983,
|
||||
GUN_VAN_LOCATION_GLOBAL = 2652581 + 2706,
|
||||
PLAYER_RP_MULTIPLIER_GLOBAL = FREEMODE_TUNABLES + 1,
|
||||
AIR_CARGO_RP_MULTIPLIER_GLOBAL = FREEMODE_TUNABLES + 22564,
|
||||
NIGHTCLUB_CASH_BONUS_1 = FREEMODE_TUNABLES + 17415,
|
||||
NIGHTCLUB_CASH_BONUS_2 = FREEMODE_TUNABLES + 17421,
|
||||
NIGHTCLUB_CASH_BASE = FREEMODE_TUNABLES + 17409,
|
||||
NIGHTCLUB_COKE_BONUS_1 = FREEMODE_TUNABLES + 17416,
|
||||
NIGHTCLUB_COKE_BONUS_2 = FREEMODE_TUNABLES + 17422,
|
||||
NIGHTCLUB_COKE_BASE = FREEMODE_TUNABLES + 17410,
|
||||
NIGHTCLUB_METH_BONUS_1 = FREEMODE_TUNABLES + 17417,
|
||||
NIGHTCLUB_METH_BONUS_2 = FREEMODE_TUNABLES + 17423,
|
||||
NIGHTCLUB_METH_BASE = FREEMODE_TUNABLES + 17411,
|
||||
NIGHTCLUB_WEED_BONUS_1 = FREEMODE_TUNABLES + 17418,
|
||||
NIGHTCLUB_WEED_BONUS_2 = FREEMODE_TUNABLES + 17424,
|
||||
NIGHTCLUB_WEED_BASE = FREEMODE_TUNABLES + 17412,
|
||||
NIGHTCLUB_DOCUMENTS_BONUS_1 = FREEMODE_TUNABLES + 17414,
|
||||
NIGHTCLUB_DOCUMENTS_BONUS_2 = FREEMODE_TUNABLES + 17420,
|
||||
NIGHTCLUB_DOCUMENTS_BASE = FREEMODE_TUNABLES + 17408,
|
||||
NIGHTCLUB_BUNKER_BONUS_1 = FREEMODE_TUNABLES + 21345,
|
||||
NIGHTCLUB_BUNKER_BONUS_2 = FREEMODE_TUNABLES + 21344,
|
||||
NIGHTCLUB_BUNKER_BASE = FREEMODE_TUNABLES + 21343,
|
||||
NIGHTCLUB_ACID_BONUS = FREEMODE_TUNABLES + 17419,
|
||||
NIGHTCLUB_ACID_BASE = FREEMODE_TUNABLES + 17413,
|
||||
}
|
||||
|
||||
function globals.DAILY_OBJECTIVE_CURRENT(index)
|
||||
return globals.current_objectives_global + 1 + 681 + 4248 + 1 + (index * 3)
|
||||
end
|
||||
function globals.DAILY_OBJECTIVE_STATE(index)
|
||||
return globals.objectives_state_global + 1 + 1 + index
|
||||
end
|
||||
function globals.WEEKLY_OBJECTIVE_STATE()
|
||||
return globals.weekly_objectives_global + 1 + 1
|
||||
end
|
||||
function globals.WEEKLY_OBJECTIVE_CURRENT()
|
||||
return globals.weekly_objectives_global + 1 + 2
|
||||
end
|
||||
function globals.NIGHTCLUB_SAFE_VALUE(player_id)
|
||||
return 1845298 + player_id + 260 + 364 + 5
|
||||
end
|
||||
function globals.APARTMENT_COOLDOWN(player_id)
|
||||
return globals.ACDg + 1 + (player_id * 77) + 76
|
||||
end
|
||||
function globals.APARTMENT_HEIST_TYPE(player_id)
|
||||
return globals.ACDg + (player_id * 77) + 24 + 2
|
||||
end
|
||||
function globals.HEIST_SOLO_LAUNCH(heist_type)
|
||||
return 794989 + 4 + 1 + (heist_type * 95) + 75
|
||||
end
|
||||
function globals.APARTMENT_FORCE_READY(player_index)
|
||||
return 2658293 + 1 + ((player_index - 1) * 468) + 270
|
||||
end
|
||||
function globals.LEGACY_HEIST_FORCE_READY(player_index)
|
||||
return 1882572 + 1 + ((player_index - 1) * 315) + 43 + 11 + player_index
|
||||
end
|
||||
function globals.CAYO_FORCE_READY(player_index)
|
||||
return 1979868 + 1 + ((player_index - 1) * 27) + 7 + player_index
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_TARGET(player_index, offset)
|
||||
return globals.KCSECONDARY_BASE + (player_index * 333) + offset
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_PRIMARY(player_index)
|
||||
return globals.KORTZ_SECONDARY_TARGET(player_index, 68)
|
||||
end
|
||||
function globals.KORTZ_SECONDARY_SECONDARY(player_index)
|
||||
return globals.KORTZ_SECONDARY_TARGET(player_index, 143)
|
||||
end
|
||||
function globals.KORTZ_PAYOUT(target_index)
|
||||
return globals.KCPAYOUT_BASE + target_index + 1
|
||||
end
|
||||
function globals.YIM_RESUPPLIER_SLOT(slot_index)
|
||||
return globals.main_global + slot_index + 1
|
||||
end
|
||||
|
||||
local locals = {
|
||||
AIFl1 = 19808, -- apartment instant finish 1
|
||||
AIFl2 = 19808 + 1062,
|
||||
AIFl3 = 19808 + 1740 + 1,
|
||||
AIFl4 = 19808 + 2686,
|
||||
AIFl5 = 28722 + 1,
|
||||
AIFl6 = 31981 + 1 + 68,
|
||||
AFHl = 11837 + 24, -- Fleeca hack
|
||||
AFDl = 10125 + 11, -- Fleeca drill
|
||||
AFPl = 9831, -- Pacific hack
|
||||
AHSo = 19808 + 2, -- apartment checkpoint bitset
|
||||
AHLIVESL = 26234 + 1325 + 1, -- apartment team lives
|
||||
|
||||
DCRBl = 217, -- casino planning reload
|
||||
DCAg = 10311, -- casino autograbber state
|
||||
DCAs = 10311 + 14, -- casino autograbber speed
|
||||
DCFHl = 54118, -- casino fingerprint hack
|
||||
DCKHl = 55188, -- casino keypad hack
|
||||
DCDVDl1 = 10125 + 7, -- casino vault drill result
|
||||
DCDVDl2 = 10125 + 37, -- casino vault drill progress
|
||||
DCLIVESL = 26234 + 1325 + 1, -- casino team lives
|
||||
DCXf1 = 19808,
|
||||
DCXf2 = 19808 + 1062,
|
||||
DCXf3 = 19808 + 1740 + 1,
|
||||
DCXf4 = 19808 + 2686,
|
||||
DCXf5 = 28722 + 1,
|
||||
DCXf6 = 31981 + 1 + 68,
|
||||
|
||||
CPRSl = 1578, -- Cayo planning reload
|
||||
CPFHl = 26217, -- Cayo fingerprint hack
|
||||
CPPCCl = 32349 + 3, -- Cayo plasma cutter
|
||||
CPSTCl = 31109, -- Cayo drainage pipe
|
||||
CPXf1 = 56070,
|
||||
CPXf2 = 56070 + 1776 + 1,
|
||||
CPLIVESL = 62851 + 1109 + 1, -- Cayo team lives
|
||||
CPMantrap1 = 68939 + (0 * 293) + 236, -- Cayo solo mantrap dual keycard 1
|
||||
CPMantrap2 = 20813, -- Cayo solo mantrap dual keycard 2
|
||||
CPSecondary = 28971 + 11, -- Cayo secondary target state
|
||||
CPLootTake = 59552 + 1376 + 60, -- Cayo loot take
|
||||
|
||||
DDSHl = 1312 + 135, -- Doomsday scenario hack
|
||||
DDIF1 = 19808,
|
||||
DDIF2 = 19808 + 1740 + 1,
|
||||
DDIF3 = 28722 + 1,
|
||||
DDIF4 = 31981 + 1 + 68,
|
||||
DDIF5 = 31981 + 97,
|
||||
DDIF6 = 19808 + 1062, -- Doomsday Act III passed flag
|
||||
DDLIVESL = 26234 + 1325 + 1, -- Doomsday team lives
|
||||
|
||||
KCBRL = 597, -- Kortz planning reload
|
||||
KCDCL = 1386, -- Kortz data crack base
|
||||
KCFHL = 26464, -- Kortz fingerprint hack
|
||||
KCAC_BASE = 32416 + 1, -- Kortz access-code base
|
||||
KCLGL = 70472, -- Kortz lasers
|
||||
KCVLL = 27512, -- Kortz vault door
|
||||
KCLDIF1 = 1058, -- Kortz lasers difficulty 1
|
||||
KCLDIF2 = 1059, -- Kortz lasers difficulty 2
|
||||
KCNoDmg = 1060, -- Kortz no-damage lasers
|
||||
KCLootTake = 60203 + 1376 + 60, -- Kortz loot take
|
||||
KCCGL_BASE = 32453 + 1, -- Kortz cut-glass base
|
||||
KCCGL_OFFSET = 3,
|
||||
KCPT_STATE = 28953 + 11, -- Kortz primary target state
|
||||
KCST_STATE = 28953 + 11, -- Kortz secondary target state
|
||||
KCLIVESL = 63515 + 1109 + 1, -- Kortz team lives
|
||||
KCIf1 = 56716 + 1,
|
||||
KCIf2 = 56716 + 1776 + 1,
|
||||
|
||||
AGFl1 = 56070 + 1, -- Agency instant finish 1
|
||||
AGFl2 = 56070 + 1776 + 1,
|
||||
ASIFl1 = 56070 + 1, -- Auto Shop instant finish 1
|
||||
ASIFl2 = 56070 + 1776 + 1,
|
||||
ASRBl = 416, -- Auto Shop planning reload
|
||||
SYRl1 = 545, -- Salvage Yard planning reload
|
||||
LSAIFl1 = 7879 + 1306, -- LSA operations instant finish 1
|
||||
LSAIFl2 = 7741 + 1, -- LSA operations instant finish 2
|
||||
HGGs1 = 20194 + 34, -- fmmc_launcher heist type
|
||||
HGGs2 = 20194 + 15, -- fmmc_launcher minimum players
|
||||
IHPB = 56070,
|
||||
IHPL = 56070 + 1776 + 1,
|
||||
NLCl = 213 + 32 + 19 + 1, -- nightclub cutscene state
|
||||
|
||||
slots_random_results_table = 1379,
|
||||
prize_wheel_win_state = 309,
|
||||
prize_wheel_prize = 14,
|
||||
prize_wheel_prize_state = 45,
|
||||
SMC1 = 574 + 1,
|
||||
SMC2 = 574 + 7,
|
||||
SMC3 = 574 + 584,
|
||||
SMC4 = 574 + 55,
|
||||
SMC5 = 574 + 595,
|
||||
SMC6 = 589,
|
||||
SMC7 = 770,
|
||||
SMC8 = 771,
|
||||
SMC9 = 632 + 5,
|
||||
SMC10 = 632 + 1,
|
||||
SMC11 = 632 + 191,
|
||||
SMC12 = 632 + 192,
|
||||
SCRIPT_STATE = 2,
|
||||
GUNCLUB_LIVERY = 206 + 747,
|
||||
}
|
||||
|
||||
function locals.KORTZ_DATA_CRACK(index)
|
||||
return locals.KCDCL + 1 + (index * 4)
|
||||
end
|
||||
function locals.KORTZ_ACCESS_CODE(index)
|
||||
return locals.KCAC_BASE + (index * 2)
|
||||
end
|
||||
function locals.KORTZ_CUT_GLASS(index)
|
||||
return locals.KCCGL_BASE + (index * 13) + locals.KCCGL_OFFSET
|
||||
end
|
||||
|
||||
local scripts = {
|
||||
FMC = "fm_mission_controller",
|
||||
FMMCL = "fmmc_launcher",
|
||||
FMC2020 = "fm_mission_controller_2020",
|
||||
FMCV3 = "fm_mission_controller_v3",
|
||||
FMMLASERS = "fmmc_lasers",
|
||||
HIP = "heist_island_planning",
|
||||
CASPL = "gb_casino_heist_planning",
|
||||
GANGPL = "gb_gang_ops_planning",
|
||||
KORTZPL = "kortz_planning",
|
||||
TUNERPL = "tuner_planning",
|
||||
SMUGOPS = "fm_content_smuggler_ops",
|
||||
CASINO_SLOTS = "casino_slots",
|
||||
CASINO_LUCKY_WHEEL = "casino_lucky_wheel",
|
||||
GUNCLUB_SHOP = "gunclub_shop",
|
||||
}
|
||||
|
||||
return {edition = "Legacy", build = "3889", globals = globals, locals = locals, scripts = scripts}
|
||||
@@ -0,0 +1,138 @@
|
||||
-- Companion information panel for the Nenyoo edition of Ultimate Menu.
|
||||
-- The menu adapter publishes text on the script thread. Draw only the
|
||||
-- published strings here; overlay.on_draw runs on Nenyoo's render thread.
|
||||
return function(compat)
|
||||
local scroll_by_page = {}
|
||||
local last_page
|
||||
|
||||
local function clamp(value, low, high)
|
||||
return math.max(low, math.min(high, value))
|
||||
end
|
||||
|
||||
local function wrap_paragraph(value, max_width, output, heading, color)
|
||||
local line = ""
|
||||
for word in value:gmatch("%S+") do
|
||||
local candidate = line == "" and word or line .. " " .. word
|
||||
if line ~= "" and text.width(font.small, candidate) > max_width then
|
||||
output[#output + 1] = {text = line, heading = heading, color = color}
|
||||
line = word
|
||||
else
|
||||
line = candidate
|
||||
end
|
||||
end
|
||||
if line ~= "" then output[#output + 1] = {text = line, heading = heading, color = color} end
|
||||
end
|
||||
|
||||
local function make_lines(rows, max_width)
|
||||
local lines = {}
|
||||
for _, row in ipairs(rows) do
|
||||
local value = tostring(row.text or ""):gsub("\r", "")
|
||||
if value == "" then
|
||||
lines[#lines + 1] = {gap = 8}
|
||||
else
|
||||
local compact = value:gsub("%s+", " "):match("^%s*(.-)%s*$")
|
||||
local heading = #compact <= 38 and (compact:sub(-1) == ":" or compact == "Preps")
|
||||
for paragraph in (value .. "\n"):gmatch("(.-)\n") do
|
||||
if paragraph:match("%S") then wrap_paragraph(paragraph, max_width, lines, heading, row.color)
|
||||
else lines[#lines + 1] = {gap = 8} end
|
||||
end
|
||||
lines[#lines + 1] = {gap = heading and 7 or 11}
|
||||
end
|
||||
if row.tooltip then
|
||||
wrap_paragraph(row.tooltip:gsub("%s+", " "), max_width, lines, false, nil)
|
||||
lines[#lines + 1] = {gap = 11}
|
||||
end
|
||||
end
|
||||
while #lines > 0 and lines[#lines].gap do lines[#lines] = nil end
|
||||
return lines
|
||||
end
|
||||
|
||||
overlay.on_draw("ultimate_menu_information", function()
|
||||
if not menu.is_visible() then return end
|
||||
local id = menu.page_id()
|
||||
local info = compat.info_for_page(id)
|
||||
if not info or #info.rows == 0 then return end
|
||||
local sw, sh = ctx.screen_w(), ctx.screen_h()
|
||||
local bx, by, bw = menu.bounds()
|
||||
if not bw or bw <= 0 then return end
|
||||
|
||||
local gap, pad, header_h = 14, 14, 36
|
||||
local width = math.min(420, math.max(280, sw * 0.30))
|
||||
local side = bx + bw + gap + width <= sw - 8 or bx - gap - width >= 8
|
||||
if not side then width = math.min(600, sw - 16) end
|
||||
local x
|
||||
if side and bx + bw + gap + width <= sw - 8 then x = bx + bw + gap
|
||||
elseif side then x = bx - gap - width
|
||||
else x = clamp(bx + (bw - width) * 0.5, 8, sw - width - 8) end
|
||||
|
||||
local lines = make_lines(info.rows, width - pad * 2)
|
||||
if #lines == 0 then return end
|
||||
local line_h = text.height(font.small) + 4
|
||||
local content_h = 0
|
||||
for _, line in ipairs(lines) do content_h = content_h + (line.gap or line_h) end
|
||||
local desired_h = header_h + pad * 2 + content_h
|
||||
local height = math.min(desired_h, sh - 16, 650)
|
||||
local y = clamp(by, 8, sh - height - 8)
|
||||
if not side then
|
||||
local _, content_y, _, content_height = menu.content_rect()
|
||||
local below = content_y + content_height + 56
|
||||
local space_below = sh - below - 8
|
||||
if content_height > 0 and space_below >= 170 then
|
||||
y = below
|
||||
height = math.min(height, space_below)
|
||||
elseif by >= 180 then
|
||||
height = math.min(height, by - 16)
|
||||
y = by - height - 8
|
||||
end
|
||||
end
|
||||
local viewport_h = height - header_h - pad * 2
|
||||
if viewport_h <= line_h then return end
|
||||
|
||||
if last_page ~= id then scroll_by_page[id] = 0; last_page = id end
|
||||
local max_scroll = math.max(0, content_h - viewport_h)
|
||||
local scroll = clamp(scroll_by_page[id] or 0, 0, max_scroll)
|
||||
local mx, my = input.mouse_x(), input.mouse_y()
|
||||
if mx >= x and mx <= x + width and my >= y and my <= y + height then
|
||||
scroll = clamp(scroll - input.mouse_wheel() * line_h * 3, 0, max_scroll)
|
||||
end
|
||||
scroll_by_page[id] = scroll
|
||||
|
||||
local ar, ag, ab = theme.accent()
|
||||
draw.rect(x, y, x + width, y + height, 12, 15, 22, 232, 7)
|
||||
draw.rect(x, y, x + width, y + header_h, 24, 32, 44, 245, 7)
|
||||
draw.rect(x, y + header_h - 2, x + width, y + header_h, ar, ag, ab, 255)
|
||||
draw.rect_outline(x, y, x + width, y + height, ar, ag, ab, 125, 7)
|
||||
text.draw_ellipsis(font.item, x + pad, y + (header_h - text.height(font.item)) * 0.5,
|
||||
240, 245, 250, 255, info.title, width - pad * 2)
|
||||
|
||||
local top = y + header_h + pad
|
||||
draw.push_clip(x + pad, top, x + width - pad, top + viewport_h)
|
||||
local cursor = top - scroll
|
||||
for _, line in ipairs(lines) do
|
||||
if line.gap then cursor = cursor + line.gap
|
||||
else
|
||||
if cursor + line_h >= top and cursor <= top + viewport_h then
|
||||
local r, g, b = 220, 228, 238
|
||||
if line.heading then r, g, b = ar, ag, ab end
|
||||
if line.color then
|
||||
local function channel(value)
|
||||
value = value or 1
|
||||
return clamp(math.floor((value <= 1 and value * 255 or value) + 0.5), 0, 255)
|
||||
end
|
||||
r, g, b = channel(line.color[1]), channel(line.color[2]), channel(line.color[3])
|
||||
end
|
||||
text.draw(font.small, x + pad, cursor, r, g, b, 245, line.text)
|
||||
end
|
||||
cursor = cursor + line_h
|
||||
end
|
||||
end
|
||||
draw.pop_clip()
|
||||
if max_scroll > 0 then
|
||||
local track_top, track_height = top, viewport_h
|
||||
local thumb_h = math.max(22, track_height * viewport_h / content_h)
|
||||
local thumb_y = track_top + (track_height - thumb_h) * scroll / max_scroll
|
||||
draw.rect(x + width - 5, thumb_y, x + width - 2, thumb_y + thumb_h,
|
||||
ar, ag, ab, 190, 2)
|
||||
end
|
||||
end)
|
||||
end
|
||||
@@ -0,0 +1,665 @@
|
||||
-- YimMenu API compatibility for Ultimate Menu on Nenyoo.
|
||||
-- Loaded by the Nenyoo entry script on Nenyoo's script thread.
|
||||
local nv = native_invoker
|
||||
local stat_out = memory.alloc_int()
|
||||
local float_out = memory.alloc_float()
|
||||
local scan_context
|
||||
|
||||
local function invoke(hash, args, result)
|
||||
nv.begin_call()
|
||||
for _, arg in ipairs(args) do
|
||||
local kind, value = arg[1], arg[2]
|
||||
if kind == "float" then nv.push_arg_float(value)
|
||||
elseif kind == "bool" then nv.push_arg_bool(value)
|
||||
elseif kind == "ptr" then nv.push_arg_pointer(value)
|
||||
else nv.push_arg_int(value) end
|
||||
end
|
||||
nv.end_call(hash)
|
||||
if result == "bool" then return nv.get_return_value_bool() end
|
||||
if result == "int" then return nv.get_return_value_int() end
|
||||
if result == "float" then return nv.get_return_value_float() end
|
||||
if result == "vector3" then return nv.get_return_value_vector3() end
|
||||
end
|
||||
|
||||
local function stat_hash(name) return util.joaat(name) end
|
||||
|
||||
stats = {}
|
||||
function stats.get_int(name)
|
||||
local ok = invoke("767FBC2AC802EF3D", {{"int", stat_hash(name)}, {"ptr", stat_out}, {"int", -1}}, "bool")
|
||||
return ok and memory.read_int(stat_out) or 0
|
||||
end
|
||||
function stats.get_float(name)
|
||||
local ok = invoke("D7AE6C9C9C6AC54C", {{"int", stat_hash(name)}, {"ptr", float_out}, {"int", -1}}, "bool")
|
||||
return ok and memory.read_float(float_out) or 0.0
|
||||
end
|
||||
function stats.get_bool(name)
|
||||
local ok = invoke("11B5E6D2AE73F48E", {{"int", stat_hash(name)}, {"ptr", stat_out}, {"int", -1}}, "bool")
|
||||
return ok and memory.read_bool(stat_out) or false
|
||||
end
|
||||
function stats.set_int(name, value)
|
||||
if scan_context then return false end
|
||||
return invoke("B3271D7AB655B441", {{"int", stat_hash(name)}, {"int", value}, {"bool", true}}, "bool")
|
||||
end
|
||||
function stats.set_float(name, value)
|
||||
if scan_context then return false end
|
||||
return invoke("4851997F37FE9B3C", {{"int", stat_hash(name)}, {"float", value}, {"bool", true}}, "bool")
|
||||
end
|
||||
function stats.set_bool(name, value)
|
||||
if scan_context then return false end
|
||||
return invoke("4B33C4243DE0C432", {{"int", stat_hash(name)}, {"bool", value}, {"bool", true}}, "bool")
|
||||
end
|
||||
function stats.get_masked_int(name, offset, width)
|
||||
local ok = invoke("655185A06D9EEAAB", {
|
||||
{"int", stat_hash(name)}, {"ptr", stat_out}, {"int", offset}, {"int", width}, {"int", -1},
|
||||
}, "bool")
|
||||
return ok and memory.read_int(stat_out) or 0
|
||||
end
|
||||
function stats.set_masked_int(name, value, offset, width)
|
||||
if scan_context then return false end
|
||||
return invoke("7BBB1B54583ED410", {
|
||||
{"int", stat_hash(name)}, {"int", value}, {"int", offset}, {"int", width}, {"bool", true},
|
||||
}, "bool")
|
||||
end
|
||||
function stats.set_bool_masked(name, value, bit)
|
||||
if scan_context then return false end
|
||||
return invoke("5BC62EC1937B9E5B", {
|
||||
{"int", stat_hash(name)}, {"bool", value}, {"int", bit}, {"bool", true},
|
||||
}, "bool")
|
||||
end
|
||||
local function character_slot() return stats.get_int("MPPLY_LAST_MP_CHAR") end
|
||||
function stats.set_packed_stat_bool(index, value)
|
||||
if scan_context then return false end
|
||||
invoke("DB8A58AEAA67CD07", {{"int", index}, {"bool", value}, {"int", character_slot()}})
|
||||
end
|
||||
function stats.set_packed_stat_int(index, value)
|
||||
if scan_context then return false end
|
||||
invoke("1581503AE529CD2E", {{"int", index}, {"int", value}, {"int", character_slot()}})
|
||||
end
|
||||
|
||||
globals = {}
|
||||
local function global_addr(index)
|
||||
local addr = memory.script_global(index)
|
||||
return addr and addr ~= 0 and addr or nil
|
||||
end
|
||||
function globals.get_int(index)
|
||||
local addr = global_addr(index)
|
||||
return addr and memory.read_int(addr) or 0
|
||||
end
|
||||
function globals.set_int(index, value)
|
||||
if scan_context then return false end
|
||||
local addr = global_addr(index)
|
||||
if addr then memory.write_int(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
function globals.set_float(index, value)
|
||||
if scan_context then return false end
|
||||
local addr = global_addr(index)
|
||||
if addr then memory.write_float(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
function globals.set_string(index, value, size)
|
||||
if scan_context then return false end
|
||||
local addr = global_addr(index)
|
||||
if not addr then return false end
|
||||
if memory.write_string then memory.write_string(addr, value or "") return true end
|
||||
return false
|
||||
end
|
||||
|
||||
locals = {}
|
||||
local function local_addr(script_name, index)
|
||||
local addr = memory.script_local(util.joaat(script_name), index)
|
||||
return addr and addr ~= 0 and addr or nil
|
||||
end
|
||||
function locals.get_int(script_name, index)
|
||||
local addr = local_addr(script_name, index)
|
||||
return addr and memory.read_int(addr) or 0
|
||||
end
|
||||
function locals.get_float(script_name, index)
|
||||
local addr = local_addr(script_name, index)
|
||||
return addr and memory.read_float(addr) or 0.0
|
||||
end
|
||||
function locals.set_int(script_name, index, value)
|
||||
if scan_context then return false end
|
||||
local addr = local_addr(script_name, index)
|
||||
if addr then memory.write_int(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
function locals.set_float(script_name, index, value)
|
||||
if scan_context then return false end
|
||||
local addr = local_addr(script_name, index)
|
||||
if addr then memory.write_float(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
|
||||
tunables = {}
|
||||
local function tunable_addr(name)
|
||||
local addr = memory.tunable(name)
|
||||
return addr and addr ~= 0 and addr or nil
|
||||
end
|
||||
function tunables.get_int(name)
|
||||
local addr = tunable_addr(name)
|
||||
return addr and memory.read_int(addr) or 0
|
||||
end
|
||||
function tunables.get_float(name)
|
||||
local addr = tunable_addr(name)
|
||||
return addr and memory.read_float(addr) or 0.0
|
||||
end
|
||||
function tunables.set_int(name, value)
|
||||
if scan_context then return false end
|
||||
local addr = tunable_addr(name)
|
||||
if addr then memory.write_int(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
function tunables.set_float(name, value)
|
||||
if scan_context then return false end
|
||||
local addr = tunable_addr(name)
|
||||
if addr then memory.write_float(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
function tunables.set_bool(name, value)
|
||||
if scan_context then return false end
|
||||
local addr = tunable_addr(name)
|
||||
if addr then memory.write_bool(addr, value); return true end
|
||||
return false
|
||||
end
|
||||
|
||||
network = network or {}
|
||||
function network.is_session_started()
|
||||
return invoke("9DE624D2FC4B603F", {}, "bool")
|
||||
end
|
||||
function network.force_script_host(name)
|
||||
if scan_context then return false end
|
||||
return __ny_request_script_host(name)
|
||||
end
|
||||
|
||||
-- Yim's generated native binding returns an output argument as a second Lua
|
||||
-- value. Nenyoo's generic named-native wrapper only returns the native result.
|
||||
-- Preserve the transaction ID required by Ultimate Menu's weapon unlocks.
|
||||
NETSHOPPING.NET_GAMESERVER_BEGIN_SERVICE = function(_, category, item, action, value, flags)
|
||||
if scan_context then return false, 0 end
|
||||
memory.write_int(stat_out, 0)
|
||||
local ok = invoke("3C5FD37B5499582E", {
|
||||
{"ptr", stat_out}, {"int", category}, {"int", item},
|
||||
{"int", action}, {"int", value}, {"int", flags},
|
||||
}, "bool")
|
||||
return ok, memory.read_int(stat_out)
|
||||
end
|
||||
NETSHOPPING.NET_GAMESERVER_BASKET_IS_ACTIVE = function()
|
||||
return invoke("A65568121DF2EA26", {}, "bool")
|
||||
end
|
||||
local disable_control_action = PAD.DISABLE_CONTROL_ACTION
|
||||
PAD.DISABLE_CONTROL_ACTION = function(...)
|
||||
if not scan_context then return disable_control_action(...) end
|
||||
end
|
||||
-- The generated native.call wrappers return one integer; blip coordinates are
|
||||
-- a three-float native result used by several Resupplier teleport actions.
|
||||
HUD.GET_BLIP_COORDS = function(blip)
|
||||
return invoke("586AFE3FF72D996E", {{"int", blip}}, "vector3")
|
||||
end
|
||||
HUD.DOES_BLIP_EXIST = function(blip)
|
||||
return invoke("A6DB27D19ECBB7DA", {{"int", blip}}, "bool")
|
||||
end
|
||||
ENTITY.DOES_ENTITY_EXIST = function(entity)
|
||||
return invoke("7239B21A38F536BA", {{"int", entity}}, "bool")
|
||||
end
|
||||
CUTSCENE.IS_CUTSCENE_PLAYING = function()
|
||||
return invoke("D3C2E180A40F031E", {}, "bool")
|
||||
end
|
||||
|
||||
joaat = util.joaat
|
||||
vec3 = {new = function(_, x, y, z) return {x = x, y = y, z = z} end}
|
||||
log = {
|
||||
info = function(message) if util.log then util.log(message) end end,
|
||||
warning = function(message) if util.log then util.log(message) end end,
|
||||
debug = function(message) if util.log then util.log(message) end end,
|
||||
}
|
||||
entities = {
|
||||
get_all_objects_as_handles = function()
|
||||
return __stand_get_all(false, false, true)
|
||||
end,
|
||||
}
|
||||
local function pattern_at(addr)
|
||||
return {
|
||||
is_null = function() return addr:is_null() end,
|
||||
add = function(_, offset) return pattern_at(addr:add(offset)) end,
|
||||
rip = function() return pattern_at(addr:rip()) end,
|
||||
get_string = function() return addr:read_string() end,
|
||||
}
|
||||
end
|
||||
memory.scan_pattern = function(pattern) return pattern_at(mem.scan_address(pattern)) end
|
||||
self = {
|
||||
get_id = function() return PLAYER.PLAYER_ID() end,
|
||||
get_ped = function() return PLAYER.PLAYER_PED_ID() end,
|
||||
}
|
||||
|
||||
weapons = {}
|
||||
local weapon_names = {}
|
||||
local weapon_catalog_loaded, next_weapon_lookup = false, 0
|
||||
local function readable_weapon_name(value)
|
||||
return value:gsub("^WEAPON_", ""):gsub("_", " "):lower():gsub("(%a)([%w']*)", function(first, rest)
|
||||
return first:upper() .. rest
|
||||
end)
|
||||
end
|
||||
function weapons.get_weapon_display_name(value)
|
||||
if value == nil or value == "" or value == 0 then return "" end
|
||||
if not weapon_catalog_loaded and __stand_get_weapons and os.clock() >= next_weapon_lookup then
|
||||
local catalog = __stand_get_weapons()
|
||||
weapon_catalog_loaded = #catalog > 0
|
||||
next_weapon_lookup = os.clock() + 1
|
||||
for _, entry in ipairs(catalog) do
|
||||
local name = entry.d or readable_weapon_name(entry.n)
|
||||
weapon_names[entry.n] = name
|
||||
weapon_names[util.joaat(entry.n)] = name
|
||||
end
|
||||
end
|
||||
if weapon_names[value] then return weapon_names[value] end
|
||||
if type(value) == "string" and value:match("^WEAPON_[%w_]+$") then
|
||||
return readable_weapon_name(value)
|
||||
end
|
||||
return ""
|
||||
end
|
||||
|
||||
local tab_methods = {}
|
||||
local imgui_sections = {}
|
||||
local info_pages = {}
|
||||
local tab_mt = {__index = tab_methods}
|
||||
local function page_id(ref)
|
||||
return util.joaat("Stand#" .. tostring(type(ref) == "table" and ref.id or ref))
|
||||
end
|
||||
local function info_page(ref, title)
|
||||
local id = page_id(ref)
|
||||
if not info_pages[id] then info_pages[id] = {title = title or "Information", static = {}} end
|
||||
return info_pages[id], id
|
||||
end
|
||||
local function text_input(parent, label, help, callback, value)
|
||||
if menu.text_input then
|
||||
return menu.text_input(parent, label, {}, help, callback, value)
|
||||
end
|
||||
return __smenu.text_input(type(parent) == "table" and parent.id or parent, label, {}, help, callback, value)
|
||||
end
|
||||
local function tab(ref, path)
|
||||
info_page(ref, path:match("([^/]+)$") or path)
|
||||
return setmetatable({ref = ref, path = path}, tab_mt)
|
||||
end
|
||||
|
||||
gui = {}
|
||||
function gui.get_tab(name)
|
||||
return tab(menu.list(menu.my_root(), name, {}, "Ultimate Menu for Nenyoo"), name)
|
||||
end
|
||||
function gui.show_message(title, message) util.toast(tostring(title) .. ": " .. tostring(message)) end
|
||||
gui.show_success = gui.show_message
|
||||
gui.show_error = gui.show_message
|
||||
function gui.add_notification(message) util.toast(tostring(message)) end
|
||||
|
||||
function tab_methods:add_tab(name)
|
||||
return tab(menu.list(self.ref, name, {}, ""), self.path .. "/" .. name)
|
||||
end
|
||||
function tab_methods:add_button(label, callback)
|
||||
return menu.action(self.ref, label, {}, "", callback)
|
||||
end
|
||||
function tab_methods:add_checkbox(label, default_value)
|
||||
local ref = menu.toggle(self.ref, label, {}, "", function() end, default_value or false)
|
||||
return {
|
||||
is_enabled = function() return menu.get_value(ref) and true or false end,
|
||||
set_enabled = function(_, value) menu.set_value(ref, value and true or false) end,
|
||||
}
|
||||
end
|
||||
function tab_methods:add_input_int(label, default_value)
|
||||
local obj = {value = default_value or 0}
|
||||
text_input(self.ref, label, "Enter an integer", function(text)
|
||||
local number = tonumber(text)
|
||||
if number then obj.value = math.tointeger(number) or math.floor(number) end
|
||||
end, tostring(obj.value))
|
||||
function obj:get_value() return self.value end
|
||||
function obj:set_value(value) self.value = value end
|
||||
return obj
|
||||
end
|
||||
function tab_methods:add_text(label)
|
||||
local page = info_page(self.ref)
|
||||
page.static[#page.static + 1] = {text = tostring(label or "")}
|
||||
end
|
||||
function tab_methods:add_separator() return menu.divider(self.ref, "") end
|
||||
function tab_methods:add_sameline() end
|
||||
function tab_methods:add_imgui(callback)
|
||||
imgui_sections[#imgui_sections + 1] = {parent = self.ref, path = self.path, callback = callback}
|
||||
end
|
||||
|
||||
script = script or {}
|
||||
-- The upstream script also calls script:sleep() directly from one menu action.
|
||||
function script.sleep(_, ms) util.yield(ms) end
|
||||
local fiber_script = {
|
||||
yield = function(_, ms) util.yield(ms) end,
|
||||
sleep = function(_, ms) util.yield(ms) end,
|
||||
}
|
||||
function script.register_looped(_, callback)
|
||||
return util.create_thread(function()
|
||||
while true do
|
||||
callback(fiber_script)
|
||||
util.yield()
|
||||
end
|
||||
end)
|
||||
end
|
||||
function script.run_in_fiber(callback)
|
||||
return util.create_thread(function() callback(fiber_script) end)
|
||||
end
|
||||
function script.execute_as_script(name, callback)
|
||||
if scan_context then return false end
|
||||
return __ny_execute_as_script(name, callback)
|
||||
end
|
||||
|
||||
local current_section, current_event, building, widget_index, widget_occurrences, separator_occurrences, parent_stack
|
||||
local function current_parent() return parent_stack[#parent_stack] end
|
||||
local function push_parent(ref) parent_stack[#parent_stack + 1] = ref end
|
||||
local function pop_parent() if #parent_stack > 1 then parent_stack[#parent_stack] = nil end end
|
||||
local function ancestors(extra)
|
||||
local out = {}
|
||||
for _, ref in ipairs(parent_stack) do
|
||||
out[type(ref) == "table" and ref.id or ref] = true
|
||||
end
|
||||
if extra then out[type(extra) == "table" and extra.id or extra] = true end
|
||||
return out
|
||||
end
|
||||
local function source_key(counters, fallback, label)
|
||||
for level = 3, 12 do
|
||||
local info = debug.getinfo(level, "Sl")
|
||||
if not info then break end
|
||||
if info.source and info.source:find("Ultimate_Menu_Legacy.lua", 1, true) then
|
||||
local line = info.currentline
|
||||
local key = tostring(line)
|
||||
if label ~= nil then key = key .. ":" .. tostring(label) end
|
||||
counters[key] = (counters[key] or 0) + 1
|
||||
return key .. ":" .. counters[key]
|
||||
end
|
||||
end
|
||||
return fallback
|
||||
end
|
||||
local function next_id(label)
|
||||
widget_index = widget_index + 1
|
||||
return source_key(widget_occurrences, tostring(widget_index), label)
|
||||
end
|
||||
local function label_for_menu(label)
|
||||
if label:sub(1, 2) ~= "##" then return label:gsub("##.*$", "") end
|
||||
if current_section.last_text and current_section.last_text ~= "" then return current_section.last_text end
|
||||
return label:sub(3):gsub("_", " "):gsub("(%l)(%u)", "%1 %2")
|
||||
end
|
||||
local function replay(section, event)
|
||||
current_section, current_event = section, event
|
||||
building, widget_index, widget_occurrences, separator_occurrences, parent_stack = false, 0, {}, {}, {section.parent}
|
||||
section.info_rows = {}
|
||||
section.callback()
|
||||
current_section, current_event, parent_stack = nil, nil, nil
|
||||
end
|
||||
local function event_for(id, value)
|
||||
return current_event and current_event.id == id and current_event.value == value
|
||||
end
|
||||
local function register_action(label, value)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
if not section.widget_refs[id] then
|
||||
local path = ancestors()
|
||||
section.widget_refs[id] = menu.action(current_parent(), label_for_menu(label), {}, "", function()
|
||||
replay(section, {id = id, value = value, ancestors = path})
|
||||
end)
|
||||
end
|
||||
section.last_ref = section.widget_refs[id]
|
||||
section.last_info_row = nil
|
||||
return event_for(id, value)
|
||||
end
|
||||
|
||||
ImGui = {}
|
||||
function ImGui.Button(label) return register_action(label, true) end
|
||||
function ImGui.Selectable(label) return register_action(label, true) end
|
||||
function ImGui.Checkbox(label, value)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
if not section.widget_refs[id] then
|
||||
local path = ancestors()
|
||||
section.widget_refs[id] = menu.toggle(current_parent(), label_for_menu(label), {}, "", function(on)
|
||||
replay(section, {id = id, value = on, ancestors = path})
|
||||
end, value and true or false)
|
||||
end
|
||||
section.last_ref = section.widget_refs[id]
|
||||
section.last_info_row = nil
|
||||
if current_event and current_event.id == id then return current_event.value, true end
|
||||
return value, false
|
||||
end
|
||||
local function numeric_input(label, value, as_float)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
if not section.widget_refs[id] then
|
||||
local path = ancestors()
|
||||
section.widget_refs[id] = text_input(current_parent(), label_for_menu(label), "Enter a number", function(text)
|
||||
local number = tonumber(text)
|
||||
if number then
|
||||
if not as_float then number = math.tointeger(number) or math.floor(number) end
|
||||
replay(section, {id = id, value = number, ancestors = path})
|
||||
end
|
||||
end, tostring(value or 0))
|
||||
end
|
||||
section.last_ref = section.widget_refs[id]
|
||||
section.last_info_row = nil
|
||||
if current_event and current_event.id == id then return current_event.value, true end
|
||||
return value, false
|
||||
end
|
||||
function ImGui.InputInt(label, value) return numeric_input(label, value, false) end
|
||||
function ImGui.InputFloat(label, value) return numeric_input(label, value, true) end
|
||||
function ImGui.DragInt(label, value) return numeric_input(label, value, false) end
|
||||
function ImGui.SliderInt(label, value, min_value, max_value)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
if not section.widget_refs[id] then
|
||||
local path = ancestors()
|
||||
section.widget_refs[id] = menu.slider(current_parent(), label_for_menu(label), {}, "", min_value, max_value, value, 1, function(selected)
|
||||
replay(section, {id = id, value = selected, ancestors = path})
|
||||
end)
|
||||
end
|
||||
section.last_ref = section.widget_refs[id]
|
||||
section.last_info_row = nil
|
||||
if current_event and current_event.id == id then return current_event.value, true end
|
||||
return value, false
|
||||
end
|
||||
function ImGui.InputText(label, value)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
if not section.widget_refs[id] then
|
||||
local path = ancestors()
|
||||
section.widget_refs[id] = text_input(current_parent(), label_for_menu(label), "", function(text)
|
||||
replay(section, {id = id, value = text, ancestors = path})
|
||||
end, value or "")
|
||||
end
|
||||
section.last_ref = section.widget_refs[id]
|
||||
section.last_info_row = nil
|
||||
if current_event and current_event.id == id then return current_event.value, true end
|
||||
return value, false
|
||||
end
|
||||
function ImGui.Combo(label, selected, choices, count)
|
||||
local id = next_id(label)
|
||||
local section = current_section
|
||||
local menu_label = label_for_menu(label)
|
||||
if not section.containers_by_id[id] then
|
||||
local list = menu.list(current_parent(), menu_label, {}, "")
|
||||
section.containers_by_id[id] = list
|
||||
section.containers[#section.containers + 1] = list
|
||||
local path = ancestors(list)
|
||||
for i = 1, count or #choices do
|
||||
local choice = choices[i] or tostring(i)
|
||||
local choice_index = i - 1
|
||||
menu.action(list, choice, {}, "", function()
|
||||
replay(section, {id = id, value = choice_index, ancestors = path})
|
||||
end)
|
||||
end
|
||||
end
|
||||
section.last_ref = section.containers_by_id[id]
|
||||
section.last_info_row = nil
|
||||
local current_choice = choices[(selected or 0) + 1]
|
||||
if current_choice then
|
||||
local display = menu_label .. ": " .. tostring(current_choice)
|
||||
if menu.get_menu_name(section.last_ref) ~= display then menu.set_menu_name(section.last_ref, display) end
|
||||
end
|
||||
if current_event and current_event.id == id then return current_event.value, true end
|
||||
return selected, false
|
||||
end
|
||||
local function record_text(value, color)
|
||||
if value == nil or value == "" then return end
|
||||
local label = tostring(value)
|
||||
if current_section.tooltip then
|
||||
if current_section.last_info_row then
|
||||
local row = current_section.last_info_row
|
||||
if row.text == "[?]" then row.text = label
|
||||
else row.tooltip = label end
|
||||
elseif current_section.last_ref then
|
||||
menu.set_help_text(current_section.last_ref, label)
|
||||
end
|
||||
return
|
||||
end
|
||||
local compact = label:gsub("%s+", " "):match("^%s*(.-)%s*$")
|
||||
local _, id = info_page(current_parent())
|
||||
local rows = current_section.info_rows[id]
|
||||
if not rows then rows = {}; current_section.info_rows[id] = rows end
|
||||
local row = {text = label, color = color}
|
||||
rows[#rows + 1] = row
|
||||
current_section.last_info_row = row
|
||||
current_section.last_ref = nil
|
||||
if compact ~= "[?]" and #compact <= 60 then
|
||||
current_section.last_text = compact:gsub(":$", "")
|
||||
end
|
||||
end
|
||||
ImGui.Text = record_text
|
||||
ImGui.TextUnformatted = ImGui.Text
|
||||
ImGui.TextWrapped = ImGui.Text
|
||||
function ImGui.TextColored(r, g, b, a, value)
|
||||
record_text(value, {r, g, b, a})
|
||||
end
|
||||
function ImGui.Separator()
|
||||
local id = source_key(separator_occurrences, "separator:" .. tostring(widget_index))
|
||||
if not current_section.separator_refs[id] then
|
||||
current_section.separator_refs[id] = menu.divider(current_parent(), "")
|
||||
end
|
||||
end
|
||||
function ImGui.Spacing() end
|
||||
function ImGui.SameLine() end
|
||||
function ImGui.Dummy() end
|
||||
function ImGui.ProgressBar(fraction, _, _, overlay)
|
||||
ImGui.Text(overlay or string.format("%d%%", math.floor(math.max(0, math.min(1, fraction or 0)) * 100)))
|
||||
end
|
||||
function ImGui.SetTooltip(message)
|
||||
if current_section.last_info_row then
|
||||
local row = current_section.last_info_row
|
||||
if row.text == "[?]" then row.text = tostring(message)
|
||||
else row.tooltip = tostring(message) end
|
||||
elseif current_section.last_ref then
|
||||
menu.set_help_text(current_section.last_ref, tostring(message))
|
||||
end
|
||||
end
|
||||
function ImGui.BeginTooltip() current_section.tooltip = true; return true end
|
||||
function ImGui.EndTooltip() current_section.tooltip = false end
|
||||
function ImGui.IsItemHovered() return true end
|
||||
function ImGui.IsItemActive() return false end
|
||||
function ImGui.GetFontSize() return 14 end
|
||||
function ImGui.PushStyleColor() end
|
||||
function ImGui.PopStyleColor() end
|
||||
function ImGui.PushTextWrapPos() end
|
||||
function ImGui.PopTextWrapPos() end
|
||||
function ImGui.PushItemWidth() end
|
||||
function ImGui.SetNextItemWidth() end
|
||||
function ImGui.SetNextWindowSize() end
|
||||
function ImGui.OpenPopup() end
|
||||
function ImGui.CloseCurrentPopup()
|
||||
-- The Gun Van editor is a Nenyoo submenu. Keep its source branch active
|
||||
-- after closing so re-entering the submenu does not leave inert controls.
|
||||
weapon_editor_popup = true
|
||||
menu.go_back()
|
||||
end
|
||||
function ImGui.BeginTabBar() return true end
|
||||
function ImGui.BeginTabItem(label)
|
||||
local id = next_id(label)
|
||||
local ref = current_section.containers_by_id[id]
|
||||
if not ref then
|
||||
ref = menu.list(current_parent(), label, {}, "")
|
||||
info_page(ref, label)
|
||||
current_section.containers[#current_section.containers + 1] = ref
|
||||
current_section.containers_by_id[id] = ref
|
||||
end
|
||||
if not ref then return false end
|
||||
if current_event and not current_event.ancestors[ref.id] then return false end
|
||||
current_section.last_info_row = nil
|
||||
push_parent(ref)
|
||||
return true
|
||||
end
|
||||
function ImGui.EndTabItem() pop_parent() end
|
||||
function ImGui.BeginListBox(label)
|
||||
return ImGui.BeginTabItem(label)
|
||||
end
|
||||
function ImGui.EndListBox() pop_parent() end
|
||||
function ImGui.TreeNode(label)
|
||||
return ImGui.BeginTabItem(label)
|
||||
end
|
||||
function ImGui.TreePop() pop_parent() end
|
||||
function ImGui.BeginPopupModal(label)
|
||||
return ImGui.BeginTabItem(label)
|
||||
end
|
||||
function ImGui.EndPopup() pop_parent() end
|
||||
function ImGui.EndTabBar() end
|
||||
|
||||
ImGuiCol = {Text = 0}
|
||||
ImGuiTabBarFlags = {None = 0}
|
||||
ImGuiWindowFlags = {Modal = 0, NoCollapse = 0, NoMove = 0, NoResize = 0}
|
||||
|
||||
local compat = {imgui_sections = imgui_sections, info_pages = info_pages}
|
||||
function compat.info_for_page(id)
|
||||
local page = info_pages[id]
|
||||
if not page then return nil end
|
||||
local rows, last_label = {}, nil
|
||||
local function append(row)
|
||||
local label = row.text:gsub("%s+", " "):match("^%s*(.-)%s*$")
|
||||
if label == "" then
|
||||
if #rows > 0 and rows[#rows].text ~= "" then rows[#rows + 1] = {text = ""} end
|
||||
last_label = nil
|
||||
elseif label ~= last_label then
|
||||
rows[#rows + 1] = row
|
||||
last_label = label
|
||||
end
|
||||
end
|
||||
for _, row in ipairs(page.static) do append(row) end
|
||||
for _, section in ipairs(imgui_sections) do
|
||||
local live = section.info_rows and section.info_rows[id]
|
||||
if live then for _, row in ipairs(live) do append(row) end end
|
||||
end
|
||||
return {title = page.title, rows = rows}
|
||||
end
|
||||
function compat.materialize_imgui()
|
||||
for _, section in ipairs(imgui_sections) do
|
||||
section.widget_refs, section.separator_refs = {}, {}
|
||||
section.info_rows = {}
|
||||
section.containers, section.containers_by_id = {}, {}
|
||||
section.tooltip, section.last_ref, section.last_text = false, nil, nil
|
||||
current_section, current_event = section, nil
|
||||
building, widget_index, widget_occurrences, separator_occurrences, parent_stack = true, 0, {}, {}, {section.parent}
|
||||
scan_context = section.path:find("Story Mode", 1, true) and "story" or "online"
|
||||
section.callback()
|
||||
scan_context = nil
|
||||
end
|
||||
current_section, current_event, parent_stack = nil, nil, nil
|
||||
if __smenu and __smenu.node_in_viewport then
|
||||
util.create_thread(function()
|
||||
while true do
|
||||
for _, section in ipairs(imgui_sections) do
|
||||
local parent = section.parent
|
||||
local visible = __smenu.node_in_viewport(type(parent) == "table" and parent.id or parent)
|
||||
if not visible then
|
||||
for _, ref in ipairs(section.containers) do
|
||||
if __smenu.node_in_viewport(type(ref) == "table" and ref.id or ref) then
|
||||
visible = true
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
if visible then replay(section, nil) end
|
||||
end
|
||||
util.yield()
|
||||
end
|
||||
end)
|
||||
end
|
||||
end
|
||||
|
||||
return compat
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 541 KiB |
@@ -1,117 +1,85 @@
|
||||
<div align="center">
|
||||
<a href="https://ghrmt.vercel.app"><img src="https://readme-typing-svg.vercel.app/?lines=Ultimate+Menu+Script;Most+Useful+Script;Written+By+L7NEG&font=Fira%20Code&size=31¢er=true&width=380&height=50&duration=4000&pause=1000" alt="Readme Typing Svg Vercel Version By L7NEG"></a>
|
||||
</div>
|
||||
<p align="center">
|
||||
<img src="https://readme-typing-svg.vercel.app/?lines=Ultimate+Menu+Script;Most+Useful+Script&font=Fira%20Code&size=31¢er=true&width=380&height=50&duration=4000&pause=1000" alt="Typing Banner">
|
||||
</p>
|
||||
|
||||
<div align="center">
|
||||
<h1><a href="https://www.unknowncheats.me/forum/grand-theft-auto-v/565688-ultimate-menu-script.html">Ultimate Menu</a></h1>
|
||||
</div>
|
||||
<h1 align="center">Ultimate Menu</h1>
|
||||
|
||||
<div align="center">
|
||||
<h1><a href="https://www.unknowncheats.me/forum/grand-theft-auto-v/597103-ultimate-menu-yimmenu.html">Ultimate Menu For YimMenu</a></h1>
|
||||
</div>
|
||||
<p align="center"><em>A powerful menu script featuring advanced recovery options, money tools, a Heist Editor, and much more.</em></p>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://www.unknowncheats.me/forum/grand-theft-auto-v/565688-ultimate-menu-script.html">[ModestMenu UKC Thread]</a> •
|
||||
<a href="https://www.unknowncheats.me/forum/grand-theft-auto-v/597103-ultimate-menu-yimmenu.html">[YimMenu UKC Thread]</a> •
|
||||
<a href="https://github.com/UltimateMenu/UltimateMenu?tab=readme-ov-file#-faq">[FAQ]</a>
|
||||
</p>
|
||||
|
||||
# How To Use Ultimate Menu Script
|
||||
For every Version of the ultimate menu (Kiddion/YimMenu) there is a different use and ways to fully Run It.
|
||||
> [!NOTE]
|
||||
> [How To Use YimMenu After BattlEye Anticheat Update (Legacy & Enhanced)](https://github.com/UltimateMenu/UltimateMenu/wiki/How-To-Use-UM-Script-With-YimMenu-After-Battleye-Anticheat-(Legacy-&-Enhanced))
|
||||
|
||||
For Kiddions script is just puting the script into scripts directory, inside the Kiddions files.
|
||||
---
|
||||
|
||||
For YimMenu it is actually the same way, but first before initiating the script you will need to go to Settings > Lua > Open Folder Option
|
||||
<h2 align="center">📸 YimMenu Preview (Legacy)</h2>
|
||||
|
||||
From There Go To Scripts Folder Then Paste The Ultimate Menu In There
|
||||
<p align="center">
|
||||
<img src="https://ultimatemenu.github.io/ScreenShots/YimMenu/15.png" alt="Ultimate Menu Preview">
|
||||
</p>
|
||||
|
||||
--------------------------------------------------------------------------------------------------
|
||||
<div align="center">
|
||||
<h1> New ScreenShots V2.0</h1>
|
||||
</div>
|
||||
---
|
||||
|
||||
[](https://i.imgur.com/hxOYdxr.png)
|
||||
[](https://i.imgur.com/r58RXk0.png)
|
||||
[](https://i.imgur.com/T7x7sLs.png)
|
||||
[](https://i.imgur.com/jJ6w7tT.png)
|
||||
[](https://i.imgur.com/fBr07Gq.png)
|
||||
[](https://i.imgur.com/7LvCnPX.png)
|
||||
[](https://i.imgur.com/BU8RI1R.png)
|
||||
--------------------------------------------------------------------------------------------------
|
||||
<div align="center"> <h1> <details>
|
||||
<summary>Old Versions ScreenShots</summary>
|
||||
<h2 align="center">📸 Nenyoo Preview (Legacy)</h2>
|
||||
|
||||
[](https://i.imgur.com/M54nsX6.png)
|
||||
[](https://i.imgur.com/qszJJNK.png)
|
||||
[](https://i.imgur.com/A5951n9.png)
|
||||
[](https://i.imgur.com/Q04ceX5.png)
|
||||
[](https://i.imgur.com/J3vquqW.png)
|
||||
[](https://i.imgur.com/OKD4ruV.png)
|
||||
[](https://i.imgur.com/MmRIRzW.png)
|
||||
[](https://i.imgur.com/tuVD0wg.png)
|
||||
[](https://i.imgur.com/b2erLqZ.png)
|
||||
[](https://i.imgur.com/C1nhfs6.png)
|
||||
[](https://i.imgur.com/2kNARYV.png)
|
||||
[](https://i.imgur.com/vfsnLz4.png)
|
||||
[](https://i.imgur.com/5ovnXIS.png)
|
||||
[](https://i.imgur.com/HtOYaT2.png)
|
||||
[](https://i.imgur.com/wSw48p7.png)
|
||||
[](https://i.imgur.com/jz13ysV.png)
|
||||
[](https://i.imgur.com/NlATJNG.png)
|
||||
[](https://i.imgur.com/SSf5TwH.png)
|
||||
[](https://i.imgur.com/0QDgNad.png)
|
||||
[](https://i.imgur.com/oBnOqdG.png)
|
||||
[](https://i.imgur.com/gspkbJq.png)
|
||||
[](https://i.imgur.com/fQnOyPM.png)
|
||||
[](https://i.imgur.com/Zfiv9po.png)
|
||||
[](https://i.imgur.com/I7QHqM8.png)
|
||||
[](https://i.imgur.com/b0JmgBF.png)
|
||||
[](https://i.imgur.com/qZpu6Uo.png)
|
||||
[](https://i.imgur.com/EFF9efF.png)
|
||||
[](https://i.imgur.com/9QRULhG.png)
|
||||
[](https://i.imgur.com/bas1EOp.png)
|
||||
[](https://i.imgur.com/JMkmB7X.png)
|
||||
[](https://i.imgur.com/Im3W9vf.png)
|
||||
[](https://i.imgur.com/qw4ir1P.png)
|
||||
[](https://i.imgur.com/IZmhyCp.png)
|
||||
[](https://i.imgur.com/EN7gLdh.png)
|
||||
[](https://i.imgur.com/rSPdw5D.png)
|
||||
[](https://i.imgur.com/KOF7T0I.png)
|
||||
[](https://i.imgur.com/c6XapmD.png)
|
||||
[](https://i.imgur.com/YNsHiEz.png)
|
||||
[](https://i.imgur.com/D1JDwWy.png)
|
||||
[](https://i.imgur.com/uRU7pEJ.png)
|
||||
[](https://i.imgur.com/QqqTWhV.png)
|
||||
[](https://i.imgur.com/FfeC0g0.png)
|
||||
[](https://i.imgur.com/ewUvo9k.png)
|
||||
[](https://i.imgur.com/aIR70Sq.png)
|
||||
[](https://i.imgur.com/M33uCnH.png)
|
||||
[](https://i.imgur.com/wuS93Jy.png)
|
||||
[](https://i.imgur.com/IGrWFv4.png)
|
||||
[](https://i.imgur.com/Wwcu6uJ.png)
|
||||
[](https://i.imgur.com/Cw3lR0K.png)
|
||||
[](https://i.imgur.com/sK8v823.png)
|
||||
[](https://i.imgur.com/TU2a1dL.png)
|
||||
[](https://i.imgur.com/I4BKPNx.png)
|
||||
[](https://i.imgur.com/TfUzBnL.png)
|
||||
[](https://i.imgur.com/he7jVbf.png)
|
||||
[](https://i.imgur.com/2gFkwgd.png)
|
||||
[](https://i.imgur.com/0JTNdeR.png)
|
||||
[](https://i.imgur.com/ZOhngs0.png)
|
||||
[](https://i.imgur.com/JdGNN5u.png)
|
||||
[](https://i.imgur.com/g1E5tET.png)
|
||||
[](https://i.imgur.com/us8pTnv.png)
|
||||
[](https://i.imgur.com/UxNxSD2.png)
|
||||
[](https://i.imgur.com/dsaBz9M.png)
|
||||
[](https://i.imgur.com/ahzoYzX.png)
|
||||
[](https://i.imgur.com/AR0fcUS.png)
|
||||
[](https://i.imgur.com/4BWvVJx.png)
|
||||
[](https://i.imgur.com/M5RIvvm.png)
|
||||
[](https://i.imgur.com/weSH8H1.png)
|
||||
<p align="center">
|
||||
<img src="Nenyoo/preview.jpg" alt="Ultimate Menu running in Nenyoo on GTA V Legacy">
|
||||
</p>
|
||||
|
||||
---
|
||||
|
||||
## ❓ FAQ
|
||||
|
||||
<details>
|
||||
<summary><strong>How To Use?</strong></summary>
|
||||
|
||||
- For **YimMenu Legacy**:
|
||||
Open YimMenu → `Settings` → `Lua` → `Open Folder` → `scripts`
|
||||
→ Paste the `.lua` file there. That’s it!
|
||||
|
||||
</details> </h1> </div>
|
||||
- For **YimMenuV2 Enhanced**:
|
||||
Coming Soon (WIP)
|
||||
- For **Nenyoo GTA V Legacy or Enhanced**:
|
||||
Copy the contents of [`Nenyoo`](Nenyoo) to `%LOCALAPPDATA%\Nenyoo\Plus\Scripts\User\UltimateMenu\`. In Nenyoo, open `Scripts` and select `Ultimate_Menu.lua` to load its menu page. The `lib` folder must stay beside the entry script. Join GTA Online before using online actions.
|
||||
Supported builds: Legacy 3889 and Enhanced 1158.13. The matching offsets are selected automatically.
|
||||
</details>
|
||||
|
||||
--------------------------------------------------------------------------------------------------
|
||||
## When Your New Updates Will Be Out?
|
||||
No ETA for big updates also because i don't know actually if im going to be able to continue this script (boths) because i have a life and i need to study. This is a helpfull and fun project for everyone who wants to use it, is free and you can use my script as a template.
|
||||
--------------------------------------------------------------------------------------------------
|
||||
## About
|
||||
- By the way to anyone who ask's about the Ultimate-Menu script, is not entire mine, there is actually in credits every single person who i taked code from and who helped me with this.
|
||||
## Latest Ultimate Menu Kiddions update was on: 12/01/2024
|
||||
## Latest Ultimate Menu YimMenu update was on: 31/12/2023
|
||||
---
|
||||
|
||||
## 📅 Update Info
|
||||
|
||||
- **Ultimate Menu for ModestMenu**: Last updated on **Dec 12, 2024** *(Final Update)*
|
||||
- **Ultimate Menu for YimMenu Legacy**: Last updated on **Jul 24, 2026**
|
||||
- **Ultimate Menu for YimMenu Enhanced**: **Might Not Coming Soon (WIP Waiting for completion of YimMenuV2 Lua API)**
|
||||
- **Ultimate Menu for Nenyoo**: Legacy and Enhanced support
|
||||
|
||||
---
|
||||
|
||||
## 🛠️ About
|
||||
|
||||
This is a fun and helpful free project for the community.
|
||||
There is **no ETA** for future big updates, as I’m currently focused on studying and personal life.
|
||||
|
||||
You're welcome to fork, use, and build on this script for your own needs.
|
||||
Treat it as a base or template if you wish.
|
||||
|
||||
Credits For Everything I Used Is Included In The Script.
|
||||
|
||||
---
|
||||
|
||||
<h2 align="left">💬 Discord Server</h2>
|
||||
|
||||
<p align="left">
|
||||
<a href="https://dsc.gg/l7neg">
|
||||
<img src="https://discord.com/api/guilds/1025804814183047218/widget.png?style=banner2" alt="L7NEG Community Discord Server">
|
||||
</a>
|
||||
</p>
|
||||
|
||||
---
|
||||
|
||||
**Thanks for using Ultimate Menu Made With ❤️ By L7NEG & Contributors/Helpers**
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user