@atlaskit/editor-core
Version:
A package contains Atlassian editor core functionality
189 lines • 9.15 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var tslib_1 = require("tslib");
var open_1 = require("@atlaskit/icon/glyph/editor/open");
var unlink_1 = require("@atlaskit/icon/glyph/editor/unlink");
var React = require("react");
var react_1 = require("react");
var PanelTextInput_1 = require("../PanelTextInput");
var styles_1 = require("./styles");
var utils_1 = require("../../plugins/hyperlink/utils");
var RecentSearch_1 = require("../RecentSearch");
var TEXT_NODE = 3;
var HyperlinkEdit = (function (_super) {
tslib_1.__extends(HyperlinkEdit, _super);
function HyperlinkEdit() {
var _this = _super !== null && _super.apply(this, arguments) || this;
_this.state = {
unlinkable: true,
editorFocused: false,
inputActive: false,
active: false,
showToolbarPanel: false,
};
_this.setInputActive = function () {
_this.setState({
inputActive: true,
});
};
_this.resetInputActive = function () {
_this.setState({
inputActive: false,
});
};
/**
* Dynamic offsets for hyperlink editing popup
* because we need to show it next to cursor even without clear target for popup.
*/
_this.adjustPosition = function (position) {
var pluginState = _this.props.pluginState;
if (!pluginState.active) {
var offsetParent = _this.getOffsetParent();
if (!offsetParent) {
return position;
}
var coordinates = pluginState.getCoordinates(_this.props.editorView, offsetParent);
if (position.left) {
position.left = coordinates.left;
}
if (position.top) {
position.top = coordinates.top;
}
if (position.bottom) {
position.bottom = coordinates.bottom;
}
if (position.right) {
position.right = coordinates.right;
}
}
return position;
};
// ED-1323 `onBlur` covers all the use cases (click outside, tab, etc) for this issue
_this.handleOnBlur = function () {
var _a = _this.props, editorView = _a.editorView, pluginState = _a.pluginState;
var _b = _this.state, href = _b.href, text = _b.text;
if (editorView.state.selection.empty && !pluginState.active) {
pluginState.hideLinkPanel();
}
else if (!href || href.length === 0) {
pluginState.removeLink(editorView);
}
else {
if (text && pluginState.text !== text) {
pluginState.updateLinkText(text, editorView);
_this.setState({ text: '' });
}
if (href && pluginState.href !== href) {
pluginState.updateLink({ href: href }, editorView);
}
}
_this.resetInputActive();
};
_this.handleUnlink = function () {
_this.props.pluginState.removeLink(_this.props.editorView);
};
_this.handlePluginStateChange = function (pluginState) {
var inputActive = _this.state.inputActive;
var hrefNotPreset = pluginState.active && (!pluginState.href || pluginState.href.length === 0);
_this.setState({
active: pluginState.active,
target: pluginState.element,
activeElement: pluginState.activeElement,
href: pluginState.href,
oldText: pluginState.text,
oldHref: pluginState.href,
textInputValue: pluginState.text,
editorFocused: pluginState.editorFocused,
inputActive: hrefNotPreset || inputActive,
showToolbarPanel: pluginState.showToolbarPanel,
});
};
_this.updateHref = function (href) {
_this.setState({ href: href });
};
_this.updateText = function (text) {
_this.setState({ text: text });
};
_this.updateLinkText = function (text) {
if (text && text.length > 0 && text !== _this.state.oldText) {
var _a = _this.props, editorView = _a.editorView, pluginState = _a.pluginState;
pluginState.updateLinkText(text, editorView);
_this.setState({ text: '' });
}
};
_this.updateLinkHref = function (href) {
var _a = _this.props, editorView = _a.editorView, pluginState = _a.pluginState;
if (_this.state.oldHref) {
pluginState.updateLink({ href: href }, editorView);
}
else {
pluginState.addLink({ href: href }, editorView);
}
editorView.focus();
};
return _this;
}
HyperlinkEdit.prototype.componentDidMount = function () {
this.props.pluginState.subscribe(this.handlePluginStateChange);
};
HyperlinkEdit.prototype.componentWillUnmount = function () {
this.props.pluginState.unsubscribe(this.handlePluginStateChange);
};
HyperlinkEdit.prototype.getOffsetParent = function () {
var popupTarget = this.getPopupTarget();
return this.props.popupsMountPoint
? this.props.popupsMountPoint.offsetParent
: popupTarget && popupTarget.offsetParent;
};
HyperlinkEdit.prototype.getPopupTarget = function () {
var _a = this.state, target = _a.target, activeElement = _a.activeElement;
var popupTarget = target;
if (!popupTarget && activeElement) {
popupTarget = activeElement.nodeType === TEXT_NODE
? activeElement.parentElement
: activeElement;
}
return popupTarget;
};
HyperlinkEdit.prototype.render = function () {
var _a = this.state, href = _a.href, oldHref = _a.oldHref, unlinkable = _a.unlinkable, active = _a.active, editorFocused = _a.editorFocused, inputActive = _a.inputActive, showToolbarPanel = _a.showToolbarPanel;
var popupTarget = this.getPopupTarget();
if (!popupTarget) {
return null;
}
if ((active || showToolbarPanel) && (editorFocused || inputActive)) {
var showOpenButton = !!oldHref;
var showUnlinkButton = unlinkable && active && oldHref;
return (React.createElement(styles_1.FloatingToolbar, { target: popupTarget, offset: [0, 3], fitWidth: 230, onPositionCalculated: this.adjustPosition, popupsMountPoint: this.props.popupsMountPoint, popupsBoundariesElement: this.props.popupsBoundariesElement },
React.createElement(styles_1.Container, null,
!showOpenButton ? null :
React.createElement(styles_1.ToolbarButton, { href: href, target: "_blank", title: "Open link in new tab", iconBefore: React.createElement(open_1.default, { label: "Open link" }) }),
!showUnlinkButton ? null :
React.createElement(styles_1.ToolbarButton, { title: "Unlink", onClick: this.handleUnlink, iconBefore: React.createElement(unlink_1.default, { label: "Unlink" }) }),
!showUnlinkButton ? null :
React.createElement(styles_1.Separator, null),
this.renderInput())));
}
else {
return null;
}
};
HyperlinkEdit.prototype.renderInput = function () {
var _a = this.state, href = _a.href, oldHref = _a.oldHref, text = _a.text, oldText = _a.oldText;
var _b = this.props, editorView = _b.editorView, pluginState = _b.pluginState, activityProvider = _b.activityProvider;
var normalizedOldText = oldText && utils_1.normalizeUrl(oldText);
// insert new link with recently viewed dropdown
if (activityProvider && !oldHref) {
return (React.createElement(RecentSearch_1.default, { editorView: editorView, pluginState: pluginState, activityProvider: activityProvider }));
}
// edit link text
if (normalizedOldText && href === normalizedOldText) {
return (React.createElement(PanelTextInput_1.default, { placeholder: "Text to display", defaultValue: !text && href === normalizedOldText ? '' : text, onSubmit: this.updateLinkText, onChange: this.updateText, onMouseDown: this.setInputActive, onBlur: this.handleOnBlur }));
}
// edit link href when text has not been set
return (React.createElement(PanelTextInput_1.default, { placeholder: "Paste link", autoFocus: !href || href.length === 0, defaultValue: href, onSubmit: this.updateLinkHref, onChange: this.updateHref, onMouseDown: this.setInputActive, onBlur: this.handleOnBlur }));
};
return HyperlinkEdit;
}(react_1.PureComponent));
exports.default = HyperlinkEdit;
//# sourceMappingURL=index.js.map