diff --git a/src/features/terminal/runInTerminal.ts b/src/features/terminal/runInTerminal.ts index b0cc9a59..00ba38e1 100644 --- a/src/features/terminal/runInTerminal.ts +++ b/src/features/terminal/runInTerminal.ts @@ -1,12 +1,12 @@ import { Terminal, TerminalShellExecution } from 'vscode'; import { PythonEnvironment, PythonTerminalExecutionOptions } from '../../api'; +import { traceLog } from '../../common/logging'; import { createDeferred } from '../../common/utils/deferred'; import { onDidEndTerminalShellExecution } from '../../common/window.apis'; import { ShellConstants } from '../common/shellConstants'; import { identifyTerminalShell } from '../common/shellDetector'; import { quoteArgs } from '../execution/execUtils'; -import { normalizeShellPath } from './shells/common/shellUtils'; -import { traceLog } from '../../common/logging'; +import { getClearLineSequence, normalizeShellPath } from './shells/common/shellUtils'; export async function runInTerminal( environment: PythonEnvironment, @@ -52,10 +52,12 @@ export async function runInTerminal( await deferred.promise; } else { let text = quoteArgs([executable, ...allArgs]).join(' '); + const clearLineSequence = getClearLineSequence(terminal); if (shellType === ShellConstants.PWSH && !text.startsWith('&')) { // PowerShell requires commands to be prefixed with '&' to run them. text = `& ${text}`; } + terminal.sendText(clearLineSequence, false); // Clear the line before sending the command terminal.sendText(`${text}\n`); traceLog(`runInTerminal: sendText ${text}`); } diff --git a/src/features/terminal/shells/common/shellUtils.ts b/src/features/terminal/shells/common/shellUtils.ts index 766fd65a..9b93ccd3 100644 --- a/src/features/terminal/shells/common/shellUtils.ts +++ b/src/features/terminal/shells/common/shellUtils.ts @@ -1,7 +1,9 @@ +import { Terminal } from 'vscode'; import { PythonCommandRunConfiguration, PythonEnvironment } from '../../../../api'; import { isWindows } from '../../../../common/utils/platformUtils'; import { getConfiguration } from '../../../../common/workspace.apis'; import { ShellConstants } from '../../../common/shellConstants'; +import { identifyTerminalShell } from '../../../common/shellDetector'; import { quoteArgs } from '../../../execution/execUtils'; /** @@ -58,6 +60,7 @@ export function normalizeShellPath(filePath: string, shellType?: string): string } return filePath; } + export function getShellActivationCommand( shell: string, environment: PythonEnvironment, @@ -76,6 +79,7 @@ export function getShellActivationCommand( return activation; } + export function getShellDeactivationCommand( shell: string, environment: PythonEnvironment, @@ -160,3 +164,19 @@ export const shellIntegrationSupportedShells = [ export function shouldUseProfileActivation(shellType: string): boolean { return isWsl() || !shellIntegrationSupportedShells.includes(shellType); } + +/** + * Returns the appropriate sequence to clear the current line in the terminal based on the shell type. + * For PowerShell and CMD, it uses the ANSI escape code to clear the entire line and return the cursor to the start. + * For other shells, it uses Ctrl+U to clear from the cursor to the start of the line. + */ +export function getClearLineSequence(terminal: Terminal): string { + const shell = identifyTerminalShell(terminal); + switch (shell) { + case ShellConstants.PWSH: + case ShellConstants.CMD: + return '\x1b[2K\r'; // Clear entire line and return cursor to start + default: + return '\x15'; // Ctrl+U to clear from cursor to start of line + } +} \ No newline at end of file diff --git a/src/features/terminal/terminalActivationState.ts b/src/features/terminal/terminalActivationState.ts index 5181c12f..60c9e7c0 100644 --- a/src/features/terminal/terminalActivationState.ts +++ b/src/features/terminal/terminalActivationState.ts @@ -11,6 +11,7 @@ import { PythonEnvironment } from '../../api'; import { traceError, traceInfo, traceVerbose } from '../../common/logging'; import { onDidEndTerminalShellExecution, onDidStartTerminalShellExecution } from '../../common/window.apis'; import { getActivationCommand, getDeactivationCommand } from '../common/activation'; +import { getClearLineSequence } from './shells/common/shellUtils'; import { getShellIntegrationTimeout, isTaskTerminal } from './utils'; export interface DidChangeTerminalActivationStateEvent { @@ -195,17 +196,21 @@ export class TerminalActivationImpl implements TerminalActivationInternal { } private activateLegacy(terminal: Terminal, environment: PythonEnvironment) { - const activationCommands = getActivationCommand(terminal, environment); - if (activationCommands) { - terminal.sendText(activationCommands); + const activationCommand = getActivationCommand(terminal, environment); + const clearLineSequence = getClearLineSequence(terminal); + if (activationCommand) { + terminal.sendText(clearLineSequence, false); // Clear the line before activation command + terminal.sendText(activationCommand); this.activatedTerminals.set(terminal, environment); } } private deactivateLegacy(terminal: Terminal, environment: PythonEnvironment) { - const deactivationCommands = getDeactivationCommand(terminal, environment); - if (deactivationCommands) { - terminal.sendText(deactivationCommands); + const deactivationCommand = getDeactivationCommand(terminal, environment); + const clearLineSequence = getClearLineSequence(terminal); + if (deactivationCommand) { + terminal.sendText(clearLineSequence, false); // Clear the line before deactivation command + terminal.sendText(deactivationCommand); this.activatedTerminals.delete(terminal); } }