UNPKG

anomaly-packer

Version:

Anomaly Packer is a utility package for STALKER Anomaly creators to help them develop addons at speed with TypeScript's type-safety and game-oriented build tools.

1,658 lines 134 kB
import { JSX } from "react"; //#region src/pack.d.ts type PackOptions = { /** * Flat identifier of the addon. Every registered script is prefixed with it (the `index` entry becomes the bare id), and the runtime scripts Anomaly Packer copies into the build are namespaced with it too, so nothing collides with other addons: e.g. importing 'anomaly-packer/mcm' emits `<addonId>__ap_mcm.script`. * * @example * * 'pcprs_healing_campfires' */ addonId: string; build?: { outDirName?: string; }; /** * Short names of the TypeScript files under /gamedata/scripts to include in the build. [typescript-to-lua](https://www.npmjs.com/package/typescript-to-lua) transpiles the entire project, so only the files listed here are picked up; every other transpiled module is discarded. Each name is written to the build prefixed with {@link addonId} — `index` becomes the bare addon id (the addon's main script), everything else becomes `<addonId>_<name>`. * * @example * * With the below configuration /gamedata/scripts/index.ts and /gamedata/scripts/mcm.ts are built to `<addonId>.script` and `<addonId>_mcm.script` * * ```ts * ['index', 'mcm'] * ``` */ scripts?: string[]; /** * Path to the original Anomaly gamedata directory. This path is the base for the relative paths that are used in certain functions of Anomaly Packer. * * @example * * 'C:/Games/Anomaly 1.5.2/gamedata' */ sourceGamedata?: string; }; declare function pack(options: PackOptions): Promise<void>; //#endregion //#region src/zip.d.ts /** * Zips a finished build into a single archive for distribution. * * The archive contains `gamedata/` at its root — the layout Mod Organizer 2 and every other * Anomaly mod manager expect, so the file installs by drag and drop with nothing to unwrap * first. Anything else in the build directory is included as it lies. */ type ZipOptions = { /** Build directory to archive. Defaults to `build` beside the project. */ buildDir?: string; /** Where to write the archive. Defaults to the project root. */ outDir?: string; /** * Base archive name, without the extension and without the version — the version from the * manifest is appended either way, since which release an archive holds is the one thing a * downloaded zip has to say for itself. Defaults to the package name. */ name?: string; cwd?: string; }; declare function zipBuild(options?: ZipOptions): Promise<{ file: string; bytes: number; }>; //#endregion //#region src/meta.d.ts /** * Mod Organizer 2 stores a mod's metadata in a `meta.ini` under a `[General]` section. Without * one MO2 lists the mod as an unmanaged "backup" and nags on every refresh, so a deploy step * writes a minimal file. This builds that file's content. */ /** * Keys MO2 reads from `[General]`. All optional so a caller writes only what it knows; the * index signature keeps the door open for any other key MO2 understands (`comments`, `notes`, * `installationFile`, …) without widening the whole type to `Record<string, unknown>`. */ type MetaIniGeneral = { modid?: number | string; /** The mod's version shown in MO2's pane; conventionally read from `package.json`'s `version`. */ version?: string; category?: number | string; /** The mod's web page, opened by MO2's "Visit website"; conventionally read from `package.json`'s `homepage`. */ url?: string; } & Record<string, string | number | boolean | undefined>; /** * The `meta.ini` content for the given `[General]` fields, serialized by `ini` rather than by * hand so escaping and quoting match a real ini parser. MO2's required keys ({@link DEFAULTS}) * are filled in when the caller omits them. Keys explicitly set to `undefined` are dropped, so * passing `{ modid: undefined }` opts out of that default rather than emitting a blank line. */ declare function buildMetaIniContent(general?: MetaIniGeneral): string; //#endregion //#region src/texts/character.d.ts type SpecificCharacter = { /** @example 'cit_killers_merc_trader_stalker' */ id: string; team_default: boolean; /** @example 'cit_killers_merc_trader_stalker_name' */ name: string; /** @example 'ui_inGame2_merc_trade' */ icon: string; map_icon: { x: number; y: number; }; /** @example 'stalker_terrain' */ terrain_sect?: string; /** * @deprecated unused * @example 'esc_wolf_bio' */ bio?: string; /** Name of the team of the syncronized zoneguards. Not tested */ team?: string; /** @example 'cit_killers_merc_trader_stalker' */ class: string; community: Community | 'trader'; /** @example 'characters_voice\\human\\killer_3\\' */ snd_config: string; /** @example 15000 */ rank: number; money: { min: number; max: number; infinitive: boolean; }; /** @example -1000 */ reputation: number; /** @example 'actors\\stalker_merc\\stalker_ki_head_2' */ visual: string; /** Character's inventory */ supplies?: { spawn?: Record<string, string | number | boolean>; /** Paths to other XML files */ include?: string[]; }; dialogs: string[]; crouch_type?: number; /** @example 0 - panic is disabled */ panic_treshold?: number; mechanic_mode?: 1 | 0; /** * Paths to other XML files * * @example ['gameplay\\character_criticals.xml', 'gameplay\\character_dialogs.xml'] */ include?: string[]; }; /** @deprecated NOT IMPLEMENTED */ declare function specificCharacter(character: SpecificCharacter): string; //#endregion //#region src/texts/dialog.d.ts type DialogPhraseShared = { /** * Ids of functions returning a boolean. If `true`, this dialog or phrase will be available * @example * ```ts * ['dialogs_jupiter.ecolog_companion_task_2_not_complete'] * ``` * Function is declared in *gamedata/scripts/dialogs_jupiter.script* * ```lua * function ecolog_companion_task_2_not_complete(speaker_1, speaker_2) * return not ecolog_companion_task_2_complete(speaker_1, speaker_2) * end * ``` */ precondition?: string | string[]; /** Only enable the dialog or the phrase if the actor does not have these info portions */ dont_has_info?: string | string[]; /** Only enable the dialog or the phrase if the actor has these info portions */ has_info?: string | string[]; /** Disable info portions for the actor after this dialog has started or this phrase has been produced */ disable_info?: string | string[]; /** * Info portions ids to give to the actor after this dialog has started or this phrase has been produced * @example ['bar_arena_fight_5', 'bar_arena_fight'] */ give_info?: string | string[]; /** * Lua functions that will be fired upon entering the dialog or producing a phrase * @example 'dialog_manager.action_disable_phrase' */ action?: string | string[]; }; type Phrase<PhraseId extends number = number> = DialogPhraseShared & { /** An arbitraty ID to which other phrases within this dialog tree will refer to in `next` */ id: PhraseId; /** * ID of the translation string that will be used as text for this phrase. If the translation was not found for a specific language, the fallback text will apear instead. Cannot be used with `script_text` * @example 'bar_arena_manager_start_21' */ text?: string; /** * ID of a scripted text. Cannot be used with `text` * @example 'dialogs_mlr.buy_extra_med_4' */ script_text?: string; /** * Array of phrases' ids of this dialog that will appear after this phrase. Not inluding this field at all will result into the initial dialog to appear after this phrase * @example * ```ts * // phrase 1 * { next: [1112] } * // phrase 2 * { id: 1112 }, * ``` */ next?: NoInfer<PhraseId> | NoInfer<PhraseId>[]; /** * True purpose is unknown. Commonly used in combination with `dialogs.break_dialog` action * @example a phrase from the game files * ```xml * <action>dialogs.break_dialog</action> * <is_final>1</is_final> * ``` */ is_final?: 0 | 1; }; type Dialog<PhraseId extends number = number> = DialogPhraseShared & { id: string; /** * ID of a scripted dialog. Cannot be used with `phrases` * @example 'dialog_manager.dm_agr_u_bandit_boss_ask' */ init_func?: string; phrases?: Phrase<PhraseId>[]; }; declare function dialog<PhraseId extends number>(dialog: Dialog<PhraseId>): string; //#endregion //#region src/types.d.ts type Texts = typeof index_d_exports; declare const separatorBrand: unique symbol; /** * A `string` at runtime, branded at compile time as a `Separator`-delimited list whose * split result is `Values` — an array or tuple (`string[]` for a homogeneous list, or a * positional tuple like `[str: string, op: Comparison, val: number]`). Carries that array * and the separator so splitters (e.g. `str_explode`) can return `Values` instead of * `string[]`. Assignable to and from plain `string`; the brand only refines what a * splitter yields. Imported from `anomaly-packer` — an AP utility, not a game global. */ type SymbolSeparatedString<Values extends readonly unknown[], Separator extends string> = string & { readonly [separatorBrand]: { values: Values; separator: Separator; }; }; /** {@link SymbolSeparatedString} split on `,`. */ type CommaSeparatedString<Values extends readonly unknown[]> = SymbolSeparatedString<Values, ','>; /** {@link SymbolSeparatedString} split on `/`. */ type SlashSeparatedString<Values extends readonly unknown[]> = SymbolSeparatedString<Values, '/'>; /** {@link SymbolSeparatedString} split on `\\` (two backslash characters). */ type TwoBackslashSeparatedString<Values extends readonly unknown[]> = SymbolSeparatedString<Values, '\\\\'>; /** * - `%=func%` return the function's returned value * - `{=func}` check the function's returned value * - `{-info}` check actor does not have info portion * - `{+info}` check actor has info portion */ type CondList = string; type ItemActionIndex = 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10; type ItemActionMode = 'inventory' | 'loot' | 'trade' | 'repair'; type ItemActionContainer = 'actor_bag' | 'actor_equ' | 'actor_belt' | 'actor_trade' | 'actor_trade_bag' | 'npc_bag' | 'npc_trade' | 'npc_trade_bag'; declare namespace Ltx { /** Interactivity with an item via interface */ interface GlobalItemActions extends Partial<Record<`use${ItemActionIndex}_${'functor' | 'action_functor'}`, string> & Record<`use${ItemActionIndex}_modes`, ItemActionMode | ItemActionMode[]> & Record<`use${ItemActionIndex}_containers`, ItemActionContainer | ItemActionContainer[]>> {} interface IdentityImmunities extends GlobalItemActions, Partial<{ immunities_sect: string; slot: number; description: string; default_to_ruck: boolean; sprint_allowed: boolean; control_inertion_factor: number; zoom_rotate_time: number; can_trade: boolean; quest_item: boolean; condition_bar: string; snd_on_take: string; }> {} interface DefaultWeaponParams extends IdentityImmunities, Partial<{ use_aim_bullet: boolean; use_first_bullet: boolean; k_hit_critical: number; frag_hit_critical: number; hit_power: number; hit_power_critical: number; silencer_hit_power: number; hit_impulse: number; silencer_hit_impulse: number; kind: string; can_be_lowered: string; weapon_lower_speed: boolean; }> {} interface Trader extends Partial<{ buy_condition: Suggest<'trade_generic_buy'>; buy_item_condition_factor: number; buy_item_exponent: number; buy_supplies: CondList; sell_item_exponent: number; sell_condition: Suggest<'trade_generic_sell'>; price_profile: Suggest<'default'>; discounts: string; }> {} interface Task extends Partial<{ icon: string; prior: number; sim_communities: Community | Community[]; storyline: boolean; title: string; title_functor: CondList; descr: string; job_descr: string; fetch_descr: string; descr_functor: string; target_functor: string; task_complete_descr: string; fetch_func: CondList; status_functor: string; status_functor_params: string[]; precondition: CondList; repeat_timeout: number; stage_complete: number; on_job_descr: string; on_init: CondList; on_complete: CondList; on_fail: CondList; } & Record<`condlist_${number}`, CondList>> {} } //#endregion //#region src/texts/ltx.d.ts type LtxValue = string | number | boolean | null | undefined | readonly (string | number | boolean | null | undefined)[]; /** * The value you pass when authoring a field, given its read-schema type. A branded * {@link SymbolSeparatedString} field is written as its underlying array/tuple (e.g. a * `[str, op, val]` condition line), so the literal — not a joined string — is checked. * Everything else is written as declared. */ type LtxWritable<T> = T extends SymbolSeparatedString<infer V, string> ? V : T; /** A section's entries in write form. Field optionality (`?`, `| undefined`) is taken * straight from the schema, so the declaration decides what may be omitted. */ type LtxEntries<Shape> = { [K in keyof Shape]: LtxWritable<Shape[K]>; }; /** * Resolve the section-map to check against from the type argument `P`, which may be: * - a registered {@link IniFileSchemas} path key — resolved like the read side ({@link IniExSchemaOf}); * - a section-map type directly (e.g. an addon's own `interface`), used as-is — so callers * can bind by naming their schema instead of restating its file path; * - anything else (or the default) — the loose untyped fallback. */ type LtxSchemaOf<P> = P extends keyof IniFileSchemas ? IniFileSchemas[P] : P extends object ? P : UntypedIniSchema; type Ltx$1<P, S extends keyof LtxSchemaOf<P>> = { section: S; with?: string[]; entries?: LtxEntries<LtxSchemaOf<P>[S]>; }; /** * Render a single ltx section to string. Bind it to a schema via the type argument to get * section-name autocomplete and per-field value checking — either a registered path key * (`ltx<'plugins\\my_addon.ltx'>({...})`) or a section-map type directly * (`ltx<MyAddonIni>({...})`). Called without the type argument, it falls back to the loose * untyped schema. * @param sort sort entries alphabetically (`true` by default) * @param align aligns table vertically, resuling in "=" signs appear under each other (`true` by default) * @returns ltx table as string */ declare function ltx<P = string, S extends keyof LtxSchemaOf<P> = keyof LtxSchemaOf<P>>(ltx: Ltx$1<P, S>, sort?: boolean, align?: boolean): string; declare namespace ltx { var f: <N extends keyof typeof xr_conditions | keyof typeof xr_effects>(name: N, ...args: SkipFirstSecond<Parameters<(typeof xr_conditions & typeof xr_effects)[N]>>) => string; } /** * An {@link ltx} pre-bound to a file path `P`, so the type argument is written once (via * {@link forFile}) instead of on every call. The binding is only a default: pass a type * argument to override the schema for a single call — `bound.ltx<'other.ltx'>({...})` — * and omit it to keep `P`. */ type BoundLtx<P> = <P2 = P, S extends keyof LtxSchemaOf<P2> = keyof LtxSchemaOf<P2>>(ltx: Ltx$1<P2, S>, sort?: boolean, align?: boolean) => string; /** * Bind {@link ltx} to a schema once, dropping the per-call type argument: `const f = * t.forFile<MyAddonIni>()` (or a registered path key) then `f.ltx({ section, entries })`. * Purely additive — the standalone `t.ltx` (with or without its own type argument) still * works, so schema binding stays opt-in at every level. */ declare function forFile<P>(): { ltx: BoundLtx<P>; }; type SkipFirstSecond<Arr> = Arr extends [infer _1, infer _2, ...infer Rest] ? Rest : never; //#endregion //#region src/texts/dltx.d.ts type DltxEntries<O extends object> = Partial<{ [K in keyof O]: (O[K] extends (infer U) ? U extends any[] ? { [_ in K | `${'<' | '>'}${K & string}`]: any; } : {} : {}) & { [_ in K | `!${K & string}`]: undefined; } & { [_ in K]: any; }; }[keyof O]>; /** Delete a section with the use of `!!` prefix */ declare function deleteSection({ sectionName }: { sectionName: string; }): string; type OverrideLtx<L extends Record<keyof L, LtxValue>> = { sectionName: string; _with?: string[]; entries?: DltxEntries<L>; }; /** * Override a section with the use of `!` prefix. * - add or override an entry - no prefix, * - delete an entry with `!`, * - add to array with `>`, * - delete from array with `<`, */ declare function override<L extends Partial<Record<keyof L, LtxValue>>>(ltx: OverrideLtx<L>, sort?: boolean, align?: boolean): string; /** Create a section if it does not exist or override if it does with the use of `@` prefix */ declare function createOrOverride<L extends Partial<Record<keyof L, LtxValue>>>(ltx: OverrideLtx<L>, sort?: boolean, align?: boolean): string; declare const dltx: { createOrOverride: typeof createOrOverride; override: typeof override; deleteSection: typeof deleteSection; }; //#endregion //#region src/texts/include.d.ts declare function include(path: string): string; //#endregion //#region src/texts/task.d.ts type Task = { /** Title in the PDA */ title: string; /** First objective in the list is considered main */ objective: { text: string; icon: string; infoportion_set_complete?: string; infoportion_complete?: string; infoportion_fail?: string; function_complete?: string; function_fail?: string; article?: string; }[]; }; //#endregion //#region src/texts/info-portions.d.ts type Location = { level: number; x: number; y: number; icon: { name: string; x: number; y: number; width: number; height: number; }; text: string; }; type InfoPortions<Id extends string = string> = Record<Id, { action?: string | string[]; article?: string | string[]; dialog?: string | string[]; actor_dialog?: string | string[]; disable?: string | string[]; location?: Location | Location[]; task?: Task | Task[]; } | null>; declare function infoPortions<Id extends string>(portions: InfoPortions<Id>): string; //#endregion //#region src/texts/localization.d.ts /** Localization folders Anomaly reads under gamedata/configs/text. The list is open-ended — unknown folder names are still accepted, the known ones just provide autocomplete. */ type Language = 'eng' | 'rus' | 'ukr' | 'pol' | 'fra' | 'ger' | 'spa' | 'ita' | 'cze' | (string & {}); /** Every localization declares exactly the same keys: `eng` is the source of truth (its keys and values are inferred), and every other language you provide is forced to mirror its key set exactly — a missing or stray translation is a compile error. The languages you pass stay present on the result (no spurious `undefined`). */ declare function bilingual<const D extends { eng: Record<string, string>; }>(dict: D & Partial<Record<Exclude<Language, 'eng'>, Record<keyof D['eng'], string>>>): D; /** In-game text color codes accepted by `%c[...]` (news, dialogs, UI strings). Mirrors the engine's color names. */ type Color = 'default' | 'red' | 'orange' | 'yellow' | 'green' | 'blue' | 'white' | 'black' | 'gray' | 'light_gray' | 'tut_gray' | 'dark_gray' | 'edit' | `d_${'orange' | 'red' | 'cyan' | 'red_1' | 'purple' | 'green' | 'blue'}` | `ui_${'red' | 'green' | 'blue' | 'white' | 'black' | 'gray' | 'yellow' | 'gray_1' | 'gray_2' | 'gray_3' | 'lime'}` | `ui_${1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10}` | `pda_${'green' | 'blue' | 'yellow' | 'white' | 'red'}`; /** Wraps a color name in the game's inline color code, e.g. `color('d_cyan')` → `%c[d_cyan]`. Everything after it is painted until the next code. */ declare function color(name: Color): string; //#endregion //#region src/texts/translation.d.ts declare function translations<Id extends string>(translation: Partial<Record<Id, string>>, idOverride?: (id: string) => string): string; //#endregion //#region src/texts/ui.d.ts /** * Convert HEX color code to RGBA object * @example * ```ts * const clr = hexToRgba('#2dd4c982') * const alpha = clr!.a // 51 * ``` */ declare function hexToRgba(hex: string): { /** 0 - 255 */ r: number; /** 0 - 255 */ g: number; /** 0 - 255 */ b: number; /** 0 - 100 */ a: number; } | null; declare function jsxToXml(tree: JSX.Element): string; declare const ui: { jsxToXml: typeof jsxToXml; hexToRgba: typeof hexToRgba; }; declare namespace index_d_exports { export { BoundLtx, Color, Dialog, FileExtension, Language, LtxValue, SpecificCharacter, bilingual, color, dialog, dltx, forFile, include, infoPortions, ltx, specificCharacter, translations, ui }; } /** * Extension of the generated text file * * @default 'xml' */ type FileExtension = 'xml' | 'ltx'; //#endregion //#region src/types/sections/index.d.ts // AUTO-GENERATED by `tsx src/scripts/gen-sections.ts`. Do not edit by hand. // The section-id types, exposed as one `Section` namespace re-exported from the package root // (`export type * from './types/sections'` in src/index.ts). Each category is an augmentable // interface with a `keyof`-derived union, composed into the aggregates: // Section.Item - every item section (spawn/give APIs), split by category. // Section.Object - Item plus non-item object sections (Npc, Squad, Vehicle, Helicopter, // Monster, Anomaly). // Section.All - the type a game object's section() can return. // Import: `import type { Section } from 'anomaly-packer'` then `Section.Weapon` / `Section.All`. // Augment: `declare module 'anomaly-packer' { namespace Section { interface Weapons { my_wpn: 0 } } }`. declare namespace Section { export interface Attachments { af_aac: 0; af_aam: 0; af_baloon_lead_box: 0; af_black_spray_lead_box: 0; af_blood_lead_box: 0; af_bracelet_lead_box: 0; af_compass_lead_box: 0; af_cristall_flower_lead_box: 0; af_cristall_lead_box: 0; af_dummy_battery_lead_box: 0; af_dummy_dummy_lead_box: 0; af_dummy_glassbeads_lead_box: 0; af_electra_flash_lead_box: 0; af_electra_moonlight_lead_box: 0; af_electra_sparkler_lead_box: 0; af_empty_lead_box: 0; af_eye_lead_box: 0; af_fire_lead_box: 0; af_fireball_lead_box: 0; af_full_empty_lead_box: 0; af_fuzz_kolobok_lead_box: 0; af_glass_lead_box: 0; af_gold_fish_lead_box: 0; af_gravi_lead_box: 0; af_iam: 0; af_ice_lead_box: 0; af_itcher_lead_box: 0; af_lobster_eyes_lead_box: 0; af_medusa_lead_box: 0; af_mincer_meat_lead_box: 0; af_misery_bread_lead_box: 0; af_night_star_lead_box: 0; af_oasis_heart_lead_box: 0; af_pin_lead_box: 0; af_quest_b14_twisted_lead_box: 0; af_ring_lead_box: 0; af_soul_lead_box: 0; af_sponge_lead_box: 0; af_vyvert_lead_box: 0; ammo_box: 0; anomaly_scaner: 0; army_isg_spy_pendrive: 0; army_patch: 0; attackers_pda: 0; bad_psy_helmet: 0; bandit_patch: 0; beadspread: 0; blackbox_mlr: 0; boots: 0; broken_pda: 0; cards: 0; cash: 0; chernobog_notes: 0; chimera_scan_device: 0; cit_doctors_key: 0; cit_doctors_pda: 0; contact_lost_pda: 0; csky_patch: 0; cutlery: 0; decoder: 0; decryption_radio: 0; device_flash_snag: 0; device_pda_port_bandit_leader: 0; device_pda_zat_b5_dealer: 0; dolg_patch: 0; drekavac_notes: 0; drx_agr_u_documents: 0; drx_jup_u_documents: 0; drx_sl_quest_item_1: 0; drx_sl_quest_item_2: 0; drx_sl_quest_item_3: 0; drx_x16_documents: 0; drx_x18_documents: 0; drx_x19_documents: 0; drx_x8_documents: 0; e_syringe: 0; ecolog_patch: 0; explo_balon_gas_empty: 0; explo_jerrycan_fuel_empty: 0; flashlight_broken: 0; freedom_patch: 0; good_psy_helmet: 0; grease: 0; greh_patch: 0; grooming: 0; guitar_a: 0; harmonica_a: 0; hb_isg_dushman_intel: 0; headlamp: 0; isg_patch: 0; itm_advancedkit: 0; itm_ammokit: 0; itm_basickit: 0; itm_drugkit: 0; itm_expertkit: 0; jar: 0; jewelry_box: 0; journal: 0; jup_a9_conservation_info: 0; jup_a9_delivery_info: 0; jup_a9_evacuation_info: 0; jup_a9_losses_info: 0; jup_a9_meeting_info: 0; jup_a9_power_info: 0; jup_a9_way_info: 0; jup_b10_notes_01: 0; jup_b10_notes_02: 0; jup_b10_notes_03: 0; jup_b10_ufo_memory: 0; jup_b10_ufo_memory_2: 0; jup_b1_half_artifact_lead_box: 0; jup_b200_tech_materials_acetone: 0; jup_b200_tech_materials_capacitor: 0; jup_b200_tech_materials_textolite: 0; jup_b200_tech_materials_transistor: 0; jup_b200_tech_materials_wire: 0; jup_b202_bandit_pda: 0; jup_b205_sokolov_note: 0; jup_b206_plant: 0; jup_b207_merc_pda_with_contract: 0; jup_b209_monster_scanner: 0; jup_b32_scanner_device: 0; jup_b46_duty_founder_pda: 0; jup_b47_jupiter_products_info: 0; jup_b47_merc_pda: 0; jup_b9_blackbox: 0; jupiter_documents: 0; killer_patch: 0; lead_box: 0; lead_box_closed: 0; lead_box_closed_dummy: 0; lead_box_dummy: 0; lead_box_half: 0; lead_box_half_dummy: 0; leatherman_tool: 0; letter_ecologist_report_1_of_3: 0; letter_ecologist_report_2_of_3: 0; letter_ecologist_report_3_of_3: 0; letter_freedom_manual_1_of_2: 0; letter_freedom_manual_2_of_2: 0; letter_letter_to_outside: 0; letter_memoirs_1_of_2: 0; letter_memoirs_2_of_2: 0; letter_mercenary: 0; letter_military_log: 0; letter_military_stalker: 0; letter_monolith_prayer_1_of_3: 0; letter_monolith_prayer_2_of_3: 0; letter_monolith_prayer_3_of_3: 0; letter_monolithian_thoughts: 0; letter_stalker_letter_1_of_2: 0; letter_stalker_letter_2_of_2: 0; letter_stalker_letter_3: 0; lx8_history_2_documents: 0; lx8_history_3_documents: 0; lx8_history_documents: 0; lx8_service_instruction: 0; main_story_1_quest_case: 0; main_story_2_lab_x18_documents: 0; main_story_3_lab_x16_documents: 0; main_story_4_lab_x10_documents: 0; main_story_5_lab_x8_documents: 0; main_story_6_jup_ug_documents: 0; main_story_7_mon_con_documents: 0; mar_base_owl_stalker_trader_task_1_pda: 0; matches: 0; medkit_ai1: 0; medkit_ai2: 0; medkit_ai3: 0; meinkampf: 0; mirror: 0; mlr_x8_copybook: 0; mlr_x8_copybook_2: 0; mlr_x8_documents: 0; monolith_patch: 0; mutant_part_boar_leg: 0; mutant_part_brain_burer: 0; mutant_part_burer_hand: 0; mutant_part_cat_claw: 0; mutant_part_cat_tail: 0; mutant_part_cat_thyroid: 0; mutant_part_chimera_claw: 0; mutant_part_chimera_kogot: 0; mutant_part_controller_glass: 0; mutant_part_controller_hand: 0; mutant_part_crow_beak: 0; mutant_part_dog_heart: 0; mutant_part_dog_liver: 0; mutant_part_dog_tail: 0; mutant_part_fang_psevdodog: 0; mutant_part_flesh_eye: 0; mutant_part_fracture_hand: 0; mutant_part_general: 0; mutant_part_general_add: 0; mutant_part_general_mlr: 0; mutant_part_heart_bloodsucker: 0; mutant_part_heart_chimera: 0; mutant_part_krovosos_jaw: 0; mutant_part_lurker_eye: 0; mutant_part_lurker_tail: 0; mutant_part_pseudogigant_eye: 0; mutant_part_pseudogigant_hand: 0; mutant_part_psevdodog_tail: 0; mutant_part_psysucker_hand: 0; mutant_part_snork_leg: 0; mutant_part_snork_mask: 0; mutant_part_tushkano_head: 0; mutant_part_tusk_boar: 0; mutant_part_zombi_hand: 0; pda_for_nps: 0; picture_woman: 0; porn: 0; porn2: 0; powder_poltergeist: 0; pri_a15_documents: 0; pri_a15_wpn_ak74: 0; pri_a15_wpn_ak74u: 0; pri_a15_wpn_svu: 0; pri_a15_wpn_wincheaster1300: 0; pri_a19_american_experiment_info: 0; pri_a19_lab_x10_info: 0; pri_a19_lab_x16_info: 0; pri_a19_lab_x18_info: 0; pri_a19_lab_x7_info: 0; pri_b36_monolith_hiding_place_pda: 0; pri_decoder_documents: 0; prt_o_ballistic_1: 0; prt_o_ballistic_10: 0; prt_o_ballistic_11: 0; prt_o_ballistic_12: 0; prt_o_ballistic_13: 0; prt_o_ballistic_14: 0; prt_o_ballistic_15: 0; prt_o_ballistic_16: 0; prt_o_ballistic_17: 0; prt_o_ballistic_18: 0; prt_o_ballistic_19: 0; prt_o_ballistic_2: 0; prt_o_ballistic_20: 0; prt_o_ballistic_3: 0; prt_o_ballistic_4: 0; prt_o_ballistic_5: 0; prt_o_ballistic_6: 0; prt_o_ballistic_7: 0; prt_o_ballistic_8: 0; prt_o_ballistic_9: 0; prt_o_fabrics_1: 0; prt_o_fabrics_2: 0; prt_o_fabrics_3: 0; prt_o_fabrics_4: 0; prt_o_retardant_1: 0; prt_o_retardant_10: 0; prt_o_retardant_11: 0; prt_o_retardant_12: 0; prt_o_retardant_13: 0; prt_o_retardant_14: 0; prt_o_retardant_15: 0; prt_o_retardant_16: 0; prt_o_retardant_17: 0; prt_o_retardant_18: 0; prt_o_retardant_19: 0; prt_o_retardant_2: 0; prt_o_retardant_20: 0; prt_o_retardant_3: 0; prt_o_retardant_4: 0; prt_o_retardant_5: 0; prt_o_retardant_6: 0; prt_o_retardant_7: 0; prt_o_retardant_8: 0; prt_o_retardant_9: 0; prt_o_support_1: 0; prt_w_barrel_1: 0; prt_w_barrel_10: 0; prt_w_barrel_11: 0; prt_w_barrel_12: 0; prt_w_barrel_2: 0; prt_w_barrel_3: 0; prt_w_barrel_4: 0; prt_w_barrel_5: 0; prt_w_barrel_6: 0; prt_w_barrel_7: 0; prt_w_barrel_8: 0; prt_w_barrel_9: 0; prt_w_bolt_1: 0; prt_w_bolt_10: 0; prt_w_bolt_11: 0; prt_w_bolt_12: 0; prt_w_bolt_13: 0; prt_w_bolt_14: 0; prt_w_bolt_15: 0; prt_w_bolt_16: 0; prt_w_bolt_17: 0; prt_w_bolt_2: 0; prt_w_bolt_3: 0; prt_w_bolt_4: 0; prt_w_bolt_5: 0; prt_w_bolt_6: 0; prt_w_bolt_7: 0; prt_w_bolt_8: 0; prt_w_bolt_9: 0; prt_w_bolt_carrier_1: 0; prt_w_bolt_carrier_10: 0; prt_w_bolt_carrier_11: 0; prt_w_bolt_carrier_2: 0; prt_w_bolt_carrier_3: 0; prt_w_bolt_carrier_4: 0; prt_w_bolt_carrier_5: 0; prt_w_bolt_carrier_6: 0; prt_w_bolt_carrier_7: 0; prt_w_bolt_carrier_8: 0; prt_w_bolt_carrier_9: 0; prt_w_gas_tube_1: 0; prt_w_gas_tube_10: 0; prt_w_gas_tube_11: 0; prt_w_gas_tube_2: 0; prt_w_gas_tube_3: 0; prt_w_gas_tube_4: 0; prt_w_gas_tube_5: 0; prt_w_gas_tube_6: 0; prt_w_gas_tube_7: 0; prt_w_gas_tube_8: 0; prt_w_gas_tube_9: 0; prt_w_p_barrel_1: 0; prt_w_p_barrel_2: 0; prt_w_p_barrel_3: 0; prt_w_p_barrel_4: 0; prt_w_p_barrel_5: 0; prt_w_p_barrel_6: 0; prt_w_p_barrel_7: 0; prt_w_p_spring_1: 0; prt_w_p_spring_2: 0; prt_w_p_spring_3: 0; prt_w_p_spring_4: 0; prt_w_p_spring_5: 0; prt_w_p_spring_6: 0; prt_w_p_trigger_1: 0; prt_w_p_trigger_2: 0; prt_w_p_trigger_3: 0; prt_w_p_trigger_4: 0; prt_w_trigger_components_1: 0; prt_w_trigger_components_2: 0; prt_w_trigger_components_3: 0; prt_w_trigger_components_4: 0; prt_w_trigger_components_5: 0; prt_w_trigger_components_6: 0; quest_package_1: 0; quest_package_2: 0; quest_package_3: 0; quest_package_4: 0; quest_package_5: 0; quest_package_6: 0; quest_package_7: 0; quest_package_8: 0; radio: 0; radio2: 0; radio_connections_pda: 0; recipe_advanced_1: 0; recipe_advanced_2: 0; recipe_advanced_3: 0; recipe_advanced_4: 0; recipe_ammo_1: 0; recipe_ammo_2: 0; recipe_ammo_3: 0; recipe_ammo_4: 0; recipe_basic_1: 0; recipe_basic_2: 0; recipe_basic_3: 0; recipe_basic_4: 0; recipe_cooking_1: 0; recipe_drug_1: 0; recipe_drug_2: 0; recipe_drug_3: 0; recipe_drug_4: 0; recipe_expert_1: 0; recipe_expert_2: 0; recipe_expert_3: 0; recipe_expert_4: 0; recover_mutant_data_device: 0; renegade_patch: 0; rioc_duty_item: 0; rioc_ecolog_item: 0; rioc_sid_item_1: 0; rioc_sid_item_2: 0; shovel_mili: 0; shovel_old: 0; sigaret_for_nps: 0; special_delivery_case: 0; stalker_patch: 0; steel_wool: 0; stick_bred: 0; stick_kolbasa: 0; stick_kolbasa_bred: 0; stitch_decoder: 0; strelok_notes: 0; strelok_pendrive: 0; swiss_knife: 0; synthrope: 0; tarpaulin: 0; tch_fuel_1_ico: 0; tch_fuel_2_ico: 0; tch_junk: 0; tch_letter: 0; tch_meal_1_ico: 0; tch_meal_2_ico: 0; tch_part: 0; tch_part_con: 0; tch_quest: 0; tch_repair0: 0; tch_upgr: 0; tch_upgr_ico: 0; toolkit_1: 0; toolkit_2: 0; toolkit_3: 0; underwear: 0; upgr_o_1_armor: 0; upgr_o_1_arty: 0; upgr_o_1_bleed: 0; upgr_o_1_burn: 0; upgr_o_1_carry: 0; upgr_o_1_chem: 0; upgr_o_1_damage: 0; upgr_o_1_durability: 0; upgr_o_1_health: 0; upgr_o_1_power: 0; upgr_o_1_psi: 0; upgr_o_1_rad: 0; upgr_o_1_run: 0; upgr_o_1_shock: 0; upgr_o_1_weight: 0; upgr_o_2_armor: 0; upgr_o_2_arty: 0; upgr_o_2_bleed: 0; upgr_o_2_burn: 0; upgr_o_2_carry: 0; upgr_o_2_chem: 0; upgr_o_2_damage: 0; upgr_o_2_durability: 0; upgr_o_2_health: 0; upgr_o_2_power: 0; upgr_o_2_psi: 0; upgr_o_2_rad: 0; upgr_o_2_run: 0; upgr_o_2_shock: 0; upgr_o_2_weight: 0; upgr_o_3_armor: 0; upgr_o_3_arty: 0; upgr_o_3_bleed: 0; upgr_o_3_burn: 0; upgr_o_3_carry: 0; upgr_o_3_chem: 0; upgr_o_3_damage: 0; upgr_o_3_durability: 0; upgr_o_3_health: 0; upgr_o_3_power: 0; upgr_o_3_psi: 0; upgr_o_3_rad: 0; upgr_o_3_run: 0; upgr_o_3_shock: 0; upgr_o_3_weight: 0; upgr_w_1_calibre: 0; upgr_w_1_dispersion: 0; upgr_w_1_firemode: 0; upgr_w_1_grenade_mount: 0; upgr_w_1_inertion: 0; upgr_w_1_magazine: 0; upgr_w_1_muffle: 0; upgr_w_1_recoil: 0; upgr_w_1_reliability: 0; upgr_w_1_rpm: 0; upgr_w_1_scope: 0; upgr_w_1_scope_mount: 0; upgr_w_1_speed: 0; upgr_w_1_weight: 0; upgr_w_2_calibre: 0; upgr_w_2_dispersion: 0; upgr_w_2_firemode: 0; upgr_w_2_grenade_mount: 0; upgr_w_2_inertion: 0; upgr_w_2_magazine: 0; upgr_w_2_muffle: 0; upgr_w_2_recoil: 0; upgr_w_2_reliability: 0; upgr_w_2_rpm: 0; upgr_w_2_scope: 0; upgr_w_2_scope_mount: 0; upgr_w_2_speed: 0; upgr_w_2_weight: 0; upgr_w_3_calibre: 0; upgr_w_3_dispersion: 0; upgr_w_3_firemode: 0; upgr_w_3_grenade_mount: 0; upgr_w_3_inertion: 0; upgr_w_3_magazine: 0; upgr_w_3_muffle: 0; upgr_w_3_recoil: 0; upgr_w_3_reliability: 0; upgr_w_3_rpm: 0; upgr_w_3_scope: 0; upgr_w_3_scope_mount: 0; upgr_w_3_speed: 0; upgr_w_3_weight: 0; vodnik_notes: 0; walkie: 0; welding_goggles: 0; wpn_addon_scope: 0; wpn_addon_scope_acog: 0; wpn_addon_scope_acog_night: 0; wpn_addon_scope_acog_trijicon: 0; wpn_addon_scope_detector: 0; wpn_addon_scope_g43: 0; wpn_addon_scope_galil: 0; wpn_addon_scope_m24: 0; wpn_addon_scope_moist: 0; wpn_addon_scope_mosin: 0; wpn_addon_scope_night: 0; wpn_addon_scope_po4x34: 0; wpn_addon_scope_pu: 0; wpn_addon_scope_pu9130: 0; wpn_addon_scope_susat: 0; wpn_addon_scope_susat_custom: 0; wpn_addon_scope_susat_dusk: 0; wpn_addon_scope_susat_moist: 0; wpn_addon_scope_susat_night: 0; wpn_addon_scope_susat_worn: 0; 'wpn_addon_scope_susat_x1.6': 0; wpn_addon_scope_sv98: 0; wpn_addon_scope_vsk: 0; wpn_addon_scope_worn: 0; wpn_addon_scope_ww2: 0; wpn_addon_scope_ww2_moist: 0; wpn_addon_scope_ww2_worn: 0; 'wpn_addon_scope_x2.7': 0; wpn_addon_scope_zf4: 0; wpn_addon_scope_zf4_moist: 0; wpn_addon_scope_zf4_worn: 0; wpn_addon_scope_zf9: 0; wpn_addon_silencer: 0; wpn_sil_45: 0; wpn_sil_57: 0; wpn_sil_6p9: 0; wpn_sil_9a91: 0; wpn_sil_9mm: 0; wpn_sil_aps: 0; wpn_sil_atg: 0; wpn_sil_gemtech: 0; wpn_sil_kzrzp: 0; wpn_sil_nato: 0; wpn_sil_pbs1: 0; wpn_sil_pbs4: 0; wpn_sil_sr25: 0; 'wpn_sil_tgp-a': 0; wpn_sil_vihr: 0; x8_documents: 0; zat_a23_gauss_rifle_docs: 0; zat_b12_documents_1: 0; zat_b12_documents_2: 0; zat_b20_noah_pda: 0; zat_b22_medic_pda: 0; zat_b33_safe_container: 0; zat_b39_joker_pda: 0; zat_b40_notebook: 0; zat_b40_pda_1: 0; zat_b40_pda_2: 0; zat_b40_sarge_pda: 0; zat_b44_barge_pda: 0; zat_b57_gas: 0; } export type Attachment = keyof Attachments; export interface Weapons { mounted_weapon: 0; stationary_mgun: 0; wpn_9a91: 0; wpn_9a91_1p29: 0; wpn_9a91_kobra: 0; wpn_9a91_ps01: 0; wpn_9a91_pso1m21: 0; wpn_abakan: 0; wpn_abakan_1p29: 0; wpn_abakan_camo: 0; wpn_abakan_camo_1p29: 0; wpn_abakan_camo_kobra: 0; wpn_abakan_camo_ps01: 0; wpn_abakan_kobra: 0; wpn_abakan_ps01: 0; wpn_ace21: 0; wpn_ace21_ac10632: 0; wpn_ace21_acog: 0; wpn_ace21_eot: 0; wpn_addon_grenade_launcher: 0; wpn_addon_grenade_launcher_m203: 0; wpn_aek: 0; wpn_aek_1p29: 0; wpn_aek_camo: 0; wpn_aek_camo_1p29: 0; wpn_aek_camo_kobra: 0; wpn_aek_camo_ps01: 0; wpn_aek_duty: 0; wpn_aek_duty_1p29: 0; wpn_aek_duty_kobra: 0; wpn_aek_duty_ps01: 0; wpn_aek_kobra: 0; wpn_aek_ps01: 0; wpn_ak: 0; wpn_ak101: 0; wpn_ak101_1p29: 0; wpn_ak101_ac10632: 0; wpn_ak101_acog: 0; wpn_ak101_camo: 0; wpn_ak101_camo_1p29: 0; wpn_ak101_camo_ac10632: 0; wpn_ak101_camo_acog: 0; wpn_ak101_camo_eot: 0; wpn_ak101_camo_kobra: 0; wpn_ak101_camo_ps01: 0; wpn_ak101_eot: 0; wpn_ak101_kobra: 0; wpn_ak101_ps01: 0; wpn_ak102: 0; wpn_ak102_1p29: 0; wpn_ak102_ac10632: 0; wpn_ak102_acog: 0; wpn_ak102_eot: 0; wpn_ak102_kobra: 0; wpn_ak102_ps01: 0; wpn_ak103: 0; wpn_ak103_1p29: 0; wpn_ak103_camo: 0; wpn_ak103_camo_1p29: 0; wpn_ak103_camo_kobra: 0; wpn_ak103_camo_ps01: 0; wpn_ak103_kobra: 0; wpn_ak103_ps01: 0; wpn_ak104: 0; wpn_ak104_1p29: 0; wpn_ak104_kobra: 0; wpn_ak104_ps01: 0; wpn_ak105: 0; wpn_ak105_1p29: 0; wpn_ak105_kobra: 0; wpn_ak105_ps01: 0; wpn_ak12: 0; wpn_ak12_ac10632: 0; wpn_ak12_acog: 0; wpn_ak12_eot: 0; wpn_ak74: 0; wpn_ak74_1p29: 0; wpn_ak74_alt: 0; wpn_ak74_alt_1p29: 0; wpn_ak74_alt_kobra: 0; wpn_ak74_alt_ps01: 0; wpn_ak74_custom: 0; wpn_ak74_custom_1p29: 0; wpn_ak74_custom_kobra: 0; wpn_ak74_custom_ps01: 0; wpn_ak74_kobra: 0; wpn_ak74_modern: 0; wpn_ak74_modern_1p29: 0; wpn_ak74_modern_kobra: 0; wpn_ak74_modern_ps01: 0; wpn_ak74_old: 0; wpn_ak74_ps01: 0; wpn_ak74_rpk: 0; wpn_ak74m: 0; wpn_ak74m_1p29: 0; wpn_ak74m_alt: 0; wpn_ak74m_alt_1p29: 0; wpn_ak74m_alt_kobra: 0; wpn_ak74m_alt_ps01: 0; wpn_ak74m_camo: 0; wpn_ak74m_camo_1p29: 0; wpn_ak74m_camo_kobra: 0; wpn_ak74m_camo_ps01: 0; wpn_ak74m_custom: 0; wpn_ak74m_custom_1p29: 0; wpn_ak74m_custom_kobra: 0; wpn_ak74m_custom_ps01: 0; wpn_ak74m_duty: 0; wpn_ak74m_duty_1p29: 0; wpn_ak74m_duty_kobra: 0; wpn_ak74m_duty_ps01: 0; wpn_ak74m_kobra: 0; wpn_ak74m_pka: 0; wpn_ak74m_ps01: 0; wpn_ak74u: 0; wpn_ak74u_1p29: 0; wpn_ak74u_camo: 0; wpn_ak74u_camo_1p29: 0; wpn_ak74u_camo_kobra: 0; wpn_ak74u_camo_ps01: 0; wpn_ak74u_custom: 0; wpn_ak74u_custom_1p29: 0; wpn_ak74u_custom_kobra: 0; wpn_ak74u_custom_ps01: 0; wpn_ak74u_kobra: 0; wpn_ak74u_old: 0; wpn_ak74u_ps01: 0; wpn_ak74u_snag: 0; wpn_akm: 0; wpn_akm_1p29: 0; wpn_akm_kobra: 0; wpn_akm_ps01: 0; wpn_akms: 0; wpn_akms_1p29: 0; wpn_akms_alt: 0; wpn_akms_alt_1p29: 0; wpn_akms_alt_kobra: 0; wpn_akms_alt_ps01: 0; wpn_akms_kobra: 0; wpn_akms_ps01: 0; wpn_aks: 0; wpn_aks74: 0; wpn_aks74_1p29: 0; wpn_aks74_kobra: 0; wpn_aks74_new: 0; wpn_aks74_new_1p29: 0; wpn_aks74_new_kobra: 0; wpn_aks74_new_ps01: 0; wpn_aks74_ps01: 0; wpn_aps: 0; wpn_ash12: 0; wpn_ash12_ac10632: 0; wpn_ash12_acog: 0; 'wpn_ash12_c-more': 0; wpn_ash12_eot: 0; wpn_aug: 0; wpn_aug_a3: 0; wpn_aug_a3_ac10632: 0; wpn_aug_a3_acog: 0; 'wpn_aug_a3_c-more': 0; wpn_aug_a3_eot: 0; wpn_aug_custom: 0; wpn_aug_freedom: 0; wpn_aug_merc: 0; wpn_aug_modern: 0; wpn_axe: 0; wpn_axe2: 0; wpn_axe3: 0; wpn_beretta: 0; wpn_beretta_alt: 0; wpn_beretta_camo: 0; wpn_beretta_modern: 0; wpn_binoc: 0; wpn_binoc_inv: 0; wpn_bizon: 0; wpn_bizon_1p29: 0; wpn_bizon_kobra: 0; wpn_bizon_ps01: 0; wpn_bm16: 0; wpn_bm16_alt: 0; wpn_bm16_full: 0; wpn_bm16_full_alt: 0; wpn_colt1911: 0; wpn_colt1911_alt: 0; wpn_colt1911_camo: 0; wpn_colt1911_custom: 0; wpn_colt1911_duty: 0; wpn_colt1911_merc: 0; wpn_colt1911_modern: 0; wpn_colt1911_new: 0; wpn_colt_kimber: 0; wpn_cz52: 0; wpn_cz75: 0; wpn_cz75_auto: 0; wpn_desert_eagle: 0; wpn_desert_eagle_custom: 0; wpn_desert_eagle_modern: 0; wpn_desert_eagle_nimble: 0; wpn_dynamo_hand: 0; wpn_fal: 0; wpn_fal_ac10632: 0; wpn_fal_acog: 0; 'wpn_fal_c-more': 0; wpn_fal_eot: 0; wpn_famas3: 0; wpn_famas3_ac10632: 0; wpn_famas3_acog: 0; wpn_famas3_eot: 0; wpn_fn2000: 0; wpn_fn2000_camo: 0; wpn_fn2000_custom: 0; wpn_fn2000_nimble: 0; wpn_fn57: 0; wpn_fnc: 0; wpn_fnp45: 0; wpn_fnp45_custom: 0; wpn_fnx45: 0; wpn_fnx45_alt: 0; wpn_fnx45_custom: 0; wpn_fort: 0; wpn_fort500: 0; wpn_fort_snag: 0; wpn_g3: 0; wpn_g36: 0; wpn_g36_camo: 0; wpn_g36_nimble: 0; wpn_g36k: 0; wpn_g3_ac10632: 0; wpn_g3_acog: 0; wpn_g3_eot: 0; wpn_g3sg1: 0; wpn_g43: 0; wpn_galil: 0; wpn_galil_custom: 0; wpn_galil_modern: 0; wpn_gauss: 0; wpn_gauss_quest: 0; wpn_glock: 0; wpn_glock_custom: 0; wpn_glock_modern: 0; wpn_groza: 0; wpn_groza_nimble: 0; wpn_gsh18: 0; wpn_gsh18_custom: 0; wpn_hk416: 0; wpn_hk416_ac10632: 0; wpn_hk416_acog: 0; wpn_hk416_eot: 0; wpn_hk417: 0; wpn_hk417_acog: 0; wpn_hk417_eot: 0; wpn_hpsa: 0; wpn_hpsa_alt: 0; wpn_k98: 0; wpn_kiparis: 0; wpn_knife: 0; wpn_knife2: 0; wpn_knife3: 0; wpn_knife4: 0; wpn_knife5: 0; wpn_l85: 0; wpn_l85_alt: 0; wpn_l85_custom: 0; wpn_l85_modern: 0; wpn_l85a2: 0; wpn_l85a2_alt: 0; wpn_l85a2_custom: 0; wpn_l85a2_modern: 0; wpn_l96a1: 0; wpn_l96a1m: 0; wpn_lr300: 0; wpn_lr300_ac10632: 0; wpn_lr300_acog: 0; wpn_lr300_camo: 0; wpn_lr300_camo_ac10632: 0; wpn_lr300_camo_acog: 0; wpn_lr300_camo_eot: 0; wpn_lr300_custom: 0; wpn_lr300_custom_ac10632: 0; wpn_lr300_custom_acog: 0; wpn_lr300_custom_eot: 0; wpn_lr300_eot: 0; wpn_m16: 0; wpn_m16_ac10632: 0; wpn_m16_acog: 0; wpn_m16_eot: 0; wpn_m16a2: 0; wpn_m24: 0; wpn_m249: 0; wpn_m249_ac10632: 0; wpn_m249_acog: 0; wpn_m249_eot: 0; wpn_m4: 0; wpn_m4_ac10632: 0; wpn_m4_acog: 0; wpn_m4_eot: 0; wpn_m4a1: 0; wpn_m4a1_ac10632: 0; wpn_m4a1_acog: 0; wpn_m4a1_camo: 0; wpn_m4a1_camo_ac10632: 0; wpn_m4a1_camo_acog: 0; wpn_m4a1_camo_eot: 0; wpn_m4a1_custom: 0; wpn_m4a1_custom_ac10632: 0; wpn_m4a1_custom_acog: 0; wpn_m4a1_custom_eot: 0; wpn_m4a1_eot: 0; wpn_m4a1_freedom: 0; wpn_m4a1_freedom_ac10632: 0; wpn_m4a1_freedom_acog: 0; wpn_m4a1_freedom_eot: 0; wpn_m60: 0; wpn_m79: 0; wpn_m82: 0; wpn_m98b: 0; wpn_mk14: 0; wpn_mk14_ac10632: 0; wpn_mk14_acog: 0; 'wpn_mk14_c-more': 0; wpn_mk14_eot: 0; wpn_mosin: 0; wpn_mossberg590: 0; wpn_mp133: 0; wpn_mp153: 0; wpn_mp412: 0; wpn_mp443: 0; wpn_mp5: 0; wpn_mp5_ac10632: 0; wpn_mp5_acog: 0; wpn_mp5_alt: 0; wpn_mp5_alt_ac10632: 0; wpn_mp5_alt_acog: 0; wpn_mp5_alt_eot: 0; wpn_mp5_custom: 0; wpn_mp5_custom_ac10632: 0; wpn_mp5_custom_acog: 0; wpn_mp5_custom_eot: 0; wpn_mp5_eot: 0; wpn_mp5_nimble: 0; wpn_mp5_nimble_ac10632: 0; wpn_mp5_nimble_acog: 0; wpn_mp5_nimble_eot: 0; wpn_mp5sd: 0; wpn_mp5sd_ac10632: 0; wpn_mp5sd_acog: 0; wpn_mp5sd_custom: 0; wpn_mp5sd_custom_ac10632: 0; wpn_mp5sd_custom_acog: 0; wpn_mp5sd_custom_eot: 0; wpn_mp5sd_eot: 0; wpn_mp5sd_new: 0; wpn_mp5sd_new_ac10632: 0; wpn_mp5sd_new_acog: 0; wpn_mp5sd_new_eot: 0; wpn_mp7: 0; wpn_mp7_ac10632: 0; wpn_mp7_acog: 0; 'wpn_mp7_c-more': 0; wpn_mp7_eot: 0; wpn_oc33: 0; wpn_p90: 0; wpn_p90_ac10632: 0; wpn_p90_acog: 0; wpn_p90_eot: 0; wpn_pb: 0; wpn_pb_custom: 0; wpn_pkm: 0; wpn_pkm_zulus: 0; wpn_pkp: 0; wpn_pm: 0; wpn_pm_custom: 0; wpn_pmm: 0; wpn_pp2000: 0; wpn_pp2000_ac10632: 0; wpn_pp2000_acog: 0; wpn_pp2000_eot: 0; wpn_ppsh41: 0; wpn_ppsh41_rednew: 0; wpn_ppsh41_woodnew: 0; wpn_protecta: 0; wpn_protecta_aim: 0; wpn_protecta_camo: 0; wpn_protecta_custom: 0; wpn_protecta_nimble: 0; wpn_remington700: 0; wpn_remington870: 0; wpn_remington870_ac10632: 0; 'wpn_remington870_c-more': 0; wpn_remington870_eot: 0; 'wpn_rg-6': 0; wpn_rpd: 0; wpn_rpg7: 0; wpn_rpk: 0; wpn_rpk74: 0; wpn_rpk74_1p29: 0; wpn_rpk74_kobra: 0; wpn_rpk74_ps01: 0; wpn_saiga12s: 0; wpn_saiga12s_1p29: 0; wpn_saiga12s_kobra: 0; wpn_saiga12s_ps01: 0; wpn_scar: 0; wpn_scar_ac10632: 0; wpn_scar_acog: 0; wpn_scar_custom: 0; wpn_scar_custom_ac10632: 0; wpn_scar_custom_acog: 0; wpn_scar_custom_eot: 0; wpn_scar_eot: 0; wpn_scar_new: 0; wpn_scar_new_ac10632: 0; wpn_scar_new_acog: 0; wpn_scar_new_eot: 0; wpn_sig220: 0; wpn_sig220_custom: 0; wpn_sig220_nimble: 0; wpn_sig550: 0; wpn_sig550_ac10632: 0; wpn_sig550_acog: 0; wpn_sig550_camo: 0; wpn_sig550_camo_ac10632: 0; wpn_sig550_camo_acog: 0; wpn_sig550_camo_eot: 0; wpn_sig550_custom: 0; wpn_sig550_custom_ac10632: 0; wpn_sig550_custom_acog: 0; wpn_sig550_custom_eot: 0; wpn_sig550_eot: 0; wpn_sig550_luckygun: 0; wpn_sig550_luckygun_ac10632: 0; wpn_sig550_luckygun_acog: 0; wpn_sig550_luckygun_eot: 0; wpn_sig550_sniper: 0; wpn_sig552: 0; wpn_sig552_ac10632: 0; wpn_sig552_acog: 0; wpn_sig552_eot: 0; wpn_sks: 0; wpn_sks_modern: 0; wpn_spas12: 0; wpn_spas12_custom: 0; wpn_spas12_nimble: 0; wpn_sr25: 0; wpn_sv98: 0; wpn_sv98_custom: 0; wpn_svd: 0; wpn_svd_1p29: 0; wpn_svd_custom: 0; wpn_svd_custom_1p29: 0; wpn_svd_custom_kobra: 0; wpn_svd_custom_ps01: 0; wpn_svd_kobra: 0; wpn_svd_nimble: 0; wpn_svd_ps01: 0; wpn_svt40: 0; wpn_svt40_modern: 0; wpn_svu: 0; wpn_svu_1p29: 0; wpn_svu_alt: 0; wpn_svu_alt_1p29: 0; wpn_svu_alt_kobra: 0; wpn_svu_alt_ps01: 0; wpn_svu_kobra: 0; wpn_svu_nimble: 0; wpn_svu_nimble_1p29: 0; wpn_svu_nimble_kobra: 0; wpn_svu_nimble_ps01: 0; wpn_svu_ps01: 0; wpn_toz34: 0; wpn_toz34_bull: 0; wpn_toz34_custom: 0; wpn_toz34_decor: 0; wpn_toz34_mark4: 0; wpn_toz34_obrez: 0; wpn_toz34_obrez_custom: 0; wpn_toz34_obrez_decor: 0; wpn_trg: 0; wpn_tt33: 0; wpn_tt33_modern: 0; wpn_type63: 0; wpn_ump45: 0; wpn_ump45_ac10632: 0; wpn_ump45_acog: 0; wpn_ump45_custom: 0; wpn_ump45_custom_ac10632: 0; wpn_ump45_custom_acog: 0; wpn_ump45_custom_eot: 0; wpn_ump45_eot: 0; wpn_upd: 0; wpn_usas12: 0; wpn_usp: 0; wpn_usp_custom: 0; wpn_usp_match: 0; wpn_usp_nimble: 0; wpn_val: 0; wpn_val_1p29: 0; wpn_val_kobra: 0; wpn_val_modern: 0; wpn_val_modern_1p29: 0; wpn_val_modern_kobra: 0; wpn_val_modern_ps01: 0; wpn_val_pso1m21: 0; wpn_vepr: 0; wpn_vepr_1p29: 0; wpn_vepr_kobra: 0; wpn_vepr_ps01: 0; wpn_vihr: 0; wpn_vihr_1p29: 0; wpn_vihr_kobra: 0; wpn_vihr_ps01: 0; wpn_vihr_pso1m21: 0; wpn_vintorez: 0; wpn_vintorez_1p29: 0; wpn_vintorez_1pn93: 0; wpn_vintorez_alt: 0; wpn_vintorez_alt_1p29: 0; wpn_vintorez_alt_kobra: 0; wpn_vintorez_alt_pso1m21: 0; wpn_vintorez_kobra: 0; wpn_vintorez_nimble: 0; wpn_vintorez_pso1m21: 0; wpn_vityaz: 0; wpn_vityaz_ac10632: 0; wpn_vityaz_acog: 0; wpn_vityaz_eot: 0; wpn_vsk94: 0; wpn_vsk94_1p29: 0; wpn_vsk94_kobra: 0; wpn_vsk94_pso1m21: 0; wpn_vssk: 0; wpn_vz61: 0; wpn_vz61_alt: 0; wpn_vz61_camo: 0; wpn_vz61_freedom: 0; wpn_wa2000: 0; wpn_walther: 0; wpn_walther_custom: 0; wpn_wincheaster1300: 0; wpn_wincheaster1300_trapper: 0; wpn_xm8: 0; wpn_xm8_ac10632: 0; wpn_xm8_ac11090: 0; wpn_xm8_acog: 0; 'wpn_xm8_c-more': 0; wpn_xm8_eot: 0; yantar_deployable_mgun: 0; } export type Weapon = keyof Weapons; export interface Grenades { ammo_m209: 0; ammo_m209_bad: 0; ammo_m209_verybad: 0; 'ammo_og-7b': 0; 'ammo_og-7b_bad': 0; 'ammo_og-7b_verybad': 0; 'ammo_vog-25': 0; 'ammo_vog-25_bad': 0; 'ammo_vog-25_verybad': 0; gl_fake_missile_ammo_m209: 0; 'gl_fake_missile_ammo_vog-25': 0; 'gl_fake_missile_ammo_vog-25p': 0; grenade_f1: 0; 'grenade_gd-05': 0; grenade_rgd5: 0; grenade_smoke: 0; wpn_fake_missile: 0; wpn_fake_missile1: 0; wpn_fake_missile2: 0; wpn_rpg7_missile: 0; } export type Grenade = keyof Grenade