Skip to content

Commit

Permalink
updating language while editor is running now possible (for some)
Browse files Browse the repository at this point in the history
  • Loading branch information
Nimaoth committed Dec 21, 2023
1 parent 8641f09 commit 1c1634d
Show file tree
Hide file tree
Showing 12 changed files with 165 additions and 67 deletions.
22 changes: 19 additions & 3 deletions config/absytree_config.nim
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,9 @@ import keybindings_helix
import keybindings_normal

proc handleAction*(action: string, args: JsonNode): bool {.wasmexport.} =
when not defined(wasm):
return false

infof "handleAction: {action}, {args}"

case action
Expand All @@ -32,6 +35,9 @@ proc handleAction*(action: string, args: JsonNode): bool {.wasmexport.} =
else: return false

proc handlePopupAction*(popup: EditorId, action: string, args: JsonNode): bool {.wasmexport.} =
when not defined(wasm):
return false

# infof "handlePopupAction: {action}, {args}"

case action:
Expand All @@ -47,16 +53,25 @@ proc handlePopupAction*(popup: EditorId, action: string, args: JsonNode): bool {
else: return false

proc handleDocumentEditorAction*(id: EditorId, action: string, args: JsonNode): bool {.wasmexport.} =
when not defined(wasm):
return false

# infof "handleDocumentEditorAction: {action}, {args}"
return false

proc handleTextEditorAction*(editor: TextDocumentEditor, action: string, args: JsonNode): bool {.wasmexport.} =
when not defined(wasm):
return false

# infof "handleTextEditorAction: {action}, {args}"

case action
else: return false

proc handleModelEditorAction*(editor: ModelDocumentEditor, action: string, args: JsonNode): bool {.wasmexport.} =
when not defined(wasm):
return false

# infof "handleModelEditorAction: {action}, {args}"

case action
Expand All @@ -68,6 +83,7 @@ proc postInitialize*(): bool {.wasmexport.} =

import default_config

loadDefaultOptions()
loadDefaultKeybindings()
loadVimKeybindings()
when defined(wasm):
loadDefaultOptions()
loadDefaultKeybindings()
loadVimKeybindings()
Binary file modified config/absytree_config_wasm.wasm
Binary file not shown.
1 change: 1 addition & 0 deletions config/keybindings_normal.nim
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,7 @@ proc loadNormalKeybindings*() {.scriptActionWasmNims("load-normal-keybindings").

addCommand "editor.model", "<LEADER>mr", "run-selected-function"
addCommand "editor.model", "<LEADER>md", "toggle-use-default-cell-builder"
addCommand "editor.model", "<LEADER>mc", "compile-language"

addCommand "editor.model", "gd", "goto-definition"
addCommand "editor.model", "gp", "goto-prev-reference"
Expand Down
14 changes: 11 additions & 3 deletions src/app.nim
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import std/[sequtils, strformat, strutils, tables, unicode, options, os, algorithm, json, macros, macrocache, sugar, streams, deques]
import misc/[id, util, timer, event, cancellation_token, myjsonutils, traits, rect_utils, custom_logger, custom_async, fuzzy_matching]
import misc/[id, util, timer, event, cancellation_token, myjsonutils, traits, rect_utils, custom_logger, custom_async, fuzzy_matching, array_set]
import ui/node
import scripting/[expose, scripting_base]
import platform/[platform, filesystem]
Expand Down Expand Up @@ -188,6 +188,7 @@ proc pushPopup*(self: App, popup: Popup)
proc popPopup*(self: App, popup: Popup)
proc openSymbolsPopup*(self: App, symbols: seq[Symbol], handleItemSelected: proc(symbol: Symbol), handleItemConfirmed: proc(symbol: Symbol), handleCanceled: proc())
proc help*(self: App, about: string = "")
proc getAllDocuments*(self: App): seq[Document]

implTrait AppInterface, App:
proc platform*(self: App): Platform = self.platform
Expand Down Expand Up @@ -215,6 +216,7 @@ implTrait AppInterface, App:
pushPopup(void, App, Popup)
popPopup(void, App, Popup)
openSymbolsPopup(void, App, seq[Symbol], proc(symbol: Symbol), proc(symbol: Symbol), proc())
getAllDocuments(seq[Document], App)

type
AppLogger* = ref object of Logger
Expand Down Expand Up @@ -537,6 +539,10 @@ proc getPopupForId*(self: App, id: EditorId): Option[Popup] =

return Popup.none

proc getAllDocuments*(self: App): seq[Document] =
for it in self.editors.values:
result.incl it.getDocument

import text/[text_editor, text_document]
import ast/[model_document]
import selector_popup
Expand Down Expand Up @@ -1051,7 +1057,7 @@ proc toggleConsoleLogger*(self: App) {.expose("editor").} =
# self.createAndAddView(newKeybindAutocompletion())

proc closeCurrentView*(self: App) {.expose("editor").} =
self.views[self.currentView].editor.unregister()
let view = self.views[self.currentView]
self.views.delete self.currentView

if self.views.len == 0:
Expand All @@ -1061,6 +1067,8 @@ proc closeCurrentView*(self: App) {.expose("editor").} =
else:
self.help()

self.hiddenViews.add view

self.currentView = self.currentView.clamp(0, self.views.len - 1)
self.platform.requestRender()

Expand Down Expand Up @@ -1103,7 +1111,7 @@ proc setLayout*(self: App, layout: string) {.expose("editor").} =
of "horizontal": HorizontalLayout()
of "vertical": VerticalLayout()
of "fibonacci": FibonacciLayout()
else: HorizontalLayout()
else: FibonacciLayout()
self.platform.requestRender()

proc commandLine*(self: App, initialValue: string = "") {.expose("editor").} =
Expand Down
3 changes: 2 additions & 1 deletion src/app_interface.nim
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import misc/[traits]
import platform/platform
import workspaces/workspace
import text/language/language_server_base
import events, document_editor, popup, config_provider
import events, document_editor, document, popup, config_provider
from scripting_api import EditorId

traitRef AppInterface:
Expand All @@ -27,5 +27,6 @@ traitRef AppInterface:
method pushPopup*(self: AppInterface, popup: Popup)
method popPopup*(self: AppInterface, popup: Popup)
method openSymbolsPopup*(self: AppInterface, symbols: seq[Symbol], handleItemSelected: proc(symbol: Symbol), handleItemConfirmed: proc(symbol: Symbol), handleCanceled: proc())
method getAllDocuments*(self: AppInterface): seq[Document]

var gAppInterface*: AppInterface = nil
4 changes: 2 additions & 2 deletions src/ast/base_language.nim
Original file line number Diff line number Diff line change
Expand Up @@ -276,7 +276,7 @@ let assignmentClass* = newNodeClass(IdAssignment, "Assignment", alias="=", base=
NodeChildDescription(id: IdAssignmentValue, role: "value", class: expressionClass.id, count: ChildCount.One),
])

var builder = newCellBuilder()
var builder = newCellBuilder(IdBaseLanguage)

builder.addBuilderFor emptyLineClass.id, idNone(), proc(map: NodeCellMap, builder: CellBuilder, node: AstNode, owner: AstNode): Cell =
var cell = ConstantCell(id: newId().CellId, node: owner ?? node, referenceNode: node)
Expand Down Expand Up @@ -1997,7 +1997,7 @@ scopeComputers[IdThenCase] = proc(ctx: ModelComputationContextBase, node: AstNod
return ctx.computeDefaultScope(node)

let baseInterfaces* = newLanguage(IdBaseInterfaces, "BaseInterfaces", @[namedInterface, declarationInterface])
registerBuilder(IdBaseInterfaces, newCellBuilder())
registerBuilder(IdBaseInterfaces, newCellBuilder(IdBaseInterfaces))

let baseLanguage* = newLanguage(IdBaseLanguage, "Base",
@[
Expand Down
43 changes: 27 additions & 16 deletions src/ast/cells.nim
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import std/[tables, strutils, strformat, options, algorithm]
import std/[tables, strutils, strformat, options, algorithm, sequtils]
import ui/node
import misc/[id, util, custom_logger, macro_utils]
import model, ast_ids
Expand Down Expand Up @@ -56,8 +56,9 @@ type
CellBuilderFunction* = proc(map: NodeCellMap, builder: CellBuilder, node: AstNode, owner: AstNode): Cell

CellBuilder* = ref object
builders*: Table[ClassId, seq[tuple[builderId: Id, impl: CellBuilderFunction, flags: CellBuilderFlags]]]
builders2*: Table[ClassId, seq[tuple[builderId: Id, impl: CellBuilderCommands, flags: CellBuilderFlags]]]
sourceLanguage*: LanguageId
builders*: Table[ClassId, seq[tuple[builderId: Id, impl: CellBuilderFunction, flags: CellBuilderFlags, sourceLanguage: LanguageId]]]
builders2*: Table[ClassId, seq[tuple[builderId: Id, impl: CellBuilderCommands, flags: CellBuilderFlags, sourceLanguage: LanguageId]]]
preferredBuilders*: Table[ClassId, Id]
forceDefault*: bool

Expand Down Expand Up @@ -555,42 +556,52 @@ template horizontalCell(cell: Cell, node: AstNode, owner: AstNode, childCell: un
finally:
cell.add childCell

proc newCellBuilder*(): CellBuilder =
proc newCellBuilder*(sourceLanguageId: LanguageId): CellBuilder =
new result
result.sourceLanguage = sourceLanguageId

proc clear*(self: CellBuilder) =
self.builders.clear()
self.preferredBuilders.clear()
self.forceDefault = false

proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, flags: CellBuilderFlags, builder: CellBuilderFunction) =
proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, flags: CellBuilderFlags, builder: CellBuilderFunction, sourceLanguage = LanguageId.none) =
# log lvlWarn, fmt"addBuilderFor {classId}"
if self.builders.contains(classId):
self.builders[classId].add (builderId, builder, flags)
self.builders[classId].add (builderId, builder, flags, self.sourceLanguage)
else:
self.builders[classId] = @[(builderId, builder, flags)]
self.builders[classId] = @[(builderId, builder, flags, self.sourceLanguage)]

proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, builder: CellBuilderFunction) =
self.addBuilderFor(classId, builderId, 0.CellBuilderFlags, builder)
proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, builder: CellBuilderFunction, sourceLanguage = LanguageId.none) =
self.addBuilderFor(classId, builderId, 0.CellBuilderFlags, builder, sourceLanguage)

proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, flags: CellBuilderFlags, commands: openArray[CellBuilderCommand]) =
proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, flags: CellBuilderFlags, commands: openArray[CellBuilderCommand], sourceLanguage = LanguageId.none) =
# log lvlWarn, fmt"addBuilderFor {classId}"
var builder = CellBuilderCommands(commands: @commands)
if self.builders2.contains(classId):
self.builders2[classId].add (builderId, builder, flags)
self.builders2[classId].add (builderId, builder, flags, sourceLanguage.get(self.sourceLanguage))
else:
self.builders2[classId] = @[(builderId, builder, flags)]
self.builders2[classId] = @[(builderId, builder, flags, sourceLanguage.get(self.sourceLanguage))]

proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, commands: openArray[CellBuilderCommand]) =
self.addBuilderFor(classId, builderId, 0.CellBuilderFlags, commands)
proc addBuilderFor*(self: CellBuilder, classId: ClassId, builderId: Id, commands: openArray[CellBuilderCommand], sourceLanguage = LanguageId.none) =
self.addBuilderFor(classId, builderId, 0.CellBuilderFlags, commands, sourceLanguage)

proc addBuilder*(self: CellBuilder, other: CellBuilder) =
# remove existing builders for the other source language
for (classId, builders) in self.builders.mpairs:
builders = builders.filterIt(it.sourceLanguage != other.sourceLanguage)
# todo: remove from preferredBuilders

for (classId, builders) in self.builders2.mpairs:
builders = builders.filterIt(it.sourceLanguage != other.sourceLanguage)
# todo: remove from preferredBuilders

for pair in other.builders.pairs:
for builder in pair[1]:
self.addBuilderFor(pair[0], builder.builderId, builder.flags, builder.impl)
self.addBuilderFor(pair[0], builder.builderId, builder.flags, builder.impl, builder.sourceLanguage.some)
for pair in other.builders2.pairs:
for builder in pair[1]:
self.addBuilderFor(pair[0], builder.builderId, builder.flags, builder.impl.commands)
self.addBuilderFor(pair[0], builder.builderId, builder.flags, builder.impl.commands, builder.sourceLanguage.some)
for pair in other.preferredBuilders.pairs:
self.preferredBuilders[pair[0]] = pair[1]

