Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 10 additions & 9 deletions src/BizHawk.Client.EmuHawk/tools/TAStudio/TAStudio.ListView.cs
Original file line number Diff line number Diff line change
Expand Up @@ -342,25 +342,26 @@ private void TasView_ColumnClick(object sender, InputRoll.ColumnClickEventArgs e
}
else if (columnName != CursorColumnName)
{
var frame = TasView.AnyRowsSelected ? TasView.FirstSelectedRowIndex : 0;
var buttonName = TasView.CurrentCell.Column!.Name;

if (ControllerType.BoolButtons.Contains(buttonName))
{
if (ModifierKeys != Keys.Alt)
{
// nifty taseditor logic
bool allPressed = true;
foreach (var index in TasView.SelectedRows)
// your TAS Editor logic failed us (it didn't account for non-contiguous `SelectedRows`) --yoshi
var selection = TasView.SelectedRows.ToArray(); // sorted asc, length >= 1
var allPressed = selection[selection.Length - 1] != CurrentTasMovie.FrameCount // last movie frame can't have input, but can be selected
&& selection.All(index => CurrentTasMovie.BoolIsPressed(index, buttonName));
CurrentTasMovie.ChangeLog.BeginNewBatch($"{(allPressed ? "Unset" : "Set")} {selection.Length} frames of {buttonName} starting at {selection[0]}");
CurrentTasMovie.SingleInvalidation(() =>
{
if (index == CurrentTasMovie.FrameCount // last movie frame can't have input, but can be selected
|| !CurrentTasMovie.BoolIsPressed(index, buttonName))
foreach (var (start, count) in selection.ChunkConsecutive())
{
allPressed = false;
break;
CurrentTasMovie.SetBoolStates(frame: start, count: count, buttonName, val: !allPressed);
}
}
CurrentTasMovie.SetBoolStates(frame, TasView.SelectedRows.Count(), buttonName, !allPressed);
});
CurrentTasMovie.ChangeLog.EndBatch();
}
else
{
Expand Down
22 changes: 22 additions & 0 deletions src/BizHawk.Common/Extensions/CollectionExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,28 @@ public static void AddRange<T>(this ICollection<T> list, IEnumerable<T> collecti
public static IEnumerable<T> AsEnumerable<T>(this IEnumerator<T> enumerator)
=> new EnumeratorAsEnumerable<T>(enumerator);

public static IEnumerable<(int Start, int Count)> ChunkConsecutive(this IReadOnlyList<int> numbers)
{
if (numbers.Count is 0) yield break;
Debug.Assert(numbers.IsSortedAsc(), "should be sorted asc.");
var i = 0;
var blockStart = 0;
var lastValueSeen = numbers[i] - 1;
while (i < numbers.Count)
{
var value = numbers[i];
if (value - lastValueSeen is not 1)
{
// discontinuity; split off another block, and this is now the start of the next block
yield return (Start: numbers[blockStart], Count: i - blockStart);
blockStart = i;
}
lastValueSeen = value;
i++;
}
yield return (Start: numbers[blockStart], Count: i - blockStart); // `count` arg will be 0 if the whole list is contiguous
}

/// <remarks>
/// Contains method for arrays which does not need Linq, but rather uses Array.IndexOf
/// similar to <see cref="ICollection{T}.Contains">ICollection's Contains</see>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,18 @@ public void TestAddRange()
Assert.AreEqual(4, b.Count, nameof(CE.AddRange) + " failed on (ICollection<int> not List<int>)");
}

[DataRow(new int[] {}, "")]
[DataRow(new int[] { 1 }, "1")]
[DataRow(new int[] { 1, 2, 4 }, "1,2;4")]
[DataRow(new int[] { 1, 4, 5, 8, 9 }, "1;4,5;8,9")]
[DataRow(new int[] { -1, 0, 1 }, "-1,0,1")]
[TestMethod]
public void TestChunkConsecutive(int[] numbers, string expectedStr)
=> Assert.AreEqual(
expectedStr,
string.Join(";", numbers.ChunkConsecutive().Select(
static range => string.Join(",", Enumerable.Range(start: range.Start, count: range.Count)))));

[TestMethod]
public void TestConcatArray()
{
Expand Down
Loading