
balrond negative skills
Extension to skills systems allowing for negative skill valuesBalrondNegativeSkills
Current version: 0.1.5
BalrondNegativeSkills extends Valheim's normal skill range from 0..100 to -100..100.
A negative skill is not only a displayed number. Below zero, the mod turns the skill into a real gameplay penalty. The intended idea is that a character can become worse than an untrained level-0 character and must relearn basic competence before normal progression resumes.
-100 <---------------- 0 ----------------> 100
severe deficiency baseline mastery
Main rules
- Positive skills
0..100remain vanilla wherever possible. - Negative values are stored in Valheim's normal character skill save data.
- Raw values are clamped to
-100..100on save/load. - A negative skill can recover through normal skill XP.
- When the skill reaches
0, normal vanilla progression resumes. - Negative skills do not count as negative credit against Valheim's total skill cap by default.
Signed skill factor
For calculations that normally use Skills.GetSkillFactor(), the mod exposes a signed factor below zero.
With default settings:
| Skill | Factor |
|---|---|
0 |
0.00 |
-25 |
-0.25 |
-50 |
-0.50 |
-75 |
-0.75 |
-100 |
-1.00 |
Negative Effect Multiplier can scale this negative branch without changing positive vanilla skill behavior.
What negative skills affect
The mod extends the existing Valheim formulas rather than inventing a separate stat system.
Examples:
- weapon skills: lower damage/knockback and higher stamina/eitr/health costs where the vanilla attack uses that skill;
- Blocking: lower block power;
- Jump: lower jump force;
- Run: lower run speed and higher stamina drain;
- Swim: higher stamina drain;
- Sneak: worse stealth and higher stamina drain;
- Dodge: higher stamina cost;
- Bows: negative skill extends the existing bow draw-time penalty path;
- Crossbows and other
skillAccuracyprojectile attacks: negative skill now extrapolates accuracy below the level-0 baseline instead of being clamped byMathf.Lerp; - Riding: lower mount performance and higher stamina usage through the signed rider-skill path;
- Crafting/Cooking: skill-scaled actions take longer and tool/action costs can increase;
- Farming: harvest radius can shrink and tool costs can increase;
- Fishing: performance can become worse and stamina costs can rise, with a safety floor preventing invalid negative/zero speeds.
Chance-only positive bonuses such as extra yield simply stop occurring below zero unless the underlying Valheim mechanic has a meaningful negative counterpart.
Blood Magic safety
Blood Magic contains several vanilla formulas that use the numeric skill level directly instead of GetSkillFactor(). Extending those formulas blindly below zero can produce zero or negative values.
Version 0.1.2 adds dedicated protection:
Summons
Vanilla copied summon performance uses a formula equivalent to:
1 + skillLevel * prefabCopyFactor
At sufficiently negative Blood Magic this could reach zero or become negative, causing nonsensical damage or inverted knockback.
For negative Blood Magic only, BalrondNegativeSkills remaps this branch so the entire negative range approaches a safe configurable floor.
Default:
Blood Magic 0 -> 100% of level-0 summon multiplier
Blood Magic -100 -> minimum 25%
Positive Blood Magic continues using the original prefab coefficient.
Protection shields
SE_Shield also scales absorb capacity directly from skill level. Negative Blood Magic could otherwise create a zero/negative barrier.
For Blood-Magic shields, the negative range is remapped from the normal level-0 absorb value down to a configurable positive floor.
Default floor: 25% of the level-0 base absorb value, before world-level additions.
Death skill loss
Hard death vs soft death
Valheim does not lower skills on every death.
Player.OnDeath() applies Skills.OnDeath() only when the death is a hard death. A death during Valheim's hard-death cooldown is a soft death and does not reduce skills. BalrondNegativeSkills preserves that vanilla rule.
The current Valheim player field uses a 10-second hard-death cooldown. Because respawning itself takes time, rapid test deaths can still land on the boundary. For testing, wait a little after respawning before killing the character again.
Why 0.1.1 looked stuck at -1
Version 0.1.1 used the percentage death factor even very close to zero. The UI floors negative values:
raw -0.05 -> displayed -1
raw -0.50 -> displayed -1
raw -0.99 -> displayed -1
raw -1.01 -> displayed -2
Therefore repeated deaths could change the saved raw skill while the visible integer stayed at -1 for a long time.
New 0.1.2 behavior
The new setting:
Minimum Negative Loss Per Hard Death = 1.0
means that, by default, every qualifying hard death removes at least one full raw skill point when the skill is already <= 0 or is inside the zero-crossing band.
The normal percentage loss still wins when it is larger.
Default example starting exactly at zero:
hard death #1: 0 -> -1
hard death #2: -1 -> -2
hard death #3: -2 -> -3
At deep negative values, percentage loss can become larger than one point and progression toward -100 accelerates.
Every time this mod actually handles Skills.LowerAllSkills, BepInEx logs a compact line like:
[BalrondNegativeSkills] Applied hard-death skill loss: factor=..., minimumNegativeLoss=1, changedSkills=..., negativeSkills=...
If that line is absent for a death, the mod's hard-death skill-loss patch was not invoked for that death (for example because it was a vanilla soft death).
Enable Diagnostics = true to log each changed skill with raw before/after values.
Negative skill UI
Valheim's vanilla Skills window casts raw skill level directly to an integer. C# truncates negative fractions toward zero, so raw -0.25 was displayed as 0.
BalrondNegativeSkills uses floor semantics for negative labels, matching Skills.GetSkillLevel():
raw -0.25 -> displayed -1
raw -1.25 -> displayed -2
Version 0.1.2 also refreshes an already-open Skills dialog immediately after the mod applies skill loss.
Relearning a negative skill
Vanilla Skills.Skill.Raise() is not safe for negative levels because its level requirement formula assumes a non-negative skill.
BalrondNegativeSkills replaces only the negative branch.
Recovery uses vanilla requirement values in reverse deficit order:
raw -100 -> next recovery step uses approximately the vanilla level-100 requirement
raw -50 -> next recovery step uses approximately the vanilla level-50 requirement
raw -1 -> next recovery step uses approximately the vanilla level-1 requirement
raw 0 -> vanilla progression resumes
A recovery step can never grant free positive levels while crossing zero.
Saving and relogging
Valheim serializes each skill's raw level as a floating-point value in the normal character save. The vanilla save/load code does not itself clamp that float to zero.
BalrondNegativeSkills therefore does not create a duplicate ZDO/custom-data database. It keeps the normal Skills.Save/Load data authoritative and clamps only to -100..100.
Negative skill values persist across logout/relogin while the mod is installed.
Keep character backups while testing mods that alter core skill data.
Console testing
Valheim's existing raiseskill command is extended for negative values and for raising an already-negative skill.
Examples:
raiseskill swords -25
raiseskill blocking -50
raiseskill bloodmagic -100
raiseskill crossbows -25
For a quick persistence test:
- enable devcommands;
- set a skill negative;
- verify it in the Skills window;
- logout and reload the character;
- verify the negative value is still present.
Configuration
Generated at:
BepInEx/config/balrond.astafaraios.BalrondNegativeSkills.cfg
Important settings:
| Setting | Default | Purpose |
|---|---|---|
Lock Configuration |
true |
ServerSync lock; server controls synchronized gameplay settings while connected |
Enabled |
true |
Master switch |
Negative Effect Multiplier |
1.0 |
Scales penalties below zero |
Death Can Cross Zero |
true |
Allows death loss below zero |
Zero Crossing Band |
1.0 |
Positive near-zero range allowed to use the crossing/minimum loss |
Minimum Negative Loss Per Hard Death |
1.0 |
Minimum raw loss for zero/negative skills on a qualifying hard death |
Prevent Negative Skill Cap Credit |
true |
Negative skills do not create extra positive skill-cap capacity |
Minimum Harvest Radius Multiplier |
0.25 |
Farming safety floor |
Minimum Fishing Performance Multiplier |
0.25 |
Fishing safety floor |
Minimum Blood Magic Summon Multiplier |
0.25 |
Prevents zero/negative summon performance |
Minimum Blood Magic Shield Multiplier |
0.25 |
Prevents zero/negative Blood Magic shield capacity |
Diagnostics |
false |
Detailed per-skill and safety-patch logging |
ServerSync and multiplayer
BalrondNegativeSkills 0.1.5 uses ServerSync for gameplay configuration.
The following settings are synchronized from the server:
EnabledNegative Effect MultiplierDeath Can Cross ZeroZero Crossing BandMinimum Negative Loss Per Hard DeathPrevent Negative Skill Cap CreditMinimum Harvest Radius MultiplierMinimum Fishing Performance MultiplierMinimum Blood Magic Summon MultiplierMinimum Blood Magic Shield Multiplier
Diagnostics is intentionally local because it only controls logging on the current machine.
Lock Configuration defaults to true. With the lock enabled, connected clients use the server values for all synchronized gameplay settings. Install the same BalrondNegativeSkills version on the server and every client.
The stable plugin GUID remains:
balrond.astafaraios.BalrondNegativeSkills
ServerSync is merged into the final BalrondNegativeSkills.dll by ILRepack. A normal completed build should not leave a separate ServerSync.dll in bin/Release.
Existing config files
Updating does not require deleting the old config. BepInEx will add the new ServerSync Lock Configuration entry automatically. Existing gameplay values remain valid.
Compatibility with custom skills
Core storage/recovery patches operate on Skills.Skill and therefore also support registered custom skill values below zero.
If another mod calculates its effect through Skills.GetSkillFactor(), it receives the signed factor automatically.
If another mod reads m_level/GetSkillLevel() directly and implements its own formula, that formula may need its own negative-value handling. This is relevant for custom systems such as BalrondExtraSkills.
Public integration API
Namespace:
BalrondNegativeSkills.API
Example:
float raw = NegativeSkillsApi.GetRawLevel(player, Skills.SkillType.Swords);
float penalty = NegativeSkillsApi.GetPenaltyFactor(player, Skills.SkillType.Swords);
float result;
NegativeSkillsApi.TrySetLevel(player, Skills.SkillType.Swords, -40f, true, out result);
NegativeSkillsApi.TryModifyLevel(player, Skills.SkillType.Swords, -5f, true, out result);
Installation
- Install BepInEx for Valheim.
- Build or obtain
BalrondNegativeSkills.dll. - Place it in:
BepInEx/plugins/BalrondNegativeSkills/BalrondNegativeSkills.dll
- Start Valheim.
For multiplayer testing, use the same mod version/config on participating clients and the server where applicable.
Building the Visual Studio project
The included solution targets:
.NET Framework 4.8- C#
7.3 - BepInEx 5
- Harmony
AllowUnsafeBlocks = true- a publicized
assembly_valheim.dllas the Valheim compile reference
1. Supply the publicized Valheim assembly
Copy your publicized assembly to:
BalrondNegativeSkills/Libs/assembly_valheim.dll
The project intentionally does not redistribute Valheim's assembly.
Alternatively:
msbuild BalrondNegativeSkills.csproj /p:PublicizedAssemblyPath="D:\Modding\Publicized\assembly_valheim.dll"
2. Set the Valheim directory
The project currently defaults to:
G:\SteamLibrary\steamapps\common\Valheim
Override when needed:
msbuild BalrondNegativeSkills.csproj /p:ValheimDir="D:\SteamLibrary\steamapps\common\Valheim"
3. Build Release
Open:
BalrondNegativeSkills.sln
Select Release and build.
Expected output:
bin/Release/BalrondNegativeSkills.dll
Or use:
Tools\BUILD_VALIDATE.ps1 -ValheimDir "G:\SteamLibrary\steamapps\common\Valheim"
Optional direct deployment:
Tools\BUILD_VALIDATE.ps1 -ValheimDir "G:\SteamLibrary\steamapps\common\Valheim" -Deploy
Design rule
The mod deliberately avoids replacing the complete Valheim skill system.
For effective skill values
>= 0, vanilla remains authoritative. Custom behavior is added only where negative values require signed extrapolation, negative progression, or a safety floor to prevent invalid game state.
0.1.4 build-lock fix
Version 0.1.4 changes only the ServerSync/ILRepack build pipeline. Older 0.1.3 builds passed bin\\<Configuration>\\BalrondNegativeSkills.dll directly to the in-process ILRepack task. Visual Studio can keep that input file open in its reusable MSBuild.exe process, causing the next build to fail while copying obj\\Debug\\BalrondNegativeSkills.dll to bin\\Debug\\BalrondNegativeSkills.dll (MSB3027 / MSB3021).
0.1.4 creates unique shadow copies under obj\\ilrepack\\... and ILRepack reads only those copies. The real output DLL is never an ILRepack input, so subsequent Debug/Release builds can replace it normally.
If Visual Studio already has the old 0.1.3 DLL locked, close Visual Studio once (or terminate the stale MSBuild.exe) before the first 0.1.4 build. That releases the lock created by the old build pipeline. Subsequent 0.1.4 builds should not recreate it.
0.1.5 ILRepack dependency-resolution fix
Version 0.1.5 keeps the 0.1.4 shadow-input lock fix and additionally gives ILRepack explicit resolver search paths for:
Libs(publicizedassembly_valheim.dll),BepInEx\core(BepInEx.dll,0Harmony.dll),valheim_Data\Managed(Unity/Valheim managed dependencies),- the normal build output and per-build shadow directory.
These directories are resolver-only. Only BalrondNegativeSkills.dll and ServerSync.dll are merge inputs. BepInEx, Harmony, Unity and Valheim assemblies remain external game dependencies and are never folded into the mod DLL.
This fixes ILRepack failures such as:
Failed to resolve assembly: 'BepInEx, Version=5.4.23.3, Culture=neutral, PublicKeyToken=null'
The previous Launch.initialized field was also removed because it had no reader and only generated CS0414.