Expand Down
2 changes: 1 addition & 1 deletion src/ast/editor_language.nim
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ let loadAppFileClass* = newNodeClass(IdLoadAppFile, "LoadAppFile", alias="load a
children=[
NodeChildDescription(id: IdLoadAppFileArgument, role: "file", class: expressionClass.id, count: ChildCount.One)])

var builder = newCellBuilder()
var builder = newCellBuilder(IdEditorLanguage)

builder.addBuilderFor IdLoadAppFile, idNone(), [
CellBuilderCommand(kind: CollectionCell, uiFlags: &{LayoutHorizontal}),
Expand Down
5 changes: 2 additions & 3 deletions src/ast/lang/cell_language.nim
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ export id, ast_ids

logCategory "cell-language"

var builder = newCellBuilder()
var builder = newCellBuilder(IdCellLanguage)
# var typeComputers = initTable[ClassId, proc(ctx: ModelComputationContextBase, node: AstNode): AstNode]()
# var valueComputers = initTable[ClassId, proc(ctx: ModelComputationContextBase, node: AstNode): AstNode]()
var scopeComputers = initTable[ClassId, proc(ctx: ModelComputationContextBase, node: AstNode): seq[AstNode]]()
Expand Down Expand Up @@ -225,5 +225,4 @@ registerBuilder(IdCellLanguage, builder)
# langLanguage.model.addRootNode createNodesForLanguage(langLanguage)

proc updateCellLanguage*(model: Model) =
cellLanguage = createLanguageFromModel(model)
cellLanguage.name = "Cells"
cellLanguage.updateLanguageFromModel(model)
18 changes: 12 additions & 6 deletions src/ast/lang/lang_language.nim
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ let classDefinitionClass* = newNodeClass(IdClassDefinition, "ClassDefinition", a
NodeChildDescription(id: IdClassDefinitionSubstitutionReference, role: "substitution reference", class: IdRoleReference, count: ChildCount.ZeroOrOne),
])

