Skip to content

Commit

Permalink
Cleaned up code
Browse files Browse the repository at this point in the history
  • Loading branch information
NonSpicyBurrito committed Sep 8, 2023
1 parent dcec9a4 commit a396191
Show file tree
Hide file tree
Showing 5 changed files with 86 additions and 77 deletions.
10 changes: 10 additions & 0 deletions src/config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import * as vscode from 'vscode'

export const getMaxCount = () =>
vscode.workspace.getConfiguration('hoverlens').get('maximumCursorCount', 3)

export const getDebounceUpdate = () =>
vscode.workspace.getConfiguration('hoverlens').get('debounceUpdate', 50)

export const getMaxShift = () =>
vscode.workspace.getConfiguration('hoverlens').get('maximumShiftCount', 20)
50 changes: 23 additions & 27 deletions src/decoration.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,16 +4,21 @@ import {
removeEmptyLines,
toPlainText,
} from './formatting'
import { getMaxCount, getMaxShift } from './config'

export async function getDecorations(
export type Decoration = {
editor: vscode.TextEditor
type: vscode.TextEditorDecorationType
line: number
}

export const getDecorations = async (
editor: vscode.TextEditor,
selections: readonly vscode.Selection[]
) {
) => {
if (!selections.length) return []

const maxCount = vscode.workspace
.getConfiguration('hoverlens')
.get('maximumCursorCount', 3)
const maxCount = getMaxCount()
if (maxCount > 0 && selections.length > maxCount) return []

const positions = selections
Expand All @@ -33,9 +38,10 @@ export async function getDecorations(
hovers.map(toPlainText).map(removeEmptyLines).join('\n').split('\n')
)

const maxShift = vscode.workspace
.getConfiguration('hoverlens')
.get('maximumShiftCount', 20)
const maxShift = getMaxShift()

const getLineLength = (line: number) =>
editor.document.lineAt(line).range.end.character

const layouts = positions.map((position, i) => {
const paddings: number[] = []
Expand Down Expand Up @@ -67,26 +73,17 @@ export async function getDecorations(
return texts
})

return layouts
.map((paddings, i) =>
paddings.map(
(padding, j) =>
[
editor,
createDecorationType(texts[i][j], padding),
positions[i].line + j,
] as const
)
)
.flat()

function getLineLength(line: number) {
return editor.document.lineAt(line).range.end.character
}
return layouts.flatMap((paddings, i) =>
paddings.map((padding, j) => ({
editor,
type: createDecorationType(texts[i][j], padding),
line: positions[i].line + j,
}))
)
}

function createDecorationType(text: string, padding: number) {
return vscode.window.createTextEditorDecorationType({
const createDecorationType = (text: string, padding: number) =>
vscode.window.createTextEditorDecorationType({
after: {
contentText: changeLeadingSpacesToNonBreaking(
' '.repeat(padding) + text
Expand All @@ -97,4 +94,3 @@ function createDecorationType(text: string, padding: number) {

isWholeLine: true,
})
}
70 changes: 38 additions & 32 deletions src/extension.ts
Original file line number Diff line number Diff line change
@@ -1,41 +1,47 @@
import * as vscode from 'vscode'
import { getDecorations } from './decoration'
import { Decoration, getDecorations } from './decoration'
import { debounce } from './utils'
import { getDebounceUpdate } from './config'

export function activate(context: vscode.ExtensionContext) {
let tokenSource: vscode.CancellationTokenSource

let currentDecorations: Awaited<ReturnType<typeof getDecorations>> = []

const updateDecorations = debounce(
async (event: vscode.TextEditorSelectionChangeEvent) => {
tokenSource = new vscode.CancellationTokenSource()

const token = tokenSource.token
const decorations = await getDecorations(
event.textEditor,
event.selections
)
if (token.isCancellationRequested) return

currentDecorations.forEach(([, type]) => type.dispose())

currentDecorations = decorations
currentDecorations.forEach(([editor, type, line]) =>
editor.setDecorations(type, [
new vscode.Selection(line, 0, line, 0),
])
)
},
() =>
vscode.workspace
.getConfiguration('hoverlens')
.get('debounceUpdate', 50)
)
let tokenSource: vscode.CancellationTokenSource | undefined
const startUpdate = () => {
tokenSource = new vscode.CancellationTokenSource()
return tokenSource.token
}
const cancelUpdate = () => tokenSource?.cancel()

let currentDecorations: Decoration[] = []
const setDecorations = (decorations: Decoration[]) => {
for (const { type } of currentDecorations) {
type.dispose()
}

currentDecorations = decorations

for (const { editor, type, line } of currentDecorations) {
editor.setDecorations(type, [new vscode.Selection(line, 0, line, 0)])
}
}

const updateDecorations = debounce(
async (event: vscode.TextEditorSelectionChangeEvent) => {
const token = startUpdate()

const decorations = await getDecorations(
event.textEditor,
event.selections
)
if (token.isCancellationRequested) return

setDecorations(decorations)
},
getDebounceUpdate
)

export const activate = (context: vscode.ExtensionContext) => {
context.subscriptions.push(
vscode.window.onDidChangeTextEditorSelection((event) => {
tokenSource?.cancel()
cancelUpdate()
updateDecorations(event)
})
)
Expand Down
28 changes: 12 additions & 16 deletions src/formatting.ts
Original file line number Diff line number Diff line change
@@ -1,28 +1,24 @@
import markdownToTxt from 'markdown-to-txt'
import * as vscode from 'vscode'

export function toPlainText(hover: vscode.Hover) {
return hover.contents
.map((content) => {
if (content instanceof vscode.MarkdownString) {
return markdownToTxt(content.value)
} else {
return typeof content === 'string'
? markdownToTxt(content)
: content.value
}
})
export const toPlainText = (hover: vscode.Hover) =>
hover.contents
.map((content) =>
content instanceof vscode.MarkdownString
? markdownToTxt(content.value)
: typeof content === 'string'
? markdownToTxt(content)
: content.value
)
.join('\n')
}

export function removeEmptyLines(text: string) {
return text
export const removeEmptyLines = (text: string) =>
text
.split('\n')
.filter((line) => !!line)
.join('\n')
}

export function changeLeadingSpacesToNonBreaking(line: string) {
export const changeLeadingSpacesToNonBreaking = (line: string) => {
let i = 0
for (; i < line.length; i++) {
if (line[i] !== ' ') break
Expand Down
5 changes: 3 additions & 2 deletions src/utils.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
export function debounce<T extends (...args: never[]) => unknown>(
export const debounce = <T extends (...args: never[]) => unknown>(
fn: T,
getMs: () => number
) {
) => {
let timer: NodeJS.Timeout

return (...args: Parameters<T>) => {
clearTimeout(timer)

Expand Down

0 comments on commit a396191

Please sign in to comment.