├── .editorconfig ├── .gitattributes ├── .github ├── FUNDING.yml └── workflows │ └── ci.yml ├── .gitignore ├── CHANGELOG.md ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── addons ├── sourcemod │ ├── configs │ │ ├── shavit-advertisements.cfg │ │ ├── shavit-chat.cfg │ │ ├── shavit-chatsettings.cfg │ │ ├── shavit-mapfixes.cfg │ │ ├── shavit-messages.cfg │ │ ├── shavit-prefix.txt │ │ ├── shavit-readme.txt │ │ ├── shavit-replay.cfg │ │ ├── shavit-sounds.cfg │ │ ├── shavit-styles.cfg │ │ └── shavit-zones.cfg │ ├── gamedata │ │ └── shavit.games.txt │ ├── scripting │ │ ├── include │ │ │ ├── DynamicChannels.inc │ │ │ ├── SteamWorks.inc │ │ │ ├── closestpos.inc │ │ │ ├── convar_class.inc │ │ │ ├── eventqueuefix.inc │ │ │ ├── rtler.inc │ │ │ ├── shavit.inc │ │ │ └── shavit │ │ │ │ ├── anti-sv_cheats.sp │ │ │ │ ├── area_and_cluster_stages.sp │ │ │ │ ├── bhopstats-timerified.inc │ │ │ │ ├── bhopstats-timerified.sp │ │ │ │ ├── chat-colors.inc │ │ │ │ ├── chat.inc │ │ │ │ ├── checkpoints.inc │ │ │ │ ├── core.inc │ │ │ │ ├── hud.inc │ │ │ │ ├── mapchooser.inc │ │ │ │ ├── maps-folder-stocks.inc │ │ │ │ ├── misc.inc │ │ │ │ ├── physicsuntouch.inc │ │ │ │ ├── rankings.inc │ │ │ │ ├── replay-file.inc │ │ │ │ ├── replay-playback.inc │ │ │ │ ├── replay-recorder.inc │ │ │ │ ├── replay-stocks.sp │ │ │ │ ├── sql-create-tables-and-migrations.sp │ │ │ │ ├── steamid-stocks.inc │ │ │ │ ├── style-settings.sp │ │ │ │ ├── tas-oblivious.inc │ │ │ │ ├── tas-xutax.inc │ │ │ │ ├── tas.inc │ │ │ │ ├── weapon-stocks.inc │ │ │ │ ├── wr.inc │ │ │ │ └── zones.inc │ │ ├── shavit-chat.sp │ │ ├── shavit-checkpoints.sp │ │ ├── shavit-core.sp │ │ ├── shavit-hud.sp │ │ ├── shavit-mapchooser.sp │ │ ├── shavit-misc.sp │ │ ├── shavit-rankings.sp │ │ ├── shavit-replay-playback.sp │ │ ├── shavit-replay-recorder.sp │ │ ├── shavit-sounds.sp │ │ ├── shavit-stats.sp │ │ ├── shavit-tas.sp │ │ ├── shavit-timelimit.sp │ │ ├── shavit-wr.sp │ │ ├── shavit-zones-json.sp │ │ └── shavit-zones.sp │ └── translations │ │ ├── shavit-chat.phrases.txt │ │ ├── shavit-common.phrases.txt │ │ ├── shavit-core.phrases.txt │ │ ├── shavit-hud.phrases.txt │ │ ├── shavit-misc.phrases.txt │ │ ├── shavit-rankings.phrases.txt │ │ ├── shavit-replay.phrases.txt │ │ ├── shavit-stats.phrases.txt │ │ ├── shavit-wr.phrases.txt │ │ └── shavit-zones.phrases.txt └── stripper │ └── maps │ ├── bhop_blueblocks.cfg │ ├── bhop_classicpillars.cfg │ ├── bhop_connectivity_fix.cfg │ ├── bhop_continuity.cfg │ ├── bhop_cys_nonstop.cfg │ ├── bhop_desert_smoke.cfg │ ├── bhop_dron.cfg │ ├── bhop_n0bs1_css.cfg │ ├── bhop_narkozzz.cfg │ ├── bhop_splrez.cfg │ └── workshop │ ├── 859067603 │ └── bhop_bless.cfg │ ├── 1195609162 │ └── bhop_bless.cfg │ └── 2117675766 │ └── bhop_craton.cfg ├── materials └── shavit │ ├── zone_beam.vmt │ ├── zone_beam.vtf │ └── zone_beam_ignorez.vmt ├── smbuild └── sound └── shavit ├── copyrights.txt ├── fr_1.mp3 ├── pb_1.mp3 ├── wr_1.mp3 ├── wr_2.mp3 ├── wr_3.mp3 └── wr_4.mp3 /.editorconfig: -------------------------------------------------------------------------------- 1 | [*] 2 | indent_style = tab 3 | indent_size = 4 4 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | * text=auto 2 | *.inc diff=sourcepawn linguist-language=SourcePawn 3 | *.sp diff=sourcepawn linguist-language=SourcePawn 4 | *.txt diff 5 | *.cfg diff 6 | 7 | *.smx binary 8 | *.mp3 binary 9 | *.vmt diff 10 | *.vtf binary 11 | -------------------------------------------------------------------------------- /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /.github/workflows/ci.yml: -------------------------------------------------------------------------------- 1 | name: Compile 2 | 3 | on: [push, pull_request, workflow_dispatch] 4 | 5 | jobs: 6 | compile: 7 | runs-on: ubuntu-latest 8 | strategy: 9 | matrix: 10 | sm-version: [ '1.12' ] 11 | 12 | name: "Build SM ${{ matrix.sm-version }}" 13 | steps: 14 | - name: Prepare env 15 | shell: bash 16 | run: echo "GITHUB_SHA_SHORT=${GITHUB_SHA::7}" >> $GITHUB_ENV 17 | 18 | - uses: actions/checkout@v4 19 | 20 | - name: Setup SP 21 | uses: rumblefrog/setup-sp@master 22 | with: 23 | version: ${{ matrix.sm-version }} 24 | 25 | - name: Download and extract dependencies 26 | shell: bash 27 | run: | 28 | # Mac zip just because it's smaller & we don't repack the extensions... 29 | wget https://github.com/ErikMinekus/sm-ripext/releases/download/1.3.1/sm-ripext-1.3.1-mac.zip 30 | unzip sm-ripext-1.3.1-mac.zip "addons/sourcemod/scripting/include/*" 31 | wget https://github.com/clugg/sm-json/archive/refs/tags/v5.0.1.tar.gz 32 | tar --strip-components=1 -xvzf v5.0.1.tar.gz sm-json-5.0.1/addons/sourcemod/scripting/include 33 | wget https://github.com/hermansimensen/eventqueue-fix/archive/refs/heads/main.tar.gz 34 | tar --strip-components=1 -xvzf main.tar.gz -C addons/sourcemod 35 | rm -rf *.zip *.tar.gz addons/sourcemod/.git* addons/sourcemod/LICENSE 36 | 37 | - name: Run compiler 38 | shell: bash 39 | run: | 40 | cd addons/sourcemod 41 | mkdir plugins 42 | for src in $(find scripting -maxdepth 1 -type f -name "*.sp"); 43 | do 44 | spcomp $src -o=plugins/$(basename $src .sp)'.smx' -i=scripting/include -v2 45 | done 46 | 47 | - name: Upload artifact 48 | uses: actions/upload-artifact@v4 49 | with: 50 | name: bhoptimer-${{ github.head_ref || github.ref_name }}-sm${{ matrix.sm-version }}-${{ env.GITHUB_SHA_SHORT }} 51 | path: | 52 | addons 53 | materials 54 | sound 55 | CHANGELOG.md 56 | LICENSE 57 | README.md 58 | retention-days: 14 59 | 60 | release: 61 | name: Release 62 | if: github.ref_type == 'tag' 63 | needs: compile 64 | runs-on: ubuntu-latest 65 | steps: 66 | - name: Download artifacts 67 | uses: actions/download-artifact@v4 68 | 69 | - name: Archive artifacts 70 | shell: bash 71 | run: find * -maxdepth 0 -type d -exec zip -rq {}.zip {} \; 72 | 73 | - uses: ncipollo/release-action@v1 74 | with: 75 | token: ${{ secrets.GITHUB_TOKEN }} 76 | draft: true 77 | name: ${{ github.ref_name }} 78 | artifacts: "*.zip" 79 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # SourcePawn 2 | *.smx 3 | *.dll 4 | *.so 5 | 6 | # editors 7 | *.atom-build.json 8 | .vscode/tasks.json 9 | 10 | \.vscode/settings\.json 11 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing to bhoptimer 2 | 3 | ## Issues 4 | Issue reports are one of the best things you can do to contribute to the development of bhoptimer. 5 | 6 | When reporting an issue, please including the following information: 7 | * The **game** your server is running. That's CS:S/CS:GO - I can't support other games or Source SDK mods! 8 | * Are you using the **latest Steam version** of the game? I can't support old versions and I can't support non-Steam versions because they might be different! 9 | * What's the operating system of your game server? 10 | * Are you running the latest stable builds of SourceMod and Metamod: Source? 11 | * What behavior were you expecting, and what's the actual behavior? 12 | 13 | ## Feature requests 14 | You can start an issue as a feature request. 15 | When doing so, please state that it's a feature request. 16 | I cannot guarantee that I will add your feature due to complexity, not having enough free time or even if I see that it doesn't fit the project. 17 | 18 | #### Steam 19 | I've had lots of people adding me as a friend on Steam to report issues regarding bhoptimer. 20 | Unfortunately that's not the place. Use the GitHub issue tracker instead! 21 | 22 | #### Donations/feedback 23 | I've been asked multiple times if I accept donations for my work on bhoptimer. 24 | The answer is yes. If you want to donate, please do it via the following link (PayPal): https://paypal.me/shavitush - please leave a note while donating! 25 | I appreciate every donation of any amount. It motivates developers a lot when people appreciate their work :). 26 | 27 | Feel like bhoptimer is a great project? I'm really glad to hear! If you want me to hear your feedback, leave it via [email](mailto:the@shav.it), as a comment on [my Steam profile](https://steamcommunity.com/id/abcdullah/) or as a [reply to the AlliedModders thread](https://forums.alliedmods.net/newreply.php?do=newreply&noquote=1&p=2313049). 28 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-advertisements.cfg: -------------------------------------------------------------------------------- 1 | // Configuration file for chat advertisements. 2 | // 3 | // Advertisements will cycle from the first one to the last one and will show up every time 4 | // 5 | // Universal color settings -- will work with both CS:S and CS:GO: 6 | // {default} - default color 7 | // {green} - green color 8 | // 9 | // Possible color values are the ones from shavit-messages.cfg: 10 | // {text} {warning} {variable} {variable2} {style} 11 | // 12 | // And also: 13 | // 14 | // For CS:S, you have the following variables available: (NOTE: The format for colors is like HTML. RRGGBBAA) 15 | // {RGB} - like \x07, usage: "{RGB}FF0000" for red 16 | // {RGBA} - like \x08, usage: "{RGBA}FF0000FE" for 254 alpha red 17 | // 18 | // CS:GO colors: 19 | // {blue}, {bluegrey}, {darkblue}, {darkred}, {gold}, {grey}, {grey2}, {lightgreen}, {lightred}, {lime}, {orchid}, {yellow} 20 | // 21 | // Extra variables to use in an advertisement message: 22 | // {name} - name of the player who receives the message. 23 | // {map} - current map. 24 | // {timeleft} - time left (formatted like timers including the .0). 25 | // {timeleftraw} - time left in seconds. 26 | // {serverip} - server IP (requires SteamWorks). 27 | // {hostname} - hostname. 28 | // 29 | // All messages will have the prefix that is defined inside configs/shavit-messages.cfg. 30 | // 31 | "Advertisements" 32 | { 33 | "0" "You may write {variable}!hide{text} to {variable2}hide{text} other players." 34 | "1" "The command {variable}!r{text} will {variable2}restart your timer{text}." 35 | "2" "{variable}!recent{text} can be used to see the latest world records set!" 36 | "3" "{variable}!style{text} will open a menu with every {variable2}bhop style{text} the server has to offer." 37 | } 38 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-chat.cfg: -------------------------------------------------------------------------------- 1 | // Available settings: 2 | // "ranks" - inclusive rank range. (i.e. 1, 2, 10-19 or 0.0%-0.5%). Use a percent sign to use a percentile of total players. Add "p" as a prefix to use points instead of ranks, don't specify a range for points if you only want a minimum to unlock the title. Add "w" as a prefix if you want to use WR count. Add "W" as a prefix if you want to use WR rank. 3 | // "name" - custom name appearance. Default: "{name}" 4 | // "message" - a prefix to the message itself. Default: "" 5 | // "display" - display text in the !chatranks menu. "" for a new line. Filling this is required. 6 | // "free" - is this title available for everyone to use? Default: "0" 7 | // "easteregg" - is this title an easter egg? Set to 1 to hide it from the !ranks menu. Default: "0" 8 | // "flag" - set to an admin flag to require privileges for this title. Can use an override instead of a flag. 9 | // Combine with "free" "1" to instantly give access to privileged users. Default: "" 10 | // 11 | // Global variables: 12 | // {default} - default color 13 | // {team} - team color 14 | // {green} - green color 15 | // {name} - player name 16 | // {clan} - clan tag 17 | // {rand} - random color. 18 | // {message} - message text 19 | // {rank} - player rank (whole number) 20 | // {rank1} - player rank in percentage (1 decimal point) 21 | // {rank2} - player rank in percentage (2 decimal points) 22 | // {rank3} - player rank in percentage (3 decimal points) 23 | // {pts} - how many points a player has 24 | // {wrs} - how many wrs a player has 25 | // {wrrank} - player rank out of wrs held 26 | // 27 | // Refer to shavit-messages.cfg for color settings. 28 | // 29 | "Chat" 30 | { 31 | "0" // unranked 32 | { 33 | "ranks" "0" 34 | "name" "{team}[Unranked] {name}" 35 | "display" "[Unranked]Title used by unranked players." 36 | } 37 | 38 | "1" 39 | { 40 | "ranks" "p10000" 41 | "free" "0" 42 | "name" "{rand}10k! {team}{name}" 43 | "display" "10k ChallengerYou are insane. You are a hero. You are a challenger.A title awarded to the magnificent players who achieve 10,000 points." 44 | } 45 | 46 | "2" 47 | { 48 | "ranks" "1" 49 | "name" "{rand}ONE TRUE GOD {team}{name}" 50 | "message" "{rand}" 51 | "display" "[ONE TRUE GOD]A title awarded only to the very best players." 52 | } 53 | 54 | "3" 55 | { 56 | "ranks" "2" 57 | "name" "{green}LEGENDARY {name}" 58 | "display" "[LEGENDARY]A title obtained by legendary players." 59 | } 60 | 61 | "4" 62 | { 63 | "ranks" "3" 64 | "name" "{green}HERO {team}{name}" 65 | "display" "[HERO]You're a hero, and you deserve this title." 66 | } 67 | 68 | "5" 69 | { 70 | "ranks" "4-10" 71 | "name" "{rand}scrub{rand}! {name}" 72 | "display" "scrub!You're a noob." 73 | } 74 | 75 | "6" 76 | { 77 | "ranks" "11-100%" 78 | "name" ":( {name}" 79 | "display" "sad faceYou're terrible. Get good!" 80 | } 81 | 82 | "7" 83 | { 84 | "free" "1" 85 | "name" "{rand}:) {name}" 86 | "display" ":)Free chat title." 87 | } 88 | 89 | "8" 90 | { 91 | "ranks" "W1" 92 | "name" "{rand}{wrs}WRs {name}" 93 | "display" "WR CHADYou may not have a life but at least you have the most WRs!" 94 | } 95 | 96 | "9" 97 | { 98 | "ranks" "w1" 99 | "name" "{green}{name} is worthless" 100 | "display" "{name} is worthlessSeriously, only 1 WR?" 101 | } 102 | 103 | "10" 104 | { 105 | "ranks" "W10%" 106 | "name" "{rand}WRTOP10% {name}" 107 | "display" "WRTOP10%Top 10% of players by WRs held." 108 | } 109 | } 110 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-chatsettings.cfg: -------------------------------------------------------------------------------- 1 | // These are the chat messages for the bhoptimer implementation of a chat processor. 2 | // Notes: 3 | // In CS:S and TF2, the colon uses the default chat color. 4 | // In CS:GO, the colon uses the same color the player name uses. 5 | "Chat Messages" 6 | { 7 | "CS:S" 8 | { 9 | "Cstrike_Chat_CT_Loc" "(Counter-Terrorist) {name} {def}{colon} {msg}" 10 | "Cstrike_Chat_CT" "(Counter-Terrorist) {name} {def}{colon} {msg}" 11 | "Cstrike_Chat_T_Loc" "(Terrorist) {name} {def}{colon} {msg}" 12 | "Cstrike_Chat_T" "(Terrorist) {name} {def}{colon} {msg}" 13 | "Cstrike_Chat_CT_Dead" "*DEAD*(Counter-Terrorist) {name} {def}{colon} {msg}" 14 | "Cstrike_Chat_T_Dead" "*DEAD*(Terrorist) {name} {def}{colon} {msg}" 15 | "Cstrike_Chat_Spec" "(Spectator) {name} {def}{colon} {msg}" 16 | "Cstrike_Chat_All" "{name} {def}{colon} {msg}" 17 | "Cstrike_Chat_AllDead" "*DEAD* {name} {def}{colon} {msg}" 18 | "Cstrike_Chat_AllSpec" "*SPEC* {name} {def}{colon} {msg}" 19 | } 20 | 21 | "CS:GO" 22 | { 23 | "Cstrike_Chat_CT_Loc" "(Counter-Terrorist) {name} {colon} {msg}" 24 | "Cstrike_Chat_CT" "(Counter-Terrorist) {name} {colon} {msg}" 25 | "Cstrike_Chat_T_Loc" "(Terrorist) {name} {colon} {msg}" 26 | "Cstrike_Chat_T" "(Terrorist) {name} {colon} {msg}" 27 | "Cstrike_Chat_CT_Dead" "*DEAD*(Counter-Terrorist) {name} {colon} {msg}" 28 | "Cstrike_Chat_T_Dead" "*DEAD*(Terrorist) {name} {colon} {msg}" 29 | "Cstrike_Chat_Spec" "(Spectator) {name} {colon} {msg}" 30 | "Cstrike_Chat_All" "{name} {colon} {msg}" 31 | "Cstrike_Chat_AllDead" "*DEAD* {name} {colon} {msg}" 32 | "Cstrike_Chat_AllSpec" "*SPEC* {name} {colon} {msg}" 33 | } 34 | 35 | "TF2" 36 | { 37 | "TF_Chat_Team_Loc" "(TEAM) {name} {def}{colon} {msg}" 38 | "TF_Chat_Team" "(TEAM) {name} {def}{colon} {msg}" 39 | "TF_Chat_Team_Dead" "*DEAD*(TEAM) {name} {def}{colon} {msg}" 40 | "TF_Chat_Spec" "(Spectator) {name} {def}{colon} {msg}" 41 | "TF_Chat_All" "{name} {def}{colon} {msg}" 42 | "TF_Chat_AllDead" "*DEAD* {name} {def}{colon} {msg}" 43 | "TF_Chat_AllSpec" "*SPEC* {name} {def}{colon} {msg}" 44 | "TF_Chat_Coach" "(Coach) {name} {def}{colon} {msg}" 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-mapfixes.cfg: -------------------------------------------------------------------------------- 1 | "Map fixes" 2 | { 3 | "bhop_strafecontrol" 4 | { 5 | "shavit_zones_extra_spawn_height" "1.0" 6 | } 7 | "bhop_tranquility" 8 | { 9 | "shavit_zones_prebuilt_visual_offset" "16" 10 | } 11 | "bhop_amaranthglow" 12 | { 13 | "shavit_zones_prebuilt_visual_offset" "16" 14 | } 15 | 16 | "bhop_apathy" 17 | { 18 | "shavit_zones_resettargetname_main" "apathy" 19 | } 20 | "bhop_crash_egypt" 21 | { 22 | "shavit_zones_resettargetname_main" "player" 23 | } 24 | "bhop_japan" 25 | { 26 | "shavit_zones_resetclassname_main" "beginner" 27 | } 28 | "bhop_space" 29 | { 30 | "shavit_zones_resetclassname_main" "sadface" 31 | } 32 | "bhop_shutdown" 33 | { 34 | "shavit_zones_resettargetname_main" "asdf" 35 | } 36 | "bhop_interloper" 37 | { 38 | "shavit_zones_resettargetname_main" "lol" 39 | } 40 | "bhop_wasd" 41 | { 42 | "shavit_zones_resettargetname_main" "default" 43 | } 44 | 45 | "bhop_solitude" 46 | { 47 | "shavit_zones_forcetargetnamereset" "1" 48 | } 49 | "bhop_drop" 50 | { 51 | "shavit_zones_forcetargetnamereset" "1" 52 | "shavit_zones_resettargetname_main" "activator_boost" 53 | "shavit_zones_resettargetname_bonus" "activator_boost3" 54 | } 55 | "kz_bhop_kairo" 56 | { 57 | "shavit_zones_forcetargetnamereset" "1" 58 | "shavit_zones_resettargetname_main" "tped" 59 | "shavit_zones_resetclassname_main" "cp0filter" 60 | } 61 | "bhop_avantasia" 62 | { 63 | "rngfix_triggerjump" "0" 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-messages.cfg: -------------------------------------------------------------------------------- 1 | // Configuration file for chat messages. 2 | // The settings here will replace the behavior of chat messages that the plugin sends. 3 | // 4 | // Universal color settings -- will work with both CS:S and CS:GO: 5 | // {default} - default color 6 | // {green} - green color 7 | // 8 | // For CS:S, you have the following variables available: (NOTE: The format for colors is like HTML. RRGGBBAA) 9 | // {RGB} - like \x07, usage: "{RGB}FF0000" for red 10 | // {RGBA} - like \x08, usage: "{RGBA}FF0000FE" for 254 alpha red 11 | // 12 | // CS:GO colors: 13 | // {blue}, {bluegrey}, {darkblue}, {darkred}, {gold}, {grey}, {grey2}, {lightgreen}, {lightred}, {lime}, {orchid}, {yellow} 14 | // 15 | "Messages" 16 | { 17 | "CS:S" // TF2 is pulled from this too, because both have the same chat capabilities! 18 | { 19 | "prefix" "{RGB}5e70d0[Timer]" 20 | "text" "{RGB}ffffff" 21 | "warning" "{RGB}af2a22" 22 | "variable" "{RGB}7fd772" 23 | "variable2" "{RGB}276f5c" 24 | "style" "{RGB}db88c2" 25 | } 26 | 27 | "CS:GO" 28 | { 29 | "prefix" "{green}[Timer]" 30 | "text" "{default}" 31 | "warning" "{darkred}" 32 | "variable" "{bluegrey}" 33 | "variable2" "{orchid}" 34 | "style" "{gold}" 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-prefix.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/addons/sourcemod/configs/shavit-prefix.txt -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-readme.txt: -------------------------------------------------------------------------------- 1 | shavit-advertisements.cfg is the file used to determine how shavit-misc posts advertisements to the server. 2 | shavit-chat.cfg is the configuration file for chat titles, colors and all this kind of stuff. 3 | shavit-messages.cfg is the configuration file for chat colors/prefixes etc. 4 | shavit-prefix.txt is the configuration file for the plugin's mysql prefix. do not touch unless you know what you are doing! 5 | shavit-replay.cfg is the configuration file used for the replay bot's name styling. 6 | shavit-sounds.cfg is the configuration file for timer sounds. 7 | shavit-styles.cfg is used to configure custom style settings for the server. 8 | shavit-zones.cfg is where you can choose your own zone sprites. comment the CS:S lines and uncomment the CS:GO lines if you need. -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-replay.cfg: -------------------------------------------------------------------------------- 1 | // Configuration file for replay bot styling. 2 | // 3 | // WARNING: DO NOT DELETE/ADD YOUR OWN KEYS! 4 | // WARNING: IF YOU DISABLE THE CENTRAL REPLAY BOT - MAKE SURE BOT NAMES CONTAIN A VARIABLE OR YOU'LL END UP WITH A MESS! 5 | // 6 | // The replay bot clan/name styling will be loaded from this file. 7 | // A central bot is the replay bot that can play all styles. It's enabled by default with "shavit_replay_centralbot". 8 | // 9 | // Keys: 10 | // "clantag" - clan tag for replay bots (central or not) to use. 11 | // "namestyle" - this is the name style replay bots will use. Including the central bot, as long as it's during playback. 12 | // "centralname" - the central bot's idle name, AKA when nothing is playing. 13 | // 14 | // Variables: 15 | // {map} - current map. 16 | // {style} - the style name. 17 | // {styletag} - the style's tag. See "clantag" in "shavit-styles.cfg". 18 | // {time} - formatted time for the WR currently being played. 19 | // {player} - the name of the player that holds the *record*, might be incorrect for replays from the beta version of bhoptimer. 20 | // {track} - track that the bot replays. Translated from the server's defined language. 21 | // {type} - Replay bot type. Central, Dynamic, and Looping... 22 | // 23 | "Replay" 24 | { 25 | "clantag" "{type}" 26 | "namestyle" "{track} {style} - {time}" 27 | "centralname" "!replay" 28 | 29 | // Replay data folder. This is where replays are loaded from and saved to. 30 | // Note: To use a path outside of the game directory, you will have to get out of it with "../". 31 | // Edit at your own risk. 32 | // 33 | // Variables: 34 | // {SM} - SourceMod folder. If this variable isn't included, you will have to specify the full path. 35 | "replayfolder" "{SM}/data/replaybot" 36 | 37 | // "enabled" - whether the looping bot will spawn in when there's replay data 38 | // "tracks" - semicolon seperated list of track numbers to loop through. 0 (main), 1-8 (bonus) 39 | // "styles" - semicolon seperated list of style numbers to loop through. 40 | "Looping Bots" 41 | { 42 | "Main Normal Bot" 43 | { 44 | "enabled" "1" 45 | "tracks" "0" 46 | "styles" "0" 47 | } 48 | "Main Segmented Bot" 49 | { 50 | "enabled" "1" 51 | "tracks" "0" 52 | "styles" "7" 53 | } 54 | "Other Styles" 55 | { 56 | "enabled" "1" 57 | "tracks" "0" 58 | "styles" "1;2;3;4;5;6;8;9;11;12;13;14;15;16" 59 | } 60 | "Bonus Normal Bot" 61 | { 62 | "enabled" "1" 63 | "tracks" "1" 64 | "styles" "0" 65 | } 66 | "Shit Bonuses Bot" 67 | { 68 | "enabled" "1" 69 | "tracks" "2;3;4;5;6;7;8" 70 | "styles" "0" 71 | } 72 | "TAS Bot" 73 | { 74 | "enabled" "1" 75 | "tracks" "0;1;2;3;4;5;6;7;8" 76 | "styles" "10" 77 | } 78 | "Dumb Styles Bot" 79 | { 80 | "enabled" "0" 81 | "tracks" "0" 82 | "styles" "4;6" 83 | } 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-sounds.cfg: -------------------------------------------------------------------------------- 1 | // default config. 2 | // modify this plugin and reset the plugin on the server side, or restart the server. 3 | // absolutely DON'T use 'sound/' in the paths 4 | // absolutely DON'T have spaces anywhere in paths 5 | // 6 | // format: 7 | // "record_type" "path/to/sound/file.ext" 8 | // 9 | // first - first record on map and style ever 10 | // personal - personal best 11 | // world - new server WR 12 | // worst - worst record for the track/style 13 | // number - rank on map, only one per rank (example: "1" "shavit/pro.mp3"), will play for every player. overrides others 14 | // noimprovement - time is worse than old PB 15 | "first" "shavit/fr_1.mp3" 16 | "personal" "shavit/pb_1.mp3" 17 | "world" "shavit/wr_1.mp3" 18 | "world" "shavit/wr_2.mp3" 19 | "world" "shavit/wr_3.mp3" 20 | "world" "shavit/wr_4.mp3" 21 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-styles.cfg: -------------------------------------------------------------------------------- 1 | // This is the configuration file for styles. 2 | // Start from 0 and increment every time. 0 is the default style. 3 | // 4 | // Strings settings are required! 5 | // If you choose to not set anything else, you can remove the lines and they will be assigned as the default settings provided with this configuration file. 6 | "Styles" 7 | { 8 | "0" 9 | { 10 | // Accessibility 11 | "enabled" "1" // When disabled, style will be unusable. -1 to also make the style not show in menus. 12 | "inaccessible" "0" // This setting makes it so you can't manually switch to this style but only by functionality from timer modules. 13 | 14 | // Strings 15 | "name" "Normal" // Style name. 16 | "shortname" "NM" // Short style name. 17 | "htmlcolor" "797FD4" // HUD style color (CS:GO only). 18 | "command" "n; nm; normal" // Commands to register for style changing, leave empty for no command. use a semicolon as a delimiter - requires server restart. 19 | "clantag" "N" // Short style name for the clantag, not exactly the same as shortname. 20 | 21 | // Jumping settings 22 | "autobhop" "1" // Enable autobhopping and +ds? 23 | "easybhop" "1" // Enable easybhop (disable stamina reset)? 24 | "prespeed" "0" // Allow prespeeding regardless of the prespeed server setting? If set to 2, the value of shavit_core_nozaxisspeed will be respected as well. 25 | "prespeed_ez_vel" "0" // Whether to set velocity on first jump for prespeed styles. 0 = Disabled. >0 = set velocity to this amount (e.g. 3500). 26 | "velocity_limit" "0.0" // Velocity limit: set to 0.0 for unlimited, 400.00 for 400vel styles etc. 27 | "bunnyhopping" "1" // Per-style sv_enablebunnyhopping. Leave as 1 if you want bunnyhopping to maintain player speed. This setting will override _strafe map settings. 28 | 29 | // Convar overrides 30 | "prespeed_type" "-1" // Set the specific value of shavit_misc_prespeed to use for this style. -1 will use the current shavit_misc_prespeed value. Requires "prespeed" to be 0. 31 | "blockprejump" "-1" // Set the specific value of shavit_core_blockprejump to use for this style. -1 will use the current shavit_core_blockprejump value. 32 | "nozaxisspeed" "-1" // Set the specific value of shavit_core_nozaxisspeed to use for this style. -1 will use the current shavit_core_nozaxisspeed value. 33 | "restrictnoclip" "-1" // Set the specific value of shavit_misc_restrictnoclip to use for this style. -1 will use the current shavit_misc_restrictnoclip value. 34 | 35 | // Physics 36 | "airaccelerate" "1000.0" // sv_airaccelerate value for the style. 37 | "runspeed" "260.00" // Running speed. Requires DHooks, shavit-misc and shavit_misc_staticprestrafe set to 1. 38 | "maxprestrafe" "0.0" // The max prestrafe that still allows your timer to start/restart. You generally do *not* need or want to change this unless for surf things (combined with style-setting "prespeed_type" "6" or cvar "shavit_misc_prespeed 6"). Default is 0.0 (disabled). 39 | "gravity" "1.0" // Gravity setting, 1.0 for default. Standard for low gravity styles is 0.6. 40 | "speed" "1.0" // Speed multiplier, 1.0 for default. Standard for slowmo styles is 0.5. This a multiplier for m_flLaggedMovementValue. 41 | "timescale" "1.0" // Timing will scale with this setting. This is a multiplier for m_flLaggedMovementValue but also affects the timer increase speed. 42 | 43 | "force_timescale" "0" // Force the timescale every jump? Default is 0 for normal timescales. 44 | "velocity" "1.0" // % of horizontal velocity to keep per jump. a value 0.9 will make the player lose 10% of their velocity per jump. Likewise, values above 1 will result in speed gains. 45 | "bonus_velocity" "0.0" // Bonus velocity to gain per jump. If set to e.g. 100.0, the player will gain 100 bonus velocity per jump. 46 | "min_velocity" "0.0" // Minimum amount of horizontal velocity to keep per jump. If set to 600.0, the player can't have less than 600 velocity per jump. 47 | "jump_multiplier" "0.0" // Mulitplier for the vertical velocity per jump. 0.0 for disabled. 48 | "jump_bonus" "0.0" // Bonus vertical velocity to gain per jump. If set to e.g. 100.0, the player will gain 100 bonus vertial velocity per jump. 49 | "startinair" "0" // 0 = Start-zones will only start the timer if the player is on the ground. 1 = timer will start without requiring the player to be on the ground in the start zone. This means with 1 that it will basically only start the timer counter once you've left the start-zone. This should only be used on gamemodes that are intended for this kind of mechanic (i.e. not bhop). Also it might be easily abusable. GL. Also this probably won't work unless you set either `"prespeed" "1"` or `"nozaxisspeed" "0"`. 50 | 51 | // Mode settings 52 | "block_w" "0" // Block +forward (W). 53 | "block_a" "0" // Block +moveleft (A). 54 | "block_s" "0" // Block +back (S). 55 | "block_d" "0" // Block +moveright (D). 56 | "block_use" "0" // Block +use (E). 57 | "a_or_d_only" "0" // Force A-only / D-only. You still want to block_w & block_s too. The default shavit-styles.cfg has an A/D-Only style example also. 58 | "force_hsw" "0" // Force half-sideways gameplay. 1 for regular HSW and 2 for surf-HSW. 59 | "force_groundkeys" "0" // Forces the above settings even while on ground. e.g. enabling this will not allow W/D or W/A prestrafing when playing styles that disable the keys. 60 | "block_pleft" "0" // Block +left. 2 to stop timer. 61 | "block_pright" "0" // Block +right. 2 to stop timer. 62 | "block_pstrafe" "0" // Prevent button inconsistencies (including +pstrafe). May have false positives when players lag. Will prevent some strafe hacks too. Set this to 2 to also stop the timer. 63 | 64 | // Feature excluding 65 | "unranked" "0" // Unranked style. No ranking points and no records. 66 | "noreplay" "0" // Disable replay bot for this style. Automatically included for unranked styles. 67 | 68 | // Minimum times (to help try to prevent accidents/cheats) 69 | "minimum_time" "3.5" // Minimum time a main-track run needs to be. 70 | "minimum_time_bonus" "0.5" // Minimum time a bonus-track run needs to be. 71 | 72 | // Sync/strafes 73 | "sync" "1" // Measure synchronization between strafes. 74 | "strafe_count_w" "0" // Count W (+forward) for the strafe counter. 75 | "strafe_count_a" "1" // Count A (+moveleft) for the strafe counter. 76 | "strafe_count_s" "0" // Count S (+back) for the strafe counter. 77 | "strafe_count_d" "1" // Count D (+moveright) for the strafe counter. 78 | 79 | // Rankings 80 | "rankingmultiplier" "1.0" // Rankings points multiplier. Don't use for unranked styles. 81 | 82 | // Special flags 83 | "special" "0" // For third-party modules. The core plugins will not need this setting. 84 | "specialstring" "" // For modularity. Separated with semicolon. Built-in flags: "segments". 85 | "permission" "" // Permission required. Syntax: "flag;override". For example "p;style_tas" to require the 'p' flag or the "style_tas" override. 86 | "ordering" "0" // Ordering in menus where styles appear. If this value is not present, style ID will be used instead. 87 | 88 | // KZ settings 89 | "kzcheckpoints" "0" // KZ styled checkpoints. They reset upon timer start and you don't get reverted to a save state, and you cannot save when airborne or someone else's checkpoints. 90 | "kzcheckpoints_ladders" "0" // KZ styled checkpoints allowed to checkpoint onto ladders (like GOKZ) 91 | "kzcheckpoints_ontele" "-1" // The style to be changed to on client teleporting to a checkpoint in KZ styles. The destination style will be inaccessible if enabled. -1 or set "kzcheckpoints" to 0 for disabled. 92 | "kzcheckpoints_onstart" "-1" // The style to be changed to on client getting inside the start zone in KZ styles. This style will be inaccessible if enabled. -1 or set "kzcheckpoints" to 0 for disabled. 93 | 94 | // TAS settings 95 | "segments" "0" // Segments styled checkpoints. 0 for disabled. 96 | "tas" "0" // 0 = Do nothing. 1 = Currently sets the following keys unless they are explicity disabled: `tas_timescale -1`, `autostrafe 1`, `autoprestrafe 1`, `edgejump 1`, and `autojumponstart 1` 97 | "tas_timescale" "0" // TAS-like timescaling. 0 = Disabled. -1 = User can edit the timescale (TAS menu, sm_ts, sm_tsplus, sm_tsminus). >0 = Fixed tas-timescale value for the style (e.g. 0.5 for a fixed timescale). Total time-increase-rate for the player = timescale * tas_timescale 98 | "autostrafe" "0" // 0 = Disabled. 1 = 1tick autostrafer. 2 = velocity/autogain. 3 = velocity/autogain (no speed loss). 4 = a basic +moveleft/+moveright presser when turning. -1 = Lets players toggle between 1tick and velocity/autogain. 99 | "autoprestrafe" "0" // 0 = Disabled. 1 = Enables TAS prestrafer on the ground to reach. 100 | "edgejump" "0" // 0 = Disabled. 1 = Automatically jumps when the player will fall off a ledge next tick. 101 | "autojumponstart" "0" // 0 = Disabled. 1 = Automatically jumps when the player will leave the start zone. 102 | } 103 | 104 | "1" 105 | { 106 | "name" "Sideways" 107 | "shortname" "SW" 108 | "htmlcolor" "B54CB3" 109 | "command" "sw; side; sideways" 110 | "clantag" "SW" 111 | 112 | "block_a" "1" 113 | "block_d" "1" 114 | 115 | "strafe_count_w" "1" 116 | "strafe_count_a" "0" 117 | "strafe_count_s" "1" 118 | "strafe_count_d" "0" 119 | 120 | "rankingmultiplier" "1.30" 121 | } 122 | 123 | "2" 124 | { 125 | "name" "W-Only" 126 | "shortname" "W" 127 | "htmlcolor" "9A59F0" 128 | "command" "w; wonly" 129 | "clantag" "W" 130 | 131 | "block_a" "1" 132 | "block_s" "1" 133 | "block_d" "1" 134 | 135 | "strafe_count_w" "1" 136 | "strafe_count_a" "0" 137 | "strafe_count_d" "0" 138 | 139 | "rankingmultiplier" "1.33" 140 | } 141 | 142 | "3" 143 | { 144 | "name" "Scroll" 145 | "shortname" "SCR" 146 | "htmlcolor" "279BC2" 147 | "command" "le; legit; scr; scroll" 148 | "clantag" "LE" 149 | 150 | "autobhop" "0" 151 | "easybhop" "0" 152 | 153 | "airaccelerate" "100.0" 154 | "runspeed" "250.00" 155 | 156 | "block_pleft" "1" 157 | "block_pright" "1" 158 | "block_pstrafe" "1" 159 | 160 | "rankingmultiplier" "1.30" 161 | } 162 | 163 | "4" 164 | { 165 | "name" "400 Velocity" 166 | "shortname" "400VEL" 167 | "htmlcolor" "C9BB8B" 168 | "command" "400; 400vel; vel" 169 | "clantag" "400" 170 | 171 | "autobhop" "0" 172 | "easybhop" "0" 173 | "velocity_limit" "400.00" 174 | 175 | "airaccelerate" "100.0" 176 | "runspeed" "250.00" 177 | 178 | "block_pleft" "1" 179 | "block_pright" "1" 180 | "block_pstrafe" "1" 181 | 182 | "rankingmultiplier" "1.50" 183 | } 184 | 185 | "5" 186 | { 187 | "name" "Half-Sideways" 188 | "shortname" "HSW" 189 | "htmlcolor" "B54CBB" 190 | "command" "hsw; halfside; halfsideways" 191 | "clantag" "HSW" 192 | 193 | "force_hsw" "1" 194 | 195 | "strafe_count_w" "0" 196 | "strafe_count_a" "1" 197 | "strafe_count_s" "0" 198 | "strafe_count_d" "1" 199 | 200 | "rankingmultiplier" "1.20" 201 | } 202 | 203 | "6" 204 | { 205 | "name" "A/D-Only" 206 | "shortname" "A/D" 207 | "htmlcolor" "9C5BBA" 208 | "command" "a; aonly; ad; d; donly" 209 | "clantag" "A/D" 210 | 211 | "autobhop" "1" 212 | "easybhop" "1" 213 | 214 | "airaccelerate" "1000.0" 215 | "runspeed" "260.00" 216 | 217 | "a_or_d_only" "1" 218 | "block_w" "1" 219 | "block_s" "1" 220 | 221 | "strafe_count_w" "0" 222 | "strafe_count_s" "0" 223 | 224 | "rankingmultiplier" "1.50" 225 | } 226 | 227 | "7" 228 | { 229 | "name" "Segmented" 230 | "shortname" "SEG" 231 | "htmlcolor" "FFFFFF" 232 | "command" "sr; seg; segment; segmented" 233 | "clantag" "SEG" 234 | 235 | "segments" "1" 236 | 237 | "rankingmultiplier" "0.0" 238 | } 239 | 240 | "8" 241 | { 242 | "name" "Low Gravity" 243 | "shortname" "LG" 244 | "htmlcolor" "DB88C2" 245 | "command" "lg; lowgrav" 246 | "clantag" "LG" 247 | 248 | "gravity" "0.5" 249 | } 250 | 251 | "9" 252 | { 253 | "name" "Slow Motion" 254 | "shortname" "SLOW" 255 | "htmlcolor" "C288DB" 256 | "command" "slow; slowmo" 257 | "clantag" "SLOW" 258 | 259 | "timescale" "0.5" 260 | } 261 | 262 | "10" 263 | { 264 | "name" "TAS" 265 | "shortname" "TAS" 266 | "htmlcolor" "123456" 267 | "command" "tas" 268 | "clantag" "TAS" 269 | 270 | "tas" "1" 271 | "segments" "1" 272 | "specialstring" "bash_bypass; oryx_bypass" 273 | 274 | "rankingmultiplier" "0.0" 275 | } 276 | } 277 | -------------------------------------------------------------------------------- /addons/sourcemod/configs/shavit-zones.cfg: -------------------------------------------------------------------------------- 1 | // Absolutely DON'T delete subkeys from this file. 2 | // 3 | // 'visible' defaults to 1, 'flat' defaults to 0. 4 | // Other values default to 255, except for width which is 0.5. 5 | "Zones" 6 | { 7 | "Sprites" 8 | { 9 | "beam" "shavit/zone_beam.vmt" 10 | "beam_ignorez" "shavit/zone_beam_ignorez.vmt" // for seeing the zones through walls when creating them 11 | "downloads" "materials/shavit/zone_beam.vtf; materials/shavit/zone_beam.vmt; materials/shavit/zone_beam_ignorez.vmt" 12 | } 13 | 14 | "Colors" 15 | { 16 | "Start" 17 | { 18 | "visible" "1" 19 | 20 | "red" "67" 21 | "green" "210" 22 | "blue" "230" 23 | 24 | "alpha" "255" 25 | "width" "0.5" 26 | 27 | "flat" "0" 28 | } 29 | 30 | "End" 31 | { 32 | "visible" "1" 33 | 34 | "red" "165" 35 | "green" "19" 36 | "blue" "194" 37 | 38 | "alpha" "255" 39 | "width" "0.5" 40 | } 41 | 42 | "Glitch_Respawn" 43 | { 44 | "visible" "0" 45 | 46 | "red" "255" 47 | "green" "200" 48 | "blue" "0" 49 | 50 | "alpha" "255" 51 | "width" "0.5" 52 | } 53 | 54 | "Glitch_Stop" 55 | { 56 | "visible" "0" 57 | 58 | "red" "255" 59 | "green" "200" 60 | "blue" "0" 61 | 62 | "alpha" "255" 63 | "width" "0.5" 64 | } 65 | 66 | "Glitch_Slay" 67 | { 68 | "visible" "0" 69 | 70 | "red" "255" 71 | "green" "200" 72 | "blue" "0" 73 | 74 | "alpha" "255" 75 | "width" "0.5" 76 | } 77 | 78 | "Freestyle" 79 | { 80 | "visible" "1" 81 | 82 | "red" "25" 83 | "green" "25" 84 | "blue" "255" 85 | 86 | "alpha" "195" 87 | "width" "0.5" 88 | } 89 | 90 | "Custom Speed Limit" 91 | { 92 | "visible" "1" 93 | 94 | "red" "247" 95 | "green" "3" 96 | "blue" "255" 97 | 98 | "alpha" "50" 99 | "width" "0.5" 100 | } 101 | 102 | "Teleport" 103 | { 104 | "visible" "0" 105 | 106 | "red" "255" 107 | "green" "200" 108 | "blue" "0" 109 | 110 | "alpha" "255" 111 | "width" "4.0" 112 | } 113 | 114 | "Easybhop" 115 | { 116 | "visible" "1" 117 | 118 | "red" "57" 119 | "green" "196" 120 | "blue" "92" 121 | 122 | "alpha" "175" 123 | "width" "2.5" 124 | } 125 | 126 | "Slide" 127 | { 128 | "visible" "1" 129 | 130 | "red" "244" 131 | "green" "66" 132 | "blue" "92" 133 | 134 | "alpha" "255" 135 | "width" "1.5" 136 | } 137 | 138 | "Airaccelerate" 139 | { 140 | "visible" "1" 141 | 142 | "red" "118" 143 | "green" "102" 144 | "blue" "173" 145 | 146 | "alpha" "255" 147 | "width" "1.5" 148 | } 149 | 150 | "Stage" 151 | { 152 | "visible" "1" 153 | 154 | "red" "255" 155 | "green" "153" 156 | "blue" "0" 157 | 158 | "alpha" "255" 159 | "width" "0.5" 160 | } 161 | 162 | "No Timer Gravity" 163 | { 164 | "visible" "1" 165 | 166 | "red" "255" 167 | "green" "0" 168 | "blue" "255" 169 | 170 | "alpha" "255" 171 | "width" "1.0" 172 | } 173 | 174 | "Gravity" 175 | { 176 | "visible" "1" 177 | 178 | "red" "255" 179 | "green" "0" 180 | "blue" "255" 181 | 182 | "alpha" "255" 183 | "width" "1.0" 184 | } 185 | 186 | "Speedmod" 187 | { 188 | "visible" "1" 189 | 190 | "red" "255" 191 | "green" "0" 192 | "blue" "255" 193 | 194 | "alpha" "255" 195 | "width" "1.0" 196 | } 197 | 198 | "No Jump" 199 | { 200 | "visible" "1" 201 | 202 | "red" "255" 203 | "green" "0" 204 | "blue" "255" 205 | 206 | "alpha" "255" 207 | "width" "0.1" 208 | } 209 | 210 | "Autobhop" 211 | { 212 | "visible" "1" 213 | 214 | "red" "255" 215 | "green" "0" 216 | "blue" "255" 217 | 218 | "alpha" "255" 219 | "width" "0.1" 220 | } 221 | 222 | "Bonus 1 Start" 223 | { 224 | "visible" "1" 225 | 226 | "red" "255" 227 | "green" "255" 228 | "blue" "255" 229 | 230 | "alpha" "255" 231 | "width" "0.1" 232 | } 233 | 234 | "Bonus 1 End" 235 | { 236 | "visible" "1" 237 | 238 | "red" "123" 239 | "green" "20" 240 | "blue" "250" 241 | 242 | "alpha" "255" 243 | "width" "0.1" 244 | } 245 | 246 | "Bonus 1 Glitch_Respawn" 247 | { 248 | "visible" "0" 249 | 250 | "red" "255" 251 | "green" "200" 252 | "blue" "0" 253 | 254 | "alpha" "255" 255 | "width" "0.1" 256 | } 257 | 258 | "Bonus 1 Glitch_Stop" 259 | { 260 | "visible" "0" 261 | 262 | "red" "255" 263 | "green" "200" 264 | "blue" "0" 265 | 266 | "alpha" "255" 267 | "width" "0.1" 268 | } 269 | 270 | "Bonus 1 Glitch_Slay" 271 | { 272 | "visible" "0" 273 | 274 | "red" "255" 275 | "green" "200" 276 | "blue" "0" 277 | 278 | "alpha" "255" 279 | "width" "0.1" 280 | } 281 | 282 | "Bonus 1 Freestyle" 283 | { 284 | "visible" "1" 285 | 286 | "red" "25" 287 | "green" "25" 288 | "blue" "255" 289 | 290 | "alpha" "195" 291 | "width" "0.1" 292 | } 293 | 294 | "Bonus 1 Custom Speed Limit" 295 | { 296 | "visible" "1" 297 | 298 | "red" "247" 299 | "green" "3" 300 | "blue" "255" 301 | 302 | "alpha" "50" 303 | "width" "0.1" 304 | } 305 | 306 | "Bonus 1 Teleport" 307 | { 308 | "visible" "0" 309 | 310 | "red" "255" 311 | "green" "200" 312 | "blue" "0" 313 | 314 | "alpha" "255" 315 | "width" "2.0" 316 | } 317 | 318 | "Bonus 1 Easybhop" 319 | { 320 | "visible" "1" 321 | 322 | "red" "57" 323 | "green" "196" 324 | "blue" "92" 325 | 326 | "alpha" "175" 327 | "width" "1.75" 328 | } 329 | 330 | "Bonus 1 Slide" 331 | { 332 | "visible" "1" 333 | 334 | "red" "244" 335 | "green" "66" 336 | "blue" "92" 337 | 338 | "alpha" "255" 339 | "width" "1.0" 340 | } 341 | 342 | "Bonus 1 Airaccelerate" 343 | { 344 | "visible" "1" 345 | 346 | "red" "118" 347 | "green" "102" 348 | "blue" "173" 349 | 350 | "alpha" "255" 351 | "width" "1.0" 352 | } 353 | 354 | "Bonus 1 Stage" 355 | { 356 | "visible" "1" 357 | 358 | "red" "204" 359 | "green" "153" 360 | "blue" "255" 361 | 362 | "alpha" "255" 363 | "width" "0.5" 364 | } 365 | 366 | "Bonus 1 No Timer Gravity" 367 | { 368 | "visible" "1" 369 | 370 | "red" "255" 371 | "green" "0" 372 | "blue" "255" 373 | 374 | "alpha" "255" 375 | "width" "1.0" 376 | } 377 | 378 | "Bonus 1 Gravity" 379 | { 380 | "visible" "1" 381 | 382 | "red" "255" 383 | "green" "0" 384 | "blue" "255" 385 | 386 | "alpha" "255" 387 | "width" "1.0" 388 | } 389 | 390 | "Bonus 1 Speedmod" 391 | { 392 | "visible" "1" 393 | 394 | "red" "255" 395 | "green" "0" 396 | "blue" "255" 397 | 398 | "alpha" "255" 399 | "width" "1.0" 400 | } 401 | 402 | "Bonus 1 No Jump" 403 | { 404 | "visible" "1" 405 | 406 | "red" "255" 407 | "green" "0" 408 | "blue" "255" 409 | 410 | "alpha" "255" 411 | "width" "0.1" 412 | } 413 | 414 | "Bonus 1 Autobhop" 415 | { 416 | "visible" "1" 417 | 418 | "red" "255" 419 | "green" "0" 420 | "blue" "255" 421 | 422 | "alpha" "255" 423 | "width" "0.1" 424 | } 425 | } 426 | } 427 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/DynamicChannels.inc: -------------------------------------------------------------------------------- 1 | #if defined _DynamicChannels_included_ 2 | #endinput 3 | #endif 4 | #define _DynamicChannels_included_ 5 | 6 | /** 7 | * Provides a game_text channel for plugins to use that will prevent conflict with map channels. 8 | * The group number is a way of sharing the same game_text channel between certain function calls/plugins 9 | * (NEW WITH V2.0!!!) The channel that each group number returns can change mid-session if the map changes a game_text channel, so call GetDynamicChannel() frequently and do not store it long term 10 | * For more help, see ExamplePlugin.sp and README.md at https://github.com/Vauff/DynamicChannels 11 | * 12 | * @param group Integer value of the group you want to get a game_text channel for. Must be between 0-5. 13 | * @return The integer value of the assigned game_text channel. 14 | */ 15 | native int GetDynamicChannel(int group); 16 | 17 | public SharedPlugin __pl_DynamicChannels = { 18 | name = "DynamicChannels", 19 | file = "DynamicChannels.smx", 20 | #if defined REQUIRE_PLUGIN 21 | required = 1, 22 | #else 23 | required = 0, 24 | #endif 25 | }; 26 | 27 | #if !defined REQUIRE_PLUGIN 28 | public void __pl_DynamicChannels_SetNTVOptional() { 29 | MarkNativeAsOptional("GetDynamicChannel"); 30 | } 31 | #endif -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/closestpos.inc: -------------------------------------------------------------------------------- 1 | 2 | #if defined _closestpos_included 3 | #endinput 4 | #endif 5 | #define _closestpos_included 6 | 7 | methodmap ClosestPos < Handle { 8 | public native ClosestPos(ArrayList input, int offset=0, int startidx=0, int count=2147483647); 9 | public native int Find(float pos[3]); 10 | }; 11 | 12 | public Extension __ext_closestpos = 13 | { 14 | name = "ClosestPos", 15 | file = "closestpos.ext", 16 | #if defined AUTOLOAD_EXTENSIONS 17 | autoload = 1, 18 | #else 19 | autoload = 0, 20 | #endif 21 | #if defined REQUIRE_EXTENSIONS 22 | required = 1, 23 | #else 24 | required = 0, 25 | #endif 26 | }; 27 | 28 | #if !defined REQUIRE_EXTENSIONS 29 | public void __ext_closestpos_SetNTVOptional() 30 | { 31 | MarkNativeAsOptional("ClosestPos.ClosestPos"); 32 | MarkNativeAsOptional("ClosestPos.Find"); 33 | } 34 | #endif 35 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/convar_class.inc: -------------------------------------------------------------------------------- 1 | /* 2 | MIT License 3 | 4 | Copyright (c) 2019-2020 KiD Fearless 5 | Copyright (c) 2021-2022 rtldg 6 | 7 | Permission is hereby granted, free of charge, to any person obtaining a copy 8 | of this software and associated documentation files (the "Software"), to deal 9 | in the Software without restriction, including without limitation the rights 10 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 11 | copies of the Software, and to permit persons to whom the Software is 12 | furnished to do so, subject to the following conditions: 13 | 14 | The above copyright notice and this permission notice shall be included in all 15 | copies or substantial portions of the Software. 16 | 17 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 18 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 19 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 20 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 21 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 22 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 23 | SOFTWARE. 24 | */ 25 | 26 | #if defined _convar_class_included 27 | #endinput 28 | #endif 29 | #define _convar_class_included 30 | 31 | // todo: track previous default values 32 | 33 | static ArrayList _ConvarList; 34 | 35 | enum struct convar_t 36 | { 37 | char name[255]; 38 | ConVar cvar; 39 | char description[512]; 40 | char defValue[512]; 41 | 42 | bool GetMin(float& input) 43 | { 44 | return this.cvar.GetBounds(ConVarBound_Lower, input); 45 | } 46 | bool GetMax(float& input) 47 | { 48 | return this.cvar.GetBounds(ConVarBound_Upper, input); 49 | } 50 | void SetMin(bool set, float& input = 0.0) 51 | { 52 | this.cvar.SetBounds(ConVarBound_Lower, set, input); 53 | } 54 | void SetMax(bool set, float& input = 0.0) 55 | { 56 | this.cvar.SetBounds(ConVarBound_Upper, set, input); 57 | } 58 | } 59 | 60 | methodmap Convar < ConVar 61 | { 62 | public Convar(const char[] name, const char[] defaultValue, const char[] description = "", 63 | int flags = 0, bool hasMin = false, float min = 0.0, bool hasMax = false, float max = 0.0, convar_t convar = {}) 64 | { 65 | if(_ConvarList == null) 66 | { 67 | _ConvarList = new ArrayList(sizeof(convar_t)); 68 | } 69 | 70 | ConVar cvar = CreateConVar(name, defaultValue, description, flags, hasMin, min, hasMax, max); 71 | 72 | convar_t savedValue; 73 | savedValue.cvar = cvar; 74 | strcopy(savedValue.name, sizeof(savedValue.name), name); 75 | strcopy(savedValue.description, 512, description); 76 | strcopy(savedValue.defValue, sizeof(savedValue.defValue), defaultValue); 77 | 78 | // Can't set default values :T 79 | savedValue.SetMin(hasMin, min); 80 | savedValue.SetMax(hasMax, max); 81 | 82 | // Have to do it this way instead of `convar = savedValue;` because SM 1.12 is a whiny bitch. 83 | convar.name = savedValue.name; 84 | convar.cvar = savedValue.cvar; 85 | convar.description = savedValue.description; 86 | convar.defValue = convar.defValue; 87 | 88 | _ConvarList.PushArray(savedValue); 89 | 90 | return view_as(cvar); 91 | } 92 | 93 | public static bool CreateConfig(const char[] fileName = "", const char[] folder = "sourcemod", const bool clearWhenDone = true) 94 | { 95 | char localFolder[PLATFORM_MAX_PATH]; 96 | FormatEx(localFolder, PLATFORM_MAX_PATH, "cfg/%s", folder); 97 | if(!DirExists(localFolder)) 98 | { 99 | if(!CreateDirectory(localFolder, 755)) 100 | { 101 | LogError("Error: Failed to create folder '%s'", localFolder); 102 | } 103 | } 104 | 105 | if(_ConvarList == null) 106 | { 107 | LogError("Error: No convars found. did you run .CreateConfig() before adding convars?"); 108 | return false; 109 | } 110 | 111 | _ConvarList.Sort(Sort_Ascending, Sort_String); 112 | 113 | // Check if the file exists. 114 | char local[PLATFORM_MAX_PATH]; 115 | if(fileName[0] == 0) 116 | { 117 | char pluginName[PLATFORM_MAX_PATH]; 118 | GetPluginFilename(GetMyHandle(), pluginName, PLATFORM_MAX_PATH); 119 | 120 | ReplaceString(pluginName, PLATFORM_MAX_PATH, ".smx", ""); 121 | ReplaceString(pluginName, PLATFORM_MAX_PATH, "\\", "/"); 122 | 123 | int start = FindCharInString(pluginName, '/', true); 124 | 125 | FormatEx(local, PLATFORM_MAX_PATH, "cfg/%s/plugin.%s.cfg", folder, pluginName[start+1]); 126 | } 127 | else 128 | { 129 | FormatEx(local, sizeof(local), "cfg/%s/%s.cfg", folder, fileName); 130 | } 131 | bool fileExists = FileExists(local); 132 | if (!fileExists) 133 | { 134 | // Create first time file 135 | File file = OpenFile(local, "wt"); 136 | if (file != null) 137 | { 138 | fileExists = true; 139 | 140 | // get the plugin name 141 | char pluginName[64]; 142 | GetPluginFilename(GetMyHandle(), pluginName, 64); 143 | 144 | // Write warning 145 | file.WriteLine("// This file was auto-generated by KiD's Convar Class. Only plugin convars are allowed."); 146 | file.WriteLine("// ConVars for plugin \"%s\"\n\n", pluginName); 147 | 148 | // Loop through all of our convars 149 | for (int i = 0; i < _ConvarList.Length; ++i) 150 | { 151 | // get the current convar and description 152 | convar_t convar; 153 | _ConvarList.GetArray(i, convar); 154 | 155 | // don't write to file if flag is set 156 | if (convar.cvar.Flags & FCVAR_DONTRECORD != 0) 157 | { 158 | continue; 159 | } 160 | 161 | // format newlines as comments 162 | ReplaceString(convar.description, 512, "\n", "\n// "); 163 | 164 | // write the values and bounds to the file if they exist 165 | file.WriteLine("// %s", convar.description); 166 | 167 | file.WriteLine("// -"); 168 | file.WriteLine("// Default: \"%s\"", convar.defValue); 169 | float x; 170 | if (convar.GetMin(x)) 171 | { 172 | file.WriteLine("// Minimum: \"%02f\"", x); 173 | } 174 | if (convar.GetMax(x)) 175 | { 176 | file.WriteLine("// Maximum: \"%02f\"", x); 177 | } 178 | file.WriteLine("%s \"%s\"\n", convar.name, convar.defValue); 179 | } 180 | // end with newline 181 | file.WriteLine(""); 182 | delete file; 183 | } 184 | else 185 | { 186 | // writing failed, notify developer. 187 | char pluginName[64]; 188 | GetPluginFilename(GetMyHandle(), pluginName, 64); 189 | LogError("Failed to auto generate config for %s at '%s', make sure the directory has write permission.", pluginName, local); 190 | if(clearWhenDone) 191 | { 192 | delete _ConvarList; 193 | } 194 | return false; 195 | } 196 | } 197 | // file already exists, just update the description and defaults 198 | else 199 | { 200 | // open the file for reading 201 | File file = OpenFile(local, "r"); 202 | // create a stringmap to hold our current convars. 203 | StringMap convars = new StringMap(); 204 | 205 | char line[512]; 206 | int currentLine = 0; 207 | while(!file.EndOfFile() && file.ReadLine(line, 512)) 208 | { 209 | TrimString(line); 210 | 211 | ++currentLine; 212 | // check if the line contains a valid statement 213 | if(line[0] != '/' && line[0] != '\n' && line[0] != 0) 214 | { 215 | char buffers[2][512]; 216 | // only convars should be in here. which should contain convar [space] value. 217 | if(ExplodeString(line, " ", buffers, 2, 512, true) == 2) 218 | { 219 | // remove any trailing whitespace. should be none 220 | TrimString(buffers[0]); 221 | TrimString(buffers[1]); 222 | // remove the quotes from the values 223 | StripQuotes(buffers[0]); 224 | StripQuotes(buffers[1]); 225 | 226 | // since convars are only ever strings we store it as strings. 227 | convars.SetString(buffers[0], buffers[1]); 228 | } 229 | else 230 | { 231 | // someone put something in there that shouldn't be. Yell at the dev for doing stupid stuff. 232 | LogError("Error exploding convar string: '%s' on line: %i", line, currentLine); 233 | } 234 | } 235 | } 236 | // close our file 237 | delete file; 238 | // yay duplicate code 239 | // rewrite the cfg with old convars removed and new convars added. 240 | /* Attempt to recreate it */ 241 | DeleteFile(local); 242 | file = OpenFile(local, "wt"); 243 | if (file != null) 244 | { 245 | fileExists = true; 246 | 247 | char pluginName[64]; 248 | GetPluginFilename(GetMyHandle(), pluginName, 64); 249 | 250 | file.WriteLine("// This file was auto-generated by KiD's Convar Class. Only plugin convars are allowed."); 251 | file.WriteLine("// ConVars for plugin \"%s\"\n\n", pluginName); 252 | 253 | float x; 254 | for (int i = 0; i < _ConvarList.Length; ++i) 255 | { 256 | convar_t convar; 257 | _ConvarList.GetArray(i, convar); 258 | 259 | if (convar.cvar.Flags & FCVAR_DONTRECORD != 0) 260 | { 261 | continue; 262 | } 263 | 264 | ReplaceString(convar.description, 512, "\n", "\n// "); 265 | file.WriteLine("// %s", convar.description); 266 | 267 | file.WriteLine("// -"); 268 | file.WriteLine("// Default: \"%s\"", convar.defValue); 269 | if (convar.GetMin(x)) 270 | { 271 | file.WriteLine("// Minimum: \"%02f\"", x); 272 | } 273 | if (convar.GetMax(x)) 274 | { 275 | file.WriteLine("// Maximum: \"%02f\"", x); 276 | } 277 | 278 | // only difference is that now we check for a stored value. 279 | char storedValue[512]; 280 | if(convars.GetString(convar.name, storedValue, 512)) 281 | { 282 | file.WriteLine("%s \"%s\"\n", convar.name, storedValue); 283 | } 284 | else 285 | { 286 | file.WriteLine("%s \"%s\"\n", convar.name, convar.defValue); 287 | } 288 | } 289 | file.WriteLine(""); 290 | delete file; 291 | } 292 | else 293 | { 294 | char pluginName[64]; 295 | GetPluginFilename(GetMyHandle(), pluginName, 64); 296 | LogError("Failed to auto generate config for %s, make sure the directory has write permission.", pluginName); 297 | 298 | if(clearWhenDone) 299 | { 300 | delete _ConvarList; 301 | } 302 | 303 | delete convars; 304 | return false; 305 | } 306 | 307 | delete convars; 308 | } 309 | if(fileExists) 310 | { 311 | ServerCommand("exec \"%s\"", local[4]); 312 | } 313 | if(clearWhenDone) 314 | { 315 | delete _ConvarList; 316 | } 317 | return true; 318 | } 319 | 320 | public static void AutoExecConfig(const char[] fileName = "", const char[] folder = "sourcemod", const bool clearWhenDone = true) 321 | { 322 | if(Convar.CreateConfig(fileName, folder, clearWhenDone)) 323 | { 324 | AutoExecConfig(false, fileName, folder); 325 | } 326 | } 327 | 328 | public void Close() 329 | { 330 | delete _ConvarList; 331 | } 332 | } 333 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/eventqueuefix.inc: -------------------------------------------------------------------------------- 1 | #if defined _eventqueuefix_included 2 | #endinput 3 | #endif 4 | #define _eventqueuefix_included 5 | 6 | public SharedPlugin __pl_eventqueuefix = 7 | { 8 | name = "eventqueuefix", 9 | file = "eventqueuefix.smx", 10 | #if defined REQUIRE_PLUGIN 11 | required = 1, 12 | #else 13 | required = 0, 14 | #endif 15 | }; 16 | 17 | enum struct event_t 18 | { 19 | char target[64]; 20 | char targetInput[64]; 21 | char variantValue[PLATFORM_MAX_PATH]; 22 | float delay; 23 | int activator; 24 | int caller; 25 | int outputID; 26 | } 27 | 28 | enum struct eventpack_t 29 | { 30 | ArrayList playerEvents; 31 | ArrayList outputWaits; 32 | } 33 | 34 | enum struct entity_t 35 | { 36 | int caller; 37 | float waitTime; 38 | } 39 | 40 | /* 41 | * Gets the current pending events for a client. 42 | * 43 | * @param client Client index. 44 | * @param eventpack Struct containg arrays for pending events and trigger cooldowns. 45 | * 46 | * @return True if successful, false otherwise. 47 | */ 48 | native bool GetClientEvents(int client, any[] eventpack); 49 | 50 | /* 51 | * Sets the current pending events for a client. 52 | * 53 | * @param client Client index. 54 | * @param eventpack Struct containg arrays for pending events and trigger cooldowns. 55 | * 56 | * @return True if successful, false otherwise. 57 | */ 58 | native bool SetClientEvents(int client, any[] eventpack); 59 | 60 | /* 61 | * Clears the current pending events for a client. 62 | * 63 | * @param client Client index. 64 | * 65 | * @return True if successful, false otherwise. 66 | */ 67 | native bool ClearClientEvents(int client); 68 | 69 | /* 70 | * Sets the current timescale for a client. 71 | * 72 | * @param client Client index. 73 | * @param timescale Timescale. 74 | * 75 | * @return True if successful, false otherwise. 76 | */ 77 | native bool SetEventsTimescale(int client, float timescale); 78 | 79 | /* 80 | * Pauses or unpauses events for a given client. 81 | * 82 | * @param client Client index. 83 | * @param paused Pause state. 84 | * 85 | * @return True if action was successful, false otherwise. 86 | */ 87 | native bool SetClientEventsPaused(int client, bool paused); 88 | 89 | /* 90 | * Check if events is paused 91 | * 92 | * @param client Client index. 93 | * 94 | * @return True if events are paused for client, false otherwise. Will throw native error if client is invalid. 95 | */ 96 | native bool IsClientEventsPaused(int client); 97 | 98 | #if !defined REQUIRE_PLUGIN 99 | public void __pl_eventqueuefix_SetNTVOptional() 100 | { 101 | MarkNativeAsOptional("GetClientEvents"); 102 | MarkNativeAsOptional("SetClientEvents"); 103 | MarkNativeAsOptional("ClearClientEvents"); 104 | MarkNativeAsOptional("SetEventsTimescale"); 105 | MarkNativeAsOptional("SetClientEventsPaused"); 106 | MarkNativeAsOptional("IsClientEventsPaused"); 107 | } 108 | #endif 109 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/rtler.inc: -------------------------------------------------------------------------------- 1 | // code by alongub https://github.com/alongubkin/ 2 | 3 | #if defined _rtler_included 4 | #endinput 5 | #endif 6 | #define _rtler_included 7 | 8 | #pragma semicolon 1 9 | 10 | /** 11 | * Converts a string that contains words in RTL languages to be displayed correctly in-game. 12 | * 13 | * @param dest Destination string buffer to copy the RTL-ed string to. 14 | * @param destLen Destination buffer length (includes null terminator). 15 | * @param original Original non-rtled string. 16 | * 17 | * @return The amount of words that needed RTLifying. 18 | */ 19 | native int RTLify(char[] dest, int destLen, const char[] original); 20 | 21 | public SharedPlugin __pl_rtler = 22 | { 23 | name = "rtler", 24 | file = "rtler.smx", 25 | #if defined REQUIRE_PLUGIN 26 | required = 1, 27 | #else 28 | required = 0, 29 | #endif 30 | }; 31 | 32 | public void __pl_rtler_SetNTVOptional() 33 | { 34 | MarkNativeAsOptional("RTLify"); 35 | } 36 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - .inc file 3 | * by: shavit, rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_included 23 | #endinput 24 | #endif 25 | #define _shavit_included 26 | 27 | // compat giga include file 28 | 29 | #include 30 | #include 31 | #include 32 | #include 33 | #include 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include 39 | 40 | // new plugins (like tas) have been excluded since you should now `#include ` yourself 41 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/anti-sv_cheats.sp: -------------------------------------------------------------------------------- 1 | /* 2 | * Anti-sv_cheats and anti- cheat-command stuff 3 | * by: rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | 23 | // This code annoys everyone but admins would sometimes set sv_cheats 1 and then 24 | // forget to toggle it back off when they were done playing around so then people 25 | // would join and teleport into the endzone and set dumb times. And now we're here... 26 | // Just add some aliases to your autoexec: 27 | // alias cheats "sm_rcon shavit_core_disable_sv_cheats 0 ; sm_rcon sv_cheats 1" 28 | // alias cheat "sm_rcon shavit_core_disable_sv_cheats 0 ; sm_rcon sv_cheats 1" 29 | 30 | 31 | Convar gCV_DisableSvCheats = null; 32 | 33 | #if !DEBUG 34 | ConVar sv_cheats = null; 35 | 36 | char gS_CheatCommands[][] = { 37 | "ent_create", 38 | "ent_orient", 39 | "ent_pause", 40 | "ent_fire", 41 | 42 | "ent_remove", 43 | "ent_remove_all", 44 | 45 | "ent_setname", 46 | "ent_setpos", 47 | 48 | "ent_teleport", 49 | 50 | "firetarget", 51 | 52 | "setpos", 53 | "setpos_exact", 54 | "setpos_player", 55 | 56 | // can be used to kill other players 57 | "explode", 58 | "explodevector", 59 | "kill", 60 | "killvector", 61 | 62 | "give", 63 | }; 64 | #endif 65 | 66 | void Anti_sv_cheats_cvars() 67 | { 68 | gCV_DisableSvCheats = new Convar("shavit_core_disable_sv_cheats", "1", "Force sv_cheats to 0.", 0, true, 0.0, true, 1.0); 69 | 70 | #if !DEBUG 71 | sv_cheats = FindConVar("sv_cheats"); 72 | sv_cheats.AddChangeHook(sv_cheats_hook); 73 | 74 | for (int i = 0; i < sizeof(gS_CheatCommands); i++) 75 | { 76 | AddCommandListener(Command_Cheats, gS_CheatCommands[i]); 77 | } 78 | #endif 79 | } 80 | 81 | void Anti_sv_cheats_OnConfigsExecuted() 82 | { 83 | if (gCV_DisableSvCheats.BoolValue) 84 | { 85 | #if !DEBUG 86 | sv_cheats.SetInt(0); 87 | #endif 88 | } 89 | } 90 | 91 | void Remove_sv_cheat_Impluses(int client, int &impulse) 92 | { 93 | #if !DEBUG 94 | if (impulse && sv_cheats.BoolValue && !(GetUserFlagBits(client) & ADMFLAG_ROOT)) 95 | { 96 | switch (impulse) 97 | { 98 | // Likely incomplete list of the most cheaty impulses... 99 | // 76 = spawn npc 100 | // 81 = something cubemap 101 | // 82 = create jeep 102 | // 83 = create airboat 103 | // 102 = something node 104 | // 195 = something node 105 | // 196 = something node 106 | // 197 = something node 107 | // 202 = something bloodsplat 108 | // 203 = remove entity 109 | case 76, 81, 82, 83, 102, 195, 196, 197, 202, 203: 110 | { 111 | impulse = 0; 112 | } 113 | } 114 | } 115 | #endif 116 | } 117 | 118 | #if !DEBUG 119 | public void sv_cheats_hook(ConVar convar, const char[] oldValue, const char[] newValue) 120 | { 121 | if (gCV_DisableSvCheats.BoolValue) 122 | { 123 | sv_cheats.SetInt(0); 124 | } 125 | } 126 | 127 | public Action Command_Cheats(int client, const char[] command, int args) 128 | { 129 | if (!sv_cheats.BoolValue || client == 0) 130 | { 131 | return Plugin_Continue; 132 | } 133 | 134 | if (StrContains(command, "kill") != -1 || StrContains(command, "explode") != -1) 135 | { 136 | bool bVector = StrContains(command, "vector") != -1; 137 | bool bKillOther = args > (bVector ? 3 : 0); 138 | 139 | if (!bKillOther) 140 | { 141 | return Plugin_Continue; 142 | } 143 | } 144 | 145 | if (!(GetUserFlagBits(client) & ADMFLAG_ROOT)) 146 | { 147 | return Plugin_Stop; 148 | } 149 | 150 | return Plugin_Continue; 151 | } 152 | #endif 153 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/area_and_cluster_stages.sp: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - area_and_cluster_stages.sp 3 | * by: carnifex 4 | * 5 | * This file is part of shavit's Timer. 6 | * 7 | * This program is free software; you can redistribute it and/or modify it under 8 | * the terms of the GNU General Public License, version 3.0, as published by the 9 | * Free Software Foundation. 10 | * 11 | * This program is distributed in the hope that it will be useful, but WITHOUT 12 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 13 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 14 | * details. 15 | * 16 | * You should have received a copy of the GNU General Public License along with 17 | * this program. If not, see . 18 | * 19 | */ 20 | 21 | // originally sourced from https://github.com/hermansimensen/mapstages 22 | 23 | Address IVEngineServer; 24 | Handle gH_GetCluster; 25 | Handle gH_GetArea; 26 | 27 | void LoadDHooks_mapstages(GameData gamedata) 28 | { 29 | StartPrepSDKCall(SDKCall_Static); 30 | if (!PrepSDKCall_SetFromConf(gamedata, SDKConf_Signature, "CreateInterface")) 31 | { 32 | SetFailState("Failed to get CreateInterface"); 33 | } 34 | 35 | PrepSDKCall_AddParameter(SDKType_String, SDKPass_Pointer); 36 | PrepSDKCall_AddParameter(SDKType_PlainOldData, SDKPass_Pointer, VDECODE_FLAG_ALLOWNULL); 37 | PrepSDKCall_SetReturnInfo(SDKType_PlainOldData, SDKPass_Plain); 38 | Handle CreateInterface = EndPrepSDKCall(); 39 | 40 | if (CreateInterface == null) 41 | { 42 | SetFailState("Unable to prepare SDKCall for CreateInterface"); 43 | } 44 | 45 | char interfaceName[64]; 46 | if (!GameConfGetKeyValue(gamedata, "IVEngineServer", interfaceName, sizeof(interfaceName))) 47 | { 48 | SetFailState("Failed to get IVEngineServer interface name"); 49 | } 50 | 51 | IVEngineServer = SDKCall(CreateInterface, interfaceName, 0); 52 | 53 | if (!IVEngineServer) 54 | { 55 | SetFailState("Failed to get IVEngineServer pointer"); 56 | } 57 | 58 | StartPrepSDKCall(SDKCall_Raw); 59 | if (!PrepSDKCall_SetFromConf(gamedata, SDKConf_Virtual, "GetClusterForOrigin")) 60 | { 61 | SetFailState("Couldn't find GetClusterForOrigin offset"); 62 | } 63 | PrepSDKCall_AddParameter(SDKType_Vector, SDKPass_Plain); 64 | PrepSDKCall_SetReturnInfo(SDKType_PlainOldData, SDKPass_Plain); 65 | gH_GetCluster = EndPrepSDKCall(); 66 | 67 | StartPrepSDKCall(SDKCall_Raw); 68 | if (!PrepSDKCall_SetFromConf(gamedata, SDKConf_Virtual, "GetArea")) 69 | { 70 | SetFailState("Couldn't find GetArea offset"); 71 | } 72 | PrepSDKCall_AddParameter(SDKType_Vector, SDKPass_Plain); 73 | PrepSDKCall_SetReturnInfo(SDKType_PlainOldData, SDKPass_Plain); 74 | gH_GetArea = EndPrepSDKCall(); 75 | 76 | delete CreateInterface; 77 | } 78 | 79 | public int GetClusterForOrigin(const float pos[3]) 80 | { 81 | return SDKCall(gH_GetCluster, IVEngineServer, pos); 82 | } 83 | 84 | public int GetAreaForOrigin(const float pos[3]) 85 | { 86 | return SDKCall(gH_GetArea, IVEngineServer, pos); 87 | } 88 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/bhopstats-timerified.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * Bunnyhop Statistics API - Include file 3 | * by: shavit 4 | * 5 | * Originally from Bunnyhop Statistics API (https://github.com/shavitush/bhopstats) 6 | * but edited to be part of shavit's Timer (https://github.com/shavitush/bhoptimer) 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_bhopstats_included 23 | #endinput 24 | #endif 25 | #define _shavit_bhopstats_included 26 | 27 | /** 28 | * Called when the jump key is pressed. 29 | * 30 | * @param client Client index. 31 | * @param onground True if the jump key will do anything for the player when tapped. 32 | * @param perfect Was the jump perfectly timed? 33 | * @noreturn 34 | */ 35 | forward void Shavit_Bhopstats_OnJumpPressed(int client, bool onground, bool perfect); 36 | 37 | /** 38 | * Called when the jump key is released. 39 | * 40 | * @param client Client index. 41 | * @param onground True if the jump key will do anything for the player when tapped. 42 | * @noreturn 43 | */ 44 | forward void Shavit_Bhopstats_OnJumpReleased(int client, bool onground); 45 | 46 | /** 47 | * Called when the player touches the ground. 48 | * 49 | * @param client Client index. 50 | * @noreturn 51 | */ 52 | forward void Shavit_Bhopstats_OnTouchGround(int client); 53 | 54 | /** 55 | * Called when the player leaves the ground, by either jumping or falling from somewhere. 56 | * AKA the HookEventless better version of player_jump. 57 | * The `jumped` variable is true if the ground was left by tapping the jump key, or false if the player fell from somewhere. 58 | * `ladder` is true if the player left the 'ground' from a ladder. 59 | * 60 | * @param client Client index. 61 | * @param jumped Did the client leave the ground by jumping? 62 | * @param ladder Did the client leave the ground by leaving a ladder, aka ladderstrafing? 63 | * @noreturn 64 | */ 65 | forward void Shavit_Bhopstats_OnLeaveGround(int client, bool jumped, bool ladder); 66 | 67 | /** 68 | * Retrieves the amount of separate +jump inputs since the player left the ground. 69 | * 70 | * @param client Client index. 71 | * @return Amount of +jump inputs since the left the ground, or 0 if the player is on ground. 72 | */ 73 | native int Shavit_Bhopstats_GetScrollCount(int client); 74 | 75 | /** 76 | * Checks if the player is on ground, or if the jump key will function as in actually triggering a jump or altering velocity. 77 | * The result will be true if the player is on a ladder or in water, as jumping will be functional. 78 | * 79 | * @param client Client index. 80 | * @return Boolean value of 'is the player on ground?' 81 | */ 82 | native bool Shavit_Bhopstats_IsOnGround(int client); 83 | 84 | /** 85 | * Checks if the player is holding his jump key. 86 | * 87 | * @param client Client index. 88 | * @return Boolean value of 'is the player holding the jump key?'' 89 | */ 90 | native bool Shavit_Bhopstats_IsHoldingJump(int client); 91 | 92 | /** 93 | * Gets a percentage of perfectly timed bunnyhops. 94 | * Resets at player connection or the Shavit_Bhopstats_ResetPerfectJumps native for it is called. 95 | * 96 | * @param client Client index. 97 | * @return Perfect jump percentage. Results are from 0.0 to 100.0. 98 | */ 99 | native float Shavit_Bhopstats_GetPerfectJumps(int client); 100 | 101 | /** 102 | * Resets the perfect jumps percentage of a player back to 0.0. 103 | * 104 | * @param client Client index. 105 | * @noreturn 106 | */ 107 | native void Shavit_Bhopstats_ResetPerfectJumps(int client); 108 | 109 | methodmap Shavit_BunnyhopStats __nullable__ 110 | { 111 | public Shavit_BunnyhopStats(int client) 112 | { 113 | return view_as(client); 114 | } 115 | 116 | property int index 117 | { 118 | public get() 119 | { 120 | return view_as(this); 121 | } 122 | } 123 | 124 | property int ScrollCount 125 | { 126 | public get() 127 | { 128 | return Shavit_Bhopstats_GetScrollCount(this.index); 129 | } 130 | } 131 | 132 | property bool OnGround 133 | { 134 | public get() 135 | { 136 | return Shavit_Bhopstats_IsOnGround(this.index); 137 | } 138 | } 139 | 140 | property bool HoldingJump 141 | { 142 | public get() 143 | { 144 | return Shavit_Bhopstats_IsHoldingJump(this.index); 145 | } 146 | } 147 | 148 | property float PerfectJumps 149 | { 150 | public get() 151 | { 152 | return Shavit_Bhopstats_GetPerfectJumps(this.index); 153 | } 154 | } 155 | 156 | public void ResetPrefects() 157 | { 158 | Shavit_Bhopstats_ResetPerfectJumps(this.index); 159 | } 160 | 161 | public static int GetScrollCount(int client) 162 | { 163 | return Shavit_Bhopstats_GetScrollCount(client); 164 | } 165 | 166 | public static bool IsOnGround(int client) 167 | { 168 | return Shavit_Bhopstats_IsOnGround(client); 169 | } 170 | 171 | public static bool IsHoldingJump(int client) 172 | { 173 | return Shavit_Bhopstats_IsHoldingJump(client); 174 | } 175 | 176 | public static float GetPerfectJumps(int client) 177 | { 178 | return Shavit_Bhopstats_GetPerfectJumps(client); 179 | } 180 | 181 | public static void ResetPrefectJumps(int client) 182 | { 183 | Shavit_Bhopstats_ResetPerfectJumps(client); 184 | } 185 | } 186 | 187 | #if !defined REQUIRE_PLUGIN 188 | public void __pl_shavit_bhopstats_SetNTVOptional() 189 | { 190 | MarkNativeAsOptional("Shavit_Bhopstats_GetScrollCount"); 191 | MarkNativeAsOptional("Shavit_Bhopstats_IsOnGround"); 192 | MarkNativeAsOptional("Shavit_Bhopstats_IsHoldingJump"); 193 | MarkNativeAsOptional("Shavit_Bhopstats_GetPerfectJumps"); 194 | MarkNativeAsOptional("Shavit_Bhopstats_ResetPerfectJumps"); 195 | } 196 | #endif 197 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/bhopstats-timerified.sp: -------------------------------------------------------------------------------- 1 | /* 2 | * Bunnyhop Statistics API - Plugin 3 | * by: shavit 4 | * 5 | * Originally from Bunnyhop Statistics API (https://github.com/shavitush/bhopstats) 6 | * but edited to be part of shavit's Timer (https://github.com/shavitush/bhoptimer) 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #pragma newdecls required 23 | #pragma semicolon 1 24 | 25 | bool gB_OnGround[MAXPLAYERS+1]; 26 | bool gB_PlayerTouchingGround[MAXPLAYERS+1]; 27 | 28 | int gI_Scrolls[MAXPLAYERS+1]; 29 | int gI_Buttons[MAXPLAYERS+1]; 30 | bool gB_JumpHeld[MAXPLAYERS+1]; 31 | 32 | int gI_Jumps[MAXPLAYERS+1]; 33 | int gI_PerfectJumps[MAXPLAYERS+1]; 34 | 35 | Handle gH_Forwards_OnJumpPressed = null; 36 | Handle gH_Forwards_OnJumpReleased = null; 37 | Handle gH_Forwards_OnTouchGround = null; 38 | Handle gH_Forwards_OnLeaveGround = null; 39 | 40 | public void Bhopstats_CreateNatives() 41 | { 42 | CreateNative("Shavit_Bhopstats_GetScrollCount", Native_GetScrollCount); 43 | CreateNative("Shavit_Bhopstats_IsOnGround", Native_IsOnGround); 44 | CreateNative("Shavit_Bhopstats_IsHoldingJump", Native_IsHoldingJump); 45 | CreateNative("Shavit_Bhopstats_GetPerfectJumps", Native_Bhopstats_GetPerfectJumps); 46 | CreateNative("Shavit_Bhopstats_ResetPerfectJumps", Native_ResetPerfectJumps); 47 | } 48 | 49 | public void Bhopstats_CreateForwards() 50 | { 51 | gH_Forwards_OnJumpPressed = CreateGlobalForward("Shavit_Bhopstats_OnJumpPressed", ET_Event, Param_Cell, Param_Cell); 52 | gH_Forwards_OnJumpReleased = CreateGlobalForward("Shavit_Bhopstats_OnJumpReleased", ET_Event, Param_Cell, Param_Cell); 53 | gH_Forwards_OnTouchGround = CreateGlobalForward("Shavit_Bhopstats_OnTouchGround", ET_Event, Param_Cell); 54 | gH_Forwards_OnLeaveGround = CreateGlobalForward("Shavit_Bhopstats_OnLeaveGround", ET_Event, Param_Cell, Param_Cell, Param_Cell); 55 | } 56 | 57 | public void Bhopstats_OnClientPutInServer(int client) 58 | { 59 | gB_OnGround[client] = false; 60 | gB_PlayerTouchingGround[client] = false; 61 | 62 | gI_Scrolls[client] = 0; 63 | gI_Buttons[client] = 0; 64 | gB_JumpHeld[client] = false; 65 | 66 | gI_Jumps[client] = 0; 67 | gI_PerfectJumps[client] = 0; 68 | 69 | SDKHook(client, SDKHook_PostThinkPost, Bhopstats_PostThinkPost); 70 | } 71 | 72 | public int Native_GetScrollCount(Handle handler, int numParams) 73 | { 74 | return gI_Scrolls[GetNativeCell(1)]; 75 | } 76 | 77 | public int Native_IsOnGround(Handle handler, int numParams) 78 | { 79 | return view_as(gB_OnGround[GetNativeCell(1)]); 80 | } 81 | 82 | public int Native_IsHoldingJump(Handle handler, int numParams) 83 | { 84 | return view_as(gI_Buttons[GetNativeCell(1)] & IN_JUMP); 85 | } 86 | 87 | public int Native_Bhopstats_GetPerfectJumps(Handle handler, int numParams) 88 | { 89 | int client = GetNativeCell(1); 90 | 91 | return view_as((float(gI_PerfectJumps[client]) / gI_Jumps[client]) * 100.0); 92 | } 93 | 94 | public int Native_ResetPerfectJumps(Handle handler, int numParams) 95 | { 96 | int client = GetNativeCell(1); 97 | 98 | gI_Jumps[client] = 0; 99 | gI_PerfectJumps[client] = 0; 100 | 101 | return 0; 102 | } 103 | 104 | public void Bhopstats_PostThinkPost(int client) 105 | { 106 | if(!IsPlayerAlive(client)) 107 | { 108 | return; 109 | } 110 | 111 | int buttons = GetClientButtons(client); 112 | bool bOldOnGround = gB_OnGround[client]; 113 | 114 | int iGroundEntity; 115 | 116 | if (gB_ReplayPlayback && IsFakeClient(client)) 117 | { 118 | iGroundEntity = (Shavit_GetReplayEntityFlags(client) & FL_ONGROUND) ? 0 : -1; 119 | } 120 | else 121 | { 122 | iGroundEntity = GetEntPropEnt(client, Prop_Send, "m_hGroundEntity"); 123 | } 124 | 125 | bool bOnLadder = (GetEntityMoveType(client) == MOVETYPE_LADDER); 126 | gB_OnGround[client] = (iGroundEntity != -1 || GetEntProp(client, Prop_Send, "m_nWaterLevel") >= 2 || bOnLadder); 127 | 128 | gB_JumpHeld[client] = (buttons & IN_JUMP && !(gI_Buttons[client] & IN_JUMP)); 129 | 130 | if(gB_PlayerTouchingGround[client] && gB_OnGround[client]) 131 | { 132 | Call_StartForward(gH_Forwards_OnTouchGround); 133 | Call_PushCell(client); 134 | Call_Finish(); 135 | 136 | gB_PlayerTouchingGround[client] = false; 137 | } 138 | else if(!gB_PlayerTouchingGround[client] && ((gB_JumpHeld[client] && iGroundEntity != -1) || iGroundEntity == -1 || bOnLadder)) 139 | { 140 | Call_StartForward(gH_Forwards_OnLeaveGround); 141 | Call_PushCell(client); 142 | Call_PushCell(gB_JumpHeld[client]); 143 | Call_PushCell(bOnLadder); 144 | Call_Finish(); 145 | 146 | gB_PlayerTouchingGround[client] = true; 147 | gI_Scrolls[client] = 0; 148 | } 149 | 150 | if(gB_JumpHeld[client]) 151 | { 152 | gI_Scrolls[client]++; 153 | 154 | Call_StartForward(gH_Forwards_OnJumpPressed); 155 | Call_PushCell(client); 156 | Call_PushCell(gB_OnGround[client]); 157 | Call_Finish(); 158 | 159 | if(gB_OnGround[client]) 160 | { 161 | gI_Jumps[client]++; 162 | 163 | if(!bOldOnGround) 164 | { 165 | gI_PerfectJumps[client]++; 166 | } 167 | } 168 | } 169 | else if(gI_Buttons[client] & IN_JUMP && !(buttons & IN_JUMP)) 170 | { 171 | Call_StartForward(gH_Forwards_OnJumpReleased); 172 | Call_PushCell(client); 173 | Call_PushCell(gB_OnGround[client]); 174 | Call_Finish(); 175 | } 176 | 177 | gI_Buttons[client] = buttons; 178 | } 179 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/chat-colors.inc: -------------------------------------------------------------------------------- 1 | #if defined _shavit_chat_colors_included 2 | #endinput 3 | #endif 4 | #define _shavit_chat_colors_included 5 | 6 | char gS_GlobalColorNames[][] = 7 | { 8 | "{default}", 9 | "{def}", 10 | "{team}", 11 | "{green}" 12 | }; 13 | 14 | char gS_GlobalColors[][] = 15 | { 16 | "\x01", 17 | "\x01", 18 | "\x03", 19 | "\x04" 20 | }; 21 | 22 | char gS_CSGOColorNames[][] = 23 | { 24 | "{blue}", 25 | "{bluegrey}", 26 | "{darkblue}", 27 | "{darkred}", 28 | "{gold}", 29 | "{grey}", 30 | "{grey2}", 31 | "{lightgreen}", 32 | "{lightred}", 33 | "{lime}", 34 | "{orchid}", 35 | "{yellow}", 36 | "{palered}" 37 | }; 38 | 39 | char gS_CSGOColors[][] = 40 | { 41 | "\x0B", 42 | "\x0A", 43 | "\x0C", 44 | "\x02", 45 | "\x10", 46 | "\x08", 47 | "\x0D", 48 | "\x05", 49 | "\x0F", 50 | "\x06", 51 | "\x0E", 52 | "\x09", 53 | "\x07" 54 | }; 55 | 56 | 57 | stock void FormatColors(char[] buffer, int size, bool colors, bool escape, bool csgo, bool funky_chars=true) 58 | { 59 | if(colors) 60 | { 61 | for(int i = 0; i < sizeof(gS_GlobalColorNames); i++) 62 | { 63 | ReplaceString(buffer, size, gS_GlobalColorNames[i], gS_GlobalColors[i]); 64 | } 65 | 66 | if(csgo) 67 | { 68 | for(int i = 0; i < sizeof(gS_CSGOColorNames); i++) 69 | { 70 | ReplaceString(buffer, size, gS_CSGOColorNames[i], gS_CSGOColors[i]); 71 | } 72 | } 73 | 74 | if (funky_chars) ReplaceString(buffer, size, "^", "\x07"); 75 | ReplaceString(buffer, size, "{RGB}", "\x07"); 76 | if (funky_chars) ReplaceString(buffer, size, "&", "\x08"); 77 | ReplaceString(buffer, size, "{RGBA}", "\x08"); 78 | } 79 | 80 | if(escape) 81 | { 82 | ReplaceString(buffer, size, "%%", ""); 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/chat.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - chat.inc file 3 | * by: rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_chat_included 23 | #endinput 24 | #endif 25 | #define _shavit_chat_included 26 | 27 | /* 28 | * Retrieves the player's chatrank trimmed and without colors. 29 | * 30 | * @param client Client index 31 | * @param buf Buffer to put the put the chatrank into 32 | * @param buflen Size of buf 33 | * @param includename Include {name} in result. 34 | * @noreturn 35 | */ 36 | native void Shavit_GetPlainChatrank(int client, char[] buf, int buflen, bool includename=false); 37 | 38 | public SharedPlugin __pl_shavit_chat = 39 | { 40 | name = "shavit-chat", 41 | file = "shavit-chat.smx", 42 | #if defined REQUIRE_PLUGIN 43 | required = 1 44 | #else 45 | required = 0 46 | #endif 47 | }; 48 | 49 | #if !defined REQUIRE_PLUGIN 50 | public void __pl_shavit_chat_SetNTVOptional() 51 | { 52 | MarkNativeAsOptional("Shavit_GetPlainChatrank"); 53 | } 54 | #endif 55 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/hud.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - hud.inc file 3 | * by: shavit 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_hud_included 23 | #endinput 24 | #endif 25 | #define _shavit_hud_included 26 | 27 | #define HUD_NONE 0 28 | #define HUD_MASTER (1 << 0) // master setting 29 | #define HUD_CENTER (1 << 1) // show hud as hint text 30 | #define HUD_ZONEHUD (1 << 2) // show start/end zone hud 31 | #define HUD_OBSERVE (1 << 3) // show the HUD of the player you spectate 32 | #define HUD_SPECTATORS (1 << 4) // show list of spectators 33 | #define HUD_KEYOVERLAY (1 << 5) // show a key overlay 34 | #define HUD_HIDEWEAPON (1 << 6) // hide the player's weapon 35 | #define HUD_TOPLEFT (1 << 7) // show top left white HUD with WR/PB times 36 | #define HUD_SYNC (1 << 8) // shows sync at right side of the screen (css only) 37 | #define HUD_TIMELEFT (1 << 9) // shows time left at right tside of the screen (css only) 38 | #define HUD_2DVEL (1 << 10) // shows 2d velocity 39 | #define HUD_NOSOUNDS (1 << 11) // disables sounds on personal best, world record etc 40 | #define HUD_NOPRACALERT (1 << 12) // hides practice mode chat alert 41 | #define HUD_USP (1 << 13) // makes you spawn with a USP 42 | #define HUD_GLOCK (1 << 14) // makes you spawn with a Glock 43 | #define HUD_DEBUGTARGETNAME (1 << 15) // admin option to show current targetname & classname 44 | #define HUD_SPECTATORSDEAD (1 << 16) // for only showing spectators list when you're dead/spectating. 45 | 46 | // HUD2 - these settings will *disable* elements for the main hud 47 | #define HUD2_TIME (1 << 0) 48 | #define HUD2_SPEED (1 << 1) 49 | #define HUD2_JUMPS (1 << 2) 50 | #define HUD2_STRAFE (1 << 3) 51 | #define HUD2_SYNC (1 << 4) 52 | #define HUD2_STYLE (1 << 5) 53 | #define HUD2_RANK (1 << 6) 54 | #define HUD2_TRACK (1 << 7) 55 | #define HUD2_SPLITPB (1 << 8) 56 | #define HUD2_MAPTIER (1 << 9) 57 | #define HUD2_TIMEDIFFERENCE (1 << 10) 58 | #define HUD2_PERFS (1 << 11) 59 | #define HUD2_TOPLEFT_RANK (1 << 12) 60 | #define HUD2_VELOCITYDIFFERENCE (1 << 13) 61 | #define HUD2_USPSILENCER (1 << 14) // spawns usps with a silencer on 62 | #define HUD2_GLOCKBURST (1 << 15) // spawns glocks with burst 63 | #define HUD2_CENTERKEYS (1 << 16) // CSGO option to toggle whether !keys is shown as center-text or in that panel thing. 64 | 65 | #define HUD_DEFAULT (HUD_MASTER|HUD_CENTER|HUD_ZONEHUD|HUD_OBSERVE|HUD_TOPLEFT|HUD_SYNC|HUD_TIMELEFT|HUD_2DVEL|HUD_SPECTATORS) 66 | #define HUD_DEFAULT2 (HUD2_PERFS) 67 | 68 | stock bool HUD1Enabled(int hudbits, int flag) 69 | { 70 | return (hudbits & flag) != 0; 71 | } 72 | 73 | stock bool HUD2Enabled(int hudbits, int flag) 74 | { 75 | return (hudbits & flag) == 0; 76 | } 77 | 78 | enum ZoneHUD 79 | { 80 | ZoneHUD_None, 81 | ZoneHUD_Start, 82 | ZoneHUD_End 83 | }; 84 | 85 | enum struct huddata_t 86 | { 87 | int iTarget; 88 | float fTime; 89 | int iSpeed; 90 | int iStyle; 91 | int iTrack; 92 | int iJumps; 93 | int iStrafes; 94 | int iRank; 95 | float fSync; 96 | float fPB; 97 | float fWR; 98 | bool bReplay; 99 | bool bPractice; 100 | TimerStatus iTimerStatus; 101 | ZoneHUD iZoneHUD; 102 | 103 | int iHUDSettings; 104 | int iHUD2Settings; 105 | 106 | int iPreviousSpeed; 107 | float fClosestReplayTime; 108 | float fClosestVelocityDifference; 109 | int iMapTier; 110 | float fClosestReplayLength; 111 | 112 | int iButtons; 113 | int iScrolls; 114 | int iScrollsPrev; 115 | float fAngleDiff; 116 | } 117 | 118 | /** 119 | * Called when top left HUD updates. 120 | * 121 | * @param client Client index that recieves the hud. 122 | * @param target Target entity that is either the client or what the client is spectating. 123 | * @param topleft Reference to the HUD buffer. 124 | * @param topleftlength Max length of the topleft buffer. 125 | * @param track Target's track. 126 | * @param style Target's style. 127 | * 128 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Anything else to pass along new values. 129 | */ 130 | forward Action Shavit_OnTopLeftHUD(int client, int target, char[] topleft, int topleftlength, int track, int style); 131 | 132 | /** 133 | * Called before the top left HUD updates and used to build the string for shavit-hud. 134 | * 135 | * @param client Client index that recieves the hud. 136 | * @param target Target entity that is either the client or what the client is spectating. 137 | * @param topleft Reference to the HUD buffer. 138 | * @param topleftlength Max length of the topleft buffer. 139 | * @param track Target's track. 140 | * @param style Target's style. 141 | * @param forceUpdate Force even if the client has disabled HUD_TOPLEFT. 142 | * 143 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Plugin_Changed to use own topleft string instead of shavit-hud building it. 144 | */ 145 | forward Action Shavit_PreOnTopLeftHUD(int client, int target, char[] topleft, int topleftlength, int track, int style, bool &forceUpdate); 146 | 147 | /** 148 | * Called when key hint (bottom left) HUD updates (Source 2013 only). 149 | * 150 | * @param client Client index that recieves the hud. 151 | * @param target Target entity that is either the client or what the client is spectating. 152 | * @param keyhint Reference to the HUD buffer. 153 | * @param keyhintlength Max length of the keyhint buffer. 154 | * @param track Target's track. 155 | * @param style Target's style. 156 | * 157 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Anything else to pass along new values. 158 | */ 159 | forward Action Shavit_OnKeyHintHUD(int client, int target, char[] keyhint, int keyhintlength, int track, int style); 160 | 161 | /** 162 | * Called before the key hint HUD (bottom left) updates and used to build the string for shavit-hud (Source 2013 only). 163 | * 164 | * @param client Client index that recieves the hud. 165 | * @param target Target entity that is either the client or what the client is spectating. 166 | * @param keyhint Reference to the HUD buffer. 167 | * @param keyhintlength Max length of the keyhint buffer. 168 | * @param track Target's track. 169 | * @param style Target's style. 170 | * @param forceUpdate Force even if the client has disabled HUD_SYNC, HUD_TIMELEFT, and HUD2_PERFS. 171 | * 172 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Plugin_Changed to use own keyhint string instead of shavit-hud building it. 173 | */ 174 | forward Action Shavit_PreOnKeyHintHUD(int client, int target, char[] keyhint, int keyhintlength, int track, int style, bool &forceUpdate); 175 | 176 | /** 177 | * Called before the center hud updates. 178 | * 179 | * @param client Client index that recieves the hud. 180 | * @param target Target entity that is either the client or what the client is spectating. 181 | * @param buffer Reference to the HUD buffer. 182 | * @param buflen Max length of the buffer. 183 | * @param data huddata_t which contains target info. 184 | * 185 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Plugin_Changed if you modify the buffer string. 186 | */ 187 | forward Action Shavit_PreOnDrawCenterHUD(int client, int target, char[] buffer, int buflen, huddata_t data); 188 | 189 | /** 190 | * Called before the !keys hud updates. 191 | * 192 | * @param client Client index that recieves the hud. 193 | * @param target Target entity that is either the client or what the client is spectating. 194 | * @param style The target's style. 195 | * @param buttons The target's buttons. 196 | * @param anglediff The difference from the target's last angles and current angles. 197 | * @param buffer Reference to the HUD buffer. 198 | * @param buflen Max length of the buffer. 199 | * @param scrolls How many scrolls the player has so far (relevant for non-auto styles). 200 | * @param prevscrolls How many scrolls previously. 201 | * @param alternate_center_keys True when you should draw a Linux-specific format since fonts & alignment are different. 202 | * 203 | * @return Plugin_Handled or Plugin_Stop to block the HUD message from appearing. Plugin_Changed if you modify the buffer string. 204 | */ 205 | forward Action Shavit_PreOnDrawKeysHUD(int client, int target, int style, int buttons, float anglediff, char[] buffer, int buflen, int scrolls, int prevscrolls, bool alternate_center_keys); 206 | 207 | /** 208 | * Force an HUD update for a player. Requires shavit-hud. 209 | * 210 | * @param client Client index. 211 | * @param spectators Should also update it for the player's spectators? 212 | * @error Error code 200 if client isn't valid. 213 | * @return Amount of players that had their HUD updated (client + spectators) or -1 on error. 214 | */ 215 | native int Shavit_ForceHUDUpdate(int client, bool spectators); 216 | 217 | /** 218 | * Gets the HUD settings of a player. 219 | * See the HUD_* defines for information. 220 | * 221 | * @param client Client index. 222 | * @return HUD settings. 223 | */ 224 | native int Shavit_GetHUDSettings(int client); 225 | 226 | /** 227 | * Gets the HUD2 settings of a player. 228 | * See the HUD2_* defines for information. 229 | * 230 | * @param client Client index. 231 | * @return HUD settings. 232 | */ 233 | native int Shavit_GetHUD2Settings(int client); 234 | 235 | public SharedPlugin __pl_shavit_hud = 236 | { 237 | name = "shavit-hud", 238 | file = "shavit-hud.smx", 239 | #if defined REQUIRE_PLUGIN 240 | required = 1 241 | #else 242 | required = 0 243 | #endif 244 | }; 245 | 246 | #if !defined REQUIRE_PLUGIN 247 | public void __pl_shavit_hud_SetNTVOptional() 248 | { 249 | MarkNativeAsOptional("Shavit_ForceHUDUpdate"); 250 | MarkNativeAsOptional("Shavit_GetHUDSettings"); 251 | MarkNativeAsOptional("Shavit_GetHUD2Settings"); 252 | } 253 | #endif 254 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/mapchooser.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - mapchooser.inc file 3 | * by: SlidyBat, KiD Fearless, mbhound, rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_mapchooser_included 23 | #endinput 24 | #endif 25 | #define _shavit_mapchooser_included 26 | 27 | /** 28 | * Called when a player RTV's. 29 | * Requires shavit-mapchooser. 30 | * 31 | * @param client Client index. 32 | * @noreturn 33 | */ 34 | forward void SMC_OnRTV(int client); 35 | 36 | /** 37 | * Called when a player UNRTV's. 38 | * Requires shavit-mapchooser. 39 | * 40 | * @param client Client index. 41 | * @noreturn 42 | */ 43 | forward void SMC_OnUnRTV(int client); 44 | 45 | /** 46 | * Called when the map changes from an RTV. 47 | * Requires shavit-mapchooser. 48 | * 49 | * @noreturn 50 | */ 51 | forward void SMC_OnSuccesfulRTV(); 52 | 53 | /** 54 | * Returns the ArrayList of maps currently on rotation. 55 | * 56 | * @return The ArrayList of Maps. Don't delete this handle. 57 | */ 58 | native ArrayList Shavit_GetMapsArrayList(); 59 | 60 | /** 61 | * Returns the StringMap of maps currently on rotation. 62 | * 63 | * @return the StringMap of maps. Don't delete this handle. 64 | */ 65 | native StringMap Shavit_GetMapsStringMap(); 66 | 67 | public SharedPlugin __pl_shavit_mapchooser = 68 | { 69 | name = "shavit-mapchooser", 70 | file = "shavit-mapchooser.smx", 71 | #if defined REQUIRE_PLUGIN 72 | required = 1 73 | #else 74 | required = 0 75 | #endif 76 | }; 77 | 78 | #if !defined REQUIRE_PLUGIN 79 | public void __pl_shavit_mapchooser_SetNTVOptional() 80 | { 81 | MarkNativeAsOptional("Shavit_GetMapsArrayList"); 82 | MarkNativeAsOptional("Shavit_GetMapsStringMap"); 83 | } 84 | #endif 85 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/maps-folder-stocks.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - maps-folder-stocks.inc file 3 | * by: rtldg, kidfearless 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_mapsfolderstocks_included 23 | #endinput 24 | #endif 25 | #define _shavit_mapsfolderstocks_included 26 | 27 | stock bool WriteNavMesh(const char[] map, bool skipExistsCheck = false) 28 | { 29 | char sTempMap[PLATFORM_MAX_PATH]; 30 | FormatEx(sTempMap, PLATFORM_MAX_PATH, "maps/%s.nav", map); 31 | 32 | if (skipExistsCheck || !FileExists(sTempMap)) 33 | { 34 | File file = OpenFile(sTempMap, "wb"); 35 | 36 | if (file != null) 37 | { 38 | int zero[1]; 39 | static int defaultNavMesh[51] = { 40 | -17958194, 16, 1, 128600, 16777217, 1, 1, 0, -1007845376, 1112014848, 1107304447, -1035468800, 41 | 1139638272, 1107304447, 1107304447, 1107304447, 0, 0, 0, 0, 4, -415236096, 2046820547, 2096962, 42 | 65858, 0, 49786, 536822394, 33636864, 0, 12745216, -12327104, 21102623, 3, -1008254976, 1139228672, 43 | 1107304447, 1, 0, 0, 0, 4386816, 4386816, 4161536, 4161536, 4161536, 20938752, 16777216, 33554432, 0, 0 44 | }; 45 | 46 | file.Write(defaultNavMesh, sizeof(defaultNavMesh), 4); 47 | file.Write(zero, 1, 1); 48 | delete file; 49 | } 50 | 51 | return true; 52 | } 53 | 54 | return false; 55 | } 56 | 57 | stock bool WriteNavMeshBz2(const char[] map, bool skipExistsCheck = false) 58 | { 59 | char sTempMap[PLATFORM_MAX_PATH]; 60 | FormatEx(sTempMap, PLATFORM_MAX_PATH, "maps/%s.nav.bz2", map); 61 | 62 | if (skipExistsCheck || !FileExists(sTempMap)) 63 | { 64 | File file = OpenFile(sTempMap, "wb"); 65 | 66 | if (file != null) 67 | { 68 | static int defaultNavMeshBz2[132/4] = { 69 | 0x39685A42, 0x26594131, 0xB8955953, 0x0000B354, 70 | 0xFEC56E4E, 0x80004004, 0x0040D800, 0x40100040, 71 | 0x00011800, 0xA0114182, 0xA7127200, 0x915133AA, 72 | 0x04B501A0, 0x64A03285, 0x31190D0D, 0x96F2A658, 73 | 0x864651CE, 0xA93468D3, 0xD269C634, 0x66EE82B6, 74 | 0x3B1D4103, 0xD4BE309C, 0x58DF5463, 0xC0076E1B, 75 | 0x346C6DC1, 0x8B9FD47B, 0x0385015D, 0x3B260D99, 76 | 0xF43C28F0, 0xD071CFB3, 0xC95DFC92, 0x4242E114, 77 | 0xCC52E156 78 | }; 79 | 80 | file.Write(defaultNavMeshBz2, sizeof(defaultNavMeshBz2), 4); 81 | delete file; 82 | } 83 | 84 | return true; 85 | } 86 | 87 | return false; 88 | } 89 | 90 | stock void CreateAllNavFiles() 91 | { 92 | StringMap mapList = new StringMap(); 93 | DirectoryListing dir = OpenDirectory("maps", true); 94 | 95 | if (dir == null) 96 | { 97 | return; 98 | } 99 | 100 | char fileName[PLATFORM_MAX_PATH]; 101 | FileType type; 102 | 103 | // Loop through maps folder. 104 | // If .bsp, mark as need .nav 105 | // If .nav, mark as have .nav 106 | while (dir.GetNext(fileName, sizeof(fileName), type)) 107 | { 108 | if (type != FileType_File) 109 | { 110 | continue; 111 | } 112 | 113 | int length = strlen(fileName); 114 | 115 | if (length < 5 || fileName[length-4] != '.') // a.bsp 116 | { 117 | continue; 118 | } 119 | 120 | if (fileName[length-3] == 'b' && fileName[length-2] == 's' && fileName[length-1] == 'p') 121 | { 122 | fileName[length-4] = 0; 123 | mapList.SetValue(fileName, false, false); // note: false for 'replace' 124 | } 125 | else if (fileName[length-3] == 'n' && fileName[length-2] == 'a' && fileName[length-1] == 'v') 126 | { 127 | fileName[length-4] = 0; 128 | mapList.SetValue(fileName, true, true); // note: true for 'replace' 129 | } 130 | } 131 | 132 | delete dir; 133 | 134 | // StringMap shenanigans are used so we don't call FileExists() 2000 times 135 | StringMapSnapshot snapshot = mapList.Snapshot(); 136 | 137 | for (int i = 0; i < snapshot.Length; i++) 138 | { 139 | snapshot.GetKey(i, fileName, sizeof(fileName)); 140 | 141 | bool hasNAV = false; 142 | mapList.GetValue(fileName, hasNAV); 143 | 144 | if (!hasNAV) 145 | { 146 | WriteNavMesh(fileName, true); 147 | } 148 | } 149 | 150 | delete snapshot; 151 | delete mapList; 152 | } 153 | 154 | stock bool ReadMapsFolderHandler(const char path[PLATFORM_MAX_PATH], bool is_stringmap, Handle data, bool lowercase, bool display, bool iter_subfolders, bool use_valve_fs, char[][] exclude_prefixes, int exclude_count) 155 | { 156 | bool first_iteration = StrEqual(path, "maps"); 157 | DirectoryListing dir = OpenDirectory(path, use_valve_fs, NULL_STRING); 158 | 159 | if (dir == null) 160 | { 161 | return false; 162 | } 163 | 164 | char buffer[PLATFORM_MAX_PATH]; 165 | FileType type; 166 | 167 | while (dir.GetNext(buffer, sizeof(buffer), type)) 168 | { 169 | if (type == FileType_Directory) 170 | { 171 | if (buffer[0] == '.' && (buffer[1] == 0 || (buffer[1] == '.' && buffer[2] == 0))) 172 | { 173 | continue; 174 | } 175 | 176 | if (iter_subfolders) 177 | { 178 | char subfolder[PLATFORM_MAX_PATH]; 179 | FormatEx(subfolder, sizeof(subfolder), "%s/%s", path, buffer); 180 | ReadMapsFolderHandler(subfolder, is_stringmap, data, lowercase, display, iter_subfolders, use_valve_fs, exclude_prefixes, exclude_count); 181 | } 182 | } 183 | else if (type == FileType_File) 184 | { 185 | int length = strlen(buffer); 186 | 187 | if (length < 5 || buffer[length-4] != '.') // a.bsp 188 | { 189 | continue; 190 | } 191 | 192 | if ((buffer[length-3] == 'b' && buffer[length-2] == 's' && buffer[length-1] == 'p') || 193 | (buffer[length-3] == 'u' && buffer[length-2] == 'g' && buffer[length-1] == 'c')) 194 | { 195 | buffer[length-4] = 0; 196 | 197 | if (lowercase) 198 | { 199 | LowercaseString(buffer); 200 | } 201 | 202 | bool skip = false; 203 | 204 | for (int i = 0; i < exclude_count; i++) 205 | { 206 | if (strncmp(buffer, exclude_prefixes[i], strlen(exclude_prefixes[i]), lowercase) == 0) 207 | { 208 | skip = true; 209 | break; 210 | } 211 | } 212 | 213 | if (skip) 214 | { 215 | continue; 216 | } 217 | 218 | if (!display && !first_iteration) 219 | { 220 | char temp[PLATFORM_MAX_PATH]; 221 | int skip_this = 5; // strlen("maps/") 222 | FormatEx(temp, sizeof(temp), "%s/%s", path[skip_this], buffer); 223 | buffer = temp; 224 | } 225 | 226 | if (is_stringmap) 227 | { 228 | view_as(data).SetValue(buffer, false, false); 229 | } 230 | else 231 | { 232 | view_as(data).PushString(buffer); 233 | } 234 | } 235 | } 236 | } 237 | 238 | delete dir; 239 | return true; 240 | } 241 | 242 | static char empty_excludes[][] = {""}; 243 | 244 | stock bool ReadMapsFolderStringMap(StringMap data, bool lowercase=true, bool display=false, bool iter_subfolders=true, bool use_valve_fs=true, char[][] exclude_prefixes=empty_excludes, int exclude_count=0) 245 | { 246 | return ReadMapsFolderHandler("maps", true, data, lowercase, display, iter_subfolders, use_valve_fs, exclude_prefixes, exclude_count); 247 | } 248 | 249 | // don't forget to declare your ArrayList like below :))) 250 | //// ArrayList maps = new ArrayList(ByteCountToCells(PLATFORM_MAX_PATH)); 251 | stock bool ReadMapsFolderArrayList(ArrayList data, bool lowercase=true, bool display=false, bool iter_subfolders=true, bool use_valve_fs=true, char[][] exclude_prefixes=empty_excludes, int exclude_count=0) 252 | { 253 | return ReadMapsFolderHandler("maps", false, data, lowercase, display, iter_subfolders, use_valve_fs, exclude_prefixes, exclude_count); 254 | } 255 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/misc.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - misc.inc file 3 | * by: EvanIMK, rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_misc_included 23 | #endinput 24 | #endif 25 | #define _shavit_misc_included 26 | 27 | /** 28 | * Checks if a player is hiding players 29 | * 30 | * @param client Client index. 31 | * @return Boolean value. 32 | */ 33 | native bool Shavit_IsClientUsingHide(int client); 34 | 35 | /** 36 | * Called before clan tag variables are processed. 37 | * 38 | * @param client Client index. 39 | * @param clantag Reference to the clan tag buffer. 40 | * @param clantaglength Max length of the customtag buffer. 41 | * @return Plugin_Handled or Plugin_Stop to block the clan tag from changing. Anything else to pass along new values. 42 | */ 43 | forward Action Shavit_OnClanTagChangePre(int client, char[] clantag, int clantaglength); 44 | 45 | /** 46 | * Called after clan tags are changed. 47 | * 48 | * @param client Client index. 49 | * @param customtag Reference to the custom clan tag buffer. 50 | * @param customtaglength Max length of the customtag buffer. 51 | * @noreturn 52 | */ 53 | forward void Shavit_OnClanTagChangePost(int client, char[] customtag, int customtaglength); 54 | 55 | public SharedPlugin __pl_shavit_misc = 56 | { 57 | name = "shavit-misc", 58 | file = "shavit-misc.smx", 59 | #if defined REQUIRE_PLUGIN 60 | required = 1 61 | #else 62 | required = 0 63 | #endif 64 | }; 65 | 66 | #if !defined REQUIRE_PLUGIN 67 | public void __pl_shavit_misc_SetNTVOptional() 68 | { 69 | MarkNativeAsOptional("Shavit_IsClientUsingHide"); 70 | } 71 | #endif 72 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/physicsuntouch.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * physicsuntouch.inc 3 | * by: rumour 4 | * 5 | * Originally from EndTouch Fix (https://github.com/rumourA/End-Touch-Fix) 6 | * but edited to be part of shavit's Timer (https://github.com/shavitush/bhoptimer) 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _physicuntouch_included 23 | #endinput 24 | #endif 25 | #define _physicuntouch_included 26 | 27 | 28 | #define EFL_CHECK_UNTOUCH (1<<24) 29 | 30 | Handle gH_PhysicsCheckForEntityUntouch; 31 | 32 | stock void LoadPhysicsUntouch(Handle gamedata) 33 | { 34 | StartPrepSDKCall(SDKCall_Entity); 35 | 36 | if (!PrepSDKCall_SetFromConf(gamedata, SDKConf_Signature, "PhysicsCheckForEntityUntouch")) 37 | { 38 | SetFailState("Failed to get PhysicsCheckForEntityUntouch"); 39 | } 40 | 41 | gH_PhysicsCheckForEntityUntouch = EndPrepSDKCall(); 42 | } 43 | 44 | stock bool GetCheckUntouch(int client) 45 | { 46 | int flags = GetEntProp(client, Prop_Data, "m_iEFlags"); 47 | return (flags & EFL_CHECK_UNTOUCH) != 0; 48 | } 49 | 50 | stock void MaybeDoPhysicsUntouch(int client) 51 | { 52 | if (GetCheckUntouch(client)) 53 | { 54 | SDKCall(gH_PhysicsCheckForEntityUntouch, client); 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/rankings.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - rankings.inc file 3 | * by: shavit 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_rankings_included 23 | #endinput 24 | #endif 25 | #define _shavit_rankings_included 26 | 27 | /** 28 | * Gets called when a map's tier is assigned. 29 | * Only called once per map, if the rankings plugin is enabled. 30 | * The exception is if the admin changes the current map's tier. 31 | * 32 | * @param map Map display name. 33 | * @param tier Map's tier. 34 | * @noreturn 35 | */ 36 | forward void Shavit_OnTierAssigned(const char[] map, int tier); 37 | 38 | /** 39 | * Gets called when the server acknowledges the client's ranking status. 40 | * It is called after OnClientPostAdminCheck and at forced rank recalculations. 41 | * 42 | * @param client Client index. 43 | * @param rank Client's rank. (0 if unranked or unassigned) 44 | * @param points Client's points. (0.0 if unranked or unassigned) 45 | * @param first True if the forward is called after the initial connection, false if it is caused by recalculation. 46 | * @noreturn 47 | */ 48 | forward void Shavit_OnRankAssigned(int client, int rank, float points, bool first); 49 | 50 | /** 51 | * Gets the map tier for a specified map. 52 | * Use the map's display name. 53 | * 54 | * @param map Map to get the tier of. Using "" will get the current map's tier. 55 | * @return Map tier. 0 if no results were found. 56 | */ 57 | native int Shavit_GetMapTier(const char[] map = ""); 58 | 59 | /** 60 | * Gets a StringMap that contains all the cached map tiers. 61 | * The returned StringMap must be deleted from memory after use! 62 | * 63 | * @return StringMap with {const char[]: map, int: tier} structure. 64 | */ 65 | native StringMap Shavit_GetMapTiers(); 66 | 67 | /** 68 | * Gets player points. 69 | * 70 | * @param client Client index. 71 | * @return Points. 0.0 if unranked. 72 | */ 73 | native float Shavit_GetPoints(int client); 74 | 75 | /** 76 | * Gets player rank. 77 | * 78 | * @param client Client index. 79 | * @return Rank. 0 if unranked. 80 | */ 81 | native int Shavit_GetRank(int client); 82 | 83 | /** 84 | * Gets the amount of players with over 0 points. 85 | * 86 | * @return Amount of ranked players. 87 | */ 88 | native int Shavit_GetRankedPlayers(); 89 | 90 | /** 91 | * Deletes tier setting for the specified map. 92 | * Points recalculation will run right after this is finished. 93 | * 94 | * @param map Map name. 95 | * @noreturn 96 | */ 97 | native void Shavit_Rankings_DeleteMap(const char[] map); 98 | 99 | /** 100 | * Retrieves the amount of #1 records a player has. 101 | * Requires shavit-rankings. 102 | * 103 | * @param client Client index. 104 | * @param track Track to retrieve WRs from. -1 to use all tracks. All bonus tracks are combined. 105 | * @param style Style to retrieve WRs from. -1 to use all styles. 106 | * @param usecvars Whether to depend on the value of `shavit_stats_mvprankones` and `shavit_stats_mvprankones_maintrack`. 107 | * @return The number of WRs. 108 | */ 109 | native int Shavit_GetWRCount(int client, int track = -1, int style = -1, bool usecvars = true); 110 | 111 | /** 112 | * Retrieves the number of players who hold #1 records. 113 | * Requires shavit-rankings. 114 | * 115 | * @param track Track to retrieve WRs from. -1 to use all tracks. All bonus tracks are combined. 116 | * @param style Style to retrieve WRs from. -1 to use all styles. 117 | * @param usecvars Whether to depend on the value of `shavit_stats_mvprankones` and `shavit_stats_mvprankones_maintrack`. 118 | * @return The number of WR holders. 0 if none. 119 | */ 120 | native int Shavit_GetWRHolders(int track = -1, int style = -1, bool usecvars = true); 121 | 122 | /** 123 | * Retrieves the player's rank based on how many #1 records they hold. 124 | * Requires shavit-rankings. 125 | * Only works with MySQL 8.0+ or with MariaDB 10.2+. 126 | * 127 | * @param client Client index. 128 | * @param track Track to retrieve WRs from. -1 to use all tracks. All bonus tracks are combined. 129 | * @param style Style to retrieve WRs from. -1 to use all styles. 130 | * @param usecvars Whether to depend on the value of `shavit_stats_mvprankones` and `shavit_stats_mvprankones_maintrack`. 131 | * @return The rank. 0 if none, or not supported. 132 | */ 133 | native int Shavit_GetWRHolderRank(int client, int track = -1, int style = -1, bool usecvars = true); 134 | 135 | /* 136 | * Calculates how many points a time will give. 137 | * Used to minimize number of SQL queries. 138 | * Requires shavit-rankings. 139 | * 140 | * @param track The track the time is from. 141 | * @param style The style the time is from. 142 | * @param tier The map tier. -1 to use the current map's tier. 143 | * @param time The time you want to calculate the points for. 144 | * @param wr WR. 145 | * 146 | * @return The number of points the time would give. 147 | */ 148 | native float Shavit_GuessPointsForTime(int track, int style, int tier, float time, float wr); 149 | 150 | public SharedPlugin __pl_shavit_rankings = 151 | { 152 | name = "shavit-rankings", 153 | file = "shavit-rankings.smx", 154 | #if defined REQUIRE_PLUGIN 155 | required = 1 156 | #else 157 | required = 0 158 | #endif 159 | }; 160 | 161 | #if !defined REQUIRE_PLUGIN 162 | public void __pl_shavit_rankings_SetNTVOptional() 163 | { 164 | MarkNativeAsOptional("Shavit_GetMapTier"); 165 | MarkNativeAsOptional("Shavit_GetMapTiers"); 166 | MarkNativeAsOptional("Shavit_GetPoints"); 167 | MarkNativeAsOptional("Shavit_GetRank"); 168 | MarkNativeAsOptional("Shavit_GetRankedPlayers"); 169 | MarkNativeAsOptional("Shavit_Rankings_DeleteMap"); 170 | MarkNativeAsOptional("Shavit_GetWRCount"); 171 | MarkNativeAsOptional("Shavit_GetWRHolders"); 172 | MarkNativeAsOptional("Shavit_GetWRHolderRank"); 173 | MarkNativeAsOptional("Shavit_GuessPointsForTime"); 174 | } 175 | #endif 176 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/replay-file.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - replay file stocks & format 3 | * by: shavit, rtldg, KiD Fearless, carnifex, Nairda, EvanIMK 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_replay_file_included 23 | #endinput 24 | #endif 25 | #define _shavit_replay_file_included 26 | 27 | // History of REPLAY_FORMAT_SUBVERSION: 28 | // 0x01: standard origin[3], angles[2], and buttons 29 | // 0x02: flags added movetype added 30 | // 0x03: integrity stuff: style, track, and map added to header. preframe count added (unimplemented until later though) 31 | // 0x04: steamid/accountid written as a 32-bit int instead of a string 32 | // 0x05: postframes & fTickrate added 33 | // 0x06: mousexy and vel added 34 | // 0x07: fixed iFrameCount because postframes were included in the value when they shouldn't be 35 | // 0x08: added zone-offsets to header 36 | // 0x09: bumped with no actual file changes because time calculation in regards to offsets have been changed/fixed since it seems to have been using the end-zone-offset incorrectly (and should now be fine hopefully since 2021-12-21 / a146b51fb16febf1847657fba7ef9e0c056d7476) 37 | 38 | #define REPLAY_FORMAT_V2 "{SHAVITREPLAYFORMAT}{V2}" 39 | #define REPLAY_FORMAT_FINAL "{SHAVITREPLAYFORMAT}{FINAL}" 40 | #define REPLAY_FORMAT_SUBVERSION 0x09 41 | 42 | #define REPLAY_FRAMES_PER_WRITE 100 // amounts of frames to write per read/write call 43 | 44 | enum struct replay_header_t 45 | { 46 | char sReplayFormat[40]; 47 | int iReplayVersion; 48 | char sMap[PLATFORM_MAX_PATH]; 49 | int iStyle; 50 | int iTrack; 51 | int iPreFrames; 52 | int iFrameCount; 53 | float fTime; 54 | int iSteamID; 55 | int iPostFrames; 56 | float fTickrate; 57 | float fZoneOffset[2]; 58 | } 59 | 60 | enum struct frame_t 61 | { 62 | float pos[3]; 63 | float ang[2]; 64 | int buttons; 65 | // iReplayVersion >= 0x02 66 | int flags; 67 | MoveType mt; 68 | // Everything below is generally NOT loaded into memory for playback 69 | // iReplayVersion >= 0x06 70 | int mousexy; // `mousex | (mousey << 16)` // unpack with UnpackSignedShorts 71 | int vel; // basically `forwardmove | (sidemove << 16)` // unpack with UnpackSignedShorts 72 | } 73 | 74 | enum struct frame_cache_t 75 | { 76 | int iFrameCount; 77 | float fTime; 78 | bool bNewFormat; 79 | int iReplayVersion; 80 | char sReplayName[MAX_NAME_LENGTH]; 81 | int iPreFrames; 82 | ArrayList aFrames; 83 | // iReplayVersion >= 0x05 84 | int iPostFrames; 85 | float fTickrate; 86 | // blah blah not affected by iReplayVersion 87 | int iSteamID; 88 | } 89 | 90 | // Can be used to unpack frame_t.mousexy and frame_t.vel 91 | stock void UnpackSignedShorts(int x, int[] out) 92 | { 93 | out[0] = ((x & 0xFFFF) ^ 0x8000) - 0x8000; 94 | out[1] = (((x >> 16) & 0xFFFF) ^ 0x8000) - 0x8000; 95 | } 96 | 97 | stock bool LoadReplayCache(frame_cache_t cache, int style, int track, const char[] path, const char[] mapname) 98 | { 99 | bool success = false; 100 | replay_header_t header; 101 | File fFile = ReadReplayHeader(path, header, style, track); 102 | 103 | if (fFile != null) 104 | { 105 | if (header.iReplayVersion > REPLAY_FORMAT_SUBVERSION) 106 | { 107 | // not going to try and read it 108 | } 109 | else if (header.iReplayVersion < 0x03 || (StrEqual(header.sMap, mapname, false) && header.iStyle == style && header.iTrack == track)) 110 | { 111 | success = ReadReplayFrames(fFile, header, cache); 112 | } 113 | 114 | delete fFile; 115 | } 116 | 117 | return success; 118 | } 119 | 120 | stock bool ReadReplayFrames(File file, replay_header_t header, frame_cache_t cache) 121 | { 122 | int total_cells = 6; 123 | int used_cells = 6; 124 | bool is_btimes = false; 125 | 126 | if (header.iReplayVersion > 0x01) 127 | { 128 | total_cells = 8; 129 | used_cells = 8; 130 | } 131 | 132 | // We have differing total_cells & used_cells because we want to save memory during playback since the latest two cells added (vel & mousexy) aren't needed and are only useful for replay file anticheat usage stuff.... 133 | if (header.iReplayVersion >= 0x06) 134 | { 135 | total_cells = 10; 136 | used_cells = 8; 137 | } 138 | 139 | any aReplayData[sizeof(frame_t)]; 140 | 141 | delete cache.aFrames; 142 | int iTotalSize = header.iFrameCount + header.iPreFrames + header.iPostFrames; 143 | cache.aFrames = new ArrayList(used_cells, iTotalSize); 144 | 145 | if (!header.sReplayFormat[0]) // old replay format. no header. 146 | { 147 | char sLine[320]; 148 | char sExplodedLine[6][64]; 149 | 150 | if(!file.Seek(0, SEEK_SET)) 151 | { 152 | return false; 153 | } 154 | 155 | while (!file.EndOfFile()) 156 | { 157 | file.ReadLine(sLine, 320); 158 | int iStrings = ExplodeString(sLine, "|", sExplodedLine, 6, 64); 159 | 160 | aReplayData[0] = StringToFloat(sExplodedLine[0]); 161 | aReplayData[1] = StringToFloat(sExplodedLine[1]); 162 | aReplayData[2] = StringToFloat(sExplodedLine[2]); 163 | aReplayData[3] = StringToFloat(sExplodedLine[3]); 164 | aReplayData[4] = StringToFloat(sExplodedLine[4]); 165 | aReplayData[5] = (iStrings == 6) ? StringToInt(sExplodedLine[5]) : 0; 166 | 167 | cache.aFrames.PushArray(aReplayData, 6); 168 | } 169 | 170 | cache.iFrameCount = cache.aFrames.Length; 171 | } 172 | else // assumes the file position will be at the start of the frames 173 | { 174 | is_btimes = StrEqual(header.sReplayFormat, "btimes"); 175 | 176 | for (int i = 0; i < iTotalSize; i++) 177 | { 178 | if(file.Read(aReplayData, total_cells, 4) >= 0) 179 | { 180 | cache.aFrames.SetArray(i, aReplayData, used_cells); 181 | 182 | if (is_btimes && (aReplayData[5] & IN_BULLRUSH)) 183 | { 184 | if (!header.iPreFrames) 185 | { 186 | header.iPreFrames = i; 187 | header.iFrameCount -= i; 188 | } 189 | else if (!header.iPostFrames) 190 | { 191 | header.iPostFrames = header.iFrameCount + header.iPreFrames - i; 192 | header.iFrameCount -= header.iPostFrames; 193 | } 194 | } 195 | } 196 | } 197 | } 198 | 199 | if (cache.aFrames.Length <= 10) // worthless replay so it doesn't get to load 200 | { 201 | delete cache.aFrames; 202 | return false; 203 | } 204 | 205 | cache.iFrameCount = header.iFrameCount; 206 | cache.fTime = header.fTime; 207 | cache.iReplayVersion = header.iReplayVersion; 208 | cache.bNewFormat = StrEqual(header.sReplayFormat, REPLAY_FORMAT_FINAL) || is_btimes; 209 | cache.sReplayName = "unknown"; 210 | cache.iPreFrames = header.iPreFrames; 211 | cache.iPostFrames = header.iPostFrames; 212 | cache.fTickrate = header.fTickrate; 213 | cache.iSteamID = header.iSteamID; 214 | 215 | if (cache.iSteamID != 0) 216 | { 217 | FormatEx(cache.sReplayName, sizeof(cache.sReplayName), "[U:1:%u]", cache.iSteamID); 218 | } 219 | 220 | return true; 221 | } 222 | 223 | stock File ReadReplayHeader(const char[] path, replay_header_t header, int style = 0, int track = 0) 224 | { 225 | replay_header_t empty_header; 226 | header = empty_header; 227 | 228 | File file = OpenFile(path, "rb"); 229 | 230 | if (file == null) 231 | { 232 | return null; 233 | } 234 | 235 | char sHeader[64]; 236 | 237 | if(!file.ReadLine(sHeader, 64)) 238 | { 239 | delete file; 240 | return null; 241 | } 242 | 243 | TrimString(sHeader); 244 | char sExplodedHeader[2][64]; 245 | ExplodeString(sHeader, ":", sExplodedHeader, 2, 64); 246 | 247 | strcopy(header.sReplayFormat, sizeof(header.sReplayFormat), sExplodedHeader[1]); 248 | 249 | if(StrEqual(header.sReplayFormat, REPLAY_FORMAT_FINAL)) // hopefully, the last of them 250 | { 251 | int version = StringToInt(sExplodedHeader[0]); 252 | 253 | header.iReplayVersion = version; 254 | 255 | // replay file integrity and PreFrames 256 | if(version >= 0x03) 257 | { 258 | file.ReadString(header.sMap, PLATFORM_MAX_PATH); 259 | file.ReadUint8(header.iStyle); 260 | file.ReadUint8(header.iTrack); 261 | 262 | file.ReadInt32(header.iPreFrames); 263 | 264 | // In case the replay was from when there could still be negative preframes 265 | if(header.iPreFrames < 0) 266 | { 267 | header.iPreFrames = 0; 268 | } 269 | } 270 | 271 | file.ReadInt32(header.iFrameCount); 272 | file.ReadInt32(view_as(header.fTime)); 273 | 274 | if (header.iReplayVersion < 0x07) 275 | { 276 | header.iFrameCount -= header.iPreFrames; 277 | } 278 | 279 | if(version >= 0x04) 280 | { 281 | file.ReadInt32(header.iSteamID); 282 | } 283 | else 284 | { 285 | char sAuthID[32]; 286 | file.ReadString(sAuthID, 32); 287 | ReplaceString(sAuthID, 32, "[U:1:", ""); 288 | ReplaceString(sAuthID, 32, "]", ""); 289 | header.iSteamID = StringToInt(sAuthID); 290 | } 291 | 292 | if (version >= 0x05) 293 | { 294 | file.ReadInt32(header.iPostFrames); 295 | file.ReadInt32(view_as(header.fTickrate)); 296 | 297 | if (header.iReplayVersion < 0x07) 298 | { 299 | header.iFrameCount -= header.iPostFrames; 300 | } 301 | } 302 | 303 | if (version >= 0x08) 304 | { 305 | file.ReadInt32(view_as(header.fZoneOffset[0])); 306 | file.ReadInt32(view_as(header.fZoneOffset[1])); 307 | } 308 | } 309 | else if(StrEqual(header.sReplayFormat, REPLAY_FORMAT_V2)) 310 | { 311 | header.iFrameCount = StringToInt(sExplodedHeader[0]); 312 | } 313 | else // old, outdated and slow - only used for ancient replays 314 | { 315 | // check for btimes replays 316 | file.Seek(0, SEEK_SET); 317 | any stuff[2]; 318 | file.Read(stuff, 2, 4); 319 | 320 | int btimes_player_id = stuff[0]; 321 | float run_time = stuff[1]; 322 | 323 | if (btimes_player_id >= 0 && run_time > 0.0 && run_time < (10.0 * 60.0 * 60.0)) 324 | { 325 | header.sReplayFormat = "btimes"; 326 | header.fTime = run_time; 327 | 328 | file.Seek(0, SEEK_END); 329 | header.iFrameCount = (file.Position / 4 - 2) / 6; 330 | file.Seek(2*4, SEEK_SET); 331 | } 332 | } 333 | 334 | if (header.iReplayVersion < 0x03) 335 | { 336 | header.iStyle = style; 337 | header.iTrack = track; 338 | } 339 | 340 | if (header.iReplayVersion < 0x05) 341 | { 342 | header.fTickrate = (1.0 / GetTickInterval()); // just assume it's our own tickrate... 343 | } 344 | 345 | return file; 346 | } 347 | 348 | stock void WriteReplayHeader(File fFile, int style, int track, float time, int steamid, int preframes, int postframes, float fZoneOffset[2], int iSize, float tickrate, const char[] sMap) 349 | { 350 | fFile.WriteLine("%d:" ... REPLAY_FORMAT_FINAL, REPLAY_FORMAT_SUBVERSION); 351 | 352 | fFile.WriteString(sMap, true); 353 | fFile.WriteInt8(style); 354 | fFile.WriteInt8(track); 355 | fFile.WriteInt32(preframes); 356 | 357 | fFile.WriteInt32(iSize - preframes - postframes); 358 | fFile.WriteInt32(view_as(time)); 359 | fFile.WriteInt32(steamid); 360 | 361 | fFile.WriteInt32(postframes); 362 | fFile.WriteInt32(view_as(tickrate)); 363 | 364 | fFile.WriteInt32(view_as(fZoneOffset[0])); 365 | fFile.WriteInt32(view_as(fZoneOffset[1])); 366 | } 367 | 368 | // file_a is usually used as the wr replay file. 369 | // file_b is usually used as the duplicate/backup replay file. 370 | stock void WriteReplayFrames(ArrayList playerrecording, int iSize, File file_a, File file_b) 371 | { 372 | any aFrameData[sizeof(frame_t)]; 373 | any aWriteData[sizeof(frame_t) * REPLAY_FRAMES_PER_WRITE]; 374 | int iFramesWritten = 0; 375 | 376 | for(int i = 0; i < iSize; i++) 377 | { 378 | playerrecording.GetArray(i, aFrameData, sizeof(frame_t)); 379 | 380 | for(int j = 0; j < sizeof(frame_t); j++) 381 | { 382 | aWriteData[(sizeof(frame_t) * iFramesWritten) + j] = aFrameData[j]; 383 | } 384 | 385 | if(++iFramesWritten == REPLAY_FRAMES_PER_WRITE || i == iSize - 1) 386 | { 387 | if (file_a) 388 | { 389 | file_a.Write(aWriteData, sizeof(frame_t) * iFramesWritten, 4); 390 | } 391 | 392 | if (file_b) 393 | { 394 | file_b.Write(aWriteData, sizeof(frame_t) * iFramesWritten, 4); 395 | } 396 | 397 | iFramesWritten = 0; 398 | } 399 | } 400 | } 401 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/replay-recorder.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - replay-recorder.inc file 3 | * by: shavit, rtldg, 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_replay_recorder_included 23 | #endinput 24 | #endif 25 | #define _shavit_replay_recorder_included 26 | 27 | /** 28 | * Called when a player finishes a time. Allows you to save a replay even if the run is not a WR. 29 | * 30 | * @param client Client index. 31 | * @param style Style the record was done on. 32 | * @param time Record time. 33 | * @param jumps Jumps amount. 34 | * @param strafes Amount of strafes. 35 | * @param sync Sync percentage (0.0 to 100.0) or -1.0 when not measured. 36 | * @param track Timer track. 37 | * @param oldtime The player's best time on the map before this finish. 38 | * @param perfs Perfect jump percentage (0.0 to 100.0) or 100.0 when not measured. 39 | * @param avgvel Player's average velocity throughout the run. 40 | * @param maxvel Player's highest reached velocity. 41 | * @param timestamp System time of when player finished. 42 | * @param isbestreplay If the time is the new replay. 43 | * @param istoolong If the time is too long to save a replay if the time is a WR. Note: replays WON'T be full length if this is true. 44 | * 45 | * @return Return Plugin_Changed (or higher) to cause a copy of the replay to be saved. Return Plugin_Continue otherwise. 46 | */ 47 | forward Action Shavit_ShouldSaveReplayCopy(int client, int style, float time, int jumps, int strafes, float sync, int track, float oldtime, float perfs, float avgvel, float maxvel, int timestamp, bool isbestreplay, bool istoolong); 48 | 49 | /** 50 | * Called when either a WR replay or a copy of a replay has been saved. 51 | * 52 | * @param client Client index. 53 | * @param style Style the record was done on. 54 | * @param time Record time. 55 | * @param jumps Jumps amount. 56 | * @param strafes Amount of strafes. 57 | * @param sync Sync percentage (0.0 to 100.0) or -1.0 when not measured. 58 | * @param track Timer track. 59 | * @param oldtime The player's best time on the map before this finish. 60 | * @param perfs Perfect jump percentage (0.0 to 100.0) or 100.0 when not measured. 61 | * @param avgvel Player's average velocity throughout the run. 62 | * @param maxvel Player's highest reached velocity. 63 | * @param timestamp System time of when player finished. 64 | * @param isbestreplay If the time is the new replay. 65 | * @param istoolong If the time is too long to save a replay if the time is a WR. Note: replays WON'T be full length if this is true. 66 | * @param iscopy If the path points to a copy of the replay. 67 | * @param replaypath Path to the saved replay. 68 | * @param frames ArrayList of the player's frames in the replay. 69 | * @param preframes The number of preframes in the replay. 70 | * @param postframes The number of postframes in the replay. 71 | * @param name Player's name at the time of the replay. 72 | * 73 | * @noreturn 74 | */ 75 | forward void Shavit_OnReplaySaved(int client, int style, float time, int jumps, int strafes, float sync, int track, float oldtime, float perfs, float avgvel, float maxvel, int timestamp, bool isbestreplay, bool istoolong, bool iscopy, const char[] replaypath, ArrayList frames, int preframes, int postframes, const char[] name); 76 | 77 | /** 78 | * Retrieves a client's frame count. 79 | * 80 | * @param client Client Index. 81 | * 82 | * @return Current number of frames. 83 | */ 84 | native int Shavit_GetClientFrameCount(int client); 85 | 86 | /* 87 | * returns the number of preframes in the players current run. 88 | * 89 | * @param client Client index 90 | * 91 | * @return Preframe count 92 | */ 93 | native int Shavit_GetPlayerPreFrames(int client); 94 | 95 | /* 96 | * Sets player's preframe length. 97 | * 98 | * @param client Client index 99 | * @param PreFrame PreFrame length 100 | * @param TimerPreFrame Timer start frame length 101 | * 102 | * @noreturn 103 | */ 104 | native void Shavit_SetPlayerPreFrames(int client, int PreFrame); 105 | 106 | /** 107 | * Sets a player's replay recording frames from a provided ArrayList. 108 | * To be used by save states/TAS etc. 109 | * 110 | * @param client Client index. 111 | * @param data ArrayList with proper replay data. 112 | * @param cheapCloneHandle False means we duplicate the frames (ArrayList.Clone). True means we clone the handle to the frames (CloneHandle). 113 | * 114 | * @noreturn 115 | */ 116 | native void Shavit_SetReplayData(int client, ArrayList data, bool cheapCloneHandle=false); 117 | 118 | /** 119 | * Saves a player's replay recording frames (if exists) into an ArrayList. 120 | * To be used by save states/TAS etc. 121 | * 122 | * @param client Client index. 123 | * @param cheapCloneHandle False means we duplicate the frames (Arraylist.Clone). True means we clone the handle to the frames (CloneHandle). This is going to be used for peristent-data in shavit-misc so we don't allocate duplicate memory needlessly. 124 | * 125 | * @return ArrayList with proper replay data, or null if the player has no recorded data. Delete this handle when you're done with it. 126 | */ 127 | native ArrayList Shavit_GetReplayData(int client, bool cheapCloneHandle=false); 128 | 129 | /** 130 | * Hijack the replay data so that this view angle will be used for the next ticks. 131 | * Use case is to make segmented runs look smoother. 132 | * 133 | * @param client Client index. 134 | * @param pitch Vertical view angle. 135 | * @param yaw Horizontal view angle. 136 | * @param ticks The number of ticks to hijack angles for. -1 will calculate the number of ticks based on the client's latency. 137 | * @param keeponstart Whether to continue hijacking angles even after someone restarts. 138 | * 139 | * @noreturn 140 | */ 141 | native void Shavit_HijackAngles(int client, float pitch, float yaw, int ticks = -1, bool keeponstart = false); 142 | 143 | public SharedPlugin __pl_shavit_replay_recorder = 144 | { 145 | name = "shavit-replay-recorder", 146 | file = "shavit-replay-recorder.smx", 147 | #if defined REQUIRE_PLUGIN 148 | required = 1 149 | #else 150 | required = 0 151 | #endif 152 | }; 153 | 154 | #if !defined REQUIRE_PLUGIN 155 | public void __pl_shavit_replay_recorder_SetNTVOptional() 156 | { 157 | MarkNativeAsOptional("Shavit_GetClientFrameCount"); 158 | MarkNativeAsOptional("Shavit_GetPlayerPreFrames"); 159 | MarkNativeAsOptional("Shavit_SetPlayerPreFrames"); 160 | MarkNativeAsOptional("Shavit_GetReplayData"); 161 | MarkNativeAsOptional("Shavit_HijackAngles"); 162 | MarkNativeAsOptional("Shavit_SetReplayData"); 163 | } 164 | #endif 165 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/replay-stocks.sp: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - stocks used by the replay plugins 3 | * by: shavit 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | stock bool Shavit_ReplayEnabledStyle(int style) 23 | { 24 | return !Shavit_GetStyleSettingBool(style, "unranked") && !Shavit_GetStyleSettingBool(style, "noreplay"); 25 | } 26 | 27 | stock void Shavit_GetReplayFilePath(int style, int track, const char[] mapname, const char[] replayfolder, char sPath[PLATFORM_MAX_PATH]) 28 | { 29 | char sTrack[4]; 30 | FormatEx(sTrack, 4, "_%d", track); 31 | FormatEx(sPath, PLATFORM_MAX_PATH, "%s/%d/%s%s.replay", replayfolder, style, mapname, (track > 0)? sTrack:""); 32 | } 33 | 34 | stock bool Shavit_GetReplayFolderPath_Stock(char buffer[PLATFORM_MAX_PATH]) 35 | { 36 | char sPath[PLATFORM_MAX_PATH]; 37 | BuildPath(Path_SM, sPath, PLATFORM_MAX_PATH, "configs/shavit-replay.cfg"); 38 | 39 | KeyValues kv = new KeyValues("shavit-replay"); 40 | 41 | if (!kv.ImportFromFile(sPath)) 42 | { 43 | delete kv; 44 | return false; 45 | } 46 | 47 | kv.GetString("replayfolder", buffer, PLATFORM_MAX_PATH, "{SM}/data/replaybot"); 48 | 49 | if (StrContains(buffer, "{SM}") != -1) 50 | { 51 | ReplaceString(buffer, PLATFORM_MAX_PATH, "{SM}/", ""); 52 | BuildPath(Path_SM, buffer, PLATFORM_MAX_PATH, "%s", buffer); 53 | } 54 | 55 | delete kv; 56 | return true; 57 | } 58 | 59 | stock void Shavit_Replay_CreateDirectories(const char[] sReplayFolder, int styles) 60 | { 61 | if (!DirExists(sReplayFolder) && !CreateDirectory(sReplayFolder, 511)) 62 | { 63 | SetFailState("Failed to create replay folder (%s). Make sure you have file permissions", sReplayFolder); 64 | } 65 | 66 | char sPath[PLATFORM_MAX_PATH]; 67 | FormatEx(sPath, PLATFORM_MAX_PATH, "%s/copy", sReplayFolder); 68 | 69 | if (!DirExists(sPath) && !CreateDirectory(sPath, 511)) 70 | { 71 | SetFailState("Failed to create replay copy folder (%s). Make sure you have file permissions", sPath); 72 | } 73 | 74 | for(int i = 0; i < styles; i++) 75 | { 76 | if (!Shavit_ReplayEnabledStyle(i)) 77 | { 78 | continue; 79 | } 80 | 81 | FormatEx(sPath, PLATFORM_MAX_PATH, "%s/%d", sReplayFolder, i); 82 | 83 | if (!DirExists(sPath) && !CreateDirectory(sPath, 511)) 84 | { 85 | SetFailState("Failed to create replay style folder (%s). Make sure you have file permissions", sPath); 86 | } 87 | } 88 | 89 | // Test to see if replay file creation works 90 | FormatEx(sPath, sizeof(sPath), "%s/0/faketestfile_69.replay", sReplayFolder); 91 | File fTest = OpenFile(sPath, "wb+"); 92 | 93 | // Check if the file was opened successfully for writing 94 | if (fTest == null) 95 | { 96 | SetFailState("Failed to write to replay folder (%s). Make sure you have file permissions.", sReplayFolder); 97 | } 98 | else 99 | { 100 | // File was opened successfully, now close it 101 | CloseHandle(fTest); 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/steamid-stocks.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * Steam ID handling stocks 3 | * by: rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _steamid_stocks_included 23 | #endinput 24 | #endif 25 | #define _steamid_stocks_included 26 | 27 | 28 | // Retrieves accountid from STEAM_X:Y:Z, [U:1:123], and 765xxxxxxxxxxxxxx 29 | stock int SteamIDToAccountID(const char[] sInput) 30 | { 31 | char sSteamID[32]; 32 | strcopy(sSteamID, sizeof(sSteamID), sInput); 33 | ReplaceString(sSteamID, 32, "\"", ""); 34 | TrimString(sSteamID); 35 | 36 | if (StrContains(sSteamID, "STEAM_") != -1) 37 | { 38 | ReplaceString(sSteamID, 32, "STEAM_", ""); 39 | 40 | char parts[3][11]; 41 | ExplodeString(sSteamID, ":", parts, 3, 11); 42 | 43 | // Let X, Y and Z constants be defined by the SteamID: STEAM_X:Y:Z. 44 | // Using the formula W=Z*2+Y, a SteamID can be converted: 45 | return StringToInt(parts[2]) * 2 + StringToInt(parts[1]); 46 | } 47 | else if (StrContains(sSteamID, "U:1:") != -1) 48 | { 49 | ReplaceString(sSteamID, 32, "[", ""); 50 | ReplaceString(sSteamID, 32, "U:1:", ""); 51 | ReplaceString(sSteamID, 32, "]", ""); 52 | 53 | return StringToInt(sSteamID); 54 | } 55 | else if (StrContains(sSteamID, "765") == 0) 56 | { 57 | return SteamID64ToAccountID(sSteamID); 58 | } 59 | 60 | return 0; 61 | } 62 | 63 | stock void AccountIDToSteamID64Num(int accountid, int num[2]) 64 | { 65 | num[0] = accountid; 66 | // universe | type | instance 67 | num[1] = (1 << 24) | (1 << 20) | 1; // 0x01100001 68 | } 69 | 70 | stock void AccountIDToSteamID64(int accountid, char[] buf, int buflen) 71 | { 72 | int num[2]; 73 | AccountIDToSteamID64Num(accountid, num); 74 | SteamID64ToString(num, buf, buflen); 75 | } 76 | 77 | stock void AccountIDToSteamID2(int accountid, char[] buf, int buflen) 78 | { 79 | FormatEx(buf, buflen, "STEAM_0:%d:%d", accountid&1, (accountid>>1) & 0x7FFFFFFF); 80 | } 81 | 82 | stock void AccountIDToSteamID3(int accountid, char[] buf, int buflen) 83 | { 84 | FormatEx(buf, buflen, "[U:1:%u]", accountid); 85 | } 86 | 87 | stock void SteamID64ToString(const int num[2], char[] buf, int buflen) 88 | { 89 | Int64ToString(num, buf, buflen); 90 | } 91 | 92 | stock int SteamID64ToAccountID(const char[] steamid64) 93 | { 94 | int num[2]; 95 | StringToInt64(steamid64, num); 96 | return num[0]; 97 | } 98 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/tas-oblivious.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * tas-oblivious.inc file 3 | * by: oblivious 4 | * 5 | * Originally from autogain (https://github.com/defiy/autogain) Mirror: https://github.com/PMArkive/autogain 6 | * and edited to be part of shavit's Timer (https://github.com/shavitush/bhoptimer) 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_tas_oblivious_included 23 | #endinput 24 | #endif 25 | #define _shavit_tas_oblivious_included 26 | 27 | 28 | stock float normalize_yaw(float _yaw) 29 | { 30 | while (_yaw > 180.0) _yaw -= 360.0; 31 | while (_yaw < -180.0) _yaw += 360.0; return _yaw; 32 | } 33 | 34 | stock float get_length_2d(float vec[3]) 35 | { 36 | return SquareRoot(vec[0] * vec[0] + vec[1] * vec[1]); 37 | } 38 | 39 | stock float ground_delta_opt(int client, float angles[3], float move[3], float surface_friction, 40 | float accelerate, float friction, float stopspeed) 41 | { 42 | float fore[3], side[3], wishvel[3]; 43 | float wishspeed; 44 | 45 | GetAngleVectors(angles, fore, side, ZERO_VECTOR); 46 | 47 | fore[2] = 0.0; 48 | side[2] = 0.0; 49 | NormalizeVector(fore, fore); 50 | NormalizeVector(side, side); 51 | 52 | wishvel[2] = 0.0; 53 | for(int i = 0; i < 2; i++) 54 | wishvel[i] = fore[i] * move[0] + side[i] * move[1]; 55 | 56 | wishspeed = GetVectorLength(wishvel); 57 | 58 | float flMaxSpeed = Shavit_GetStyleSettingFloat(Shavit_GetBhopStyle(client), "runspeed"); 59 | if(wishspeed > flMaxSpeed && flMaxSpeed != 0.0) wishspeed = flMaxSpeed; 60 | 61 | float velocity[3]; 62 | GetEntPropVector(client, Prop_Data, "m_vecVelocity", velocity); 63 | float speed = GetVectorLength(velocity); 64 | 65 | float interval_per_tick = GetTickInterval(); 66 | 67 | float accelspeed = accelerate * wishspeed * interval_per_tick * surface_friction; 68 | 69 | float control = speed; 70 | if (control < stopspeed) control = stopspeed; 71 | float drop = control * friction * interval_per_tick * surface_friction; 72 | 73 | float newspeed = speed - drop; 74 | if (newspeed < 0.0) newspeed = 0.0; 75 | 76 | float tmp = wishspeed - accelspeed; 77 | 78 | if (tmp <= newspeed) 79 | { 80 | float gamma = RadToDeg(ArcCosine(tmp / newspeed)); 81 | float vel_dir_ang = RadToDeg(ArcTangent2(velocity[1], velocity[0])); 82 | 83 | vel_dir_ang = normalize_yaw(vel_dir_ang); 84 | 85 | float accel_yaw = RadToDeg(ArcTangent2(wishvel[1], wishvel[0])); 86 | 87 | float diffm = vel_dir_ang - gamma; 88 | float diffp = vel_dir_ang + gamma; 89 | 90 | diffm = normalize_yaw(diffm - accel_yaw); 91 | diffp = normalize_yaw(diffp - accel_yaw); 92 | 93 | float delta_opt = 0.0; 94 | if (FloatAbs(diffm) <= FloatAbs(diffp)) 95 | delta_opt = -diffm; 96 | else 97 | delta_opt = -diffp; 98 | delta_opt = normalize_yaw(delta_opt); 99 | 100 | return delta_opt; 101 | } 102 | 103 | return 0.0; 104 | } 105 | 106 | stock Action ObliviousOnPlayerRunCmd(int client, int& buttons, int& impulse, float vel[3], float angles[3], int& weapon, int& subtype, int& cmdnum, int& tickcount, int& seed, int mouse[2], 107 | float air_accelerate, float surface_friction, float flAirSpeedCap, float flMaxMove, 108 | bool no_speed_loss) 109 | { 110 | float flMaxSpeed = Shavit_GetStyleSettingFloat(Shavit_GetBhopStyle(client), "runspeed"); 111 | 112 | bool set_back = true; 113 | if (vel[0] != 0.0 || vel[1] != 0.0) 114 | set_back = false; 115 | if (set_back) 116 | vel[1] = flMaxMove; 117 | 118 | float velocity[3], velocity_opt[3]; 119 | GetEntPropVector(client, Prop_Data, "m_vecVelocity", velocity); 120 | 121 | velocity_opt[0] = velocity[0]; velocity_opt[1] = velocity[1]; velocity_opt[2] = velocity[2]; 122 | 123 | float vel_yaw = ArcTangent2(velocity[1], velocity[0]) * 180.0 / FLOAT_PI; 124 | 125 | float delta_opt = -normalize_yaw(angles[1] - vel_yaw); 126 | 127 | if (get_length_2d(velocity) == 0.0) 128 | delta_opt = 90.0; 129 | 130 | if (vel[0] != 0.0 && vel[1] == 0.0) 131 | { 132 | float sign = vel[0] > 0.0 ? -1.0 : 1.0; 133 | delta_opt = -normalize_yaw(angles[1] - (vel_yaw + (90.0 * sign))); 134 | } 135 | if (vel[0] != 0.0 && vel[1] != 0.0) 136 | { 137 | float sign = vel[1] > 0.0 ? -1.0 : 1.0; 138 | if (vel[0] < 0.0) 139 | sign = -sign; 140 | delta_opt = -normalize_yaw(angles[1] - (vel_yaw + (45.0 * sign))); 141 | } 142 | 143 | float frac = 1.0; 144 | 145 | if (buttons & IN_DUCK && no_speed_loss) 146 | frac = 0.34; 147 | 148 | float _addspeed = 0.0; 149 | if (!set_back) 150 | { 151 | float _fore[3], _side[3], _wishvel[3], _wishdir[3]; 152 | float _wishspeed, _wishspd, _currentspeed; 153 | 154 | GetAngleVectors(angles, _fore, _side, ZERO_VECTOR); 155 | 156 | _fore[2] = 0.0; _side[2] = 0.0; 157 | NormalizeVector(_fore, _fore); NormalizeVector(_side, _side); 158 | 159 | for(int i = 0; i < 2; i++) 160 | _wishvel[i] = _fore[i] * vel[0] * frac + _side[i] * vel[1] * frac; 161 | 162 | _wishspeed = NormalizeVector(_wishvel, _wishdir); 163 | 164 | if(_wishspeed > flMaxSpeed && flMaxSpeed != 0.0) _wishspeed = flMaxSpeed; 165 | 166 | _wishspd = _wishspeed; 167 | if (_wishspd > flAirSpeedCap) 168 | _wishspd = flAirSpeedCap; 169 | 170 | _currentspeed = GetVectorDotProduct(velocity, _wishdir); 171 | _addspeed = _wishspd - _currentspeed; 172 | if (_addspeed < 0.0) 173 | _addspeed = 0.0; 174 | } 175 | 176 | float fore[3], side[3], wishvel[3], wishdir[3]; 177 | float wishspeed, wishspd, addspeed, currentspeed; 178 | 179 | float tmp[3]; 180 | tmp[0] = 0.0; tmp[2] = 0.0; 181 | tmp[1] = normalize_yaw(angles[1] + delta_opt); 182 | GetAngleVectors(tmp, fore, side, ZERO_VECTOR); 183 | 184 | fore[2] = 0.0; side[2] = 0.0; 185 | NormalizeVector(fore, fore); NormalizeVector(side, side); 186 | 187 | for(int i = 0; i < 2; i++) 188 | wishvel[i] = fore[i] * vel[0] * frac + side[i] * vel[1] * frac; 189 | 190 | wishspeed = NormalizeVector(wishvel, wishdir); 191 | 192 | if(wishspeed > flMaxSpeed && wishspeed != 0.0) wishspeed = flMaxSpeed; 193 | 194 | wishspd = wishspeed; 195 | if (wishspd > flAirSpeedCap) 196 | wishspd = flAirSpeedCap; 197 | 198 | currentspeed = GetVectorDotProduct(velocity, wishdir); 199 | addspeed = wishspd - currentspeed; 200 | 201 | if (no_speed_loss) 202 | { 203 | if (_addspeed > addspeed) 204 | { 205 | addspeed = _addspeed - addspeed; 206 | } 207 | else 208 | { 209 | addspeed -= _addspeed; 210 | } 211 | } 212 | else 213 | { 214 | addspeed = addspeed - _addspeed; 215 | 216 | if (addspeed > flAirSpeedCap) 217 | addspeed = flAirSpeedCap; 218 | } 219 | 220 | if (buttons & IN_DUCK) 221 | { 222 | float vel2d[3]; vel2d[0] = velocity[0]; vel2d[1] = velocity[1]; 223 | //PrintToChat(client, "%f %f\n", GetVectorLength(vel2d), addspeed); 224 | } 225 | 226 | if (addspeed < 0.0) 227 | addspeed = 0.0; 228 | 229 | float accelspeed = wishspeed * air_accelerate * GetTickInterval() * surface_friction; 230 | 231 | if (accelspeed > addspeed) 232 | accelspeed = addspeed; 233 | 234 | for (int i = 0; i < 3; i++) 235 | velocity_opt[i] += accelspeed * wishdir[i]; 236 | 237 | float new_vel[3]; 238 | 239 | float numer = velocity_opt[0] * velocity[0] + velocity_opt[1] * velocity[1]; 240 | //float denom = SquareRoot(velocity_opt[0] * velocity_opt[0] + velocity_opt[1] * velocity_opt[1]) * SquareRoot(velocity[0] * velocity[0] + velocity[1] * velocity[1]); 241 | float denom = get_length_2d(velocity_opt) * get_length_2d(velocity); 242 | float ang = 0.0; 243 | if (denom > numer) 244 | ang = ArcCosine(numer / denom) * 180.0 / FLOAT_PI; 245 | if (vel[1] < 0.0) ang = -ang; 246 | 247 | float st = Sine(ang * FLOAT_PI / 180.0); 248 | float ct = Cosine(ang * FLOAT_PI / 180.0); 249 | 250 | new_vel[0] = (velocity_opt[0] * ct) - (velocity_opt[1] * st); 251 | new_vel[1] = (velocity_opt[0] * st) + (velocity_opt[1] * ct); 252 | new_vel[2] = velocity_opt[2]; 253 | 254 | float base_vel[3]; 255 | GetEntPropVector(client, Prop_Data, "m_vecBaseVelocity", base_vel); 256 | 257 | //PrintToChat(client, "%.2f, %.2f, %.2f", base_vel[0], base_vel[1], base_vel[2]); 258 | 259 | if (GetVectorLength(new_vel) < 99999.0 && GetVectorLength(new_vel) > 0.0) 260 | { 261 | SetEntPropVector(client, Prop_Data, "m_vecVelocity", new_vel); 262 | SetEntPropVector(client, Prop_Data, "m_vecAbsVelocity", new_vel); 263 | } 264 | 265 | if (set_back) 266 | vel[1] = 0.0; 267 | 268 | return Plugin_Continue; 269 | } 270 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/tas.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - tas.inc file 3 | * by: xutaxkamay, shavit, rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_tas_included 23 | #endinput 24 | #endif 25 | #define _shavit_tas_included 26 | 27 | enum AutostrafeOverride 28 | { 29 | AutostrafeOverride_Normal, // only w/s disables autostrafe 30 | AutostrafeOverride_Surf, // w/s always disables, a/d only over surf ramps 31 | AutostrafeOverride_Surf_W_Okay, // s always disables, a/d only over surf ramps 32 | AutostrafeOverride_All, // all keys disable 33 | AutostrafeOverride_Size // size 34 | }; 35 | 36 | enum AutostrafeType 37 | { 38 | AutostrafeType_Any = -1, 39 | AutostrafeType_Disabled = 0, 40 | AutostrafeType_1Tick = 1, // xutaxkamay 41 | AutostrafeType_Autogain, // oblivious 42 | AutostrafeType_AutogainNoSpeedLoss, // oblivious 43 | AutostrafeType_Basic, // 44 | AutostrafeType_Size 45 | }; 46 | 47 | /** 48 | * Sets whether the client has the autostrafe/strafehack enabled. 49 | * 50 | * @param client Client index 51 | * @param value New value to set the autostrafe/strafehack to. 52 | * @noreturn 53 | */ 54 | native void Shavit_SetAutostrafeEnabled(int client, bool value); 55 | 56 | /** 57 | * Retrieves whether the client has the autostrafe/strafehack enabled. 58 | * 59 | * @param client Client index 60 | * @return The current autostrafe/strafehack enabled value. 61 | */ 62 | native bool Shavit_GetAutostrafeEnabled(int client); 63 | 64 | /** 65 | * Sets the autostrafe/strafehack type on the given client index. 66 | * 67 | * @param client Client index of the player to set the autostrafe/strafehack on. 68 | * @param value New type to set the strafehack to. 69 | * @noreturn 70 | */ 71 | native void Shavit_SetAutostrafeType(int client, AutostrafeType value); 72 | 73 | /** 74 | * Retrieves the current strafehack type for the given client index. 75 | * 76 | * @param client Client index of the player to get the strafehack type from. 77 | * @return The current strafehack type. 78 | */ 79 | native AutostrafeType Shavit_GetAutostrafeType(int client); 80 | 81 | /** 82 | * Sets the strafehack power on the given client index. Power is the cut off point before it will turn into an autostrafe. 1.0 is the default. 83 | * 84 | * @param client Client index of the player to set the power on. 85 | * @param value New power setting. 86 | * @noreturn 87 | */ 88 | native void Shavit_SetAutostrafePower(int client, float value); 89 | 90 | /** 91 | * Retrieves the current strafehack power for the given client index. Default is 1.0 92 | * 93 | * @param client Client index of the player to get the strafehack power. 94 | * @return The current strafehack power. 95 | */ 96 | native float Shavit_GetAutostrafePower(int client); 97 | 98 | /** 99 | * Sets the key override type on the given client index. 100 | * 101 | * @param client Client index 102 | * @param value New type to set the key override to. 103 | * @noreturn 104 | */ 105 | native void Shavit_SetAutostrafeKeyOverride(int client, AutostrafeOverride value); 106 | 107 | /** 108 | * Retrieves the current key override type for the given client index. 109 | * 110 | * @param client Client index 111 | * @return The current key override type. 112 | */ 113 | native AutostrafeOverride Shavit_GetAutostrafeKeyOverride(int client); 114 | 115 | /** 116 | * Sets whether the client has automatic prestrafe enabled. 117 | * 118 | * @param client Client index 119 | * @param value New value to set the automatic prestrafe to. 120 | * @noreturn 121 | */ 122 | native void Shavit_SetAutoPrestrafe(int client, bool value); 123 | 124 | /** 125 | * Retrieves whether the client has automatic prestrafe enabled. 126 | * 127 | * @param client Client index 128 | * @return The current auto prestrafe value. 129 | */ 130 | native bool Shavit_GetAutoPrestrafe(int client); 131 | 132 | /** 133 | * Sets whether the client automatically jumps when they leave the start zone. 134 | * 135 | * @param client Client index 136 | * @param value New value to set the automatic jump to. 137 | * @noreturn 138 | */ 139 | native void Shavit_SetAutoJumpOnStart(int client, bool value); 140 | 141 | /** 142 | * Retrieves whether the client automatically jumps when they leave the start zone. 143 | * 144 | * @param client Client index 145 | * @return The current auto jump value. 146 | */ 147 | native bool Shavit_GetAutoJumpOnStart(int client); 148 | 149 | /** 150 | * Sets whether the client uses the autogain basic strafer. 151 | * 152 | * @param client Client index 153 | * @param value New value to set the autogain basic strafer to. 154 | * @noreturn 155 | */ 156 | native void Shavit_SetAutogainBasicStrafer(int client, bool value); 157 | 158 | /** 159 | * Retrieves whether the client has has enabled the autogain basic strafer :tm: 160 | * 161 | * @param client Client index 162 | * @return The current autogain basic strafer setting. 163 | */ 164 | native bool Shavit_GetAutogainBasicStrafer(int client); 165 | 166 | 167 | 168 | // taken from shavit's oryx 169 | stock bool IsSurfing(int client) 170 | { 171 | float fPosition[3]; 172 | GetClientAbsOrigin(client, fPosition); 173 | 174 | float fEnd[3]; 175 | fEnd = fPosition; 176 | fEnd[2] -= 64.0; 177 | 178 | float fMins[3]; 179 | GetEntPropVector(client, Prop_Send, "m_vecMins", fMins); 180 | 181 | float fMaxs[3]; 182 | GetEntPropVector(client, Prop_Send, "m_vecMaxs", fMaxs); 183 | 184 | Handle hTR = TR_TraceHullFilterEx(fPosition, fEnd, fMins, fMaxs, MASK_PLAYERSOLID, TRFilter_NoPlayers, client); 185 | 186 | if(TR_DidHit(hTR)) 187 | { 188 | float fNormal[3]; 189 | TR_GetPlaneNormal(hTR, fNormal); 190 | 191 | delete hTR; 192 | 193 | // If the plane normal's Z axis is 0.7 or below (alternatively, -0.7 when upside-down) then it's a surf ramp. 194 | // https://github.com/alliedmodders/hl2sdk/blob/92dcf04225a278b75170cc84917f04e98f5d08ec/game/server/physics_main.cpp#L1059 195 | // https://github.com/ValveSoftware/source-sdk-2013/blob/0d8dceea4310fde5706b3ce1c70609d72a38efdf/mp/src/game/server/physics_main.cpp#L1065 196 | 197 | return (-0.7 <= fNormal[2] <= 0.7); 198 | } 199 | 200 | delete hTR; 201 | 202 | return false; 203 | } 204 | 205 | stock bool TRFilter_NoPlayers(int entity, int mask, any data) 206 | { 207 | return !(1 <= entity <= MaxClients); 208 | } 209 | 210 | 211 | public SharedPlugin __pl_shavit_tas = 212 | { 213 | name = "shavit-tas", 214 | file = "shavit-tas.smx", 215 | #if defined REQUIRE_PLUGIN 216 | required = 1 217 | #else 218 | required = 0 219 | #endif 220 | }; 221 | 222 | #if !defined REQUIRE_PLUGIN 223 | public void __pl_shavit_tas_SetNTVOptional() 224 | { 225 | MarkNativeAsOptional("Shavit_SetAutostrafeEnabled"); 226 | MarkNativeAsOptional("Shavit_GetAutostrafeEnabled"); 227 | MarkNativeAsOptional("Shavit_SetAutostrafeType"); 228 | MarkNativeAsOptional("Shavit_GetAutostrafeType"); 229 | MarkNativeAsOptional("Shavit_SetAutostrafePower"); 230 | MarkNativeAsOptional("Shavit_GetAutostrafePower"); 231 | MarkNativeAsOptional("Shavit_SetAutostrafeKeyOverride"); 232 | MarkNativeAsOptional("Shavit_GetAutostrafeKeyOverride"); 233 | MarkNativeAsOptional("Shavit_SetAutoPrestrafe"); 234 | MarkNativeAsOptional("Shavit_GetAutoPrestrafe"); 235 | MarkNativeAsOptional("Shavit_SetAutoJumpOnStart"); 236 | MarkNativeAsOptional("Shavit_GetAutoJumpOnStart"); 237 | MarkNativeAsOptional("Shavit_SetEdgeJump"); 238 | MarkNativeAsOptional("Shavit_GetEdgeJump"); 239 | MarkNativeAsOptional("Shavit_SetAutogainBasicStrafer"); 240 | MarkNativeAsOptional("Shavit_GetAutogainBasicStrafer"); 241 | } 242 | #endif 243 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/include/shavit/weapon-stocks.inc: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - weapon stocks 3 | * by: shavit, psychonic, Kxnrl, rtldg 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #if defined _shavit_weapon_stocks_included 23 | #endinput 24 | #endif 25 | #define _shavit_weapon_stocks_included 26 | 27 | // based on code by Kxnrl in SurfTimer 28 | // which is based on code by splewis from csgo-deathmatch? 29 | // https://github.com/Maxximou5/csgo-deathmatch/pull/24/commits/207cbfe3f1b9a1082c4a710841c190bb753485dc#diff-2c9694977d0a3fe527ca8b484add6a58f53bab303e5dcaa583cb2917ec04d89cR3122-R3130 30 | // https://github.com/surftimer/SurfTimer/commit/134887a29a396e01a721a78ab69e81a80593411a#diff-0b2bae39ae9de87ea2952bfd12c8777c7301e06ce683acc518229704cf024c33R4894-R4910 31 | stock int GiveSkinnedWeapon(int client, const char[] classname) 32 | { 33 | int target_team = 0; 34 | int current_team = 0; 35 | 36 | if (StrContains(classname, "usp") != -1) 37 | { 38 | target_team = 3; 39 | } 40 | else if (StrContains(classname, "glock") != -1) 41 | { 42 | target_team = 2; 43 | } 44 | 45 | if (target_team != 0) 46 | { 47 | current_team = GetEntProp(client, Prop_Send, "m_iTeamNum"); 48 | 49 | if (current_team != target_team) 50 | { 51 | SetEntProp(client, Prop_Send, "m_iTeamNum", target_team); 52 | } 53 | } 54 | 55 | int weapon = GivePlayerItem(client, classname); 56 | 57 | if (current_team != target_team) 58 | { 59 | SetEntProp(client, Prop_Send, "m_iTeamNum", current_team); 60 | } 61 | 62 | return weapon; 63 | } 64 | 65 | // based on testsuite code from psychonic 66 | // https://github.com/alliedmodders/sourcemod/blob/c5701503185d7e1cb8411c7347abdd31eee75c4e/plugins/testsuite/entpropelements.sp#L88-L96 67 | stock void RemoveAllWeapons(int client) 68 | { 69 | int weapon = -1, max = GetEntPropArraySize(client, Prop_Send, "m_hMyWeapons"); 70 | for (int i = 0; i < max; i++) 71 | { 72 | if ((weapon = GetEntPropEnt(client, Prop_Send, "m_hMyWeapons", i)) == -1) 73 | continue; 74 | 75 | if (RemovePlayerItem(client, weapon)) 76 | { 77 | AcceptEntityInput(weapon, "Kill"); 78 | } 79 | } 80 | } 81 | 82 | stock void SetMaxWeaponAmmo(int client, int weapon, bool setClip1) 83 | { 84 | static EngineVersion engine = Engine_Unknown; 85 | 86 | if (engine == Engine_Unknown) 87 | { 88 | engine = GetEngineVersion(); 89 | } 90 | 91 | int iAmmo = GetEntProp(weapon, Prop_Send, "m_iPrimaryAmmoType"); 92 | 93 | if (iAmmo < 0) 94 | { 95 | return; 96 | } 97 | 98 | SetEntProp(client, Prop_Send, "m_iAmmo", 255, 4, iAmmo); 99 | 100 | if (engine == Engine_CSGO) 101 | { 102 | SetEntProp(weapon, Prop_Send, "m_iPrimaryReserveAmmoCount", 255); 103 | } 104 | 105 | if (setClip1) 106 | { 107 | int amount = GetEntProp(weapon, Prop_Send, "m_iClip1") + 1; 108 | 109 | if (HasEntProp(weapon, Prop_Send, "m_bBurstMode") && GetEntProp(weapon, Prop_Send, "m_bBurstMode")) 110 | { 111 | amount += 2; 112 | } 113 | 114 | SetEntProp(weapon, Prop_Data, "m_iClip1", amount); 115 | } 116 | } 117 | -------------------------------------------------------------------------------- /addons/sourcemod/scripting/shavit-sounds.sp: -------------------------------------------------------------------------------- 1 | /* 2 | * shavit's Timer - Sounds 3 | * by: shavit, KiD Fearless 4 | * 5 | * This file is part of shavit's Timer (https://github.com/shavitush/bhoptimer) 6 | * 7 | * 8 | * This program is free software; you can redistribute it and/or modify it under 9 | * the terms of the GNU General Public License, version 3.0, as published by the 10 | * Free Software Foundation. 11 | * 12 | * This program is distributed in the hope that it will be useful, but WITHOUT 13 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 14 | * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 15 | * details. 16 | * 17 | * You should have received a copy of the GNU General Public License along with 18 | * this program. If not, see . 19 | * 20 | */ 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | 27 | #include 28 | #include 29 | 30 | #undef REQUIRE_PLUGIN 31 | #include 32 | 33 | #pragma newdecls required 34 | #pragma semicolon 1 35 | 36 | bool gB_HUD; 37 | 38 | ArrayList gA_FirstSounds = null; 39 | ArrayList gA_PersonalSounds = null; 40 | ArrayList gA_WorldSounds = null; 41 | ArrayList gA_WorstSounds = null; 42 | ArrayList gA_NoImprovementSounds = null; 43 | StringMap gSM_RankSounds = null; 44 | 45 | // cvars 46 | Convar gCV_MinimumWorst = null; 47 | Convar gCV_Enabled = null; 48 | 49 | Handle gH_OnPlaySound = null; 50 | 51 | public Plugin myinfo = 52 | { 53 | name = "[shavit] Sounds", 54 | author = "shavit, KiD Fearless", 55 | description = "Play custom sounds when timer-related events happen.", 56 | version = SHAVIT_VERSION, 57 | url = "https://github.com/shavitush/bhoptimer" 58 | } 59 | 60 | public APLRes AskPluginLoad2(Handle myself, bool late, char[] error, int err_max) 61 | { 62 | // registers library, check "bool LibraryExists(const char[] name)" in order to use with other plugins 63 | RegPluginLibrary("shavit-sounds"); 64 | 65 | return APLRes_Success; 66 | } 67 | 68 | public void OnPluginStart() 69 | { 70 | // cache 71 | int cells = ByteCountToCells(PLATFORM_MAX_PATH); 72 | gA_FirstSounds = new ArrayList(cells); 73 | gA_PersonalSounds = new ArrayList(cells); 74 | gA_WorldSounds = new ArrayList(cells); 75 | gA_WorstSounds = new ArrayList(cells); 76 | gA_NoImprovementSounds = new ArrayList(cells); 77 | gSM_RankSounds = new StringMap(); 78 | 79 | // modules 80 | gB_HUD = LibraryExists("shavit-hud"); 81 | 82 | // cvars 83 | gCV_MinimumWorst = new Convar("shavit_sounds_minimumworst", "10", "Minimum amount of records to be saved for a \"worst\" sound to play.", 0, true, 1.0); 84 | gCV_Enabled = new Convar("shavit_sounds_enabled", "1", "Enables/Disables functionality of the plugin", 0, true, 0.0, true, 1.0); 85 | 86 | Convar.AutoExecConfig(); 87 | 88 | gH_OnPlaySound = CreateGlobalForward("Shavit_OnPlaySound", ET_Event, Param_Cell, Param_String, Param_Cell, Param_Array, Param_CellByRef); 89 | } 90 | 91 | public void OnLibraryAdded(const char[] name) 92 | { 93 | if(StrEqual(name, "shavit-hud")) 94 | { 95 | gB_HUD = true; 96 | } 97 | } 98 | 99 | public void OnLibraryRemoved(const char[] name) 100 | { 101 | if(StrEqual(name, "shavit-hud")) 102 | { 103 | gB_HUD = false; 104 | } 105 | } 106 | 107 | public void OnMapStart() 108 | { 109 | gA_FirstSounds.Clear(); 110 | gA_PersonalSounds.Clear(); 111 | gA_WorldSounds.Clear(); 112 | gA_WorstSounds.Clear(); 113 | gA_NoImprovementSounds.Clear(); 114 | gSM_RankSounds.Clear(); 115 | 116 | char sFile[PLATFORM_MAX_PATH]; 117 | BuildPath(Path_SM, sFile, PLATFORM_MAX_PATH, "configs/shavit-sounds.cfg"); 118 | 119 | File fFile = OpenFile(sFile, "r"); // readonly, unless i implement in-game editing 120 | 121 | if(fFile == null && gCV_Enabled.BoolValue) 122 | { 123 | SetFailState("Cannot open \"configs/shavit-sounds.cfg\". Make sure this file exists and that the server has read permissions to it."); 124 | } 125 | else 126 | { 127 | char sLine[PLATFORM_MAX_PATH*2]; 128 | char sDownloadString[PLATFORM_MAX_PATH]; 129 | 130 | while(fFile.ReadLine(sLine, PLATFORM_MAX_PATH*2)) 131 | { 132 | TrimString(sLine); 133 | 134 | if(sLine[0] != '\"') 135 | { 136 | continue; 137 | } 138 | 139 | ReplaceString(sLine, PLATFORM_MAX_PATH*2, "\"", ""); 140 | 141 | char sExploded[2][PLATFORM_MAX_PATH]; 142 | ExplodeString(sLine, " ", sExploded, 2, PLATFORM_MAX_PATH); 143 | 144 | if(StrEqual(sExploded[0], "first")) 145 | { 146 | gA_FirstSounds.PushString(sExploded[1]); 147 | } 148 | else if(StrEqual(sExploded[0], "personal")) 149 | { 150 | gA_PersonalSounds.PushString(sExploded[1]); 151 | } 152 | else if(StrEqual(sExploded[0], "world")) 153 | { 154 | gA_WorldSounds.PushString(sExploded[1]); 155 | } 156 | else if(StrEqual(sExploded[0], "worst")) 157 | { 158 | gA_WorstSounds.PushString(sExploded[1]); 159 | } 160 | else if(StrEqual(sExploded[0], "worse") || StrEqual(sExploded[0], "noimprovement")) 161 | { 162 | gA_NoImprovementSounds.PushString(sExploded[1]); 163 | } 164 | else 165 | { 166 | gSM_RankSounds.SetString(sExploded[0], sExploded[1]); 167 | } 168 | 169 | if(PrecacheSound(sExploded[1], true)) 170 | { 171 | FormatEx(sDownloadString, PLATFORM_MAX_PATH, "sound/%s", sExploded[1]); 172 | AddFileToDownloadsTable(sDownloadString); 173 | } 174 | else 175 | { 176 | LogError("\"sound/%s\" could not be accessed.", sExploded[1]); 177 | } 178 | } 179 | } 180 | 181 | delete fFile; 182 | } 183 | 184 | public void Shavit_OnFinish(int client, int style, float time, int jumps, int strafes, float sync, int track, float oldtime, float perfs) 185 | { 186 | if(!gCV_Enabled.BoolValue) 187 | { 188 | return; 189 | } 190 | 191 | if(oldtime != 0.0 && time > oldtime && gA_NoImprovementSounds.Length != 0) 192 | { 193 | char sSound[PLATFORM_MAX_PATH]; 194 | gA_NoImprovementSounds.GetString(GetRandomInt(0, gA_NoImprovementSounds.Length - 1), sSound, PLATFORM_MAX_PATH); 195 | 196 | PlayEventSound(client, false, sSound); 197 | } 198 | } 199 | 200 | public void Shavit_OnFinish_Post(int client, int style, float time, int jumps, int strafes, float sync, int rank, int overwrite, int track, float fOldTime) 201 | { 202 | if(!gCV_Enabled.BoolValue) 203 | { 204 | return; 205 | } 206 | 207 | char sSound[PLATFORM_MAX_PATH]; 208 | bool bEveryone = false; 209 | 210 | char sRank[8]; 211 | IntToString(rank, sRank, 8); 212 | 213 | if((time < fOldTime || fOldTime == 0.0) && gSM_RankSounds.GetString(sRank, sSound, PLATFORM_MAX_PATH)) 214 | { 215 | bEveryone = true; 216 | } 217 | else if(gA_WorldSounds.Length != 0 && rank == 1) 218 | { 219 | bEveryone = true; 220 | 221 | gA_WorldSounds.GetString(GetRandomInt(0, gA_WorldSounds.Length - 1), sSound, PLATFORM_MAX_PATH); 222 | } 223 | else if(gA_PersonalSounds.Length != 0 && time < fOldTime) 224 | { 225 | gA_PersonalSounds.GetString(GetRandomInt(0, gA_PersonalSounds.Length - 1), sSound, PLATFORM_MAX_PATH); 226 | } 227 | else if(gA_FirstSounds.Length != 0 && overwrite == 1) 228 | { 229 | gA_FirstSounds.GetString(GetRandomInt(0, gA_FirstSounds.Length - 1), sSound, PLATFORM_MAX_PATH); 230 | } 231 | 232 | if(StrContains(sSound, ".") != -1) // file has an extension? 233 | { 234 | PlayEventSound(client, bEveryone, sSound); 235 | } 236 | } 237 | 238 | public void Shavit_OnWorstRecord(int client, int style, float time, int jumps, int strafes, float sync, int track) 239 | { 240 | if(!gCV_Enabled.BoolValue) 241 | { 242 | return; 243 | } 244 | 245 | if(gA_WorstSounds.Length != 0 && Shavit_GetRecordAmount(style, track) >= gCV_MinimumWorst.IntValue) 246 | { 247 | char sSound[PLATFORM_MAX_PATH]; 248 | gA_WorstSounds.GetString(GetRandomInt(0, gA_WorstSounds.Length - 1), sSound, PLATFORM_MAX_PATH); 249 | 250 | if(StrContains(sSound, ".") != -1) 251 | { 252 | PlayEventSound(client, false, sSound); 253 | } 254 | } 255 | } 256 | 257 | void PlayEventSound(int client, bool everyone, char sound[PLATFORM_MAX_PATH]) 258 | { 259 | int clients[MAXPLAYERS+1]; 260 | int count = 0; 261 | 262 | for(int i = 1; i <= MaxClients; i++) 263 | { 264 | if(!IsValidClient(i) || (gB_HUD && (Shavit_GetHUDSettings(i) & HUD_NOSOUNDS) > 0)) 265 | { 266 | continue; 267 | } 268 | 269 | if (everyone || i == client || GetSpectatorTarget(i) == client) 270 | { 271 | clients[count++] = i; 272 | } 273 | } 274 | 275 | Action result = Plugin_Continue; 276 | Call_StartForward(gH_OnPlaySound); 277 | Call_PushCell(client); 278 | Call_PushStringEx(sound, PLATFORM_MAX_PATH, SM_PARAM_STRING_COPY, SM_PARAM_COPYBACK); 279 | Call_PushCell(PLATFORM_MAX_PATH); 280 | Call_PushArrayEx(clients, MaxClients, SM_PARAM_COPYBACK); 281 | Call_PushCellRef(count); 282 | Call_Finish(result); 283 | 284 | if(result != Plugin_Continue && result != Plugin_Changed) 285 | { 286 | return; 287 | } 288 | 289 | if(count > 0) 290 | { 291 | EmitSound(clients, count, sound); 292 | } 293 | } 294 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-chat.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Commands ---------- // 4 | "ChatUpdated" 5 | { 6 | "en" "Setting updated." 7 | } 8 | "ChatCurrent" 9 | { 10 | "#format" "{1:s}" 11 | "en" "Current setting: {1}" 12 | } 13 | "NameOff" 14 | { 15 | "en" "Custom chat name is now off." 16 | } 17 | "MessageOff" 18 | { 19 | "en" "Custom chat text color is now off." 20 | } 21 | "CheckConsole" 22 | { 23 | "en" "Check your console." 24 | } 25 | "CCAccessGrantedToPlayer" 26 | { 27 | "#format" "{1:s},{2:s}" 28 | "en" "You've been given access to custom chat! Use {1}!cchelp{2} for more info." 29 | } 30 | "CCHelp_Intro" 31 | { 32 | "en" "- You have access to custom chat.\nUsage information:" 33 | } 34 | "CCHelp_Generic" 35 | { 36 | "en" "- !ccname can be used to change your custom chat name. Use \"!ccname off\" to toggle it off.\n- !ccmsg can be used to change your custom message prefix/color. Use \"!ccmsg off\" to toggle it off.\nThere are custom variables, such as:" 37 | } 38 | "CCHelp_GenericVariables" 39 | { 40 | "en" "- {name} - your in-game name.\n- {clan} - your clan tag.\n- {rand} - a random color.\n- {team} - your team color.\n- {green} - green color." 41 | } 42 | "CCHelp_CSS_1" 43 | { 44 | "en" "- To use a custom color, write ^RRGGBB (HEX/HTML colors). For example, ^FFFFFF is white and ^000000 is black." 45 | } 46 | "CCHelp_CSS_2" 47 | { 48 | "en" "- You can also use a set alpha (opacity in HEX, where FF is 255). &RRGGBBAA. For example, &FFFFFF7F is 127 alpha, so all text after the color will have 50% opacity." 49 | } 50 | "CCHelp_CSGO_1" 51 | { 52 | "en" "- The following colors are also available: {blue}, {bluegrey}, {darkblue}, {darkred}, {gold}, {grey}, {grey2}, {lightgreen}, {lightred}, {lime}, {orchid}, {yellow} and {palered}." 53 | } 54 | // ---------- Menu ---------- // 55 | "SelectChatRank" 56 | { 57 | "en" "Select chat rank:\n" 58 | } 59 | "SelectChatRankType" 60 | { 61 | "en" "Which chat ranks do you want to see?\n" 62 | } 63 | "SelectChatRankUnlocked" 64 | { 65 | "en" "Unlocked chat ranks\n" 66 | } 67 | "SelectChatRankAll" 68 | { 69 | "en" "All chat ranks\n" 70 | } 71 | "AutoAssign" 72 | { 73 | "en" "Auto-assign\nAutomatically assign using your rank." 74 | } 75 | "CustomChat" 76 | { 77 | "en" "Custom\nUse custom chat settings. See !cchelp for more information." 78 | } 79 | "ChatRanksMenu" 80 | { 81 | "en" "Obtainable chat ranks:\nSelect an entry to preview.\n" 82 | } 83 | "ChatRanksMenu_SampleText" 84 | { 85 | "en" "The quick brown fox jumps over the lazy dog" 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-common.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Tracks ---------- // 4 | "Track" 5 | { 6 | "en" "Track" 7 | } 8 | "Track_Unknown" 9 | { 10 | "en" "UNKNOWN TRACK" 11 | } 12 | "Track_Main" 13 | { 14 | "en" "Main" 15 | } 16 | "Track_Bonus" 17 | { 18 | "#format" "{1:d}" 19 | "en" "Bonus {1}" 20 | } 21 | "Track_Bonus_NoNum" 22 | { 23 | "en" "Bonus" 24 | } 25 | // ---------- Commands ---------- // 26 | "NoCommandAccess" 27 | { 28 | "en" "You do not have access to this command." 29 | } 30 | "NoConsole" 31 | { 32 | "en" "Run this command from inside the game." 33 | } 34 | "ArgumentsMissing" 35 | { 36 | "#format" "{1:s}" 37 | "en" "Usage: {1}" 38 | } 39 | "TimerCommands" 40 | { 41 | "en" "Timer Commands" 42 | } 43 | // ---------- Timelimit ---------- // 44 | "Minutes" 45 | { 46 | "#format" "{1:s}" 47 | "en" "{1} minutes remaining." 48 | } 49 | "Seconds" 50 | { 51 | "#format" "{1:s}" 52 | "en" "{1} seconds remaining." 53 | } 54 | "Extended" 55 | { 56 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:d},{6:s}" 57 | "en" "{1}{2}{3} extended the map by {4}{5}{6} minutes." 58 | } 59 | // ----------- Random ----------- // 60 | "TimerLoading" 61 | { 62 | "en" "Loading.." 63 | } 64 | "Timescale" 65 | { 66 | "en" "Timescale" 67 | } 68 | "CurrentTimescale" 69 | { 70 | "en" "Current Timescale" 71 | } 72 | "OpenSteamProfile" 73 | { 74 | "en" "Open Steam profile" 75 | } 76 | "ReRolling Maps" 77 | { 78 | "#format" "{1:i},{2:i}" 79 | "en" "Voting for next map has restarted. Reroll complete. (Received {1}%% of {2} votes)" 80 | } 81 | } 82 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-core.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Commands ---------- // 4 | "AutobhopEnabled" 5 | { 6 | "#format" "{1:s},{2:s}" 7 | "en" "Autobhop {1}enabled{2}." 8 | } 9 | "AutobhopDisabled" 10 | { 11 | "#format" "{1:s},{2:s}" 12 | "en" "Autobhop {1}disabled{2}." 13 | } 14 | "CheatTimerStop" 15 | { 16 | "#format" "{1:s},{2:s},{3:s}" 17 | "en" "{1}Timer stopped! {2}{3}" 18 | } 19 | "CommandDisabled" 20 | { 21 | "#format" "{1:s},{2:s},{3:s}" 22 | "en" "The command ({1}{2}{3}) is disabled." 23 | } 24 | "StyleNoAccess" 25 | { 26 | "#format" "{1:s},{2:s}" 27 | "en" "You lack the {1}permissions{2} for this style." 28 | } 29 | "NoEditingTimescale" 30 | { 31 | "en" "This style doesn't allow you to change timescale." 32 | } 33 | // ---------- Errors ---------- // 34 | "VerificationFailed" 35 | { 36 | "en" "Couldn't verify your, or the server's connection to Steam." 37 | } 38 | "TimeUnderMinimumTime" 39 | { 40 | "#format" "{1:f},{2:f},{3:s}" 41 | "en" "Your time ({2}) was faster than the style's {3} setting ({1}) and did not count." 42 | } 43 | "TimeUnderMinimumTime2" 44 | { 45 | "#format" "{1:f},{2:f}" 46 | "en" "Your time ({2}) was faster or equal to the timer's minimum ({1}) and did not count." 47 | } 48 | // ---------- Menus ---------- // 49 | "StyleMenuTitle" 50 | { 51 | "en" "Choose a style:" 52 | } 53 | "StyleSelection" 54 | { 55 | "#format" "{1:s},{2:s},{3:s}" 56 | "en" "You have chosen to play {1}{2}{3}." 57 | } 58 | "StyleUnranked" 59 | { 60 | "en" "[Unranked]" 61 | } 62 | // ---------- Misc ---------- // 63 | "LeftRightCheat" 64 | { 65 | "en" "Detected +left/right on a disallowed style." 66 | } 67 | "Inconsistencies" 68 | { 69 | "en" "Detected inconsistencies in button presses." 70 | } 71 | "UnrankedWarning" 72 | { 73 | "#format" "{1:s},{2:s}" 74 | "en" "{1}WARNING: {2}This style is unranked. Your times WILL NOT be saved and will be only displayed to you!" 75 | } 76 | "PracticeModeAlert" 77 | { 78 | "#format" "{1:s},{2:s}" 79 | "en" "{1}WARNING: {2}You're now in practice mode. Your times WILL NOT be saved and will be only displayed to you!" 80 | } 81 | "SHSWCombination0" 82 | { 83 | "#format" "{1:s},{2:s}" 84 | "en" "Your SHSW combination is {1}W/A & S/D{2}." 85 | } 86 | "SHSWCombination1" 87 | { 88 | "#format" "{1:s},{2:s}" 89 | "en" "Your SHSW combination is {1}W/D & S/A{2}." 90 | } 91 | "NewAiraccelerate" 92 | { 93 | "#format" "{1:d},{2:s},{3:d},{4:s}" 94 | "en" "Your airacceleration has been changed from {1} to {2}{3}{4}." 95 | } 96 | // ---------- Pauses ---------- // 97 | "MessagePause" 98 | { 99 | "#format" "{1:s},{2:s},{3:s}" 100 | "en" "{1}Timer has been {2}paused{3}." 101 | } 102 | "MessageUnpause" 103 | { 104 | "#format" "{1:s},{2:s},{3:s}" 105 | "en" "{1}Timer has been {2}resumed{3}." 106 | } 107 | "PauseNotOnGround" 108 | { 109 | "#format" "{1:s},{2:s}" 110 | "en" "You {1}are not{2} allowed to pause when not on ground." 111 | } 112 | "PauseStartZone" 113 | { 114 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s}" 115 | "en" "{1}You {2}cannot{3} pause in the {4}start zone{5}." 116 | } 117 | "PauseEndZone" 118 | { 119 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s}" 120 | "en" "{1}You {2}cannot{3} pause in the {4}end zone{5}." 121 | } 122 | "PauseMoving" 123 | { 124 | "#format" "{1:s},{2:s}" 125 | "en" "You {1}are not{2} allowed to pause while moving." 126 | } 127 | "PauseDuck" 128 | { 129 | "#format" "{1:s},{2:s}" 130 | "en" "You {1}are not{2} allowed to pause while crouching." 131 | } 132 | "TimerUnpaused" 133 | { 134 | "#format" "{1:s},{2:s}" 135 | "en" "Timer has been {1}unpaused{2}." 136 | } 137 | "TimerPaused" 138 | { 139 | "#format" "{1:s},{2:s}" 140 | "en" "Timer has been {1}paused{2}." 141 | } 142 | // ---------- Zones ---------- // 143 | "StartZoneUndefined" 144 | { 145 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s}" 146 | "en" "Your timer {1}will not{2} start because the {3}{4}{5} start zone is not set." 147 | } 148 | "EndZoneUndefined" 149 | { 150 | "#format" "{1:s},{2:s}" 151 | "en" "You {1}can't{2} teleport as an end zone for the map is not defined." 152 | } 153 | "DebugOffsets" 154 | { 155 | "#format" "{1:f},{2:s}" 156 | "en" "Your zone offset was {1}. The distance was {2} units." 157 | } 158 | "TrackChangeFromMain" 159 | { 160 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s},{6:s}" 161 | "en" "Use {1}!m{2}/{3}!main{4} go to back to the main track. Or {5}!ihate!main{6}." 162 | } 163 | } 164 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-hud.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- HUD Components ---------- // 4 | // DO NOT MAKE NAMES LONGER THAN DISPLAYED HERE // 5 | "HudStartZone" 6 | { 7 | "en" "Start Zone" 8 | } 9 | "HudZoneTier" 10 | { 11 | "#format" "{1:d}" 12 | "en" "Tier {1}" 13 | } 14 | "HudInStartZone" 15 | { 16 | "#format" "{1:d}" 17 | "en" "In Start Zone\n\n{1}" 18 | } 19 | "HudInStartZoneNoSpeed" 20 | { 21 | "#format" "{1:d}" 22 | "en" "In Start Zone" 23 | } 24 | "HudInStartZoneCSGO" 25 | { 26 | "#format" "{1:d}" 27 | "en" "In Start Zone" 28 | } 29 | "HudEndZone" 30 | { 31 | "en" "End Zone" 32 | } 33 | "HudInEndZone" 34 | { 35 | "#format" "{1:d}" 36 | "en" "In End Zone\n\n{1}" 37 | } 38 | "HudInEndZoneNoSpeed" 39 | { 40 | "#format" "{1:d}" 41 | "en" "In End Zone" 42 | } 43 | "HudInEndZoneCSGO" 44 | { 45 | "#format" "{1:d}" 46 | "en" "In End Zone" 47 | } 48 | "HudPaused" 49 | { 50 | "en" "[PAUSED]" 51 | } 52 | "HudTimeText" 53 | { 54 | "en" "Time" 55 | } 56 | "HudBestText" 57 | { 58 | "en" "Best" 59 | } 60 | "HudJumpsText" 61 | { 62 | "en" "Jumps" 63 | } 64 | "HudStyleText" 65 | { 66 | "en" "Style" 67 | } 68 | "HudSpeedText" 69 | { 70 | "en" "Speed" 71 | } 72 | "HudStrafeText" 73 | { 74 | "en" "Strafes" 75 | } 76 | "HudTimeLeft" 77 | { 78 | "en" "Time left" 79 | } 80 | "HudSync" 81 | { 82 | "en" "Sync" 83 | } 84 | "HudPerfs" 85 | { 86 | "en" "Perfect jumps" 87 | } 88 | "HudDefaultPistol" 89 | { 90 | "en" "Default Pistol: 1=USP 2=Glock" 91 | } 92 | "HudUSPSilencer" 93 | { 94 | "en" "Spawn USPs with a silencer attached" 95 | } 96 | "HudGlockBurst" 97 | { 98 | "en" "Spawn Glocks with Burst" 99 | } 100 | "HudPracticeMode" 101 | { 102 | "en" "[PRACTICE]" 103 | } 104 | "HudNoSpeedLimit" 105 | { 106 | "en" "(No Speed Limit)" 107 | } 108 | "HudCustomSpeedLimit" 109 | { 110 | "#format" "{1:d}" 111 | "en" "(Speed Limit: {1})" 112 | } 113 | "HudCenterKeys" 114 | { 115 | "en" "!keys in the center" 116 | } 117 | // ---------- Menus ---------- // 118 | "HUDMenuTitle" 119 | { 120 | "en" "HUD settings:" 121 | } 122 | "HudMaster" 123 | { 124 | "en" "Master" 125 | } 126 | "HudCenter" 127 | { 128 | "en" "Center text" 129 | } 130 | "HudZoneHud" 131 | { 132 | "en" "Zone HUD" 133 | } 134 | "HudObserve" 135 | { 136 | "en" "Spectate HUD" 137 | } 138 | "HudSpectators" 139 | { 140 | "en" "Spectator list" 141 | } 142 | "HudSpectatorsDead" 143 | { 144 | "en" "Spectator list (only when dead)" 145 | } 146 | "HudKeyOverlay" 147 | { 148 | "en" "Key display" 149 | } 150 | "HudHideWeapon" 151 | { 152 | "en" "Hide weapons" 153 | } 154 | "HudTopLeft" 155 | { 156 | "en" "Top left HUD (WR/PB)" 157 | } 158 | "Hud2dVel" 159 | { 160 | "en" "Use 2D Velocity" 161 | } 162 | "HudNoRecordSounds" 163 | { 164 | "en" "No record sounds" 165 | } 166 | "HudPracticeModeAlert" 167 | { 168 | "en" "No practice mode alert" 169 | } 170 | "HudRankText" 171 | { 172 | "en" "Expected rank" 173 | } 174 | "HudTrackText" 175 | { 176 | "en" "Timer track" 177 | } 178 | "HudSplitPbText" 179 | { 180 | "en" "Split PB" 181 | } 182 | "HudMapTierText" 183 | { 184 | "en" "Map tier" 185 | } 186 | "HudTimeDifference" 187 | { 188 | "en" "Time Difference" 189 | } 190 | "HudTopLeftRankText" 191 | { 192 | "en" "Top left Rank" 193 | } 194 | "HudVelocityDifference" 195 | { 196 | "en" "Velocity Difference" 197 | } 198 | "HudDebugTargetname" 199 | { 200 | "en" "Debug targetname" 201 | } 202 | // ---------- Record Bots ---------- // 203 | "ReplayText" 204 | { 205 | "en" "Replay" 206 | } 207 | "NoReplayData" 208 | { 209 | "en" "No replay data loaded\nPress USE or beat #1 to play" 210 | } 211 | "NoReplayDataTF2" 212 | { 213 | "en" "No replay data loaded\n!replay or beat #1 to play" 214 | } 215 | // ---------- Panels ---------- // 216 | "SpectatorPersonal" 217 | { 218 | "en" "Spectators" 219 | } 220 | "SpectatorWatching" 221 | { 222 | "en" "Other Spectators" 223 | } 224 | // ---------- Commands ---------- // 225 | "HudEnabledComponent" 226 | { 227 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s}" 228 | "en" "{1}{2} {3}HUD setting {4}enabled{5}." 229 | } 230 | "HudDisabledComponent" 231 | { 232 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s}" 233 | "en" "{1}{2} {3}HUD setting {4}disabled{5}." 234 | } 235 | } 236 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-misc.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Commands ---------- // 4 | "CommandAlive" 5 | { 6 | "#format" "{1:s},{2:s}" 7 | "en" "You have to be {1}alive{2} to use this command." 8 | } 9 | "CommandAliveSpectate" 10 | { 11 | "#format" "{1:s},{2:s},{3:s},{4:s}" 12 | "en" "You have to be {1}alive{2} or {3}spectating a player{4} to use this command." 13 | } 14 | "CommandSaveCPKZInvalid" 15 | { 16 | "en" "You cannot perform this action when airborne or while watching another player." 17 | } 18 | "CommandSaveCPKZZone" 19 | { 20 | "en" "You cannot perform this action while in the start zone." 21 | } 22 | "CommandTeleCPInvalid" 23 | { 24 | "en" "You may not teleport to this checkpoint due to setting mismatch." 25 | } 26 | "CommandNoPause" 27 | { 28 | "#format" "{1:s},{2:s}" 29 | "en" "Your timer has to be {1}resumed{2} to use this command." 30 | } 31 | "CommandDisabled" 32 | { 33 | "#format" "{1:s},{2:s}" 34 | "en" "This command is {1}disabled{2}." 35 | } 36 | "FeatureDisabled" 37 | { 38 | "#format" "{1:s},{2:s}" 39 | "en" "This feature is {1}disabled{2}." 40 | } 41 | "HideEnabled" 42 | { 43 | "#format" "{1:s},{2:s}" 44 | "en" "You are now {1}hiding{2} players." 45 | } 46 | "HideDisabled" 47 | { 48 | "#format" "{1:s},{2:s}" 49 | "en" "You are now {1}not hiding{2} players." 50 | } 51 | "AutoRestartEnabled" 52 | { 53 | "#format" "{1:s},{2:s}" 54 | "en" "You will now {1}automatically restart{2} if you are slower than your PB." 55 | } 56 | "AutoRestartDisabled" 57 | { 58 | "#format" "{1:s},{2:s}" 59 | "en" "You will no longer {1}automatically restart{2}." 60 | } 61 | "AutoRestartTriggered1" 62 | { 63 | "#format" "{1:s},{2:s}" 64 | "en" "You were {1}automatically restarted{2} due to being slower than your PB." 65 | } 66 | "AutoRestartTriggered2" 67 | { 68 | "#format" "{1:s},{2:s}" 69 | "en" "Use {1}!autorestart{2} to disable this." 70 | } 71 | "LackingAccess" 72 | { 73 | "#format" "{1:s},{2:s}" 74 | "en" "You're {1}lacking access{2} to this command." 75 | } 76 | "SpectateDead" 77 | { 78 | "#format" "{1:s},{2:s}" 79 | "en" "You {1}cannot{2} target a dead player." 80 | } 81 | "SpectatorCount" 82 | { 83 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:i},{6:s},{7:s}" 84 | "en" "{1}{2}{3} has {4}{5}{6} spectators: {7}" 85 | } 86 | "SpectatorCountZero" 87 | { 88 | "#format" "{1:s},{2:N},{3:s}" 89 | "en" "No one is spectating {1}{2}{3}." 90 | } 91 | "SpectatorInvalid" 92 | { 93 | "en" "You should be alive or spectate someone to see your/their spectators." 94 | } 95 | "TeleportAlive" 96 | { 97 | "en" "You can teleport only if you are alive." 98 | } 99 | "TeleportInvalidTarget" 100 | { 101 | "en" "Invalid target." 102 | } 103 | "MiscCheckpointsSaved" 104 | { 105 | "#format" "{1:d},{2:s},{3:s}" 106 | "en" "Checkpoint ({1}) {2}saved{3}." 107 | } 108 | "MiscCheckpointsTeleported" 109 | { 110 | "#format" "{1:d},{2:s},{3:s}" 111 | "en" "{2}Teleported{3} to checkpoint ({1})." 112 | } 113 | "MiscCheckpointsEmpty" 114 | { 115 | "#format" "{1:d},{2:s},{3:s}" 116 | "en" "Checkpoint {1} is {2}empty{3}." 117 | } 118 | "MiscCheckpointsOverflow" 119 | { 120 | "en" "Unable to save due to checkpoint overflow." 121 | } 122 | "MiscCheckpointOwnerInvalid" 123 | { 124 | "en" "The checkpoint's owner is invalid or has disconnected." 125 | } 126 | "MiscSegmentedCommand" 127 | { 128 | "#format" "{1:s},{2:s}" 129 | "en" "Use {1}!cp{2} to re-open the checkpoints menu." 130 | } 131 | // ---------- Menus ---------- // 132 | "StopTimerWarning" 133 | { 134 | "en" "Are you sure you want to stop your timer?" 135 | } 136 | "StopTimerYes" 137 | { 138 | "en" "Yes, stop my timer." 139 | } 140 | "StopTimerNo" 141 | { 142 | "en" "No, keep my timer running." 143 | } 144 | "ClearCPWarning" 145 | { 146 | "en" "Are you sure you want to clear your checkpoints?" 147 | } 148 | "ClearCPYes" 149 | { 150 | "en" "Yes, and I know this action cannot be reversed." 151 | } 152 | "ClearCPNo" 153 | { 154 | "en" "No." 155 | } 156 | "MiscCheckpointNoOtherPlayers" 157 | { 158 | "en" "You are alone (also, the server is empty)" 159 | } 160 | "TeleportMenuTitle" 161 | { 162 | "en" "Teleport to:" 163 | } 164 | "WeaponAlive" 165 | { 166 | "#format" "{1:s},{2:s}" 167 | "en" "You need to be {1}alive{2} to spawn weapons." 168 | } 169 | "MiscCheckpointMenu" 170 | { 171 | "en" "Checkpoints" 172 | } 173 | "MiscCheckpointMenuSegmented" 174 | { 175 | "en" "Segmented Checkpoints" 176 | } 177 | "MiscCheckpointWarning" 178 | { 179 | "en" "WARNING: Teleporting will stop your timer!" 180 | } 181 | "MiscCheckpointSave" 182 | { 183 | "#format" "{1:d},{2:d}" 184 | "en" "Save checkpoint ({1}/{2})" 185 | } 186 | "MiscCheckpointDuplicate" 187 | { 188 | "#format" "{1:d},{2:d}" 189 | "en" "Duplicate checkpoint ({1}/{2})" 190 | } 191 | "MiscCheckpointTeleport" 192 | { 193 | "#format" "{1:d}" 194 | "en" "Teleport to checkpoint ({1})" 195 | } 196 | "MiscCheckpointPrevious" 197 | { 198 | "en" "Previous" 199 | } 200 | "MiscCheckpointNext" 201 | { 202 | "en" "Next" 203 | } 204 | "MiscCheckpointUseOthers" 205 | { 206 | "en" "Use another player's checkpoints" 207 | } 208 | "MiscCheckpointBack" 209 | { 210 | "en" "Back to your checkpoints" 211 | } 212 | "MiscCheckpointReset" 213 | { 214 | "en" "Reset checkpoints" 215 | } 216 | "MiscCheckpointDeleteCurrent" 217 | { 218 | "en" "Delete current checkpoint" 219 | } 220 | "MiscCheckpointPause" 221 | { 222 | "en" "Pause" 223 | } 224 | "MiscCheckpointUseAngles" 225 | { 226 | "en" "Use angles" 227 | } 228 | "MiscCheckpointUseVelocity" 229 | { 230 | "en" "Use velocity" 231 | } 232 | "TasSettings" 233 | { 234 | "en" "TAS Settings" 235 | } 236 | "Autostrafer" 237 | { 238 | "en" "Autostrafer" 239 | } 240 | "AutoJumpOnStart" 241 | { 242 | "en" "Jump on start-zone exit" 243 | } 244 | "EdgeJump" 245 | { 246 | "en" "Edge jump" 247 | } 248 | "AutogainBasicStrafer" 249 | { 250 | "en" "Autogain basic strafer" 251 | } 252 | "AutoPrestrafe" 253 | { 254 | "en" "Auto Prestrafe" 255 | } 256 | "Autostrafer_type" 257 | { 258 | "en" "Type" 259 | } 260 | "Autostrafer_1tick" 261 | { 262 | "en" "1Tick (xutaxkamay)" 263 | } 264 | "Autostrafer_autogain" 265 | { 266 | "en" "Velocity/autogain (oblivious)" 267 | } 268 | "Autostrafer_autogain_nsl" 269 | { 270 | "en" "Velocity/autogain (No speed loss) (oblivious)" 271 | } 272 | "Autostrafer_basic" 273 | { 274 | "en" "Basic" 275 | } 276 | "TASEnabled" 277 | { 278 | "en" "Enabled" 279 | } 280 | "TASDisabled" 281 | { 282 | "en" "Disabled" 283 | } 284 | "AutostrafeOverride" 285 | { 286 | "en" "Key Override" 287 | } 288 | "AutostrafeOverride_Normal" 289 | { 290 | "en" "W/S" 291 | } 292 | "AutostrafeOverride_Surf" 293 | { 294 | "en" "W/S (and A/D on surf ramps)" 295 | } 296 | "AutostrafeOverride_Surf_W_Okay" 297 | { 298 | "en" "S (and A/D on surf ramps)" 299 | } 300 | "AutostrafeOverride_All" 301 | { 302 | "en" "W/S A/D" 303 | } 304 | // ---------- Misc ---------- // 305 | "BHStartZoneDisallowed" 306 | { 307 | "#format" "{1:s},{2:s},{3:s},{4:s}" 308 | "en" "Bunnyhopping in the {1}start zone{2} is {3}not allowed{4}." 309 | } 310 | "WRNotice" 311 | { 312 | "#format" "{1:s},{2:s}" 313 | "en" "{1}NEW {2} WR!!!" 314 | } 315 | "AdvertisementsEnabled" 316 | { 317 | "en" "Advertisements enabled" 318 | } 319 | "AdvertisementsDisabled" 320 | { 321 | "en" "Advertisements disabled" 322 | } 323 | } 324 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-rankings.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Commands ---------- // 4 | "CurrentTier" 5 | { 6 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:d},{6:s}" 7 | "en" "{1}{2}{3} is tier {4}{5}{6}." 8 | } 9 | "SetTier" 10 | { 11 | "#format" "{1:s},{2:d},{3:s}" 12 | "en" "Tier changed to {1}{2}{3}." 13 | } 14 | "Rank" 15 | { 16 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:d},{6:s},{7:d},{8:s},{9:.1f},{10:s}" 17 | "en" "{1}{2}{3} is ranked {4}{5}{6} out of {7} with {8}{9}{10} points." 18 | } 19 | "Unranked" 20 | { 21 | "#format" "{1:s},{2:N},{3:s}" 22 | "en" "{1}{2}{3} is unranked." 23 | } 24 | // ---------- Menus ---------- // 25 | "Top100" 26 | { 27 | "en" "Top 100 ranked players:" 28 | } 29 | "NoRankedPlayers" 30 | { 31 | "en" "No ranked players found." 32 | } 33 | } -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-replay.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Menus ---------- // 4 | "DeleteReplayAdminMenu" 5 | { 6 | "en" "Delete replay" 7 | } 8 | "DeleteReplayMenuTitle" 9 | { 10 | "en" "Delete a replay:" 11 | } 12 | "MenuResponseNo" 13 | { 14 | "en" "NO!" 15 | } 16 | "MenuResponseYes" 17 | { 18 | "en" "Yes, I understand this action cannot be reversed!" 19 | } 20 | "ReplayDeletionConfirmation" 21 | { 22 | "#format" "{1:s}" 23 | "en" "Confirm deletion of {1} replay?" 24 | } 25 | "ReplaysUnavailable" 26 | { 27 | "en" "No replays available." 28 | } 29 | // ---------- Replay Deletion ---------- // 30 | "ReplayDeleted" 31 | { 32 | "#format" "{1:s},{2:s},{3:s}" 33 | "en" "Deleted replay for {1}{2}{3}." 34 | } 35 | "ReplayDeleteFailure" 36 | { 37 | "#format" "{1:s},{2:s},{3:s}" 38 | "en" "Could not delete replay for {1}{2}{3}." 39 | } 40 | // ---------- Central Replay Menu ---------- // 41 | "CentralReplayTitle" 42 | { 43 | "en" "Select a replay style to play:" 44 | } 45 | "CentralReplayPlaying" 46 | { 47 | "en" "The replay bot is busy, try again when it's idle." 48 | } 49 | "CentralReplayStop" 50 | { 51 | "en" "Stop the current replay." 52 | } 53 | "CentralReplayStopped" 54 | { 55 | "en" "Forcibly stopped replay." 56 | } 57 | "CentralReplayTrack" 58 | { 59 | "en" "Select a track to play:" 60 | } 61 | "Replay_Central" 62 | { 63 | "en" "!replay" 64 | } 65 | "Replay_Dynamic" 66 | { 67 | "en" "Dynamic" 68 | } 69 | "Replay_Looping" 70 | { 71 | "en" "Looping" 72 | } 73 | "Menu_ReplayBotType" 74 | { 75 | "en" "Replay bot type:" 76 | } 77 | "Menu_Replay_Central" 78 | { 79 | "en" "Central !replay bot" 80 | } 81 | "Menu_Replay_Dynamic" 82 | { 83 | "en" "Spawn dynamic bot" 84 | } 85 | "Menu_Replay_Prop" 86 | { 87 | "en" "Spawn physics prop bot" 88 | } 89 | "TooManyDynamicBots" 90 | { 91 | "en" "Too many dynamic bots are playing. Can't spawn more." 92 | } 93 | "FailedToCreateReplay" 94 | { 95 | "en" "Failed to create replay" 96 | } 97 | "Menu_Replay" 98 | { 99 | "en" "Replay" 100 | } 101 | "Menu_SpawnReplay" 102 | { 103 | "en" "Spawn replay" 104 | } 105 | "Menu_Replay2X" 106 | { 107 | "#format" "{1:s}" 108 | "en" "[{1}] Toggle 2x speed" 109 | } 110 | "Menu_PlaybackSpeed" 111 | { 112 | "#format" "{1:.1f}" 113 | "en" "Playback speed: {1}x" 114 | } 115 | "Menu_RefreshReplay" 116 | { 117 | "en" "Refresh" 118 | } 119 | } 120 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-stats.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Errors ---------- // 4 | "StatsMenuFailure" 5 | { 6 | "#format" "{1:s},{2:s}" 7 | "en" "{1}ERROR: {2}Could not open the stats menu." 8 | } 9 | "StatsMenuUnknownPlayer" 10 | { 11 | "#format" "{1:s},{2:s},{3:s},{4:d}" 12 | "en" "{1}ERROR: {2}Unknown player {3}[U:1:{4}]" 13 | } 14 | // ---------- Map Completions ---------- // 15 | "SelectTrack" 16 | { 17 | "en" "Select timer track:" 18 | } 19 | "MapsDone" 20 | { 21 | "en" "Maps done" 22 | } 23 | "MapsDoneFor" 24 | { 25 | "#format" "{1:s},{2:s},{3:d}" 26 | "en" "[{1}] Maps done for {2}: ({3})" 27 | } 28 | "MapsDoneOnStyle" 29 | { 30 | "#format" "{1:s}" 31 | "en" "Maps done for {1} on style:" 32 | } 33 | "MapsLeft" 34 | { 35 | "en" "Maps left" 36 | } 37 | "MapsLeftFor" 38 | { 39 | "#format" "{1:s},{2:s},{3:d}" 40 | "en" "[{1}] Maps left for {2}: ({3})" 41 | } 42 | "MapsLeftOnStyle" 43 | { 44 | "#format" "{1:s}" 45 | "en" "Maps left for {1} on style:" 46 | } 47 | "MapsMenu" 48 | { 49 | "#format" "{1:s}" 50 | "en" "[{1}] Stats:" 51 | } 52 | "MapsPoints" 53 | { 54 | "en" "points" 55 | } 56 | "MapsJumps" 57 | { 58 | "en" "jumps" 59 | } 60 | "Nope" 61 | { 62 | "en" "nope" 63 | } 64 | "NoResults" 65 | { 66 | "en" "No results." 67 | } 68 | // ---------- Player Profiles ---------- // 69 | "Country" 70 | { 71 | "en" "Country" 72 | } 73 | "LastLogin" 74 | { 75 | "en" "Last Login" 76 | } 77 | "FirstLogin" 78 | { 79 | "en" "First Login" 80 | } 81 | "MapCompletions" 82 | { 83 | "en" "Map completions" 84 | } 85 | "NoRecords" 86 | { 87 | "en" "Nothing." 88 | } 89 | "Rank" 90 | { 91 | "en" "Rank" 92 | } 93 | "Playtime" 94 | { 95 | "en" "Play time" 96 | } 97 | "YourPlaytime" 98 | { 99 | "en" "Yours" 100 | } 101 | "Points" 102 | { 103 | "en" "Points" 104 | } 105 | "PointsUnranked" 106 | { 107 | "en" "Unranked" 108 | } 109 | "Profile" 110 | { 111 | "en" "profile" 112 | } 113 | "WorldRecords" 114 | { 115 | "en" "World records" 116 | } 117 | // ---------- Record Data ---------- // 118 | "Date" 119 | { 120 | "en" "Date" 121 | } 122 | "Jumps" 123 | { 124 | "en" "Jumps" 125 | } 126 | "Strafes" 127 | { 128 | "en" "Strafes" 129 | } 130 | "Style" 131 | { 132 | "en" "Style" 133 | } 134 | "Time" 135 | { 136 | "en" "Time" 137 | } 138 | } 139 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-wr.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Commands ---------- // 4 | "DeletionAborted" 5 | { 6 | "en" "Aborted deletion." 7 | } 8 | "DeletedRecord" 9 | { 10 | "en" "Deleted record." 11 | } 12 | "DeletedRecordsMap" 13 | { 14 | "#format" "{1:s},{2:s},{3:s}" 15 | "en" "Deleted ALL records for {1}{2}{3}." 16 | } 17 | "DeletedRecordsStyle" 18 | { 19 | "#format" "{1:s},{2:s},{3:s}" 20 | "en" "Deleted ALL records for {1}{2}{3}." 21 | } 22 | // ---------- Client Menus ---------- // 23 | "ListClientRecords" 24 | { 25 | "#format" "{1:s},{2:s}" 26 | "en" "Records for {1}:\n({2})" 27 | } 28 | "ListPersonalBest" 29 | { 30 | "#format" "{1:s},{2:s}" 31 | "en" "Personal best for {1} on {2}" 32 | } 33 | // ---------- Completion Messages ---------- // 34 | "FirstCompletion" 35 | { 36 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:s},{6:s},{7:s},{8:s},{9:s},{10:s},{11:d},{12:s},{13:d},{14:d},{15:s},{16:s}" 37 | "en" "{1}{2}{3} finished ({4}{5}{6}) in {7}{8}{9} ({10}#{11}{12}) with {13} jumps, {14} strafes{15}{16}." 38 | } 39 | "NotFirstCompletion" 40 | { 41 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:s},{6:s},{7:s},{8:s},{9:s},{10:s},{11:d},{12:s},{13:d},{14:d},{15:s},{16:s},{17:s},{18:s}" 42 | "en" "{1}{2}{3} finished ({4}{5}{6}) in {7}{8}{9} ({10}#{11}{12}) with {13} jumps, {14} strafes{15}{16} {17}(-{18})" 43 | } 44 | "NotFirstCompletionWorse" 45 | { 46 | "#format" "{1:s},{2:N},{3:s},{4:s},{5:s},{6:s},{7:s},{8:s},{9:s},{10:s},{11:d},{12:s},{13:d},{14:d},{15:s},{16:s},{17:s}" 47 | "en" "{1}{2}{3} finished ({4}{5}{6}) in {7}{8}{9} ({10}#{11}{12}) with {13} jumps, {14} strafes{15}{16} (+{17})" 48 | } 49 | "WorseTime" 50 | { 51 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s},{6:s},{7:d},{8:d},{9:s},{10:s},{11:s}" 52 | "en" "You have finished ({1}{2}{3}) in {4}{5}{6} with {7} jumps, {8} strafes{9}{10} (+{11})" 53 | } 54 | "UnrankedTime" 55 | { 56 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s},{6:s},{7:d},{8:d},{9:s},{10:s}" 57 | "en" "You have finished ({1}{2}{3}) in {4}{5}{6} with {7} jumps, {8} strafes{9}{10}." 58 | } 59 | "CompletionExtraInfo" 60 | { 61 | "#format" "{1:s},{2:.2f},{3:s},{4:s},{5:.2f},{6:s},{7:s},{8:.1f},{9:s}" 62 | "en" "Avg/Max Spd: {1}{2}{3}/{4}{5}{6}. Perfs: {7}{8}{9}%%." 63 | } 64 | // ---------- Deletion Menus ---------- // 65 | "DeleteAllRecords" 66 | { 67 | "en" "Delete ALL map records" 68 | } 69 | "DeleteAllRecordsMenuTitle" 70 | { 71 | "#format" "{1:s},{2:s},{3:s}" 72 | "en" "Delete ALL the records for '{1}'? (Track: {2} | Style: {3})" 73 | } 74 | "DeleteConfirm" 75 | { 76 | "en" "Are you sure?" 77 | } 78 | "DeleteMenuTitle" 79 | { 80 | "en" "Delete a record from:" 81 | } 82 | "DeleteSingleRecord" 83 | { 84 | "en" "Delete a single record" 85 | } 86 | "MenuResponseNo" 87 | { 88 | "en" "NO!" 89 | } 90 | "MenuResponseYesSingle" 91 | { 92 | "en" "YES!!! DELETE THE RECORD!!!" 93 | } 94 | "MenuResponseYes" 95 | { 96 | "en" "YES!!! DELETE ALL THE RECORDS!!! THIS ACTION IS IRREVERSIBLE!" 97 | } 98 | "DeleteStyleRecordsRecordsMenuTitle" 99 | { 100 | "#format" "{1:s}" 101 | "en" "Choose a style to delete all the records for '{1}':" 102 | } 103 | "DeleteConfirmStyle" 104 | { 105 | "#format" "{1:s}" 106 | "en" "Are you sure you want to delete ALL THE RECORDS for {1}?" 107 | } 108 | "MenuResponseYesStyle" 109 | { 110 | "#format" "{1:s}" 111 | "en" "YES!!! DELETE THE RECORDS FOR {1}!!! THIS ACTION IS IRREVERSIBLE!" 112 | } 113 | "DeleteTrackSingle" 114 | { 115 | "en" "Choose a track to delete a single record from:" 116 | } 117 | "DeleteTrackAll" 118 | { 119 | "en" "Choose a track to delete a ALL records from:" 120 | } 121 | "DeleteTrackAllStyle" 122 | { 123 | "#format" "{1:s}" 124 | "en" "Choose a style to delete all the records for ({1}):" 125 | } 126 | // ---------- Errors ---------- // 127 | "DatabaseError" 128 | { 129 | "en" "Database error" 130 | } 131 | "Error" 132 | { 133 | "en" "ERROR" 134 | } 135 | "NoStyles" 136 | { 137 | "#format" "{1:s},{2:s}" 138 | "en" "{1}FATAL ERROR: {2}No styles are available. Contact the server owner immediately!" 139 | } 140 | "NoPB" 141 | { 142 | "#format" "{1:s},{2:s},{3:s},{4:s},{5:s},{6:s}" 143 | "en" "No PB records were found for {1}{2}{3} on map {4}{5}{6}." 144 | } 145 | // ---------- RR Menu ---------- // 146 | "RecentRecords" 147 | { 148 | "#format" "{1:d}" 149 | "en" "Recent {1} record(s)" 150 | } 151 | "RecentRecordsFirstMenuTitle" 152 | { 153 | "en" "Recent records" 154 | } 155 | "RecentRecordsStyleSelectionMenuTitle" 156 | { 157 | "en" "Recent records (by style)" 158 | } 159 | "RecentRecordsAll" 160 | { 161 | "en" "All recent records" 162 | } 163 | "RecentRecordsByStyle" 164 | { 165 | "en" "Sorted by style" 166 | } 167 | "RecentRecordsMainOnly" 168 | { 169 | "en" "Main only" 170 | } 171 | // ---------- WR Menu ---------- // 172 | "WRDate" 173 | { 174 | "en" "Date" 175 | } 176 | "WRJump" 177 | { 178 | "en" "jump" 179 | } 180 | "WRJumps" 181 | { 182 | "en" "Jumps" 183 | } 184 | "WRMap" 185 | { 186 | "#format" "{1:s}" 187 | "en" "Records for {1}" 188 | } 189 | "WRMapNoRecords" 190 | { 191 | "en" "No records found." 192 | } 193 | "WRMenuTitle" 194 | { 195 | "en" "Choose a style:" 196 | } 197 | "WRPoints" 198 | { 199 | "en" "points" 200 | } 201 | "WRPlayerStats" 202 | { 203 | "en" "Player stats" 204 | } 205 | "WRDeleteRecord" 206 | { 207 | "en" "Delete record" 208 | } 209 | "WRPointsCap" 210 | { 211 | "en" "Points" 212 | } 213 | "WRRecord" 214 | { 215 | "en" "records" 216 | } 217 | "WRRecordFor" 218 | { 219 | "en" "Records for" 220 | } 221 | "WRStrafes" 222 | { 223 | "en" "Strafes" 224 | } 225 | "WRCompletions" 226 | { 227 | "en" "Completions" 228 | } 229 | "WRStyle" 230 | { 231 | "en" "Style" 232 | } 233 | "WRStyleNothing" 234 | { 235 | "en" "Nothing." 236 | } 237 | "WRTime" 238 | { 239 | "en" "Time" 240 | } 241 | // ---------- Messages ---------- // 242 | "WRStageTime" 243 | { 244 | "#format" "{1:s},{2:s},{3:d},{4:s},{5:s},{6:s},{7:s},{8:s},{9:s},{10:s}" 245 | "en" "{1}You have reached stage {2}{3}{4} with a time of {5}{6}{7} (WR {8}{9}{10})." 246 | } 247 | } 248 | -------------------------------------------------------------------------------- /addons/sourcemod/translations/shavit-zones.phrases.txt: -------------------------------------------------------------------------------- 1 | "Phrases" 2 | { 3 | // ---------- Admin Menu ---------- // 4 | "AddMapZone" 5 | { 6 | "en" "Add map zone" 7 | } 8 | "DeleteAllMapZone" 9 | { 10 | "en" "Delete ALL map zones" 11 | } 12 | "DeleteMapZone" 13 | { 14 | "en" "Delete map zone" 15 | } 16 | // --------- Set Start --------- // 17 | "SetStart" 18 | { 19 | "#format" "{1:s},{2:s}" 20 | "en" "Start position has been {1}set{2}." 21 | } 22 | "SetStartCommandAlive" 23 | { 24 | "#format" "{1:s},{2:s}" 25 | "en" "You have to be {1}alive{2} to set your start position." 26 | } 27 | "DeleteSetStart" 28 | { 29 | "#format" "{1:s},{2:s}" 30 | "en" "Start position has been {1}deleted{2}." 31 | } 32 | "DeleteSetStartMenuTitle" 33 | { 34 | "en" "Start position to delete" 35 | } 36 | // ---------- ZoneHook ---------- // 37 | "ZoneHook_Crosshair" 38 | { 39 | "en" "Entity under crosshair" 40 | } 41 | "ZoneHook_Tpto" 42 | { 43 | "en" "Teleport to (stops timer)" 44 | } 45 | "ZoneHook_Draw" 46 | { 47 | "en" "Draw beams around entity" 48 | } 49 | "ZoneHook_Zonetype" 50 | { 51 | "#format" "{1:s}" 52 | "en" "Zone type: {1}" 53 | } 54 | "ZoneHook_Hooktype" 55 | { 56 | "#format" "{1:s},{2:s}" 57 | "en" "Hook type: {1} ({2})" 58 | } 59 | "ZoneHook_Confirm" 60 | { 61 | "en" "Go to confirm" 62 | } 63 | // ---------- Commands ---------- // 64 | "StageCommandAlive" 65 | { 66 | "#format" "{1:s},{2:s}" 67 | "en" "You have to be {1}alive{2} to use this command." 68 | } 69 | "ModifierCommandNoArgs" 70 | { 71 | "en" "Usage: sm_modifier " 72 | } 73 | "ModifierTooLow" 74 | { 75 | "en" "Modifier must be higher than 0." 76 | } 77 | "ModifierSet" 78 | { 79 | "en" "Modifier set to" 80 | } 81 | "ZonesCommand" 82 | { 83 | "#format" "{1:s},{2:s}" 84 | "en" "You {1}cannot{2} setup mapzones when you're dead." 85 | } 86 | "ZonesNotSQL" 87 | { 88 | "#format" "{1:s},{2:s}" 89 | "en" "You {1}cannot{2} add/edit/delete non-sql zones." 90 | } 91 | "ZoneCustomSpawnMenuTitle" 92 | { 93 | "en" "Add custom spawn for track:" 94 | } 95 | "ZoneCustomSpawnMenuDeleteTitle" 96 | { 97 | "en" "Delete custom spawn for track:" 98 | } 99 | "ZoneCustomSpawnExists" 100 | { 101 | "#format" "{1:s},{2:s},{3:s}" 102 | "en" "Custom Spawn for track {1}{2}{3} already exists. Please delete it before placing a new one." 103 | } 104 | "ZoneCustomSpawnMissing" 105 | { 106 | "#format" "{1:s},{2:s},{3:s}" 107 | "en" "Custom Spawn for track {1}{2}{3} is missing." 108 | } 109 | "ZoneCustomSpawnDelete" 110 | { 111 | "en" "Deleted Custom Spawn successfully." 112 | } 113 | "ZoneDead" 114 | { 115 | "en" "You can't place zones when you're dead." 116 | } 117 | // ---------- Panel Text ---------- // 118 | "AbortZoneCreation" 119 | { 120 | "en" "Abort zone creation" 121 | } 122 | "GridSnapPlus" 123 | { 124 | "#format" "{1:d}" 125 | "en" "Grid snap + (x{1})" 126 | } 127 | "GridSnapMinus" 128 | { 129 | "en" "Grid snap -" 130 | } 131 | "WallSnap" 132 | { 133 | "#format" "{1:T}" 134 | "en" "Snap to wall: {1}" 135 | } 136 | "CursorZone" 137 | { 138 | "#format" "{1:T}" 139 | "en" "Use cursor position: {1}" 140 | } 141 | // ---------- Zone Menu ---------- // 142 | "ZoneAdjustCancel" 143 | { 144 | "en" "Cancel" 145 | } 146 | "ZoneAdjustDone" 147 | { 148 | "en" "Done!" 149 | } 150 | "ZoneAdjustPosition" 151 | { 152 | "en" "Adjust the zone's position.\nUse 'sm_modifier ' to set a new modifier." 153 | } 154 | "ZoneAxis" 155 | { 156 | "en" "Change Axis" 157 | } 158 | "ZoneCustomSpawnSuccess" 159 | { 160 | "en" "Successfully placed custom spawn!" 161 | } 162 | "ZoneDecreased" 163 | { 164 | "en" "decreased" 165 | } 166 | "ZoneEditConfirm" 167 | { 168 | "en" "Confirm?" 169 | } 170 | "ZoneDeleteSuccessful" 171 | { 172 | "#format" "{1:s},{2:s},{3:s}" 173 | "en" "Deleted {1}{2}{3} successfully." 174 | } 175 | "ZoneDeleteAllSuccessful" 176 | { 177 | "en" "Deleted all map zones successfully" 178 | } 179 | "ZoneFirst" 180 | { 181 | "en" "FIRST" 182 | } 183 | "ZoneIncreased" 184 | { 185 | "en" "increased" 186 | } 187 | "ZoneMenuDeleteTitle" 188 | { 189 | "en" "Delete a zone:\nPressing a zone will delete it. This action CANNOT BE REVERTED!" 190 | } 191 | "ZoneMenuDeleteALLTitle" 192 | { 193 | "en" "Delete ALL mapzones?\nPressing 'Yes' will delete all the existing mapzones for this map.\nThis action CANNOT BE REVERTED!" 194 | } 195 | "ZoneMenuNo" 196 | { 197 | "en" "NO!" 198 | } 199 | "ZonesMenuNoneFound" 200 | { 201 | "en" "No zones found." 202 | } 203 | "ZoneMenuStage" 204 | { 205 | "en" "Select A Stage:" 206 | } 207 | "ZoneMenuTrack" 208 | { 209 | "en" "Select a track:" 210 | } 211 | "ZoneMenuTitle" 212 | { 213 | "#format" "{1:s}" 214 | "en" "Select a zone type: ({1})" 215 | } 216 | "ZoneMenuYes" 217 | { 218 | "en" "YES!!! DELETE ALL THE MAPZONES!!!" 219 | } 220 | "ZonePlaceText" 221 | { 222 | "#format" "{1:s}" 223 | "en" "Press USE (default 'E') to set the {1} corner in your current position." 224 | } 225 | "ZonePlaceTextTF2" 226 | { 227 | "#format" "{1:s}" 228 | "en" "Press ATTACK2 (default 'right click') to set the {1} corner in your current position." 229 | } 230 | "ZonePoint" 231 | { 232 | "#format" "{1:d},{2:c}" 233 | "en" "Point {1} | {2} axis" 234 | } 235 | "ZoneSecond" 236 | { 237 | "en" "SECOND" 238 | } 239 | "ZoneSetAdjust" 240 | { 241 | "en" "Adjust position" 242 | } 243 | "ZoneForceRender" 244 | { 245 | "#format" "{1:s}" 246 | "en" "[{1}] Force zone drawing" 247 | } 248 | "ZoneSetAiraccelerate" 249 | { 250 | "#format" "{1:d}" 251 | "en" "Airaccelerate: {1}" 252 | } 253 | "ZoneSetSpeedLimit" 254 | { 255 | "#format" "{1:d}" 256 | "en" "Custom speed limit: {1}" 257 | } 258 | "ZoneSetSpeedLimitUnlimited" 259 | { 260 | "#format" "{1:d}" 261 | "en" "Custom speed limit: {1} (No Limit)" 262 | } 263 | "ZoneSetSpeedLimitDefault" 264 | { 265 | "#format" "{1:d}" 266 | "en" "Custom speed limit: {1} (Default Speedcap)" 267 | } 268 | "ZoneSetStage" 269 | { 270 | "#format" "{1:d}" 271 | "en" "Stage: {1}" 272 | } 273 | "ZoneSetGravity" 274 | { 275 | "#format" "{1:f}" 276 | "en" "Gravity scale: {1}" 277 | } 278 | "ZoneSetSpeedmod" 279 | { 280 | "#format" "{1:f}" 281 | "en" "Speedmod: {1}" 282 | } 283 | "ZoneEnterDataChat" 284 | { 285 | "en" "Input your desired data in chat." 286 | } 287 | "ZoneSetNo" 288 | { 289 | "en" "No" 290 | } 291 | "ZoneSetTP" 292 | { 293 | "en" "Yes (choose teleport destination first)" 294 | } 295 | "ZoneSetTPZone" 296 | { 297 | "en" "Update teleport destination" 298 | } 299 | "ZoneSetYes" 300 | { 301 | "en" "Yes" 302 | } 303 | "ZoneSizeIncrease" 304 | { 305 | "#format" "{1:s},{2:c},{3:s},{4:d},{5:s},{6:.01f},{7:s}" 306 | "en" "{1}{2} axis{3} (point {4}) increased by {5}{6}{7}." 307 | } 308 | "ZoneSizeDecrease" 309 | { 310 | "#format" "{1:s},{2:c},{3:s},{4:d},{5:s},{6:.01f},{7:s}" 311 | "en" "{1}{2} axis{3} (point {4}) decreased by {5}{6}{7}." 312 | } 313 | "ZoneTeleportUpdated" 314 | { 315 | "en" "Teleport destination updated." 316 | } 317 | "ZoneTeleportInsideZone" 318 | { 319 | "en" "You may not place the destination inside the zone." 320 | } 321 | "ZoneEditTrack" 322 | { 323 | "#format" "{1:s}" 324 | "en" "Zone track: {1}" 325 | } 326 | "ZoneEdit" 327 | { 328 | "en" "Edit a map zone" 329 | } 330 | "HookZone" 331 | { 332 | "en" "Hook a trigger, teleporter, or button." 333 | } 334 | "HookZone2" 335 | { 336 | "#format" "{1:s}" 337 | "en" "Hook {1}" 338 | } 339 | "ZoneEditTitle" 340 | { 341 | "en" "Choose a zone to edit:" 342 | } 343 | "ZoneInside" 344 | { 345 | "en" "(Inside!)" 346 | } 347 | "ZoneEditRefresh" 348 | { 349 | "en" "Refresh menu" 350 | } 351 | "TpToZone" 352 | { 353 | "en" "Teleport to a zone" 354 | } 355 | // ---------- Custom Zone ---------- // 356 | "CustomZone_MainMenuTitle" 357 | { 358 | "en" "Select the zone you want to customize" 359 | } 360 | "CustomZone_SubMenuTitle" 361 | { 362 | "#format" "{1:s},{2:s}" 363 | "en" "Customizing {1} - {2}" 364 | } 365 | "CustomZone_DisplayType" 366 | { 367 | "en" "Zone display type" 368 | } 369 | "CustomZone_Color" 370 | { 371 | "en" "Zone color" 372 | } 373 | "CustomZone_Width" 374 | { 375 | "en" "Zone width" 376 | } 377 | "CustomZone_Default" 378 | { 379 | "en" "Default" 380 | } 381 | 382 | "CustomZone_DisplayType_None" 383 | { 384 | "en" "None" 385 | } 386 | "CustomZone_DisplayType_Box" 387 | { 388 | "en" "Box" 389 | } 390 | "CustomZone_DisplayType_Flat" 391 | { 392 | "en" "Flat" 393 | } 394 | 395 | "CustomZone_Color_White" 396 | { 397 | "en" "White" 398 | } 399 | "CustomZone_Color_Red" 400 | { 401 | "en" "Red" 402 | } 403 | "CustomZone_Color_Orange" 404 | { 405 | "en" "Orange" 406 | } 407 | "CustomZone_Color_Yellow" 408 | { 409 | "en" "Yellow" 410 | } 411 | "CustomZone_Color_Green" 412 | { 413 | "en" "Green" 414 | } 415 | "CustomZone_Color_Cyan" 416 | { 417 | "en" "Cyan" 418 | } 419 | "CustomZone_Color_Blue" 420 | { 421 | "en" "Blue" 422 | } 423 | "CustomZone_Color_Purple" 424 | { 425 | "en" "Purple" 426 | } 427 | "CustomZone_Color_Pink" 428 | { 429 | "en" "Pink" 430 | } 431 | 432 | "CustomZone_Width_UltraThin" 433 | { 434 | "en" "Ultra thin" 435 | } 436 | "CustomZone_Width_Thin" 437 | { 438 | "en" "Thin" 439 | } 440 | "CustomZone_Width_Normal" 441 | { 442 | "en" "Normal" 443 | } 444 | "CustomZone_Width_Thick" 445 | { 446 | "en" "Thick" 447 | } 448 | // ---------- Messages ---------- // 449 | "ZoneSlayEnter" 450 | { 451 | "#format" "{1:s},{2:s},{3:s}" 452 | "en" "{1}You have been slain for entering a {2}glitch zone{3}." 453 | } 454 | "ZoneStopEnter" 455 | { 456 | "#format" "{1:s},{2:s},{3:s}" 457 | "en" "{1}Your timer has been stopped for entering a {2}glitch zone{3}." 458 | } 459 | "ZoneStageEnter" 460 | { 461 | "#format" "{1:s},{2:s},{3:d},{4:s},{5:s},{6:s}{7:s}" 462 | "en" "{1}Stage {2}{3}{4} @ {5}{6}{7} " 463 | } 464 | "Zone_Start" 465 | { 466 | "en" "Start zone" 467 | } 468 | "Zone_End" 469 | { 470 | "en" "End zone" 471 | } 472 | "Zone_Respawn" 473 | { 474 | "en" "Glitch Zone (Respawn Player)" 475 | } 476 | "Zone_Stop" 477 | { 478 | "en" "Glitch Zone (Stop Timer)" 479 | } 480 | "Zone_Slay" 481 | { 482 | "en" "Slay Player" 483 | } 484 | "Zone_Freestyle" 485 | { 486 | "en" "Freestyle Zone" 487 | } 488 | "Zone_CustomSpeedLimit" 489 | { 490 | "en" "Custom Speed Limit" 491 | } 492 | "Zone_Teleport" 493 | { 494 | "en" "Teleport Zone" 495 | } 496 | "Zone_CustomSpawn" 497 | { 498 | "en" "SPAWN POINT" 499 | } 500 | "Zone_Easybhop" 501 | { 502 | "en" "Easybhop Zone" 503 | } 504 | "Zone_Slide" 505 | { 506 | "en" "Slide Zone" 507 | } 508 | "Zone_Airaccelerate" 509 | { 510 | "en" "Custom Airaccelerate" 511 | } 512 | "Zone_Stage" 513 | { 514 | "en" "Stage Zone" 515 | } 516 | "Zone_NoTimerGravity" 517 | { 518 | "en" "No Timer Gravity Zone" 519 | } 520 | "Zone_Gravity" 521 | { 522 | "en" "Gravity Zone" 523 | } 524 | "Zone_Speedmod" 525 | { 526 | "en" "Speedmod Zone" 527 | } 528 | "Zone_NoJump" 529 | { 530 | "en" "No Jump Zone" 531 | } 532 | "Zone_Autobhop" 533 | { 534 | "en" "Autobhop Zone" 535 | } 536 | "Zone_Unknown" 537 | { 538 | "en" "UNKNOWN ZONE" 539 | } 540 | } 541 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_blueblocks.cfg: -------------------------------------------------------------------------------- 1 | ;; removes empty classname entity that crashes servers 2 | filter: 3 | { 4 | "hammerid" "396" 5 | } 6 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_classicpillars.cfg: -------------------------------------------------------------------------------- 1 | remove: 2 | { 3 | "targetname" "mod_zone_start" 4 | } 5 | remove: 6 | { 7 | "targetname" "mod_zone_end" 8 | } 9 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_connectivity_fix.cfg: -------------------------------------------------------------------------------- 1 | ;; empty classname entities 2 | filter: 3 | { 4 | "model" "*57" 5 | "hammerid" "197699" 6 | } 7 | filter: 8 | { 9 | "model" "*58" 10 | "hammerid" "197718" 11 | } 12 | filter: 13 | { 14 | "model" "*59" 15 | "hammerid" "197727" 16 | } 17 | filter: 18 | { 19 | "model" "*60" 20 | "hammerid" "197743" 21 | } 22 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_continuity.cfg: -------------------------------------------------------------------------------- 1 | ; empty classnames crash server 2 | filter: 3 | { 4 | "model" "*57" 5 | "hammerid" "197699" 6 | } 7 | filter: 8 | { 9 | "model" "*58" 10 | "hammerid" "197718" 11 | } 12 | filter: 13 | { 14 | "model" "*59" 15 | "hammerid" "197727" 16 | } 17 | filter: 18 | { 19 | "model" "*60" 20 | "hammerid" "197743" 21 | } 22 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_cys_nonstop.cfg: -------------------------------------------------------------------------------- 1 | ;; empty entity classname 2 | filter: 3 | { 4 | "origin" "1708.02 696.406 64" 5 | "hammerid" "716" 6 | } 7 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_desert_smoke.cfg: -------------------------------------------------------------------------------- 1 | ;; shitty small zones that are shit 2 | filter: 3 | { 4 | "targetname" "mod_zone_start" 5 | } 6 | filter: 7 | { 8 | "targetname" "mod_zone_end" 9 | } 10 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_dron.cfg: -------------------------------------------------------------------------------- 1 | ;; fix missing empty classnames 2 | modify: 3 | { 4 | match: 5 | { 6 | "origin" "3019.49 1646.03 1.73" 7 | "hammerid" "9981" 8 | } 9 | replace: 10 | { 11 | "classname" "trigger_teleport" 12 | } 13 | } 14 | modify: 15 | { 16 | match: 17 | { 18 | "origin" "3019.49 1646.03 3.24" 19 | "hammerid" "9984" 20 | } 21 | replace: 22 | { 23 | "classname" "trigger_multiple" 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_n0bs1_css.cfg: -------------------------------------------------------------------------------- 1 | ;; shit zone 2 | filter: 3 | { 4 | "targetname" "mod_zone_start" 5 | } 6 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_narkozzz.cfg: -------------------------------------------------------------------------------- 1 | ;; empty entity classname 2 | filter: 3 | { 4 | "model" "*18" 5 | "hammerid" "5005" 6 | } 7 | -------------------------------------------------------------------------------- /addons/stripper/maps/bhop_splrez.cfg: -------------------------------------------------------------------------------- 1 | ;; empty entity classname 2 | filter: 3 | { 4 | "model" "*215" 5 | "hammerid" "79725" 6 | } 7 | -------------------------------------------------------------------------------- /addons/stripper/maps/workshop/1195609162/bhop_bless.cfg: -------------------------------------------------------------------------------- 1 | modify: 2 | { 3 | match: 4 | { 5 | "targetname" "filter_activator" 6 | "classname" "filter_activator_name" 7 | } 8 | insert: 9 | { 10 | "filtername" "activator" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /addons/stripper/maps/workshop/2117675766/bhop_craton.cfg: -------------------------------------------------------------------------------- 1 | modify: 2 | { 3 | match: 4 | { 5 | "targetname" "filter_activator" 6 | "classname" "filter_activator_name" 7 | } 8 | insert: 9 | { 10 | "filtername" "bhop" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /addons/stripper/maps/workshop/859067603/bhop_bless.cfg: -------------------------------------------------------------------------------- 1 | modify: 2 | { 3 | match: 4 | { 5 | "targetname" "filter_activator" 6 | "classname" "filter_activator_name" 7 | } 8 | insert: 9 | { 10 | "filtername" "activator" 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /materials/shavit/zone_beam.vmt: -------------------------------------------------------------------------------- 1 | "Sprite" 2 | { 3 | "$spriteorientation" "vp_parallel" 4 | "$spriteorigin" "[ 0.50 0.50 ]" 5 | "$basetexture" "shavit/zone_beam" 6 | } 7 | -------------------------------------------------------------------------------- /materials/shavit/zone_beam.vtf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/materials/shavit/zone_beam.vtf -------------------------------------------------------------------------------- /materials/shavit/zone_beam_ignorez.vmt: -------------------------------------------------------------------------------- 1 | "Sprite" 2 | { 3 | "$spriteorientation" "vp_parallel" 4 | "$spriteorigin" "[ 0.50 0.50 ]" 5 | "$basetexture" "shavit/zone_beam" 6 | "$ignorez" "1" 7 | } 8 | -------------------------------------------------------------------------------- /smbuild: -------------------------------------------------------------------------------- 1 | Plugin(source='addons/sourcemod/scripting/shavit-chat.sp') 2 | Plugin(source='addons/sourcemod/scripting/shavit-core.sp') 3 | Plugin(source='addons/sourcemod/scripting/shavit-hud.sp') 4 | Plugin(source='addons/sourcemod/scripting/shavit-mapchooser.sp') 5 | Plugin(source='addons/sourcemod/scripting/shavit-misc.sp') 6 | Plugin(source='addons/sourcemod/scripting/shavit-rankings.sp') 7 | Plugin(source='addons/sourcemod/scripting/shavit-replay-playback.sp') 8 | Plugin(source='addons/sourcemod/scripting/shavit-replay-recorder.sp') 9 | Plugin(source='addons/sourcemod/scripting/shavit-sounds.sp') 10 | Plugin(source='addons/sourcemod/scripting/shavit-stats.sp') 11 | Plugin(source='addons/sourcemod/scripting/shavit-tas.sp') 12 | Plugin(source='addons/sourcemod/scripting/shavit-timelimit.sp') 13 | Plugin(source='addons/sourcemod/scripting/shavit-wr.sp') 14 | Plugin(source='addons/sourcemod/scripting/shavit-zones.sp') 15 | 16 | Package(name='bhoptimer', 17 | plugins=['shavit-chat', 'shavit-core', 'shavit-hud', 'shavit-misc', 'shavit-mapchooser', 'shavit-rankings', 'shavit-replay-playback', 'shavit-replay-recorder', 'shavit-sounds', 'shavit-stats', 'shavit-tas', 'shavit-timelimit', 'shavit-wr', 'shavit-zones'], 18 | filegroups={ 19 | '.': ['README.md', 'LICENSE'], 20 | }, 21 | ) 22 | -------------------------------------------------------------------------------- /sound/shavit/copyrights.txt: -------------------------------------------------------------------------------- 1 | I'm in no way the owner of the sound samples included in this directory. 2 | They are used for this project, if you want any of those files removed, 3 | please contact me through GitHub by creating an issue here: https://github.com/shavitush/bhoptimer/issues - 4 | and request to have them removed instead of filing a DMCA against my open-source and non-profiting project. 5 | 6 | Appreciated, thank you. -------------------------------------------------------------------------------- /sound/shavit/fr_1.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/fr_1.mp3 -------------------------------------------------------------------------------- /sound/shavit/pb_1.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/pb_1.mp3 -------------------------------------------------------------------------------- /sound/shavit/wr_1.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/wr_1.mp3 -------------------------------------------------------------------------------- /sound/shavit/wr_2.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/wr_2.mp3 -------------------------------------------------------------------------------- /sound/shavit/wr_3.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/wr_3.mp3 -------------------------------------------------------------------------------- /sound/shavit/wr_4.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/shavitush/bhoptimer/321cdb28d97df4c720136a33b63b8df5bdd93534/sound/shavit/wr_4.mp3 --------------------------------------------------------------------------------