Files
openidea/src/features/vcs/recentChanges.ts
T
l0ng-ai 1e00ea5ee2 feat: Third pass aligning core experience with IntelliJ IDEA
Project & files
- Project view modes (Project Files / Open Files / All Changed Files /
  Scratches); External Libraries for Python, JDK (src.zip), Node, Cargo, Go,
  Maven/Gradle jars; read-only jar/zip browsing
- ⌘N New popup with type search and more file kinds; New Project, Rename
  Project, Reload All from Disk, Export/Import Settings, Power Save Mode
- File type associations, extra content roots and exclude patterns (indexed
  and watched without reopening the project)

Editor & navigation
- Find bar: search scope (comments/strings), Preserve Case, Exclude, multiline,
  history; Find in Files: Module scope, custom pattern scopes, multiline
- Search Everywhere filters, Assign Shortcut, settings results; named bookmark
  lists, file/folder bookmarks; Structure filters and Show Inherited; Recent
  Locations timestamps and breadcrumbs; Code Vision author
- Completion options, editor tab placement/layout, inline completion (LSP 3.18)
- Spell checking (Typo inspection, ide-spell) and Inspections settings with
  custom profiles; Code Style schemes, formatter markers, Do not format

Run, VCS, services, database
- Typed run configurations (Shell, Program, npm, Gradle, Maven, Docker,
  Compound), Modify options, Before launch, env dialog, Current File,
  Emulate terminal (PTY)
- Git log graph/view options, Go to Hash/Branch/Tag, date filter keeps the
  graph; Pull/Merge/Rebase dialogs, Manage Remotes, Worktrees
- Generic Services host (Docker connections/registries, run sessions); TODO
  scope/changes tabs with changelists; Coverage report import
- Data sources: wire-compatible vendors, URL import, SSL certs, Options,
  Schemas and Advanced tabs, color and comment

Workbench
- Run Anything, Customize Main Toolbar, named tool window layouts, menu
  completeness, Code Cleanup, macros, "Don't Show Again", editor banners
- Chinese translations for the new UI

Claude-Session: https://claude.ai/code/session_01SaPPsVPuk6ZTNsoUCNCbMv
2026-10-25 21:24:00 +08:00

60 lines
2.3 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* View › Recent Changes (⌥⇧C): the project's latest Local History events —
* labels, system events and saved file revisions — in a popup; choosing one
* opens its Local History.
*/
import type { HistoryEntry } from "@/bindings";
import { openPopup, type ListPopupItem } from "@/editor/lsp/popupStore";
import { call, commands } from "@/platform/ipc";
import { relativePath, useProject } from "@/platform/project";
import { notifications } from "@/workbench/contributions";
import { openLocalHistory } from "./localHistoryKind";
import { formatTime } from "./model";
import { errorMessage } from "./ops";
const MAX_ROWS = 40;
/**
* Newest first; consecutive revisions of one file with the same label collapse
* into the newest (typing saves often).
*/
export function recentChanges(entries: readonly HistoryEntry[], limit = MAX_ROWS): HistoryEntry[] {
const sorted = [...entries].sort((a, b) => (b.timestampMs ?? 0) - (a.timestampMs ?? 0));
const out: HistoryEntry[] = [];
for (const e of sorted) {
const prev = out[out.length - 1];
if (prev && prev.kind !== "label" && e.kind !== "label" && prev.path === e.path && prev.label === e.label) continue;
out.push(e);
if (out.length >= limit) break;
}
return out;
}
export function recentChangeLabel(e: HistoryEntry, root: string): string {
if (e.kind === "label") return e.label;
return `${relativePath(root, e.path)}${e.label ? ` — ${e.label}` : ""}`;
}
export async function showRecentChanges() {
const root = useProject.getState().project?.root;
if (!root) return;
let entries: HistoryEntry[];
try {
entries = recentChanges((await call(commands.historyListDir(root))).entries);
} catch (e) {
notifications().notify({ level: "error", title: "Cannot read Local History", body: errorMessage(e) });
return;
}
const now = Date.now();
const items: ListPopupItem[] = entries.map((e, i) => ({
id: `${i}`,
label: recentChangeLabel(e, root),
detail: formatTime(e.timestampMs, now),
icon: e.kind === "label" ? "bookmark" : "history",
run: () => openLocalHistory(e.kind === "label" ? root : e.path),
}));
if (!items.length)
items.push({ id: "none", label: "No recent changes", disabled: "Local History has no entries yet", run: () => {} });
openPopup({ kind: "list", anchor: { x: window.innerWidth / 2 - 200, y: 96 }, title: "Recent Changes", items });
}