Godot WIP

This commit is contained in:
Matt Parker
2025-08-18 18:13:22 +10:00
parent 0701af3ac3
commit c0c240cf0e
10 changed files with 232 additions and 10 deletions

View File

@@ -121,7 +121,8 @@ public static class RoslynAnalysis
Guard.Against.Null(compilation, nameof(compilation));
var diagnostics = compilation.GetDiagnostics(cancellationToken);
return diagnostics.Where(d => d.Severity is not DiagnosticSeverity.Hidden).ToImmutableArray();
diagnostics = diagnostics.Where(d => d.Severity is not DiagnosticSeverity.Hidden).ToImmutableArray();
return diagnostics;
}
public static async Task<ImmutableArray<CodeAction>> GetCodeFixesAsync(Diagnostic diagnostic)

Binary file not shown.

View File

@@ -0,0 +1,35 @@
[remap]
importer="font_data_dynamic"
type="FontFile"
uid="uid://7jc0nj310cu6"
path="res://.godot/imported/CascadiaCode.ttf-a3719bc78bb5325e1cfcc893e4ab58da.fontdata"
[deps]
source_file="res://CascadiaCode.ttf"
dest_files=["res://.godot/imported/CascadiaCode.ttf-a3719bc78bb5325e1cfcc893e4ab58da.fontdata"]
[params]
Rendering=null
antialiasing=1
generate_mipmaps=false
disable_embedded_bitmaps=true
multichannel_signed_distance_field=false
msdf_pixel_range=8
msdf_size=48
allow_system_fallback=true
force_autohinter=false
hinting=1
subpixel_positioning=4
keep_rounding_remainders=true
oversampling=0.0
Fallbacks=null
fallbacks=[]
Compress=null
compress=true
preload=[]
language_support={}
script_support={}
opentype_features={}

View File

@@ -0,0 +1,30 @@
using System.Linq;
using Godot;
using Godot.Collections;
using System.Text.RegularExpressions;
namespace SharpIDE.Godot;
public partial class CustomHighlighter : SyntaxHighlighter
{
public override Dictionary _GetLineSyntaxHighlighting(int line)
{
var highlights = new Dictionary();
var text = GetTextEdit().GetLine(line);
var regex = new Regex(@"\bTODO\b");
var matches = regex.Matches(text);
foreach (Match match in matches)
{
highlights[match.Index] = new Dictionary
{
{ "color", new Color(1, 0, 0) }, // red
{ "underline", true }, // not implemented
{ "length", match.Length } // not implemented
};
}
return highlights;
}
}

View File

@@ -0,0 +1 @@
uid://b6wpiabl7sutg

View File

@@ -1,6 +1,51 @@
extends Node
extends Node2D
# Declare an empty dictionary object
var game = {}
# asdfasdfasdfadsf asdf asdfa sdfadf
func _ready():
# Initialize a player dictionary
var player = {
"name": "Thor",
"inventory": ["sword", "shield", "map"],
"location": "Castellion",
"energy": 67
}
if game.empty():
# Add data to the game dictionary
game["player"] = player
game["score"] = 0
game["dummy"] = null
if game.has("dummy"):
game.erase("dummy")
print(game.get("dummy", "Key not found!"))
if game.has_all(["player", "score"]):
print(game["player"]["name"])
player["energy"] += 1
print(game.keys().size())
print(game.size())
print(player.values()[0])
# Alternative way to initialize a dictionary
var d = {
a = {
a1 = {
a11 = 1, a12 = 2
},
a2 = 3
},
b = 1
}
# Make copies of the dictionary
var deep_copy = d.duplicate(true)
var shallow_copy = d.duplicate()
print(deep_copy)
# I expected the shallow copy to be truncated
print(shallow_copy)

View File

@@ -1,4 +1,14 @@
using System;
using System.IO;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Runtime.Loader;
using Godot;
using Microsoft.Build.Locator;
using Microsoft.CodeAnalysis.CodeFixes;
using Microsoft.CodeAnalysis.Host.Mef;
using SharpIDE.Application.Features.Analysis;
using SharpIDE.Application.Features.SolutionDiscovery.VsPersistence;
namespace SharpIDE.Godot;
@@ -8,13 +18,26 @@ public partial class IdeRoot : Control
private FileDialog _fileDialog = null!;
public override void _Ready()
{
MSBuildLocator.RegisterDefaults();
_openSlnButton = GetNode<Button>("%OpenSlnButton");
_fileDialog = GetNode<FileDialog>("%OpenSolutionDialog");
_fileDialog.FileSelected += OnFileSelected;
//_fileDialog.Visible = true;
}
private void OnFileSelected(string path)
private async void OnFileSelected(string path)
{
GD.Print($"Selected: {path}");
try
{
GD.Print($"Selected: {path}");
var solutionModel = await VsPersistenceMapper.GetSolutionModel(path);
RoslynAnalysis.StartSolutionAnalysis(path);
}
catch (Exception e)
{
GD.PrintErr($"Error loading solution: {e.Message}");
GD.PrintErr(e.StackTrace);
}
}
}

