UNPKG

alm

Version:

The best IDE for TypeScript

288 lines (287 loc) 13.4 kB
"use strict"; var __extends = (this && this.__extends) || (function () { var extendStatics = Object.setPrototypeOf || ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; }; return function (d, b) { extendStatics(d, b); function __() { this.constructor = d; } d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); }; })(); Object.defineProperty(exports, "__esModule", { value: true }); var ui = require("../../ui"); var csx = require("../../base/csx"); var React = require("react"); var socketClient_1 = require("../../../socket/socketClient"); var commands = require("../../commands/commands"); var utils = require("../../../common/utils"); var styles = require("../../styles/styles"); var typeIcon = require("../../components/typeIcon"); var gls = require("../../base/gls"); var typestyle = require("typestyle"); var markdown_1 = require("../../markdown/markdown"); var styles_1 = require("../../styles/styles"); var DocumentationViewStyles; (function (DocumentationViewStyles) { DocumentationViewStyles.header = typestyle.style({ cursor: 'pointer', $nest: { '&:hover': { textDecoration: 'underline' } } }); DocumentationViewStyles.folderName = typestyle.style({ padding: "2px", fontSize: '.5em', '-webkit-user-select': 'none', maxWidth: '200px', overflow: 'hidden', textOverflow: 'ellipsis' }); })(DocumentationViewStyles = exports.DocumentationViewStyles || (exports.DocumentationViewStyles = {})); var DocumentationView = /** @class */ (function (_super) { __extends(DocumentationView, _super); function DocumentationView(props) { var _this = _super.call(this, props) || this; _this.handleNodeClick = function (node) { commands.doOpenOrFocusFile.emit({ filePath: node.location.filePath, position: node.location.position }); }; _this.handleRootSelected = function (node) { _this.setState({ selected: node }); setTimeout(function () { return _this.filter(); }); }; _this.handleKey = function (e) { var unicode = e.charCode; if (String.fromCharCode(unicode).toLowerCase() === "r") { _this.loadData(); } }; _this.loadData = function () { socketClient_1.server.getTopLevelModuleNames({}).then(function (res) { _this.setState({ files: res.files, selected: null }); _this.filter(); }); }; _this.filter = function () { var filter = (_this.state.filter || '').toLowerCase(); if (!filter) { var filtered_1 = _this.state.files; var selected_1 = _this.state.selected && filtered_1.find(function (f) { return f.name == _this.state.selected.name; }); _this.setState({ filtered: filtered_1, selected: selected_1, selectedDoesNotMatchFilter: false }); return; } /** * Does the name match or does some subItem name match */ var doesNameMatchRecursive = function (type) { return type.name.toLowerCase().indexOf(filter) !== -1 || type.subItems.some(function (t) { return doesNameMatchRecursive(t); }); }; /** * Only leaves in the subItems that match */ var mapChildrenRecursive = function (item) { var subItems = item.subItems .filter(doesNameMatchRecursive) .map(mapChildrenRecursive); var result = { name: item.name, icon: item.icon, comment: item.comment, location: item.location, subItems: subItems, }; return result; }; var filtered = _this.state.files .filter(function (f) { return doesNameMatchRecursive(f); }) .map(mapChildrenRecursive); _this.setState({ filtered: filtered }); // Also filter inside the selected if possible var selected = _this.state.selected && filtered.find(function (f) { return f.name == _this.state.selected.name; }); if (_this.state.selected && !selected) { _this.setState({ selectedDoesNotMatchFilter: true }); } else { _this.setState({ selected: selected, selectedDoesNotMatchFilter: false }); } }; /** * TAB implementation */ _this.resize = function () { // Not needed }; _this.focus = function () { _this.refs.root.focus(); }; _this.save = function () { }; _this.close = function () { }; _this.gotoPosition = function (position) { }; _this.search = { doSearch: function (options) { _this.setState({ filter: options.query }); _this.filter(); }, hideSearch: function () { _this.setState({ filter: '' }); _this.filter(); }, findNext: function (options) { }, findPrevious: function (options) { }, replaceNext: function (_a) { var newText = _a.newText; }, replacePrevious: function (_a) { var newText = _a.newText; }, replaceAll: function (_a) { var newText = _a.newText; } }; _this.filePath = utils.getFilePathFromUrl(props.url); _this.state = { filtered: [], files: [], selected: null, }; return _this; } DocumentationView.prototype.componentDidMount = function () { var _this = this; /** * Initial load + load on project change */ this.loadData(); this.disposible.add(socketClient_1.cast.activeProjectFilePathsUpdated.on(function () { _this.loadData(); })); /** * If a file is selected and it gets edited, reload the file module information */ var isFilePathOfSignificance = function (filePath) { return !!_this.state.selected && _this.state.selected.location.filePath === filePath; }; var reloadSelectedDebounced = utils.debounce(function (filePath) { if (!isFilePathOfSignificance(filePath)) return; socketClient_1.server.getUpdatedModuleInformation({ filePath: filePath }).then(function (res) { if (!isFilePathOfSignificance(filePath)) return; var files = _this.state.files.map(function (f) { return (f.location.filePath === filePath) ? res : f; }); _this.setState({ files: files, selected: res }); _this.filter(); }); }, 3000); this.disposible.add(commands.fileContentsChanged.on(function (res) { if (!isFilePathOfSignificance(res.filePath)) return; reloadSelectedDebounced(res.filePath); })); /** * Handle focus to inform tab container */ var focused = function () { _this.props.onFocused(); }; this.refs.root.addEventListener('focus', focused); this.disposible.add({ dispose: function () { _this.refs.root.removeEventListener('focus', focused); } }); // Listen to tab events var api = this.props.api; this.disposible.add(api.resize.on(this.resize)); this.disposible.add(api.focus.on(this.focus)); this.disposible.add(api.save.on(this.save)); this.disposible.add(api.close.on(this.close)); this.disposible.add(api.gotoPosition.on(this.gotoPosition)); // Listen to search tab events this.disposible.add(api.search.doSearch.on(this.search.doSearch)); this.disposible.add(api.search.hideSearch.on(this.search.hideSearch)); this.disposible.add(api.search.findNext.on(this.search.findNext)); this.disposible.add(api.search.findPrevious.on(this.search.findPrevious)); this.disposible.add(api.search.replaceNext.on(this.search.replaceNext)); this.disposible.add(api.search.replacePrevious.on(this.search.replacePrevious)); this.disposible.add(api.search.replaceAll.on(this.search.replaceAll)); }; DocumentationView.prototype.render = function () { return (React.createElement("div", { ref: "root", tabIndex: 0, style: csx.extend(csx.vertical, csx.flex, csx.newLayerParent, styles.someChildWillScroll, { color: styles.textColor }), onKeyPress: this.handleKey }, React.createElement("div", { style: { overflow: 'hidden', padding: '10px 0px 10px 10px', display: 'flex' } }, React.createElement(gls.FlexHorizontal, { style: {} }, React.createElement(gls.Content, { style: { width: '200px', overflow: 'auto' } }, React.createElement(typeIcon.SectionHeader, { text: "Files" }), React.createElement(gls.SmallVerticalSpace, null), this.renderFiles()), React.createElement(gls.FlexVertical, { style: { marginLeft: '5px', overflow: 'auto' } }, this.state.selected && this.state.selectedDoesNotMatchFilter && React.createElement(gls.Content, { style: { backgroundColor: '#111', padding: '5px' } }, "Note: Nothing in the selected module matches the filter, so showing it all"), this.state.selected ? this.renderSelectedNode() : 'Select a module from the left to view its documentation 🌹', React.createElement("div", { style: { marginTop: '10px', marginRight: '10px' } }, React.createElement("hr", null), React.createElement(typeIcon.TypeIconLegend, null))))))); }; DocumentationView.prototype.renderFiles = function () { var _this = this; /** For two items in different file paths we render the folder name in between */ var toRender = []; var lastKnownFolder = ''; this.state.filtered.forEach(function (type) { var folder = utils.getDirectory(type.name); if (folder !== lastKnownFolder) { toRender.push({ folder: folder }); lastKnownFolder = folder; } toRender.push({ type: type }); }); return toRender.map(function (item, i) { if (item.type) { var file_1 = item.type; var name_1 = utils.getFileName(file_1.name); var backgroundColor = _this.state.selected && _this.state.selected.name === file_1.name ? styles_1.blackHighlightColor : 'transparent'; return (React.createElement("div", { title: file_1.name, key: i, style: { cursor: 'pointer', backgroundColor: backgroundColor, paddingTop: '2px', paddingBottom: '2px', paddingLeft: '2px' }, onClick: function () { return _this.handleRootSelected(file_1); } }, React.createElement(typeIcon.DocumentedTypeHeader, { name: name_1, icon: file_1.icon }))); } else { var folder = item.folder; return (React.createElement("div", { title: folder, key: i, className: DocumentationViewStyles.folderName }, folder)); } }); }; DocumentationView.prototype.renderSelectedNode = function () { var node = this.state.selected; return this.renderNode(node); }; DocumentationView.prototype.renderNode = function (node, i) { var _this = this; if (i === void 0) { i = 0; } return (React.createElement("div", { key: i, style: { paddingTop: '5px' } }, React.createElement(gls.InlineBlock, { className: DocumentationViewStyles.header, onClick: function () { return _this.handleNodeClick(node); } }, React.createElement(typeIcon.DocumentedTypeHeader, { name: node.name, icon: node.icon })), node.comment && React.createElement("div", { style: { padding: '5px', backgroundColor: styles_1.blackHighlightColor } }, React.createElement(markdown_1.MarkDown, { markdown: node.comment })), node.subItems && !!node.subItems.length && React.createElement("div", { style: { border: '1px solid grey', marginTop: '5px', padding: '5px' } }, node.subItems.map(function (n, i) { return _this.renderNode(n, i); })))); }; return DocumentationView; }(ui.BaseComponent)); exports.DocumentationView = DocumentationView;