# Reference: the app API > Neutral description of what a command may call on an editor built on turbo-core. This is not the whole of `app`; it is the part a command and its tests use. ## Construction | Function | Description | | --- | --- | | `New(screen tcell.Screen, themeName string, p profile.Profile) *App` | An editor drawing on `screen`, being the editor `p` describes. An unknown theme name falls back to the default rather than failing. | | `ProjectRoot(p profile.Profile, files []string) string` | The directory a language server should work in: the nearest directory at or above the first file holding one of `p.RootMarkers`, or the working directory. | ## Running it | Method | Description | | --- | --- | | `Run() error` | Draws and handles events until the user leaves. Returns nil when the screen was finalised. | | `Quitting() bool` | Whether the editor is on its way out. | | `Tick()` | One turn of the loop's state-driven work, without waiting for an event. | | `Handle(event tcell.Event)` | Routes one event through the whole chain, as the loop does. | | `Render()` | Lays out and paints one frame. | `Tick`, `Handle` and `Render` are exported so an editor can drive itself end to end from a test, with no terminal and no event loop. ## Files | Method | Description | | --- | --- | | `NewFile()` | Opens an empty window. | | `Open(path string)` | Opens a file, raising the window when it is already open. | | `SaveFile()`, `SaveFileAs()`, `CloseFile()` | As the File menu. | | `Undo()`, `Redo()`, `Cut()`, `Copy()`, `Paste()`, `SelectAll()` | As the Edit menu. Redo is `Ctrl-R`; `Ctrl-Y` deletes a line. | | `InsertLine()`, `DeleteLine()` | Turbo C's `Ctrl-N` and `Ctrl-Y`: a blank line opened above the cursor, and the cursor's own line removed. | | `ActiveView() *editor.View` | The editing view of the front window, or nil when it is a terminal, the tree, or nothing. | ## Settings | Method | Description | | --- | --- | | `UseSettings(s settings.Settings, path string)` | Applies a project's settings and remembers where they came from. The theme is not applied here — the caller resolves it, because a `-theme` flag overrides the project's choice. | | `SettingsPath() string` | The settings file being followed, or `""`. | | `SetAutosave(on bool, delay time.Duration)` | Turns autosave on or off. | The settings file is also re-read **after every save that writes it**, from either save path, so a change made in the editor takes effect without a restart. Autosave and its delay are re-applied; the theme is not. A file that no longer parses reports `Saved, but not applied: …` and leaves the previous values in force. ## The project's three files `settings.toml`, `snippets.toml` and `tools.toml` behave alike, and exactly one of each create/open pair is ever available: you can create the file the project has not got, and open the one it has. The menus grey out the other. | Method | Description | | --- | --- | | `CreateProjectSettings()`, `CreateSnippets()`, `CreateTools()` | Write the starter file from the profile's template and open it. Creating over an existing file reports `Already there` and opens it unchanged — unreachable from the menu, which greys the item out. | | `OpenProjectSettings()`, `OpenSnippets()`, `OpenTools()` | Open the project's file. Never writes: a project without one is told which item makes it. `OpenSnippets` opens the **project's** file, never the user's. | | `HasProjectSettings() bool`, `HasProjectSnippets() bool`, `HasProjectTools() bool` | Whether the project has each file. What decides, for all six menu items, which of the pair is greyed out. | ## The language server | Method | Description | | --- | --- | | `StartLanguageServer(ctx context.Context, root string)` | Starts it in the background, so a slow start-up does not hold the first keystroke up. | | `Language() *Language` | The language-server side. Every method on it is a no-op when nothing is connected. | | `RequestCompletion()` | Asks for a completion at the cursor. | | `DescribeSymbol()`, `GoToDefinition()`, `GoToTypeDefinition()`, `FindImplementations()`, `FindReferences()` | The Code menu's questions about the symbol under the cursor. Each jumps when there is one answer, offers a list when there are several, and distinguishes "nothing found" from "the server is not ready". | | `SymbolInFile()`, `SymbolInProject()` | The file's own outline, and a search across the project. Both always offer the list, even for a single match: finding *which* thing has a name is the answer. | | `ShowProblems()` | Every diagnostic the server has reported, for every file it has spoken about. | ### Language | Method | Description | | --- | --- | | `Ready() bool` | Whether a server is connected and initialised. | | `Knows(path string) bool` | Whether the server has been told the document is open. Spelling-independent: a file opened by a relative path is known by its absolute one too, and one opened through a symbolic link by its real path. | | `Status() string` | The one-line state shown on the status bar. | | `Report() Report` | Status, server path, root and readiness together. | | `Stop(ctx context.Context)` | Shuts the server down. | | `TypeDefinition`, `Implementation`, `References` | The three location requests beside `Definition`. `References` counts the declaration as one of the answers. | | `DocumentSymbols(ctx, path) ([]lsp.Symbol, error)` | What one file declares, flattened, in file order. | | `WorkspaceSymbols(ctx, query) ([]lsp.Symbol, error)` | Symbols matching a query anywhere in the project. What "matching" means belongs to the server. | | `Diagnostics(path string) []lsp.Diagnostic` | What the server reported for a file. The path is resolved to an absolute one first: a server publishes absolute URIs and a buffer may hold the relative path the command line gave it. | | `FirstError(path string) (lsp.Diagnostic, bool)` | The first error-level diagnostic. | | `AllDiagnostics() []FileDiagnostic` | Every problem for every file, sorted by file then line. | Saving keeps the server's set of open documents true. Writing a file the server knows sends `didSave`; writing one it does not know — a window that began Untitled, saved for the first time — sends `didOpen`, so the document works from that save on. A save that creates the file also reports it created (`workspace/didChangeWatchedFiles`), for servers that list a package's files from the directory and would otherwise never diagnose it — moon-lsp. Save As under a genuinely different name also closes the old document on the server first; a mere change of spelling of the same file does not count as a rename. ## What is on screen | Method | Description | | --- | --- | | `Profile() profile.Profile` | Which editor this is. | | `Theme() *theme.Theme`, `ThemeName() string` | The theme in use. | | `Desktop() *ui.Desktop` | The windows. | | `MenuBar() *ui.MenuBar` | The bar. | | `StatusBar() *ui.StatusBar` | The bar along the bottom. | | `Completion() *CompletionBox` | The completion popup. | | `Modals() int`, `TopModal() *ui.Dialog` | The dialog stack. | | `Message(text string)` | A one-line note on the status bar. | | `ShowMessage(title, message string)` | A modal box. | ## Tool parameters A command may ask for values before it runs, by writing `{{label}}` where the value goes. `app.RunTool` opens a box for them; nothing here draws anything. | Function or method | Description | | --- | --- | | `(Tool) Placeholders() []Placeholder` | The values the command asks for, in first-appearance order, a repeated label reported once. Nil when it asks for none. | | `(Tool) Fill(values map[string]string) string` | The command with every placeholder replaced. A value is shell-quoted unless its placeholder is `Raw`; a label with no entry becomes empty. | | `ShellQuote(value string) string` | Wraps a string so `sh -c` sees exactly one argument, whatever is in it. | | `Placeholder` field | Type | Description | | --- | --- | --- | | `Label` | `string` | What to ask for: the text between the braces, trimmed, without a trailing `...`. | | `Raw` | `bool` | The value goes in verbatim rather than shell-quoted. | `Load` refuses a command with an unclosed `{{` or a placeholder with no label, so a `Tool` that came from a file always parses. | Function | Description | | --- | --- | | `app.MaxParameterFields(screenHeight int) int` | How many values a box can ask for on a screen that tall. A caller with more to ask must say so rather than opening one. | | `app.NewParametersDialog(title string, labels []string, initial map[string]string, screen ui.Rect) *ParametersDialog` | The box. `initial` pre-fills a field by label. | | `(*ParametersDialog) Dialog() *ui.Dialog` | The modal to push. | | `(*ParametersDialog) Values() map[string]string` | What was typed, by label. | ## Errors `app` returns no errors from its actions: everything that can fail is reported to the user on the status bar or in a dialog, because the editor is what they would use to fix it. ## See also - [Build an editor](../tutorials/build-an-editor.md) - [Profile reference](profile.md)