Skip to content

make reserving states on branch frames optional#4773

Open
SuuperW wants to merge 5 commits into
TASEmulators:masterfrom
SuuperW:no-branch-state
Open

make reserving states on branch frames optional#4773
SuuperW wants to merge 5 commits into
TASEmulators:masterfrom
SuuperW:no-branch-state

Conversation

@SuuperW

@SuuperW SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

Currently, TAStudio will keep a greenzone state on each branch frame. This is a waste of space in the greenzone buffer. This PR makes those states optional.

Check if completed:

@Morilli

Morilli commented Jun 17, 2026

Copy link
Copy Markdown
Collaborator

This is a waste of space in the greenzone buffer

I don't think that's generally the case. Sure, when it's random unrelated branches it doesn't really make sense, but having a savestate on the (current) branch frame is useful, especially when the area before it isn't greenzoned.

I also don't think we should be changing the default here which it seems like you've done.

Thinking about it, this logic applying to all branches really doesn't make sense, maybe it should only ever reserve branch frame states when it's the current branch?

@SuuperW

SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor Author

having a savestate on the (current) branch frame is useful

Why? I don't see why the current branch is anything special here, nor why any branch frame having a state would ever be useful.

I also don't think we should be changing the default here which it seems like you've done.

I very much disagree. Since they seem totally useless, they should not be enabled by default.

@Morilli

Morilli commented Jun 17, 2026

Copy link
Copy Markdown
Collaborator

If you think reserved states on branch frames is completely useless, why make an option for it instead of removing this logic outright?

I feel like you explained it decently well yourself in the tooltip text; branch states guarantee that you can edit parts of the movie after a branch state (for example after loading that branch) without ever being forced to greenzone everything before the branch state, even if everything before was invalidated due to the branch load. Having such an anchor on the branch state makes a lot of sense in my opinion, I don't know why you would want to remove it.

@SuuperW

SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor Author

If you think reserved states on branch frames is completely useless, why make an option for it instead of removing this logic outright?

Some people in Discord, CPP I think was one, insisted before that they are somehow useful. I never got any explanation for how, though.

(for example after loading that branch)

Apparently, I did not explain it well enough. This feature is not related to the savestate that is part of a branch. It is only for the "greenzone": savestates that are created automatically and can be invalidated by editing the movie. The state that is loaded when you load a branch is a different thing that I have not touched.

@Morilli

Morilli commented Jun 17, 2026

Copy link
Copy Markdown
Collaborator

If you don't understand what this feature does, then don't remove it, not even as a default.

This is not related to the savestate stored in branches at all, this is simply to guarantee that after loading a branch you immediately get a greenzoned frame that is reserved and won't decay. If a branch load invalidates a lot of greenzone that ensures that you can navigate past the branch frame freely without having to re-greenzone everything before it.

Apparently "reserved" states aren't actually reserved on the new state manager and can just disappear, but that's a separate issue.

@SuuperW

SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor Author

If you don't understand what this feature does, then don't remove it, not even as a default.

I understand that it is using up space in the greenzone buffer (which is significant with large states and large numbers of branches), that in all my TASing I have never once wanted it, and that the state manager is designed in a way that is not meant to rely on them.

after loading a branch you immediately get a greenzoned frame

