Skip to content

DearCrazyLeaf/EmitSoundEditor

Repository files navigation

CounterStrikeSharp


EmitSoundEditor

Guide

中文版介绍 Release License Issues Pull Requests Downloads GitHub Stars

A Counter-Strike 2 server plugin that replaces weapon fire sounds based on equipped custom subclasses or official weapon definitions

Features

  • Custom weapon override: play a custom soundevent when a player fires a store-equipped subclass
  • Official weapon fallback: map normal weapons by item_def_index to duplicated soundevents
  • Silencer aware: optional target_event_unsilenced for M4A1-S / USP-S
  • Low overhead: constant-time lookups per fire event

Requirements

Installation

  1. Download the latest release
  2. Extract to game/csgo/addons/counterstrikesharp/plugins/EmitSoundEditor
  3. Restart the server or load the plugin

Configuration

Path .\counterstrikesharp\configs\plugins\EmitSoundEditor\EmitSoundEditor.json:

{
  "overrides": [
    {
      "subclass": "weapon_ak47+13",
      "target_event": "weapon.example.fire"
    },
    {
      "subclass": "weapon_m4a1_silencer+25",
      "target_event": "weapon.example.fire_silenced",
      "target_event_unsilenced": "weapon.example.fire"
    }
  ],
  "official_overrides": [
    {
      "item_def_index": 7,
      "target_event": "dup.Weapon_AK47.Single"
    },
    {
      "item_def_index": 60,
      "target_event": "dup.Weapon_M4A1.Silenced",
      "target_event_unsilenced": "dup.Weapon_M4A4.Single"
    }
  ],
  "force_mute_all_firebullets": false,
  "custom_sound_default_enabled": true,
  "mysql": {
    "enabled": false,
    "host": "127.0.0.1",
    "port": 3306,
    "database": "cs2",
    "user": "root",
    "password": "",
    "table": "emsound_settings"
  }
}

Fields

Field Type Description
overrides array Custom weapon subclass overrides.
overrides[].subclass string Right side of weapon_base:subclass
overrides[].target_event string Soundevent to play on fire
overrides[].target_event_unsilenced string Optional; used when the silencer is off
official_overrides array Fallback mapping by item_def_index to duplicated soundevents (example prefix: dup.)
official_overrides[].item_def_index number Official weapon item definition index
official_overrides[].target_event string Duplicated soundevent to play on fire
official_overrides[].target_event_unsilenced string Optional; used when the silencer is off
force_mute_all_firebullets boolean Optional global mute for native firebullet sounds
custom_sound_default_enabled boolean Default state for !emsound (custom sounds on/off)
mysql object Optional persistence for the !emsound toggle
mysql.enabled boolean Enable MySQL storage for per-player toggle
mysql.host string MySQL host
mysql.port number MySQL port
mysql.database string MySQL database name
mysql.user string MySQL user
mysql.password string MySQL password
mysql.table string Table name for toggle storage

Toggle command + database

  • !emsound toggles custom sounds for the caller only and prints a localized message
  • If MySQL is enabled, the toggle is saved per SteamID and restored on reconnect

Store + subclass setup (AG2 custom weapons)

Short version (see Wiki for the full guide):

  • Store uses base:subclass in the weapon field (e.g., weapon_knife:weapon_knife_karambit+1550)
  • weapons.vdata defines the subclass only (e.g., weapon_knife_karambit+1550)
  • EmitSoundEditor.json uses subclass only in overrides[].subclass

How it works:

  • On equip or entity creation, the Store plugin parses base:subclass and calls ChangeSubclass when the active base matches
  • Inspect temporarily swaps the active weapon's subclass and then resets it
  • Only one skin is equipped per weapon base to avoid conflicts

Store config example:

"Custom Weapon": {
  "karambit": {
    "karambit_custom": {
      "uniqueid": "karambitcustom",
      "type": "customweapon",
      "weapon": "weapon_knife:weapon_knife_karambit+1550",
      "price": "1000",
      "slot": "1"
    }
  }
}

Note

Vdata note:

  • Add a subclass entry like weapon_knife_karambit+1550 and point m_szModel_AG2 to your model
  • Ensure the .vmdl_c exists under your addon path (uploaded/compiled)

Workflow Overview

  1. Author your soundevents (use any naming scheme you like)
  2. Compile sounds and .vsndevts
  3. Package to VPK / Workshop and distribute to clients
  4. Configure EmitSoundEditor.json

Required mute + duplicate soundevents

AG2 ignores subclass fire-sound changes in weapons.vdata, so you must mute the original fire events and replay sounds via the plugin.

  • mute_sounds.vsndevts: contains the official parent fire events (e.g., Weapon_AK47.Single, silenced variants) but with volume = 0. These are referenced by weapons.vdata, so muting them prevents double sound.
  • dup_sounds.vsndevts: exact copies of those events, but with new names (example prefix: dup.) and normal volume. The plugin uses these for non-custom weapons so default guns still sound normal.
  • your custom file (example: custom_sounds.vsndevts): contains your custom fire events.

If you only mute without duplicates, all default weapons become silent. All three files must be compiled and packaged together, and their event names must match your plugin config.

Custom vsndevts naming

  • If you do not use soundevents_addon.vsndevts, the engine will not auto-register your soundevents file. You must precache the custom .vsndevts via Resource Precacher, otherwise events may not play.

Recommended: use a custom filename to avoid map conflicts, and always precache it

Notes

  • target_event_unsilenced only applies to silencer-capable weapons (M4A1-S / USP-S)
  • If a custom subclass is equipped, it takes priority over official_overrides

Full Guide:

License

GPL v3 License

中文版介绍

Guide

English Release License Issues Pull Requests Downloads GitHub Stars

一个用于 CS2 服务器的枪声替换插件,可根据商店自定义武器或官方武器类型播放指定音效事件

功能

  • 自定义武器替换:根据商店装备的 subclass 播放指定音效
  • 官方武器回退:按 item_def_index 映射官方武器事件副本
  • 消音器识别:支持 target_event_unsilenced 分支
  • 性能友好:开火事件使用常量时间查找

依赖

安装

  1. 下载最新版本
  2. 解压到 game/csgo/addons/counterstrikesharp/plugins/EmitSoundEditor
  3. 重启服务器或加载插件

配置说明

路径 .\counterstrikesharp\configs\plugins\EmitSoundEditor\EmitSoundEditor.json

{
  "overrides": [
    {
      "subclass": "weapon_ak47+13",
      "target_event": "weapon.example.fire"
    },
    {
      "subclass": "weapon_m4a1_silencer+25",
      "target_event": "weapon.example.fire_silenced",
      "target_event_unsilenced": "weapon.example.fire"
    }
  ],
  "official_overrides": [
    {
      "item_def_index": 7,
      "target_event": "dup.Weapon_AK47.Single"
    },
    {
      "item_def_index": 60,
      "target_event": "dup.Weapon_M4A1.Silenced",
      "target_event_unsilenced": "dup.Weapon_M4A4.Single"
    }
  ],
  "force_mute_all_firebullets": false,
  "custom_sound_default_enabled": true,
  "mysql": {
    "enabled": false,
    "host": "127.0.0.1",
    "port": 3306,
    "database": "cs2",
    "user": "root",
    "password": "",
    "table": "emsound_settings"
  }
}

字段说明

字段 类型 说明
overrides array 自定义武器替换列表
overrides[].subclass string weapon_base:subclass 的右侧部分
overrides[].target_event string 开火时播放的音效事件
overrides[].target_event_unsilenced string 可选,不消音时使用。
official_overrides array 官方武器事件副本映射(建议使用 dup. 之类的前缀)
official_overrides[].item_def_index number 官方武器定义索引
official_overrides[].target_event string 对应的副本音效事件
official_overrides[].target_event_unsilenced string 可选,不消音时使用
force_mute_all_firebullets boolean 可选,全局静音原始开火音效
custom_sound_default_enabled boolean !emsound 的默认状态(自定义音效开/关)
mysql object 可选,!emsound 开关的持久化存储配置
mysql.enabled boolean 是否启用 MySQL 存储玩家开关状态
mysql.host string MySQL地址
mysql.port number MySQL端口
mysql.database string 数据库名称
mysql.user string 数据库用户名
mysql.password string 数据库密码
mysql.table string 保存开关状态的表名

开关指令 + 数据库

  • !emsound 用于切换是否播放自定义音效(只对自己生效)
  • 如果启用了 MySQL,则开关状态会按 SteamID 保存在数据库中,并在重新连接时读取

商店与子类配置(AG2)

简版说明(完整内容见 Wiki)

  • 商店 weapon 使用 base:subclass(例如 weapon_knife:weapon_knife_karambit+1550
  • weapons.vdata 只定义 subclass(例如 weapon_knife_karambit+1550
  • EmitSoundEditor.jsonoverrides[].subclass 也只填 subclass

工作流程

  • 装备或实体创建时,商店插件解析 base:subclass,当武器 base 匹配时调用 ChangeSubclass
  • 检视会临时切换当前武器的 subclass,之后恢复
  • 同一 base 只允许装备一个皮肤,避免冲突

商店配置示例:

"Custom Weapon": {
  "karambit": {
    "karambit_custom": {
      "uniqueid": "karambitcustom",
      "type": "customweapon",
      "weapon": "weapon_knife:weapon_knife_karambit+1550",
      "price": "1000",
      "slot": "1"
    }
  }
}

Note

Vdata 说明:

  • 添加 subclass 条目,例如 weapon_knife_karambit+1550,并将 m_szModel_AG2 指向你的模型路径
  • 确保 .vmdl_c 已在 addon 路径中(已上传/编译)

使用流程概要

  1. 编写音效事件文件
  2. 编译 sounds 与 .vsndevts
  3. 打包并分发资源
  4. 配置 EmitSoundEditor.json

必需的静音与副本音效事件

AG2 下 weapons.vdata 的 subclass 开火音效不会生效,因此必须先静音原始事件,再由插件播放

  • mute_sounds.vsndevts:写入父级官方开火事件(例如 Weapon_AK47.Single 及消音变体),但把 volume = 0。这些事件被 weapons.vdata 引用,静音可避免原声叠加
  • dup_sounds.vsndevts:上述事件的副本,名称改成新前缀(示例:dup.),音量正常。插件用它来给非自定义武器播放默认音效
  • 自定义音效文件(如 custom_sounds.vsndevts):放你的自定义开火事件

只静音而不做副本,会导致所有默认武器无声。三份文件必须一起编译与打包,事件名称必须与插件配置保持一致

自定义 vsndevts 文件名

  • 如果不使用 soundevents_addon.vsndevts,引擎不会自动注册你的 soundevents 文件,此时必须通过 Resource Precacher 预载该自定义 .vsndevts,否则事件可能无法播放

建议使用自定义文件名以避免与地图冲突,并务必进行预载

注意事项

  • target_event_unsilenced 仅适用于可装消音器的武器(M4A1-S / USP-S)
  • 若装备了自定义 subclass,将优先生效,覆盖 official_overrides

详情见

许可协议

GPL v3 License

About

A Counter-Strike 2 server plugin that replaces weapon fire sounds based on equipped custom subclasses or official weapon definitions.

Resources

License

Stars

Watchers

Forks

Packages

No packages published

Languages