var builder = newCellBuilder()
var builder = newCellBuilder(IdLangLanguage)

builder.addBuilderFor IdPropertyTypeBool, idNone(), [CellBuilderCommand(kind: AliasCell, themeForegroundColors: @["keyword"], disableEditing: true)]
builder.addBuilderFor IdPropertyTypeString, idNone(), [CellBuilderCommand(kind: AliasCell, themeForegroundColors: @["keyword"], disableEditing: true)]
Expand Down Expand Up @@ -620,11 +620,11 @@ proc createCellBuilderFromDefinition(builder: CellBuilder, def: AstNode) =

builder.addBuilderFor targetClass.ClassId, idNone(), commands

proc createLanguageFromModel*(model: Model): Language =
log lvlInfo, fmt"createLanguageFromModel {model.path} ({model.id})"
proc updateLanguageFromModel*(language: Language, model: Model) =
log lvlInfo, fmt"updateLanguageFromModel {model.path} ({model.id})"
var classMap = initTable[ClassId, NodeClass]()
var classes: seq[NodeClass] = @[]
var builder = newCellBuilder()
var builder = newCellBuilder(language.id)

for def in model.rootNodes:
for _, c in def.children(IdLangRootChildren):
Expand All @@ -639,9 +639,15 @@ proc createLanguageFromModel*(model: Model): Language =
var scopeComputers = initTable[ClassId, proc(ctx: ModelComputationContextBase, node: AstNode): seq[AstNode]]()
var validationComputers = initTable[ClassId, proc(ctx: ModelComputationContextBase, node: AstNode): bool]()

language.update(classes, typeComputers, valueComputers, scopeComputers, validationComputers, )
registerBuilder(language.id, builder)

proc createLanguageFromModel*(model: Model): Language =
log lvlInfo, fmt"createLanguageFromModel {model.path} ({model.id})"

let name = model.path.splitFile.name
result = newLanguage(model.id.LanguageId, name, classes, typeComputers, valueComputers, scopeComputers, validationComputers)
registerBuilder(result.id, builder)
result = newLanguage(model.id.LanguageId, name)
result.updateLanguageFromModel(model)

proc createNodeFromNodeClass(classes: var Table[ClassId, AstNode], class: NodeClass): AstNode =
# log lvlInfo, fmt"createNodeFromNodeClass {class.name}"
Expand Down
Loading

0 comments on commit 1c1634d

Please sign in to comment.