You still get that, unless there is already a nearby state ("nearby" according to the state manager's settings), which means you can quickly seek there anyway. A state can be captured without being reserved.

that is reserved and won't decay

Why does it need to not decay? If I go on editing after loading a branch, why would I be expected to want to return to the frame(s) after the branch frame in the distant future (I say distant future because that's when a non-reserved state would have decayed)? Even immediately after loading a branch, in my experience I am more likely to want to look at the branch frame itself and the frames preceding it. (For example I often make a branch when I get some trick to work, which naturally means the branch is after the trick and there are no meaningful input after that frame.)

Also relevant: 8d066ff. You removed this feature entirely in the past, and @CasualPokePlayer reverted it in 48c545a (with no explanation, at least not in git or GitHub). The feature was added by adelikat with #2321, along with the original implementation of reserving marker states. The comment given for branches references a "reserved list" which does not exist anywhere, indicating that however things worked at the time it was implemented, is not how things work now. All the talk in the PR and linked issue regarding reserved states are for markers, nobody is talking about branch frames.

It's possible some people want to use branches as markers, without having to manually keep a maker synced with the branch. But the current implementation is not fulfilling that purpose, since it does not reserve the state prior to the branch like markers do. If that was the intent, this feature should be "treat branches as markers" and the reserved frame should be changed to be the one before. And I still think it should be default off, since this is not the primary intent of branches.

@vadosnaprimer

vadosnaprimer commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

If that was the intent, this feature should be "treat branches as markers" and the reserved frame should be changed to be the one before.

Sounds acceptable, tho that exact wording is not very clear about which aspects of branches would be mirroring which aspects of markers.

And I still think it should be default off, since this is not the primary intent of branches.

It only becomes a problem with big savestates or if someone mindlessly spams branches. Those sound like rarer scenarios than normal, therefore default should be to have it enabled.

And no, jumping to branch frame is absolutely part of their everyday use. Maybe some of the benefits from it were obsoleted by popup screenshots, but still. If I repeatedly tweak some big portion of the input with branch saving involved, I will use jumping to branch frame just like I'd use a marker, to get back to some milestone frame to start new edits from there.

@SuuperW

SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor Author

And no, jumping to branch frame is absolutely part of their everyday use.

Part of my point was that the current implementation does not support jumping to branch frame; only jumping to after the branch frame. Since people are using the jump to branch frame feature and the lack of a reserved savestate on the prior frame doesn't appear to be a significant issue, we apparently don't actually have much or any need for a reserved state there.

It only becomes a problem with big savestates

And because the savestate manager gets better at keeping states everywhere with small states, having a reserved state prior to the branch frame becomes less important with smaller states. I don't normally use cores other than melonDS (which has rather large states), so I cannot say from experience but I would expect that with small states there will usually be states around there anyway. And with large states it is harmful. If it's always either nearly useless or actually harmful, then I think it should be default off. (but I'm less concerned about the default value than my ability to stop wasting space for these states.)

@Morilli

Morilli commented Jun 17, 2026

Copy link
Copy Markdown
Collaborator

Also relevant: 8d066ff. You removed this feature entirely in the past

That's true, and it caused an immdiate discussion and revert, evidently because people want this feature to exist. I mainly touched this because there was no code for un-reserving states at the time, so it was possible for dozens or hundreds of old reserved states to remain when constantly updating a single branch.

Jumping to the branch frame is not helped by this state reserving, but I don't think that can be implemented properly, unless you allow TAStudio to re-use the branch savestate.

The main thing reserved states guarantee is that you have a state anchor on the branch frame, no matter what other greenzone exists or doesn't exist.

because the savestate manager gets better at keeping states everywhere with small states, having a reserved state prior to the branch frame becomes less important with smaller states

Right, in cases where you expect dense greenzone this matters less, but it also doesn't cause any harm when savestates are that small. In cases where you have very few or no states at all (3DS), having a reserved state is valuable imo.

As I said above, I think limiting the reserve logic to only reserve a state for the currently active branch would make sense and resolve all concerns regarding workflows that use many branches.

@SuuperW

SuuperW commented Jun 17, 2026

Copy link
Copy Markdown
Contributor Author

The main thing reserved states guarantee is that you have a state anchor on the branch frame, no matter what other greenzone exists or doesn't exist.

Again, why is it useful for this state to be reserved?

As I said above, I think limiting the reserve logic to only reserve a state for the currently active branch would make sense and resolve all concerns regarding workflows that use many branches.

Without knowing why people want this feature to exist, I am not confident that this will keep said people happy. But if it does, I am in favor of it.

you allow TAStudio to re-use the branch savestate

I hope to eventually allow special greenzone states (such as this one) to have screenshots. I do not know if I will do it any time soon. (I'd probably want to change TAStudio's LoadState to call the savetate load event instead of UpdateAfter first, but that could be a thorny issue given lots of Lua scripts already exist.)

@Morilli

Morilli commented Jun 18, 2026

Copy link
Copy Markdown
Collaborator

The main thing reserved states guarantee is that you have a state anchor on the branch frame, no matter what other greenzone exists or doesn't exist.

Again, why is it useful for this state to be reserved?

It is useful for that state to exist, and marking it as reserved is a way to ensure it does.

@SuuperW

SuuperW commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

What I meant to ask is, why is it important for that particular state to exist? Or more precisely, why is it important that the amount of re-greenzoning required to seek to branchFrame + 1 is always less than "Frames Between Old States" or "Ancient State Interval"? (because it is only when said gap is smaller that the state would be removed before old states start being removed)

@vadosnaprimer

vadosnaprimer commented Jun 22, 2026

Copy link
Copy Markdown
Contributor

As I said above, I think limiting the reserve logic to only reserve a state for the currently active branch would make sense and resolve all concerns regarding workflows that use many branches.

If it's only allowed for active branch, then the initial intent is not met: for cases when branches are used as markers. If something needs to be compared or observed on that exact frame (like if the user intentionally saved it on some milestone frame), jumping back to that frame is nicer than having to also put a marker there every time.

However...

The workflow of loading states in read-only mode just to jump back is indeed partially obsoleted by the very concept of greenzone. And at first it was strictly consecutive (with constant gaps), so replicating it with those reserved states felt warranted. Then we implemented smart decay like in TASEditor in order to cover more space/time. Then zwinder made them consecutive again, with several additional buffers for older states. And if managed wisely, they may work as proper decay system, where you can access almost anything in the past, granted with a little wait.

It's true that if we don't have to drop states too fast, greenzone is likely to remain on those branch frames (or around them), and if states are huge, those extra states are costly. And judging by the fact nobody complained about this feature not actually working right, maybe it's not so important. And CPP is silent now...

@SuuperW

SuuperW commented Jun 30, 2026

Copy link
Copy Markdown
Contributor Author

Updated so that branch greenzone states are on the frame before the branch, since seeking to branch frame seems to be what they're supposed to enable. Since the behavior changed, does it make more sense to default off now? (the old behavior would be gone either way) or do we still want these on by default

Also, the state captured when loading a branch is now reserve captured (mainly so that it can work with Zwinder) but not permanently reserved. (Meaning it won't be reserve captured again after being invalidated and re-emulating, and the new manager is able to remove it if there are nearby states before it [or it gets to removing old states].)

@vadosnaprimer

Copy link
Copy Markdown
Contributor

Wild idea: what if instead giving user option to enable or disable based on vibes, instead have an option to set above which size states should not be reserved?

@SuuperW

SuuperW commented Jun 30, 2026

Copy link
Copy Markdown
Contributor Author

I don't like that idea. For one, I would think that users who want states to be reserved probably want them reserved regardless of size. And two, nobody is going to know what an appropriate number is and users will have to just experiment, which makes that option more complicated than a simple toggle with no benefit.

@vadosnaprimer

Copy link
Copy Markdown
Contributor

Since the behavior changed, does it make more sense to default off now? (the old behavior would be gone either way) or do we still want these on by default

Old behavior was the thing not really working, so if it's fixed we should let people use it, and only disable it in problematic situations, which are still not majority of cases.

@Morilli

Morilli commented Jul 1, 2026

Copy link
Copy Markdown
Collaborator

This is getting decently complex now...

If I'm understanding it correctly the option now determines whether "branch frame - 1" is reserved (instead of branch frame directly), which is probably fine. Additionally, branch frames are now reserve captured on load just like before, but they don't count as reserved, and they aren't unreserved either, so this leaks reserved states now.

And because creating a branch will no longer reserve or save a state, cores like encore will probably no longer be usable by making branches to force states.

In general I like the idea of reserving branch frame - 1 usually and branch state specifically for the currently loaded branch, but this needs more considerations.

@SuuperW

SuuperW commented Jul 9, 2026

Copy link
Copy Markdown
Contributor Author

this leaks reserved states

They'll still get invalidated like regular states when inputs change, so I don't think this is a big problem. Unless there is another way of leaking reserved states than what I'm thinking:

  1. Load a branch on frame 2
  2. Advance to frame 4 (not 3!)
  3. Update the branch (or delete then make a new one)
  4. Re-load the branch to make a new state
  5. Repeat 2-4 (advancing 2 more frames each time)

I added a commit to call Unreserve on those frames when the branch is updated/deleted so it won't leak like that anymore. (and another to delay actually removing the state until the space is needed, since I feel like users might sometimes want to keep the original branch frame state for a while)

cores like encore will probably no longer be usable by making branches to force states

Are the greenzone states a thing that's used like that? That seems like a pretty weird way to get a greenzone state. (you're making two states plus an input log copy, when you only want one state?) The branch can still be loaded to load its state. If a greenzone state is the goal, perhaps we should have a new feature for that.

In general I like the idea of reserving branch frame - 1 usually and branch state specifically for the currently loaded branch

Do you mean current branch frame - 1 should explicitly be NOT reserved?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants