deploy: current vibn theia state
Made-with: Cursor
This commit is contained in:
10
packages/outline-view/.eslintrc.js
Normal file
10
packages/outline-view/.eslintrc.js
Normal file
@@ -0,0 +1,10 @@
|
||||
/** @type {import('eslint').Linter.Config} */
|
||||
module.exports = {
|
||||
extends: [
|
||||
'../../configs/build.eslintrc.json'
|
||||
],
|
||||
parserOptions: {
|
||||
tsconfigRootDir: __dirname,
|
||||
project: 'tsconfig.json'
|
||||
}
|
||||
};
|
||||
31
packages/outline-view/README.md
Normal file
31
packages/outline-view/README.md
Normal file
@@ -0,0 +1,31 @@
|
||||
<div align='center'>
|
||||
|
||||
<br />
|
||||
|
||||
<img src='https://raw.githubusercontent.com/eclipse-theia/theia/master/logo/theia.svg?sanitize=true' alt='theia-ext-logo' width='100px' />
|
||||
|
||||
<h2>ECLIPSE THEIA - OUTLINE-VIEW EXTENSION</h2>
|
||||
|
||||
<hr />
|
||||
|
||||
</div>
|
||||
|
||||
## Description
|
||||
|
||||
The `@theia/outline-view` extension contributes the code outline tree based on a document's symbols.
|
||||
|
||||
## Additional Information
|
||||
|
||||
- [API documentation for `@theia/outline-view`](https://eclipse-theia.github.io/theia/docs/next/modules/_theia_outline-view.html)
|
||||
- [Theia - GitHub](https://github.com/eclipse-theia/theia)
|
||||
- [Theia - Website](https://theia-ide.org/)
|
||||
|
||||
## License
|
||||
|
||||
- [Eclipse Public License 2.0](http://www.eclipse.org/legal/epl-2.0/)
|
||||
- [一 (Secondary) GNU General Public License, version 2 with the GNU Classpath Exception](https://projects.eclipse.org/license/secondary-gpl-2.0-cp)
|
||||
|
||||
## Trademark
|
||||
|
||||
"Theia" is a trademark of the Eclipse Foundation
|
||||
<https://www.eclipse.org/theia>
|
||||
48
packages/outline-view/package.json
Normal file
48
packages/outline-view/package.json
Normal file
@@ -0,0 +1,48 @@
|
||||
{
|
||||
"name": "@theia/outline-view",
|
||||
"version": "1.68.0",
|
||||
"description": "Theia - Outline View Extension",
|
||||
"dependencies": {
|
||||
"@theia/core": "1.68.0",
|
||||
"tslib": "^2.6.2"
|
||||
},
|
||||
"publishConfig": {
|
||||
"access": "public"
|
||||
},
|
||||
"theiaExtensions": [
|
||||
{
|
||||
"frontend": "lib/browser/outline-view-frontend-module"
|
||||
}
|
||||
],
|
||||
"keywords": [
|
||||
"theia-extension"
|
||||
],
|
||||
"license": "EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/eclipse-theia/theia.git"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/eclipse-theia/theia/issues"
|
||||
},
|
||||
"homepage": "https://github.com/eclipse-theia/theia",
|
||||
"files": [
|
||||
"lib",
|
||||
"src"
|
||||
],
|
||||
"scripts": {
|
||||
"build": "theiaext build",
|
||||
"clean": "theiaext clean",
|
||||
"compile": "theiaext compile",
|
||||
"lint": "theiaext lint",
|
||||
"test": "theiaext test",
|
||||
"watch": "theiaext watch"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@theia/ext-scripts": "1.68.0"
|
||||
},
|
||||
"nyc": {
|
||||
"extends": "../../configs/nyc.json"
|
||||
},
|
||||
"gitHead": "21358137e41342742707f660b8e222f940a27652"
|
||||
}
|
||||
18
packages/outline-view/src/browser/index.ts
Normal file
18
packages/outline-view/src/browser/index.ts
Normal file
@@ -0,0 +1,18 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
export * from './outline-view-widget';
|
||||
export * from './outline-view-frontend-module';
|
||||
@@ -0,0 +1,233 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2019 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { injectable, inject, postConstruct } from '@theia/core/shared/inversify';
|
||||
import { LabelProvider, BreadcrumbsService, Widget, TreeNode, OpenerService, open, SelectableTreeNode, BreadcrumbsContribution, Breadcrumb } from '@theia/core/lib/browser';
|
||||
import URI from '@theia/core/lib/common/uri';
|
||||
import { OutlineViewService } from './outline-view-service';
|
||||
import { OutlineSymbolInformationNode, OutlineViewWidget } from './outline-view-widget';
|
||||
import { Disposable, DisposableCollection, Emitter, Event, UriSelection } from '@theia/core/lib/common';
|
||||
|
||||
export const OutlineBreadcrumbType = Symbol('OutlineBreadcrumb');
|
||||
export const BreadcrumbPopupOutlineViewFactory = Symbol('BreadcrumbPopupOutlineViewFactory');
|
||||
export const OUTLINE_BREADCRUMB_CONTAINER_CLASS = 'outline-element';
|
||||
export interface BreadcrumbPopupOutlineViewFactory {
|
||||
(): BreadcrumbPopupOutlineView;
|
||||
}
|
||||
export class BreadcrumbPopupOutlineView extends OutlineViewWidget {
|
||||
@inject(OpenerService) protected readonly openerService: OpenerService;
|
||||
|
||||
@inject(OutlineViewService)
|
||||
protected readonly outlineViewService: OutlineViewService;
|
||||
|
||||
protected override tapNode(node?: TreeNode): void {
|
||||
if (UriSelection.is(node) && OutlineSymbolInformationNode.hasRange(node)) {
|
||||
open(this.openerService, node.uri, { selection: node.range });
|
||||
} else {
|
||||
this.outlineViewService.didTapNode(node as OutlineSymbolInformationNode);
|
||||
super.tapNode(node);
|
||||
}
|
||||
}
|
||||
|
||||
cloneState(roots: OutlineSymbolInformationNode[]): void {
|
||||
const nodes = this.reconcileTreeState(roots);
|
||||
const root = this.getRoot(nodes);
|
||||
this.model.root = this.inflateFromStorage(this.deflateForStorage(root));
|
||||
}
|
||||
}
|
||||
|
||||
@injectable()
|
||||
export class OutlineBreadcrumbsContribution implements BreadcrumbsContribution {
|
||||
@inject(LabelProvider)
|
||||
protected readonly labelProvider: LabelProvider;
|
||||
|
||||
@inject(OutlineViewService)
|
||||
protected readonly outlineViewService: OutlineViewService;
|
||||
|
||||
@inject(BreadcrumbsService)
|
||||
protected readonly breadcrumbsService: BreadcrumbsService;
|
||||
|
||||
@inject(BreadcrumbPopupOutlineViewFactory)
|
||||
protected readonly outlineFactory: BreadcrumbPopupOutlineViewFactory;
|
||||
|
||||
protected outlineView: BreadcrumbPopupOutlineView;
|
||||
|
||||
readonly type = OutlineBreadcrumbType;
|
||||
readonly priority: number = 200;
|
||||
|
||||
protected currentUri: URI | undefined = undefined;
|
||||
protected currentBreadcrumbs: OutlineBreadcrumb[] = [];
|
||||
protected roots: OutlineSymbolInformationNode[] = [];
|
||||
|
||||
protected readonly onDidChangeBreadcrumbsEmitter = new Emitter<URI>();
|
||||
get onDidChangeBreadcrumbs(): Event<URI> {
|
||||
return this.onDidChangeBreadcrumbsEmitter.event;
|
||||
}
|
||||
|
||||
@postConstruct()
|
||||
init(): void {
|
||||
this.outlineView = this.outlineFactory();
|
||||
this.outlineView.node.style.height = 'auto';
|
||||
this.outlineView.node.style.maxHeight = '200px';
|
||||
this.outlineViewService.onDidChangeOutline(roots => {
|
||||
if (roots.length > 0) {
|
||||
this.roots = roots;
|
||||
const first = roots[0];
|
||||
if (UriSelection.is(first)) {
|
||||
this.updateOutlineItems(first.uri, this.findSelectedNode(roots));
|
||||
}
|
||||
} else {
|
||||
this.currentBreadcrumbs = [];
|
||||
this.roots = [];
|
||||
}
|
||||
});
|
||||
this.outlineViewService.onDidSelect(node => {
|
||||
if (UriSelection.is(node)) {
|
||||
this.updateOutlineItems(node.uri, node);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
protected async updateOutlineItems(uri: URI, selectedNode: OutlineSymbolInformationNode | undefined): Promise<void> {
|
||||
this.currentUri = uri;
|
||||
const outlinePath = this.toOutlinePath(selectedNode);
|
||||
if (outlinePath && selectedNode) {
|
||||
this.currentBreadcrumbs = outlinePath.map((node, index) =>
|
||||
new OutlineBreadcrumb(
|
||||
node,
|
||||
uri,
|
||||
index.toString(),
|
||||
this.labelProvider.getName(node),
|
||||
'symbol-icon-center codicon codicon-symbol-' + node.iconClass,
|
||||
OUTLINE_BREADCRUMB_CONTAINER_CLASS,
|
||||
)
|
||||
);
|
||||
if (selectedNode.children && selectedNode.children.length > 0) {
|
||||
this.currentBreadcrumbs.push(new OutlineBreadcrumb(
|
||||
selectedNode.children as OutlineSymbolInformationNode[],
|
||||
uri,
|
||||
this.currentBreadcrumbs.length.toString(),
|
||||
'…',
|
||||
'',
|
||||
OUTLINE_BREADCRUMB_CONTAINER_CLASS,
|
||||
));
|
||||
}
|
||||
} else {
|
||||
this.currentBreadcrumbs = [];
|
||||
if (this.roots) {
|
||||
this.currentBreadcrumbs.push(new OutlineBreadcrumb(
|
||||
this.roots,
|
||||
uri,
|
||||
this.currentBreadcrumbs.length.toString(),
|
||||
'…',
|
||||
'',
|
||||
OUTLINE_BREADCRUMB_CONTAINER_CLASS
|
||||
));
|
||||
}
|
||||
}
|
||||
this.onDidChangeBreadcrumbsEmitter.fire(uri);
|
||||
}
|
||||
|
||||
async computeBreadcrumbs(uri: URI): Promise<Breadcrumb[]> {
|
||||
if (this.currentUri && uri.toString() === this.currentUri.toString()) {
|
||||
return this.currentBreadcrumbs;
|
||||
}
|
||||
return [];
|
||||
}
|
||||
|
||||
async attachPopupContent(breadcrumb: Breadcrumb, parent: HTMLElement): Promise<Disposable | undefined> {
|
||||
if (!OutlineBreadcrumb.is(breadcrumb)) {
|
||||
return undefined;
|
||||
}
|
||||
const node = Array.isArray(breadcrumb.node) ? breadcrumb.node[0] : breadcrumb.node;
|
||||
if (!node.parent) {
|
||||
return undefined;
|
||||
}
|
||||
const siblings = node.parent.children.filter((child): child is OutlineSymbolInformationNode => OutlineSymbolInformationNode.is(child));
|
||||
|
||||
const toDisposeOnHide = new DisposableCollection();
|
||||
this.outlineView.cloneState(siblings);
|
||||
this.outlineView.model.selectNode(node);
|
||||
this.outlineView.model.collapseAll();
|
||||
Widget.attach(this.outlineView, parent);
|
||||
this.outlineView.activate();
|
||||
toDisposeOnHide.pushAll([
|
||||
this.outlineView.model.onExpansionChanged(expandedNode => SelectableTreeNode.is(expandedNode) && this.outlineView.model.selectNode(expandedNode)),
|
||||
Disposable.create(() => {
|
||||
this.outlineView.model.root = undefined;
|
||||
Widget.detach(this.outlineView);
|
||||
}),
|
||||
]);
|
||||
return toDisposeOnHide;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the path of the given outline node.
|
||||
*/
|
||||
protected toOutlinePath(node: OutlineSymbolInformationNode | undefined, path: OutlineSymbolInformationNode[] = []): OutlineSymbolInformationNode[] | undefined {
|
||||
if (!node) { return undefined; }
|
||||
if (node.id === 'outline-view-root') { return path; }
|
||||
if (node.parent) {
|
||||
return this.toOutlinePath(node.parent as OutlineSymbolInformationNode, [node, ...path]);
|
||||
} else {
|
||||
return [node, ...path];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Find the node that is selected. Returns after the first match.
|
||||
*/
|
||||
protected findSelectedNode(roots: OutlineSymbolInformationNode[]): OutlineSymbolInformationNode | undefined {
|
||||
const result = roots.find(node => node.selected);
|
||||
if (result) {
|
||||
return result;
|
||||
}
|
||||
for (const node of roots) {
|
||||
const result2 = this.findSelectedNode(node.children.map(child => child as OutlineSymbolInformationNode));
|
||||
if (result2) {
|
||||
return result2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export class OutlineBreadcrumb implements Breadcrumb {
|
||||
constructor(
|
||||
readonly node: OutlineSymbolInformationNode | OutlineSymbolInformationNode[],
|
||||
readonly uri: URI,
|
||||
readonly index: string,
|
||||
readonly label: string,
|
||||
readonly iconClass: string,
|
||||
readonly containerClass: string,
|
||||
) { }
|
||||
|
||||
get id(): string {
|
||||
return this.type.toString() + '_' + this.uri.toString() + '_' + this.index;
|
||||
}
|
||||
|
||||
get type(): symbol {
|
||||
return OutlineBreadcrumbType;
|
||||
}
|
||||
|
||||
get longLabel(): string {
|
||||
return this.label;
|
||||
}
|
||||
}
|
||||
export namespace OutlineBreadcrumb {
|
||||
export function is(breadcrumb: Breadcrumb): breadcrumb is OutlineBreadcrumb {
|
||||
return 'node' in breadcrumb && 'uri' in breadcrumb;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,36 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2018 Redhat, Ericsson and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { inject, injectable, named } from '@theia/core/shared/inversify';
|
||||
import { ContributionProvider } from '@theia/core/lib/common/contribution-provider';
|
||||
import { TreeDecorator, AbstractTreeDecoratorService } from '@theia/core/lib/browser/tree/tree-decorator';
|
||||
|
||||
/**
|
||||
* Symbol for all decorators that would like to contribute into the outline.
|
||||
*/
|
||||
export const OutlineTreeDecorator = Symbol('OutlineTreeDecorator');
|
||||
|
||||
/**
|
||||
* Decorator service for the outline.
|
||||
*/
|
||||
@injectable()
|
||||
export class OutlineDecoratorService extends AbstractTreeDecoratorService {
|
||||
|
||||
constructor(@inject(ContributionProvider) @named(OutlineTreeDecorator) protected readonly contributions: ContributionProvider<TreeDecorator>) {
|
||||
super(contributions.getContributions());
|
||||
}
|
||||
|
||||
}
|
||||
132
packages/outline-view/src/browser/outline-view-contribution.ts
Normal file
132
packages/outline-view/src/browser/outline-view-contribution.ts
Normal file
@@ -0,0 +1,132 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { injectable } from '@theia/core/shared/inversify';
|
||||
import { AbstractViewContribution } from '@theia/core/lib/browser/shell/view-contribution';
|
||||
import { FrontendApplication } from '@theia/core/lib/browser/frontend-application';
|
||||
import { FrontendApplicationContribution } from '@theia/core/lib/browser/frontend-application-contribution';
|
||||
import { Command, CommandRegistry } from '@theia/core/lib/common/command';
|
||||
import { TabBarToolbarContribution, TabBarToolbarRegistry } from '@theia/core/lib/browser/shell/tab-bar-toolbar';
|
||||
import { codicon, Widget } from '@theia/core/lib/browser/widgets';
|
||||
import { OutlineViewWidget } from './outline-view-widget';
|
||||
import { CompositeTreeNode } from '@theia/core/lib/browser/tree';
|
||||
import { OS } from '@theia/core/lib/common/os';
|
||||
import { nls } from '@theia/core/lib/common/nls';
|
||||
|
||||
export const OUTLINE_WIDGET_FACTORY_ID = 'outline-view';
|
||||
|
||||
/**
|
||||
* Collection of `outline-view` commands.
|
||||
*/
|
||||
export namespace OutlineViewCommands {
|
||||
/**
|
||||
* Command which collapses all nodes from the `outline-view` tree.
|
||||
*/
|
||||
export const COLLAPSE_ALL: Command = {
|
||||
id: 'outlineView.collapse.all',
|
||||
iconClass: codicon('collapse-all')
|
||||
};
|
||||
|
||||
/**
|
||||
* Command which expands all nodes from the `outline-view` tree.
|
||||
*/
|
||||
export const EXPAND_ALL: Command = {
|
||||
id: 'outlineView.expand.all',
|
||||
iconClass: codicon('expand-all')
|
||||
};
|
||||
}
|
||||
|
||||
@injectable()
|
||||
export class OutlineViewContribution extends AbstractViewContribution<OutlineViewWidget> implements FrontendApplicationContribution, TabBarToolbarContribution {
|
||||
|
||||
constructor() {
|
||||
super({
|
||||
widgetId: OUTLINE_WIDGET_FACTORY_ID,
|
||||
widgetName: OutlineViewWidget.LABEL,
|
||||
defaultWidgetOptions: {
|
||||
area: 'right',
|
||||
rank: 500
|
||||
},
|
||||
toggleCommandId: 'outlineView:toggle',
|
||||
toggleKeybinding: OS.type() !== OS.Type.Linux
|
||||
? 'ctrlcmd+shift+i'
|
||||
: undefined
|
||||
});
|
||||
}
|
||||
|
||||
async initializeLayout(app: FrontendApplication): Promise<void> {
|
||||
await this.openView();
|
||||
}
|
||||
|
||||
override registerCommands(commands: CommandRegistry): void {
|
||||
super.registerCommands(commands);
|
||||
commands.registerCommand(OutlineViewCommands.COLLAPSE_ALL, {
|
||||
isEnabled: w => this.withWidget(w, () => true),
|
||||
isVisible: w => this.withWidget(w, widget => !widget.model.areNodesCollapsed()),
|
||||
execute: () => this.collapseAllItems()
|
||||
});
|
||||
commands.registerCommand(OutlineViewCommands.EXPAND_ALL, {
|
||||
isEnabled: w => this.withWidget(w, () => true),
|
||||
isVisible: w => this.withWidget(w, widget => widget.model.areNodesCollapsed()),
|
||||
execute: () => this.expandAllItems()
|
||||
});
|
||||
}
|
||||
|
||||
async registerToolbarItems(toolbar: TabBarToolbarRegistry): Promise<void> {
|
||||
const widget = await this.widget;
|
||||
const onDidChange = widget.onDidUpdate;
|
||||
toolbar.registerItem({
|
||||
id: OutlineViewCommands.COLLAPSE_ALL.id,
|
||||
command: OutlineViewCommands.COLLAPSE_ALL.id,
|
||||
tooltip: nls.localizeByDefault('Collapse All'),
|
||||
priority: 0,
|
||||
onDidChange
|
||||
});
|
||||
toolbar.registerItem({
|
||||
id: OutlineViewCommands.EXPAND_ALL.id,
|
||||
command: OutlineViewCommands.EXPAND_ALL.id,
|
||||
tooltip: nls.localizeByDefault('Expand All'),
|
||||
priority: 0,
|
||||
onDidChange
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Collapse all nodes in the outline view tree.
|
||||
*/
|
||||
protected async collapseAllItems(): Promise<void> {
|
||||
const { model } = await this.widget;
|
||||
const root = model.root;
|
||||
if (CompositeTreeNode.is(root)) {
|
||||
model.collapseAll(root);
|
||||
}
|
||||
}
|
||||
|
||||
protected async expandAllItems(): Promise<void> {
|
||||
const { model } = await this.widget;
|
||||
model.expandAll(model.root);
|
||||
}
|
||||
|
||||
/**
|
||||
* Determine if the current widget is the `outline-view`.
|
||||
*/
|
||||
protected withWidget<T>(widget: Widget | undefined = this.tryGetWidget(), cb: (widget: OutlineViewWidget) => T): T | false {
|
||||
if (widget instanceof OutlineViewWidget && widget.id === OUTLINE_WIDGET_FACTORY_ID) {
|
||||
return cb(widget);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { ContainerModule, interfaces } from '@theia/core/shared/inversify';
|
||||
import { OutlineViewService } from './outline-view-service';
|
||||
import { OutlineViewContribution } from './outline-view-contribution';
|
||||
import { WidgetFactory } from '@theia/core/lib/browser/widget-manager';
|
||||
import {
|
||||
FrontendApplicationContribution,
|
||||
createTreeContainer,
|
||||
bindViewContribution,
|
||||
TreeProps,
|
||||
defaultTreeProps,
|
||||
BreadcrumbsContribution
|
||||
} from '@theia/core/lib/browser';
|
||||
import { TabBarToolbarContribution } from '@theia/core/lib/browser/shell/tab-bar-toolbar';
|
||||
import { OutlineViewWidgetFactory, OutlineViewWidget } from './outline-view-widget';
|
||||
import '../../src/browser/styles/index.css';
|
||||
import { bindContributionProvider } from '@theia/core/lib/common/contribution-provider';
|
||||
import { OutlineDecoratorService, OutlineTreeDecorator } from './outline-decorator-service';
|
||||
import { OutlineViewTreeModel } from './outline-view-tree-model';
|
||||
import { BreadcrumbPopupOutlineView, BreadcrumbPopupOutlineViewFactory, OutlineBreadcrumbsContribution } from './outline-breadcrumbs-contribution';
|
||||
|
||||
export default new ContainerModule(bind => {
|
||||
bind(OutlineViewWidgetFactory).toFactory(ctx =>
|
||||
() => createOutlineViewWidget(ctx.container)
|
||||
);
|
||||
|
||||
bind(BreadcrumbPopupOutlineViewFactory).toFactory(({ container }) => () => {
|
||||
const child = createOutlineViewWidgetContainer(container);
|
||||
child.rebind(OutlineViewWidget).to(BreadcrumbPopupOutlineView);
|
||||
child.rebind(TreeProps).toConstantValue({ ...defaultTreeProps, expandOnlyOnExpansionToggleClick: true, search: false, virtualized: false });
|
||||
return child.get(OutlineViewWidget);
|
||||
});
|
||||
|
||||
bind(OutlineViewService).toSelf().inSingletonScope();
|
||||
bind(WidgetFactory).toService(OutlineViewService);
|
||||
|
||||
bindViewContribution(bind, OutlineViewContribution);
|
||||
bind(FrontendApplicationContribution).toService(OutlineViewContribution);
|
||||
bind(TabBarToolbarContribution).toService(OutlineViewContribution);
|
||||
|
||||
bind(OutlineBreadcrumbsContribution).toSelf().inSingletonScope();
|
||||
bind(BreadcrumbsContribution).toService(OutlineBreadcrumbsContribution);
|
||||
});
|
||||
|
||||
function createOutlineViewWidgetContainer(parent: interfaces.Container): interfaces.Container {
|
||||
const child = createTreeContainer(parent, {
|
||||
props: { expandOnlyOnExpansionToggleClick: true, search: true },
|
||||
widget: OutlineViewWidget,
|
||||
model: OutlineViewTreeModel,
|
||||
decoratorService: OutlineDecoratorService,
|
||||
});
|
||||
bindContributionProvider(child, OutlineTreeDecorator);
|
||||
return child;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an `OutlineViewWidget`.
|
||||
* - The creation of the `OutlineViewWidget` includes:
|
||||
* - The creation of the tree widget itself with it's own customized props.
|
||||
* - The binding of necessary components into the container.
|
||||
* @param parent the Inversify container.
|
||||
*
|
||||
* @returns the `OutlineViewWidget`.
|
||||
*/
|
||||
function createOutlineViewWidget(parent: interfaces.Container): OutlineViewWidget {
|
||||
const child = createOutlineViewWidgetContainer(parent);
|
||||
|
||||
return child.get(OutlineViewWidget);
|
||||
}
|
||||
91
packages/outline-view/src/browser/outline-view-service.ts
Normal file
91
packages/outline-view/src/browser/outline-view-service.ts
Normal file
@@ -0,0 +1,91 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { injectable, inject } from '@theia/core/shared/inversify';
|
||||
import { Event, Emitter, DisposableCollection } from '@theia/core';
|
||||
import { WidgetFactory } from '@theia/core/lib/browser';
|
||||
import { OutlineViewWidget, OutlineViewWidgetFactory, OutlineSymbolInformationNode } from './outline-view-widget';
|
||||
import { Widget } from '@theia/core/shared/@lumino/widgets';
|
||||
|
||||
@injectable()
|
||||
export class OutlineViewService implements WidgetFactory {
|
||||
|
||||
id = 'outline-view';
|
||||
|
||||
protected widget?: OutlineViewWidget;
|
||||
protected readonly onDidChangeOutlineEmitter = new Emitter<OutlineSymbolInformationNode[]>();
|
||||
protected readonly onDidChangeOpenStateEmitter = new Emitter<boolean>();
|
||||
protected readonly onDidSelectEmitter = new Emitter<OutlineSymbolInformationNode>();
|
||||
protected readonly onDidOpenEmitter = new Emitter<OutlineSymbolInformationNode>();
|
||||
protected readonly onDidTapNodeEmitter = new Emitter<OutlineSymbolInformationNode>();
|
||||
|
||||
constructor(@inject(OutlineViewWidgetFactory) protected factory: OutlineViewWidgetFactory) { }
|
||||
|
||||
get onDidSelect(): Event<OutlineSymbolInformationNode> {
|
||||
return this.onDidSelectEmitter.event;
|
||||
}
|
||||
|
||||
get onDidOpen(): Event<OutlineSymbolInformationNode> {
|
||||
return this.onDidOpenEmitter.event;
|
||||
}
|
||||
|
||||
get onDidChangeOutline(): Event<OutlineSymbolInformationNode[]> {
|
||||
return this.onDidChangeOutlineEmitter.event;
|
||||
}
|
||||
|
||||
get onDidChangeOpenState(): Event<boolean> {
|
||||
return this.onDidChangeOpenStateEmitter.event;
|
||||
}
|
||||
|
||||
get onDidTapNode(): Event<OutlineSymbolInformationNode> {
|
||||
return this.onDidTapNodeEmitter.event;
|
||||
}
|
||||
|
||||
get open(): boolean {
|
||||
return this.widget !== undefined && this.widget.isVisible;
|
||||
}
|
||||
|
||||
didTapNode(node: OutlineSymbolInformationNode): void {
|
||||
this.onDidTapNodeEmitter.fire(node);
|
||||
}
|
||||
|
||||
/**
|
||||
* Publish the collection of outline view symbols.
|
||||
* - Publishing includes setting the `OutlineViewWidget` tree with symbol information.
|
||||
* @param roots the list of outline symbol information nodes.
|
||||
*/
|
||||
publish(roots: OutlineSymbolInformationNode[]): void {
|
||||
if (this.widget) {
|
||||
this.widget.setOutlineTree(roots);
|
||||
}
|
||||
// onDidChangeOutline needs to be fired even when the outline view widget is closed
|
||||
// in order to update breadcrumbs.
|
||||
this.onDidChangeOutlineEmitter.fire(roots);
|
||||
}
|
||||
|
||||
createWidget(): Promise<Widget> {
|
||||
this.widget = this.factory();
|
||||
const disposables = new DisposableCollection();
|
||||
disposables.push(this.widget.onDidChangeOpenStateEmitter.event(open => this.onDidChangeOpenStateEmitter.fire(open)));
|
||||
disposables.push(this.widget.model.onOpenNode(node => this.onDidOpenEmitter.fire(node as OutlineSymbolInformationNode)));
|
||||
disposables.push(this.widget.model.onSelectionChanged(selection => this.onDidSelectEmitter.fire(selection[0] as OutlineSymbolInformationNode)));
|
||||
this.widget.disposed.connect(() => {
|
||||
this.widget = undefined;
|
||||
disposables.dispose();
|
||||
});
|
||||
return Promise.resolve(this.widget);
|
||||
}
|
||||
}
|
||||
77
packages/outline-view/src/browser/outline-view-tree-model.ts
Normal file
77
packages/outline-view/src/browser/outline-view-tree-model.ts
Normal file
@@ -0,0 +1,77 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2019 Ericsson and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { injectable } from '@theia/core/shared/inversify';
|
||||
import { CompositeTreeNode, TreeModelImpl, ExpandableTreeNode, TreeNode } from '@theia/core/lib/browser';
|
||||
|
||||
@injectable()
|
||||
export class OutlineViewTreeModel extends TreeModelImpl {
|
||||
|
||||
/**
|
||||
* Handle the expansion of the tree node.
|
||||
* - The method is a no-op in order to preserve focus on the editor
|
||||
* after attempting to perform a `collapse-all`.
|
||||
* @param node the expandable tree node.
|
||||
*/
|
||||
protected override handleExpansion(node: Readonly<ExpandableTreeNode>): void {
|
||||
// no-op
|
||||
}
|
||||
|
||||
override async collapseAll(raw?: Readonly<CompositeTreeNode>): Promise<boolean> {
|
||||
const node = raw || this.getFocusedNode();
|
||||
if (CompositeTreeNode.is(node)) {
|
||||
return this.expansionService.collapseAll(node);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* The default behavior of `openNode` calls `doOpenNode` which by default
|
||||
* toggles the expansion of the node. Overriding to prevent expansion, but
|
||||
* allow for the `onOpenNode` event to still fire on a double-click event.
|
||||
*/
|
||||
override openNode(raw?: TreeNode | undefined): void {
|
||||
const node = raw || this.getFocusedNode();
|
||||
if (node) {
|
||||
this.onOpenNodeEmitter.fire(node);
|
||||
}
|
||||
}
|
||||
|
||||
expandAll(raw?: TreeNode): void {
|
||||
if (CompositeTreeNode.is(raw)) {
|
||||
for (const child of raw.children) {
|
||||
if (ExpandableTreeNode.is(child)) {
|
||||
this.expandAll(child);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (ExpandableTreeNode.is(raw)) {
|
||||
this.expandNode(raw);
|
||||
}
|
||||
}
|
||||
|
||||
areNodesCollapsed(): boolean {
|
||||
if (CompositeTreeNode.is(this.root)) {
|
||||
for (const child of this.root.children) {
|
||||
if (!ExpandableTreeNode.isCollapsed(child)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
212
packages/outline-view/src/browser/outline-view-widget.tsx
Normal file
212
packages/outline-view/src/browser/outline-view-widget.tsx
Normal file
@@ -0,0 +1,212 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017-2018 TypeFox and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
import { injectable, inject, postConstruct } from '@theia/core/shared/inversify';
|
||||
import {
|
||||
TreeWidget,
|
||||
TreeNode,
|
||||
NodeProps,
|
||||
SelectableTreeNode,
|
||||
CompositeTreeNode,
|
||||
TreeProps,
|
||||
ContextMenuRenderer,
|
||||
TreeModel,
|
||||
ExpandableTreeNode,
|
||||
codicon
|
||||
} from '@theia/core/lib/browser';
|
||||
import { OutlineViewTreeModel } from './outline-view-tree-model';
|
||||
import { Message } from '@theia/core/shared/@lumino/messaging';
|
||||
import { Emitter, Event, isObject, Mutable, UriSelection } from '@theia/core';
|
||||
import * as React from '@theia/core/shared/react';
|
||||
import { Range } from '@theia/core/shared/vscode-languageserver-protocol';
|
||||
import URI from '@theia/core/lib/common/uri';
|
||||
import { nls } from '@theia/core/lib/common/nls';
|
||||
|
||||
/**
|
||||
* Representation of an outline symbol information node.
|
||||
*/
|
||||
export interface OutlineSymbolInformationNode extends CompositeTreeNode, SelectableTreeNode, ExpandableTreeNode {
|
||||
/**
|
||||
* The `iconClass` for the given tree node.
|
||||
*/
|
||||
iconClass: string;
|
||||
}
|
||||
|
||||
/**
|
||||
* Collection of outline symbol information node functions.
|
||||
*/
|
||||
export namespace OutlineSymbolInformationNode {
|
||||
/**
|
||||
* Determine if the given tree node is an `OutlineSymbolInformationNode`.
|
||||
* - The tree node is an `OutlineSymbolInformationNode` if:
|
||||
* - The node exists.
|
||||
* - The node is selectable.
|
||||
* - The node contains a defined `iconClass` property.
|
||||
* @param node the tree node.
|
||||
*
|
||||
* @returns `true` if the given node is an `OutlineSymbolInformationNode`.
|
||||
*/
|
||||
export function is(node: TreeNode): node is OutlineSymbolInformationNode {
|
||||
return !!node && SelectableTreeNode.is(node) && 'iconClass' in node;
|
||||
}
|
||||
|
||||
export function hasRange(node: unknown): node is { range: Range } {
|
||||
return isObject<{ range: Range }>(node) && Range.is(node.range);
|
||||
}
|
||||
}
|
||||
|
||||
export type OutlineViewWidgetFactory = () => OutlineViewWidget;
|
||||
export const OutlineViewWidgetFactory = Symbol('OutlineViewWidgetFactory');
|
||||
|
||||
@injectable()
|
||||
export class OutlineViewWidget extends TreeWidget {
|
||||
|
||||
static LABEL = nls.localizeByDefault('Outline');
|
||||
|
||||
readonly onDidChangeOpenStateEmitter = new Emitter<boolean>();
|
||||
|
||||
protected readonly onDidUpdateEmitter = new Emitter<void>();
|
||||
readonly onDidUpdate: Event<void> = this.onDidUpdateEmitter.event;
|
||||
|
||||
constructor(
|
||||
@inject(TreeProps) treeProps: TreeProps,
|
||||
@inject(OutlineViewTreeModel) override readonly model: OutlineViewTreeModel,
|
||||
@inject(ContextMenuRenderer) contextMenuRenderer: ContextMenuRenderer
|
||||
) {
|
||||
super(treeProps, model, contextMenuRenderer);
|
||||
|
||||
this.id = 'outline-view';
|
||||
this.title.label = OutlineViewWidget.LABEL;
|
||||
this.title.caption = OutlineViewWidget.LABEL;
|
||||
this.title.closable = true;
|
||||
this.title.iconClass = codicon('symbol-class');
|
||||
this.addClass('theia-outline-view');
|
||||
}
|
||||
|
||||
@postConstruct()
|
||||
protected override init(): void {
|
||||
super.init();
|
||||
this.toDispose.push(this.model.onExpansionChanged(() => this.onDidUpdateEmitter.fire()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the outline tree with the list of `OutlineSymbolInformationNode`.
|
||||
* @param roots the list of `OutlineSymbolInformationNode`.
|
||||
*/
|
||||
public setOutlineTree(roots: OutlineSymbolInformationNode[]): void {
|
||||
// Gather the list of available nodes.
|
||||
const nodes = this.reconcileTreeState(roots);
|
||||
// Update the model root node, appending the outline symbol information nodes as children.
|
||||
this.model.root = this.getRoot(nodes);
|
||||
}
|
||||
|
||||
protected getRoot(children: TreeNode[]): CompositeTreeNode {
|
||||
return {
|
||||
id: 'outline-view-root',
|
||||
name: OutlineViewWidget.LABEL,
|
||||
visible: false,
|
||||
children,
|
||||
parent: undefined
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Reconcile the outline tree state, gathering all available nodes.
|
||||
* @param nodes the list of `TreeNode`.
|
||||
*
|
||||
* @returns the list of tree nodes.
|
||||
*/
|
||||
protected reconcileTreeState(nodes: TreeNode[]): TreeNode[] {
|
||||
nodes.forEach(node => {
|
||||
if (OutlineSymbolInformationNode.is(node)) {
|
||||
const treeNode = this.model.getNode(node.id);
|
||||
if (treeNode && OutlineSymbolInformationNode.is(treeNode)) {
|
||||
treeNode.expanded = node.expanded;
|
||||
treeNode.selected = node.selected;
|
||||
}
|
||||
this.reconcileTreeState(Array.from(node.children));
|
||||
}
|
||||
});
|
||||
return nodes;
|
||||
}
|
||||
|
||||
protected override onAfterHide(msg: Message): void {
|
||||
super.onAfterHide(msg);
|
||||
this.onDidChangeOpenStateEmitter.fire(false);
|
||||
}
|
||||
|
||||
protected override onAfterShow(msg: Message): void {
|
||||
super.onAfterShow(msg);
|
||||
this.onDidChangeOpenStateEmitter.fire(true);
|
||||
}
|
||||
|
||||
override renderIcon(node: TreeNode, props: NodeProps): React.ReactNode {
|
||||
if (OutlineSymbolInformationNode.is(node)) {
|
||||
return <div className={'symbol-icon-center codicon codicon-symbol-' + node.iconClass}></div>;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
protected override createNodeAttributes(node: TreeNode, props: NodeProps): React.Attributes & React.HTMLAttributes<HTMLElement> {
|
||||
const elementAttrs = super.createNodeAttributes(node, props);
|
||||
return {
|
||||
...elementAttrs,
|
||||
title: this.getNodeTooltip(node)
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the tooltip for the given tree node.
|
||||
* - The tooltip is discovered when hovering over a tree node.
|
||||
* - If available, the tooltip is the concatenation of the node name, and it's type.
|
||||
* @param node the tree node.
|
||||
*
|
||||
* @returns the tooltip for the tree node if available, else `undefined`.
|
||||
*/
|
||||
protected getNodeTooltip(node: TreeNode): string | undefined {
|
||||
if (OutlineSymbolInformationNode.is(node)) {
|
||||
return node.name + ` (${node.iconClass})`;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
protected override isExpandable(node: TreeNode): node is ExpandableTreeNode {
|
||||
return OutlineSymbolInformationNode.is(node) && node.children.length > 0;
|
||||
}
|
||||
|
||||
protected override renderTree(model: TreeModel): React.ReactNode {
|
||||
if (CompositeTreeNode.is(this.model.root) && !this.model.root.children.length) {
|
||||
return <div className='theia-widget-noInfo no-outline'>{nls.localizeByDefault('The active editor cannot provide outline information.')}</div>;
|
||||
}
|
||||
return super.renderTree(model);
|
||||
}
|
||||
|
||||
protected override deflateForStorage(node: TreeNode): object {
|
||||
const deflated = super.deflateForStorage(node) as { uri: string };
|
||||
if (UriSelection.is(node)) {
|
||||
deflated.uri = node.uri.toString();
|
||||
}
|
||||
return deflated;
|
||||
}
|
||||
|
||||
protected override inflateFromStorage(node: any, parent?: TreeNode): TreeNode { /* eslint-disable-line @typescript-eslint/no-explicit-any */
|
||||
const inflated = super.inflateFromStorage(node, parent) as Mutable<TreeNode & UriSelection>;
|
||||
if (node && 'uri' in node && typeof node.uri === 'string') {
|
||||
inflated.uri = new URI(node.uri);
|
||||
}
|
||||
return inflated;
|
||||
}
|
||||
}
|
||||
24
packages/outline-view/src/browser/styles/index.css
Normal file
24
packages/outline-view/src/browser/styles/index.css
Normal file
@@ -0,0 +1,24 @@
|
||||
/********************************************************************************
|
||||
* Copyright (C) 2017-2018 TypeFox and others.
|
||||
*
|
||||
* This program and the accompanying materials are made available under the
|
||||
* terms of the Eclipse Public License v. 2.0 which is available at
|
||||
* http://www.eclipse.org/legal/epl-2.0.
|
||||
*
|
||||
* This Source Code may also be made available under the following Secondary
|
||||
* Licenses when the conditions for such availability set forth in the Eclipse
|
||||
* Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
* with the GNU Classpath Exception which is available at
|
||||
* https://www.gnu.org/software/classpath/license.html.
|
||||
*
|
||||
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
********************************************************************************/
|
||||
|
||||
.no-outline {
|
||||
color: var(--theia-foreground);
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.theia-side-panel .no-outline {
|
||||
margin-left: 9px;
|
||||
}
|
||||
28
packages/outline-view/src/package.spec.ts
Normal file
28
packages/outline-view/src/package.spec.ts
Normal file
@@ -0,0 +1,28 @@
|
||||
// *****************************************************************************
|
||||
// Copyright (C) 2017 Ericsson and others.
|
||||
//
|
||||
// This program and the accompanying materials are made available under the
|
||||
// terms of the Eclipse Public License v. 2.0 which is available at
|
||||
// http://www.eclipse.org/legal/epl-2.0.
|
||||
//
|
||||
// This Source Code may also be made available under the following Secondary
|
||||
// Licenses when the conditions for such availability set forth in the Eclipse
|
||||
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
||||
// with the GNU Classpath Exception which is available at
|
||||
// https://www.gnu.org/software/classpath/license.html.
|
||||
//
|
||||
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
||||
// *****************************************************************************
|
||||
|
||||
/* note: this bogus test file is required so that
|
||||
we are able to run mocha unit tests on this
|
||||
package, without having any actual unit tests in it.
|
||||
This way a coverage report will be generated,
|
||||
showing 0% coverage, instead of no report.
|
||||
This file can be removed once we have real unit
|
||||
tests in place. */
|
||||
|
||||
describe('outline view package', () => {
|
||||
|
||||
it('should support code coverage statistics', () => true);
|
||||
});
|
||||
16
packages/outline-view/tsconfig.json
Normal file
16
packages/outline-view/tsconfig.json
Normal file
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"extends": "../../configs/base.tsconfig",
|
||||
"compilerOptions": {
|
||||
"composite": true,
|
||||
"rootDir": "src",
|
||||
"outDir": "lib"
|
||||
},
|
||||
"include": [
|
||||
"src"
|
||||
],
|
||||
"references": [
|
||||
{
|
||||
"path": "../core"
|
||||
}
|
||||
]
|
||||
}
|
||||
Reference in New Issue
Block a user