import React from 'react'; import Mousetrap, {MousetrapInstance} from 'mousetrap'; import {connect} from '../utils/plugins'; import * as uiActions from '../actions/ui'; import {getRegisteredKeys, getCommandHandler, shouldPreventDefault} from '../command-registry'; import stylis from 'stylis'; import {HeaderContainer} from './header'; import TermsContainer from './terms'; import NotificationsContainer from './notifications'; import {HyperState, HyperProps, HyperDispatch} from '../hyper'; import Terms from '../components/terms'; const isMac = /Mac/.test(navigator.userAgent); class Hyper extends React.PureComponent { mousetrap!: MousetrapInstance; terms!: Terms; constructor(props: HyperProps) { super(props); } componentDidUpdate(prev: HyperProps) { if (this.props.backgroundColor !== prev.backgroundColor) { // this can be removed when `setBackgroundColor` in electron // starts working again document.body.style.backgroundColor = this.props.backgroundColor; } const {lastConfigUpdate} = this.props; if (lastConfigUpdate && lastConfigUpdate !== prev.lastConfigUpdate) { this.attachKeyListeners(); } if (prev.activeSession !== this.props.activeSession) { this.handleFocusActive(this.props.activeSession!); } } handleFocusActive = (uid?: string) => { const term = uid && this.terms.getTermByUid(uid); if (term) { term.focus(); } }; handleSelectAll = () => { const term = this.terms.getActiveTerm(); if (term) { term.selectAll(); } }; attachKeyListeners() { if (!this.mousetrap) { // eslint-disable-next-line @typescript-eslint/no-unsafe-call this.mousetrap = new (Mousetrap as any)(window, true); this.mousetrap.stopCallback = () => { // All events should be intercepted even if focus is in an input/textarea return false; }; } else { this.mousetrap.reset(); } const keys = getRegisteredKeys(); Object.keys(keys).forEach((commandKeys) => { this.mousetrap.bind( commandKeys, (e) => { const command = keys[commandKeys]; // We should tell to xterm that it should ignore this event. (e as any).catched = true; this.props.execCommand(command, getCommandHandler(command), e); shouldPreventDefault(command) && e.preventDefault(); }, 'keydown' ); }); } componentDidMount() { this.attachKeyListeners(); window.rpc.on('term selectAll', this.handleSelectAll); } onTermsRef = (terms: Terms) => { this.terms = terms; window.focusActiveTerm = (uid?: string) => { if (uid) { this.handleFocusActive(uid); } else { this.terms.getActiveTerm().focus(); } }; }; componentWillUnmount() { document.body.style.backgroundColor = 'inherit'; this.mousetrap?.reset(); } render() { const {isMac: isMac_, customCSS, uiFontFamily, borderColor, maximized, fullScreen} = this.props; const borderWidth = isMac_ ? '' : `${maximized ? '0' : '1'}px`; stylis.set({prefix: false}); return (
{this.props.customInnerChildren}
{this.props.customChildren} {/* Add custom CSS to Hyper. We add a scope to the customCSS so that it can get around the weighting applied by styled-jsx */}