-
Notifications
You must be signed in to change notification settings - Fork 1
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
你别管它实不实用 在终端中操作 你就说帅不帅就得了 Signed-off-by: 舰队的偶像-岛风酱! <[email protected]>
- Loading branch information
Showing
6 changed files
with
250 additions
and
0 deletions.
There are no files selected for viewing
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
<?xml version="1.0" encoding="UTF-8"?> | ||
<Project> | ||
|
||
<Import Project="$(MSBuildThisFileDirectory)..\build\Common.props" /> | ||
|
||
<Import Project="$(MSBuildThisFileDirectory)..\build\NugetPackage.props" /> | ||
|
||
<Import Condition=" '$(MSBuildProjectExtension)' == '.csproj' " | ||
Project="$(MSBuildThisFileDirectory)..\build\CSharp.props" /> | ||
|
||
</Project> |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
<?xml version="1.0" encoding="UTF-8"?> | ||
<Project> | ||
|
||
<Import Condition=" '$(MSBuildProjectExtension)' == '.csproj' " | ||
Project="$(MSBuildThisFileDirectory)..\build\CSharp.targets" /> | ||
|
||
</Project> |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
using Shimakaze.Sdk.Pal; | ||
|
||
namespace Shimakaze.Sdk.Vpl.Editor; | ||
|
||
/// <summary> | ||
/// 颜色 扩展 | ||
/// </summary> | ||
public static class ColorExtensions | ||
{ | ||
/// <summary> | ||
/// 转 ANSI Color 字符串 用于在终端显示颜色 | ||
/// </summary> | ||
/// <param name="color">颜色</param> | ||
/// <param name="isBackground">是否是背景色</param> | ||
/// <returns></returns> | ||
public static string GetANSIString(this in Color color, bool isBackground = false) => $"\x1B[{(isBackground ? 4 : 3)}8;2;{color.GetR5()};{color.GetG6()};{color.GetB5()}m"; | ||
|
||
/// <summary> | ||
/// 反转颜色 | ||
/// </summary> | ||
/// <param name="color">颜色</param> | ||
/// <returns>被反转后的颜色</returns> | ||
public static Color GetReverse(this in Color color) => new( | ||
(byte)~color.Red, | ||
(byte)~color.Green, | ||
(byte)~color.Blue | ||
); | ||
} |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
using Sharprompt; | ||
|
||
using Shimakaze.Sdk.IO.Pal; | ||
using Shimakaze.Sdk.IO.Vpl; | ||
using Shimakaze.Sdk.Pal; | ||
using Shimakaze.Sdk.Vpl; | ||
using Shimakaze.Sdk.Vpl.Editor; | ||
|
||
string vplPath = Prompt.Input<string>("What VPL File do you want edit?").Trim('"'); | ||
string palPath = Prompt.Input<string>("What PAL File do you want see?").Trim('"'); | ||
|
||
VoxelPalette vpl; | ||
Palette pal; | ||
|
||
await using (var vplStream = File.OpenRead(vplPath)) | ||
await using (VoxelPaletteReader vplReader = new(vplStream)) | ||
vpl = vplReader.Read(); | ||
|
||
await using (var palStream = File.OpenRead(palPath)) | ||
await using (PaletteReader palReader = new(palStream)) | ||
pal = palReader.Read(); | ||
|
||
VplEditor editor = new(vpl, pal, async (editor) => | ||
{ | ||
string path = Prompt.Input<string>("Where is your new VPL file save to?", vplPath); | ||
await using var fs = File.Create(path); | ||
await using VoxelPaletteWriter writer = new(fs); | ||
writer.Write(editor.Vpl); | ||
}); | ||
|
||
await editor.RunAsync(); |
14 changes: 14 additions & 0 deletions
14
app/Shimakaze.Sdk.Vpl.Editor/Shimakaze.Sdk.Vpl.Editor.csproj
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
<Project Sdk="Microsoft.NET.Sdk"> | ||
<PropertyGroup> | ||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks> | ||
<OutputType>Exe</OutputType> | ||
</PropertyGroup> | ||
|
||
<ItemGroup> | ||
<ProjectReference Include="..\..\src\Shimakaze.Sdk.Vpl\Shimakaze.Sdk.Vpl.csproj" /> | ||
</ItemGroup> | ||
|
||
<ItemGroup> | ||
<PackageReference Include="Sharprompt" Version="3.0.0-preview2" /> | ||
</ItemGroup> | ||
</Project> |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,159 @@ | ||
using Sharprompt; | ||
|
||
using Shimakaze.Sdk.Pal; | ||
|
||
namespace Shimakaze.Sdk.Vpl.Editor; | ||
|
||
internal sealed class VplEditor | ||
{ | ||
private const int X_SECTION_OFFSET = 3 * 16 + 4; | ||
private const int Y_OFFSET = 1; | ||
private const int SIZE_OF_CELL = 3; | ||
public readonly VoxelPalette Vpl; | ||
private readonly Palette _pal; | ||
private readonly Func<VplEditor, Task> _saver; | ||
private bool _isEditing; | ||
private (int X, int Y, int Section) _current; | ||
private (int X, int Y) _editing; | ||
|
||
public VplEditor(VoxelPalette vpl, Palette pal, Func<VplEditor, Task> saver) | ||
{ | ||
Vpl = vpl; | ||
_pal = pal; | ||
_saver = saver; | ||
} | ||
|
||
public async Task RunAsync() | ||
{ | ||
PrintColor(); | ||
while (true) | ||
{ | ||
if (_isEditing) | ||
Console.SetCursorPosition(_editing.X * SIZE_OF_CELL, Y_OFFSET + _editing.Y); | ||
else | ||
Console.SetCursorPosition(X_SECTION_OFFSET + _current.X * SIZE_OF_CELL, Y_OFFSET + _current.Y); | ||
|
||
var key = Console.ReadKey(true); | ||
switch (key.Key) | ||
{ | ||
case ConsoleKey.Tab when !_isEditing && key.Modifiers is ConsoleModifiers.Shift && _current.Section > 0: | ||
case ConsoleKey.N when !_isEditing && _current.Section > 0: | ||
_current.Section--; | ||
PrintColor(); | ||
break; | ||
case ConsoleKey.Tab when !_isEditing && key.Modifiers is 0 && _current.Section + 1 < Vpl.Header.SectionCount: | ||
case ConsoleKey.M when !_isEditing && _current.Section + 1 < Vpl.Header.SectionCount: | ||
_current.Section++; | ||
PrintColor(); | ||
break; | ||
case ConsoleKey.LeftArrow when !_isEditing && _current.X > 0: | ||
case ConsoleKey.H when !_isEditing && _current.X > 0: | ||
_current.X--; | ||
break; | ||
case ConsoleKey.RightArrow when !_isEditing && _current.X < 15: | ||
case ConsoleKey.L when !_isEditing && _current.X < 15: | ||
_current.X++; | ||
break; | ||
case ConsoleKey.UpArrow when !_isEditing && _current.Y > 0: | ||
case ConsoleKey.K when !_isEditing && _current.Y > 0: | ||
_current.Y--; | ||
break; | ||
case ConsoleKey.DownArrow when !_isEditing && _current.Y < 15: | ||
case ConsoleKey.J when !_isEditing && _current.Y < 15: | ||
_current.Y++; | ||
break; | ||
case ConsoleKey.LeftArrow when _isEditing && _editing.X > 0: | ||
case ConsoleKey.H when _isEditing && _editing.X > 0: | ||
_editing.X--; | ||
break; | ||
case ConsoleKey.RightArrow when _isEditing && _editing.X < 15: | ||
case ConsoleKey.L when _isEditing && _editing.X < 15: | ||
_editing.X++; | ||
break; | ||
case ConsoleKey.UpArrow when _isEditing && _editing.Y > 0: | ||
case ConsoleKey.K when _isEditing && _editing.Y > 0: | ||
_editing.Y--; | ||
break; | ||
case ConsoleKey.DownArrow when _isEditing && _editing.Y < 15: | ||
case ConsoleKey.J when _isEditing && _editing.Y < 15: | ||
_editing.Y++; | ||
break; | ||
case ConsoleKey.Enter when !_isEditing: | ||
case ConsoleKey.Spacebar when !_isEditing: | ||
byte index = Vpl[_current.Section][(_current.Y * 16) + _current.X]; | ||
_editing.X = index % 16; | ||
_editing.Y = index / 16; | ||
_isEditing = true; | ||
PrintColor(); | ||
break; | ||
case ConsoleKey.Enter when _isEditing: | ||
case ConsoleKey.Spacebar when _isEditing: | ||
index = (byte)((_editing.Y * 16) + _editing.X); | ||
{ | ||
var tmp = Vpl[_current.Section]; | ||
tmp[(_current.Y * 16) + _current.X] = index; | ||
Vpl[_current.Section] = tmp; | ||
} | ||
_isEditing = false; | ||
PrintColor(); | ||
break; | ||
case ConsoleKey.Escape when _isEditing: | ||
case ConsoleKey.Q when _isEditing: | ||
_isEditing = false; | ||
PrintColor(); | ||
break; | ||
case ConsoleKey.Escape when !_isEditing: | ||
case ConsoleKey.Q when !_isEditing: | ||
Console.SetCursorPosition(0, Y_OFFSET + 16); | ||
var isExit = Prompt.Confirm("Are you sure you want to exit? Your changed will NOT saved!", false); | ||
if (isExit) | ||
Environment.Exit(0); | ||
|
||
PrintColor(); | ||
break; | ||
case ConsoleKey.S: | ||
Console.SetCursorPosition(0, Y_OFFSET + 16); | ||
await _saver(this); | ||
PrintColor(); | ||
break; | ||
} | ||
} | ||
} | ||
|
||
void PrintColor() | ||
{ | ||
Console.CursorVisible = false; | ||
Console.Clear(); | ||
Console.SetCursorPosition(0, 0); | ||
Console.Write("色板:"); | ||
Console.SetCursorPosition(X_SECTION_OFFSET, 0); | ||
Console.Write("Section: #"); | ||
Console.Write((_current.Section + 1).ToString("D2")); | ||
Console.WriteLine("\x1B[0m"); | ||
for (int y = 0; y < 256 / 16; y++) | ||
{ | ||
for (int x = 0; x < 16; x++) | ||
{ | ||
Console.Write(_pal[(y * 16) + x].GetANSIString(true)); | ||
Console.Write(" "); | ||
} | ||
|
||
Console.Write("\x1B[0m "); | ||
|
||
for (int x = 0; x < 16; x++) | ||
{ | ||
Console.Write(_pal[Vpl[_current.Section][(y * 16) + x]].GetANSIString(true)); | ||
if (x == _current.X && y == _current.Y && _isEditing) | ||
{ | ||
Console.Write(_pal[Vpl[_current.Section][(y * 16) + x]].GetReverse().GetANSIString(false)); | ||
Console.Write(" x "); | ||
} | ||
else | ||
Console.Write(" "); | ||
} | ||
|
||
Console.WriteLine("\x1B[0m"); | ||
} | ||
Console.CursorVisible = true; | ||
} | ||
} |