Ionite
1 year ago
12 changed files with 218 additions and 194 deletions
@ -0,0 +1,59 @@
|
||||
<Styles xmlns="https://github.com/avaloniaui" |
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" |
||||
xmlns:controls="using:StabilityMatrix.Avalonia.Controls" |
||||
xmlns:mocks="clr-namespace:StabilityMatrix.Avalonia.DesignData" |
||||
xmlns:avaloniaEdit="https://github.com/avaloniaui/avaloniaedit" |
||||
xmlns:vmInference="clr-namespace:StabilityMatrix.Avalonia.ViewModels.Inference" |
||||
x:DataType="vmInference:PromptCardViewModel"> |
||||
<Design.PreviewWith> |
||||
<Grid Height="600" Width="600"> |
||||
<controls:PromptCard DataContext="{x:Static mocks:DesignData.PromptCardViewModel}"/> |
||||
</Grid> |
||||
</Design.PreviewWith> |
||||
|
||||
<Style Selector="controls|PromptCard"> |
||||
<!-- Set Defaults --> |
||||
<Setter Property="Template"> |
||||
<ControlTemplate> |
||||
<controls:Card Padding="8" HorizontalAlignment="{TemplateBinding HorizontalAlignment}"> |
||||
<controls:Card.Styles> |
||||
<Style Selector="avaloniaEdit|TextEditor"> |
||||
<Setter Property="Margin" Value="0,8,0,8"/> |
||||
<Setter Property="CornerRadius" Value="8" /> |
||||
<Setter Property="LineNumbersForeground" Value="DarkSlateGray"/> |
||||
<Setter Property="ShowLineNumbers" Value="True"/> |
||||
<Setter Property="WordWrap" Value="True"/> |
||||
<Setter Property="VerticalScrollBarVisibility" Value="Auto"/> |
||||
<Setter Property="Background" Value="{DynamicResource ScrollBarTrackStroke}" /> |
||||
</Style> |
||||
</controls:Card.Styles> |
||||
|
||||
<Grid Margin="4,8" RowDefinitions="Auto,*,Auto,*"> |
||||
<!-- Prompt --> |
||||
<TextBlock |
||||
Grid.Row="0" |
||||
Margin="4" |
||||
FontSize="14" |
||||
Text="Prompt" /> |
||||
<avaloniaEdit:TextEditor |
||||
x:Name="PromptEditor" |
||||
Grid.Row="1" |
||||
Document="{Binding PromptDocument}" |
||||
FontFamily="Cascadia Code,Consolas,Menlo,Monospace"/> |
||||
<!-- Negative Prompt --> |
||||
<TextBlock |
||||
Grid.Row="2" |
||||
Margin="4" |
||||
FontSize="14" |
||||
Text="Negative Prompt" /> |
||||
<avaloniaEdit:TextEditor |
||||
x:Name="NegativePromptEditor" |
||||
Grid.Row="3" |
||||
Document="{Binding NegativePromptDocument}" |
||||
FontFamily="Cascadia Code,Consolas,Menlo,Monospace"/> |
||||
</Grid> |
||||
</controls:Card> |
||||
</ControlTemplate> |
||||
</Setter> |
||||
</Style> |
||||
</Styles> |
@ -0,0 +1,80 @@
|
||||
using System.IO; |
||||
using System.Reflection; |
||||
using Avalonia.Controls; |
||||
using Avalonia.Controls.Primitives; |
||||
using Avalonia.Media; |
||||
using AvaloniaEdit; |
||||
using AvaloniaEdit.TextMate; |
||||
using StabilityMatrix.Avalonia.Extensions; |
||||
using TextMateSharp.Grammars; |
||||
using TextMateSharp.Internal.Themes.Reader; |
||||
using TextMateSharp.Registry; |
||||
using TextMateSharp.Themes; |
||||
|
||||
namespace StabilityMatrix.Avalonia.Controls; |
||||
|
||||
public class PromptCard : TemplatedControl |
||||
{ |
||||
/// <inheritdoc /> |
||||
protected override void OnApplyTemplate(TemplateAppliedEventArgs e) |
||||
{ |
||||
base.OnApplyTemplate(e); |
||||
|
||||
InitializeEditors(e); |
||||
} |
||||
|
||||
private static IRawTheme GetThemeFromStream(Stream stream) |
||||
{ |
||||
using var reader = new StreamReader(stream); |
||||
return ThemeReader.ReadThemeSync(reader); |
||||
} |
||||
|
||||
private static IRawTheme GetCustomTheme() |
||||
{ |
||||
using var stream = Assets.ThemeMatrixDarkJson.Open(); |
||||
return GetThemeFromStream(stream); |
||||
} |
||||
|
||||
private void InitializeEditors(TemplateAppliedEventArgs e) |
||||
{ |
||||
const ThemeName themeName = ThemeName.DimmedMonokai; |
||||
var registryOptions = new RegistryOptions(themeName); |
||||
|
||||
var registry = new Registry(registryOptions); |
||||
|
||||
using var stream = Assets.ImagePromptLanguageJson.Open(); |
||||
var promptGrammar = registry.LoadGrammarFromStream(stream); |
||||
|
||||
// Load theme |
||||
var theme = GetCustomTheme(); |
||||
|
||||
foreach (var editor in new[] |
||||
{ |
||||
e.NameScope.Find<TextEditor>("PromptEditor"), |
||||
e.NameScope.Find<TextEditor>("NegativePromptEditor") |
||||
}) |
||||
{ |
||||
if (editor is not null) |
||||
{ |
||||
var editorOptions = editor.Options; |
||||
editorOptions.ShowColumnRulers = true; |
||||
editorOptions.EnableTextDragDrop = true; |
||||
editorOptions.ExtendSelectionOnMouseUp = true; |
||||
// Config hyperlinks |
||||
editorOptions.EnableHyperlinks = true; |
||||
editorOptions.RequireControlModifierForHyperlinkClick = true; |
||||
editor.TextArea.TextView.LinkTextForegroundBrush = Brushes.Coral; |
||||
|
||||
var installation = editor.InstallTextMate(registryOptions); |
||||
|
||||
// Set the _textMateRegistry property |
||||
var field = typeof(TextMate.Installation).GetField("_textMateRegistry", BindingFlags.Instance | BindingFlags.NonPublic); |
||||
field!.SetValue(installation, registry); |
||||
|
||||
installation.SetGrammar(promptGrammar.GetScopeName()); |
||||
|
||||
installation.SetTheme(theme); |
||||
} |
||||
} |
||||
} |
||||
} |
@ -0,0 +1,10 @@
|
||||
using System.Text.Json.Serialization; |
||||
|
||||
namespace StabilityMatrix.Avalonia.Models.Inference; |
||||
|
||||
[JsonSerializable(typeof(PromptCardModel))] |
||||
public class PromptCardModel |
||||
{ |
||||
public string? Prompt { get; set; } |
||||
public string? NegativePrompt { get; set; } |
||||
} |
@ -0,0 +1,31 @@
|
||||
using AvaloniaEdit.Document; |
||||
using StabilityMatrix.Avalonia.Controls; |
||||
using StabilityMatrix.Avalonia.Models; |
||||
using StabilityMatrix.Avalonia.Models.Inference; |
||||
using StabilityMatrix.Core.Attributes; |
||||
|
||||
namespace StabilityMatrix.Avalonia.ViewModels.Inference; |
||||
|
||||
[View(typeof(PromptCard))] |
||||
public class PromptCardViewModel : ViewModelBase, ILoadableState<PromptCardModel> |
||||
{ |
||||
public TextDocument PromptDocument { get; } = new(); |
||||
public TextDocument NegativePromptDocument { get; } = new(); |
||||
|
||||
/// <inheritdoc /> |
||||
public void LoadState(PromptCardModel state) |
||||
{ |
||||
PromptDocument.Text = state.Prompt ?? ""; |
||||
NegativePromptDocument.Text = state.NegativePrompt ?? ""; |
||||
} |
||||
|
||||
/// <inheritdoc /> |
||||
public PromptCardModel SaveState() |
||||
{ |
||||
return new PromptCardModel |
||||
{ |
||||
Prompt = PromptDocument.Text, |
||||
NegativePrompt = NegativePromptDocument.Text |
||||
}; |
||||
} |
||||
} |
Loading…
Reference in new issue