Conversation
NbtUtils.fromClipboard(ISerializable) deserialises onto the existing object, so pasting NBT mutated the SettingColor in place without ever going through Setting#set and therefore without firing onChanged(). Every other mutation path in the screen (the RGBA boxes, the hue and brightness quads, the rainbow checkbox, the reset button) notifies the setting afterwards; paste did not. Settings whose value object is read directly appeared to work, but any setting that relies on its onChanged callback to propagate the value silently kept the old colour. In Block ESP that callback is also what registers the block in the map, so pasting a block config fell back to the default. Notify the setting on the NBT branch, and run the screen's action on both branches so paste is consistent with the other mutation paths. The trailing validate() moves into the NBT branch: the parse branch already validates through Setting#set -> ColorSetting#isValueValid.
c8dhjp4tyv-bit
force-pushed
the
fix/color-paste-not-applied
branch
from
September 13, 2026 05:08
57257d5 to
c726b00
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Type of change
Description
Copying a colour config and pasting it into another one appears to work in the colour picker, but the value never reaches the setting's owner. In Block ESP the pasted block config is dropped entirely and falls back to the default.
NbtUtils.fromClipboard(ISerializable)deserialises onto the existing object:So
NbtUtils.fromClipboard(setting.get())mutates theSettingColorin place. It never goes throughSetting#setorSetting#fromTag, both of which callonChanged()— andfromClipboard()did not call it either:Every other mutation path in this screen notifies the setting afterwards —
rgbaChanged(),hsvChanged(), the rainbow checkbox and the reset button all end insetting.onChanged(). Paste was the only one that did not, and only on the NBT branch, which is the branch the copy button produces.Settings whose value object is read directly still looked fine, because the mutated object is the live one. Settings that rely on their
onChangedcallback to propagate the value did not:ESPBlockDataScreen— the callback copies the colour into theESPBlockDataand runsfirstChangeConsumer, which is what puts the block intoBlockDataSetting's map. Without it the block is never registered, so it renders with the default config. This is the reported symptom.DefaultSettingsWidgetFactory#colorListWFill— the callback writes back into the list entry (setting.get().get(_i).set(settingColor)), so pasting into a colour-list entry did nothing.BaritoneSettings— the callback mirrors the colour into the Baritone setting.The fix notifies the setting on the NBT branch. Two notes on the rest of the diff:
callAction()now runs on both branches, matching the reset button and the other mutation paths. It is a no-op in-tree (nothing assignsaction), but it is public API and paste is a value change like any other.validate()moves into the NBT branch rather than running unconditionally. It is not load-bearing in either branch —Color#fromTagalready validates, and the parse branch validates throughSetting#set→ColorSetting#isValueValidbeforeonChanged()runs — but keeping it on the branch that mutates in place makes the "valid before the callback sees it" invariant explicit whereSettingis not doing it for us.Related issues
Closes #6511
How Has This Been Tested?
./gradlew compileJavapasses.I modelled the
Setting/SettingColor/ESPBlockDataScreenwiring in isolation and pasted(255, 0, 128, 255)into a block config:The picker shows the pasted colour either way — which is why it looks like it worked — but before the fix the block data keeps the default and is never added to the map, exactly as described in #6511.
In-game: Block ESP → block configs → pick a block → change the colour → copy → pick another block → paste → back. The second block now keeps the pasted colour instead of resetting. Colour-list entries and normal module colour settings paste correctly too, and copy/paste on a plain module colour behaves as before.
Checklist: