Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .github/ISSUE_TEMPLATE/bug_report.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,9 @@ Yes / No
// Keeping focus when running
"r.source.focus": "editor",

// Use active terminal for all commands, rather than creating a new R terminal
"r.alwaysUseActiveTerminal": false,

// Use bracketed paste mode
"r.bracketedPaste": false,
```
Expand Down
6 changes: 6 additions & 0 deletions ISSUE_TEMPLATE.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,4 +36,10 @@ Yes / No

// Keeping focus when running
"r.source.focus": "editor",

// Use active terminal for all commands, rather than creating a new R terminal
"r.alwaysUseActiveTerminal": false,

// Use bracketed paste mode
"r.bracketedPaste": false,
```
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ Requires [R](https://www.r-project.org/).
![Create R terminal](images/terminal.png)

* Run code in terminal containing existing R session, for example over SSH (`Run Selection/Line in Active Terminal`)
* Run all commands in terminal containing existing R session (enable config `r.alwaysUseActiveTerminal`)

![R over SSH](images/ssh.gif)

Expand Down Expand Up @@ -54,6 +55,7 @@ This extension contributes the following settings:
* `r.rterm.option`: R command line options (i.e: --vanilla)
* `r.source.encoding`: An optional encoding to pass to R when executing the file
* `r.source.focus`: Keeping focus when running (editor or terminal)
* `r.alwaysUseActiveTerminal`: Use active terminal for all commands, rather than creating a new R terminal
* `r.bracketedPaste`: For consoles supporting bracketed paste mode (such as Radian)

* Language server(developing [here](https://github.com/REditorSupport/languageserver))
Expand Down
5 changes: 5 additions & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -352,6 +352,11 @@
],
"description": "Keeping focus when running"
},
"r.alwaysUseActiveTerminal": {
"type": "boolean",
"default": false,
"description": "Use active terminal for all commands, rather than creating a new R terminal"
},
"r.bracketedPaste": {
"type": "boolean",
"default": false,
Expand Down
129 changes: 17 additions & 112 deletions src/extension.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,12 @@
// Import the module and reference it with the alias vscode in your code below
import { isNull } from "util";
import { commands, CompletionItem, ExtensionContext, IndentAction,
languages, Position, Terminal, TextDocument, window } from "vscode";
import { buildPkg, documentPkg, installPkg, loadAllPkg, testPkg } from "./package";
languages, Position, TextDocument, window } from "vscode";
import { previewDataframe, previewEnvironment } from "./preview";
import { createGitignore } from "./rGitignore";
import { createRTerm, deleteTerminal, rTerm } from "./rTerminal";
import { getSelection } from "./selection";
import { config, delay } from "./util";
import { chooseTerminal, chooseTerminalAndSendText, createRTerm, deleteTerminal,
runSelectionInTerm } from "./rTerminal";
import { config, ToRStringLiteral } from "./util";

const wordPattern = /(-?\d*\.\d\w*)|([^\`\~\!\@\$\^\&\*\(\)\=\+\[\{\]\}\\\|\;\:\'\"\,\<\>\/\s]+)/g;

Expand Down Expand Up @@ -47,12 +46,7 @@ export function activate(context: ExtensionContext) {
if (echo) {
rPath = [rPath, "echo = TRUE"].join(", ");
}
if (!rTerm) {
const success = createRTerm(true);
if (!success) { return; }
}
rTerm.sendText(`source(${rPath})`);
setFocus(rTerm);
chooseTerminalAndSendText(`source(${rPath})`);
}

function knitRmd(echo: boolean, outputFormat: string) {
Expand All @@ -67,14 +61,10 @@ export function activate(context: ExtensionContext) {
if (echo) {
rPath = [rPath, "echo = TRUE"].join(", ");
}
if (!rTerm) {
const success = createRTerm(true);
if (!success) { return; }
}
if (isNull(outputFormat)) {
rTerm.sendText(`rmarkdown::render(${rPath})`);
chooseTerminalAndSendText(`rmarkdown::render(${rPath})`);
} else {
rTerm.sendText(`rmarkdown::render(${rPath}, "${outputFormat}")`);
chooseTerminalAndSendText(`rmarkdown::render(${rPath}, "${outputFormat}")`);
}
}

Expand All @@ -83,83 +73,15 @@ export function activate(context: ExtensionContext) {
if (isNull(callableTerminal)) {
return;
}
setFocus(callableTerminal);
runSelectionInTerm(callableTerminal, rFunctionName);
}

async function chooseTerminal() {
if (window.terminals.length > 0) {
const RTermNameOpinions = ["R", "R Interactive"];
if (window.activeTerminal) {
const activeTerminalName = window.activeTerminal.name;
if (RTermNameOpinions.includes(activeTerminalName)) {
return window.activeTerminal;
}
} else {
// Creating a terminal when there aren't any already
// does not seem to set activeTerminal
if (window.terminals.length === 1) {
const activeTerminalName = window.terminals[0].name;
if (RTermNameOpinions.includes(activeTerminalName)) {
return window.terminals[0];
}
} else {
// tslint:disable-next-line: max-line-length
window.showInformationMessage("Error identifying terminal! This shouldn't happen, so please file an issue at https://github.com/Ikuyadeu/vscode-R/issues");
return null;
}
}
}

if (!rTerm) {
const success = createRTerm(true);
await delay(200); // Let RTerm warm up
if (!success) {
return null;
}
}
return rTerm;
}

function runSelectionInActiveTerm(rFunctionName: string[]) {
if (window.terminals.length < 1) {
window.showInformationMessage("There are no open terminals.");
} else {
runSelectionInTerm(window.activeTerminal, rFunctionName);
setFocus(window.activeTerminal);
}
}

async function runSelectionInTerm(term: Terminal, rFunctionName: string[]) {
const selection = getSelection();
if (selection.linesDownToMoveCursor > 0) {
commands.executeCommand("cursorMove", { to: "down", value: selection.linesDownToMoveCursor });
commands.executeCommand("cursorMove", { to: "wrappedLineFirstNonWhitespaceCharacter" });
}

if (selection.selectedTextArray.length > 1 && config.get("bracketedPaste")) {
// Surround with ANSI control characters for bracketed paste mode
selection.selectedTextArray[0] = "\x1b[200~" + selection.selectedTextArray[0];
selection.selectedTextArray[selection.selectedTextArray.length - 1] += "\x1b[201~";
}

for (let line of selection.selectedTextArray) {
await delay(8); // Increase delay if RTerm can't handle speed.

if (rFunctionName && rFunctionName.length) {
let rFunctionCall = "";
for (const feature of rFunctionName) {
rFunctionCall += feature + "(";
}
line = rFunctionCall + line.trim() + ")".repeat(rFunctionName.length);
}
term.sendText(line);
async function runSelectionInActiveTerm(rFunctionName: string[]) {
const callableTerminal = await chooseTerminal(true);
if (isNull(callableTerminal)) {
return;
}
}

function setFocus(term: Terminal) {
const focus = config.get("source.focus") as string;
term.show(focus !== "terminal");
runSelectionInTerm(callableTerminal, rFunctionName);
}

languages.registerCompletionItemProvider("r", {
Expand Down Expand Up @@ -198,30 +120,13 @@ export function activate(context: ExtensionContext) {
commands.registerCommand("r.createGitignore", createGitignore),
commands.registerCommand("r.previewDataframe", previewDataframe),
commands.registerCommand("r.previewEnvironment", previewEnvironment),
commands.registerCommand("r.loadAll", loadAllPkg),
commands.registerCommand("r.test", testPkg),
commands.registerCommand("r.install", installPkg),
commands.registerCommand("r.build", buildPkg),
commands.registerCommand("r.document", documentPkg),
commands.registerCommand("r.loadAll", () => chooseTerminalAndSendText("devtools::load_all()")),
commands.registerCommand("r.test", () => chooseTerminalAndSendText("devtools::test()")),
commands.registerCommand("r.install", () => chooseTerminalAndSendText("devtools::install()")),
commands.registerCommand("r.build", () => chooseTerminalAndSendText("devtools::build()")),
commands.registerCommand("r.document", () => chooseTerminalAndSendText("devtools::document()")),
window.onDidCloseTerminal(deleteTerminal),
);

function ToRStringLiteral(s: string, quote: string) {
if (s === null) {
return "NULL";
}
return (quote +
s.replace(/\\/g, "\\\\")
.replace(/"""/g, "\\" + quote)
.replace(/\\n/g, "\\n")
.replace(/\\r/g, "\\r")
.replace(/\\t/g, "\\t")
.replace(/\\b/g, "\\b")
.replace(/\\a/g, "\\a")
.replace(/\\f/g, "\\f")
.replace(/\\v/g, "\\v") +
quote);
}
}

// This method is called when your extension is deactivated
Expand Down
53 changes: 0 additions & 53 deletions src/package.ts

This file was deleted.

14 changes: 3 additions & 11 deletions src/preview.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,11 @@

import fs = require("fs-extra");
import { commands, extensions, window, workspace } from "vscode";
import { createRTerm, rTerm } from "./rTerminal";
import { chooseTerminalAndSendText } from "./rTerminal";
import { getSelection } from "./selection";
import { checkForSpecialCharacters, checkIfFileExists, delay } from "./util";

export async function previewEnvironment() {
if (!rTerm) {
const success = createRTerm(true);
if (!success) { return; }
}
if (!checkcsv()) {
return;
}
Expand All @@ -24,15 +20,11 @@ export async function previewEnvironment() {
+ envClass + ","
+ envOut + "), '"
+ pathToTmpCsv + "', row.names=FALSE, quote = TRUE)";
rTerm.sendText(rWriteCsvCommand);
chooseTerminalAndSendText(rWriteCsvCommand);
await openTmpCSV(pathToTmpCsv, tmpDir);
}

export async function previewDataframe() {
if (!rTerm) {
const success = createRTerm(true);
if (!success) { return; }
}
if (!checkcsv()) {
return;
}
Expand All @@ -52,7 +44,7 @@ export async function previewDataframe() {
const rWriteCsvCommand = "write.csv(" + dataframeName + ", '"
+ pathToTmpCsv
+ "', row.names = FALSE, quote = FALSE)";
rTerm.sendText(rWriteCsvCommand);
chooseTerminalAndSendText(rWriteCsvCommand);
await openTmpCSV(pathToTmpCsv, tmpDir);
}

Expand Down
Loading