View File

@@ -1,6 +1,8 @@
[gd_scene load_steps=2 format=3 uid="uid://b2oniigcp5ew5"]
[gd_scene load_steps=4 format=3 uid="uid://b2oniigcp5ew5"]
[ext_resource type="Script" uid="uid://bavypuy7b375x" path="res://IdeRoot.cs" id="1_whawi"]
[ext_resource type="Script" uid="uid://du2lt7r1p1qfy" path="res://SharpIdeCodeEdit.cs" id="2_qjf5e"]
[ext_resource type="FontFile" uid="uid://7jc0nj310cu6" path="res://CascadiaCode.ttf" id="2_rk34b"]
[node name="IdeRoot" type="Control"]
layout_mode = 3
@@ -46,16 +48,20 @@ split_offset = 250
[node name="SolutionExplorerPanel" type="Panel" parent="VBoxContainer/HBoxContainer/HSplitContainer"]
layout_mode = 2
[node name="CodeEdit" type="CodeEdit" parent="VBoxContainer/HBoxContainer/HSplitContainer"]
[node name="SharpIdeCodeEdit" type="CodeEdit" parent="VBoxContainer/HBoxContainer/HSplitContainer"]
layout_mode = 2
theme_override_fonts/font = ExtResource("2_rk34b")
highlight_current_line = true
gutters_draw_line_numbers = true
code_completion_enabled = true
auto_brace_completion_enabled = true
script = ExtResource("2_qjf5e")
HighlightStartOffset = 0
[node name="OpenSolutionDialog" type="FileDialog" parent="."]
unique_name_in_owner = true
title = "Open a File"
visible = true
position = Vector2i(0, 36)
ok_button_text = "Open"
dialog_hide_on_ok = true
file_mode = 0

View File

@@ -0,0 +1,80 @@
using Godot;
namespace SharpIDE.Godot;
public partial class SharpIdeCodeEdit : CodeEdit
{
[Signal]
public delegate void CodeFixesRequestedEventHandler();
[Export]
public int HighlightStartOffset = 0;
[Export]
public int HighlightEndOffset = 0;
private int _currentLine;
private int _selectionStartCol;
private int _selectionEndCol;
public override void _Ready()
{
//AddThemeFontOverride("Cascadia Code", ResourceLoader.Load<Font>("res://CascadiaCode.ttf"));
this.CodeCompletionRequested += OnCodeCompletionRequested;
this.CodeFixesRequested += OnCodeFixesRequested;
this.CaretChanged += () =>
{
_selectionStartCol = GetSelectionFromColumn();
_selectionEndCol = GetSelectionToColumn();
_currentLine = GetCaretLine();
GD.Print($"Selection changed to line {_currentLine}, start {_selectionStartCol}, end {_selectionEndCol}");
};
this.SyntaxHighlighter = new CustomHighlighter();
}
public void UnderlineRange(int line, int caretStartCol, int caretEndCol, Color color, float thickness = 1.5f)
{
if (line < 0 || line >= GetLineCount())
return;
if (caretStartCol >= caretEndCol) // nothing to draw
return;
// Clamp columns to line length
int lineLength = GetLine(line).Length;
caretStartCol = Mathf.Clamp(caretStartCol, 0, lineLength);
caretEndCol = Mathf.Clamp(caretEndCol, 0, lineLength);
var charRect = GetRectAtLineColumn(line, caretEndCol);
var charWidth = charRect.Size.X;
var startPos = GetPosAtLineColumn(line, caretStartCol);
if (caretStartCol is 0)
{
startPos.X -= 9; // Seems to be a bug or intended "feature" of GetPosAtLineColumn
}
var endPos = GetPosAtLineColumn(line, caretEndCol);
startPos.X += charWidth;
endPos.X += charWidth;
startPos.Y -= 1;
endPos.Y -= 1;
DrawLine(startPos, endPos, color, thickness);
}
public override void _Draw()
{
UnderlineRange(_currentLine, _selectionStartCol, _selectionEndCol, new Color(1, 0, 0));
//UnderlineRange(_currentLine, 0, 7, new Color(1, 0, 0));
}
private void OnCodeFixesRequested()
{
GD.Print("Code fixes requested");
}
private void OnCodeCompletionRequested()
{
var caretColumn = GetCaretColumn();
var caretLine = GetCaretLine();
GD.Print($"Code completion requested at line {caretLine}, column {caretColumn}");
}
}

View File

@@ -0,0 +1 @@
uid://du2lt7r1p1qfy