Skip to content

Commit

Permalink
[lexical-playground] fix: hard coded theme classes for table hover ac…
Browse files Browse the repository at this point in the history
…tions (#7182)
  • Loading branch information
umaranis authored Feb 22, 2025
1 parent a5c26cf commit 90bc029
Show file tree
Hide file tree
Showing 3 changed files with 47 additions and 9 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,17 @@ import {
TableRowNode,
} from '@lexical/table';
import {$findMatchingParent, mergeRegister} from '@lexical/utils';
import {$getNearestNodeFromDOMNode, isHTMLElement, NodeKey} from 'lexical';
import {
$getNearestNodeFromDOMNode,
EditorThemeClasses,
isHTMLElement,
NodeKey,
} from 'lexical';
import {useEffect, useMemo, useRef, useState} from 'react';
import * as React from 'react';
import {createPortal} from 'react-dom';

import {getThemeSelector} from '../../utils/getThemeSelector';
import {useDebounce} from '../CodeActionMenuPlugin/utils';

const BUTTON_WIDTH_PX = 20;
Expand All @@ -38,7 +44,7 @@ function TableHoverActionsContainer({
}: {
anchorElem: HTMLElement;
}): JSX.Element | null {
const [editor] = useLexicalComposerContext();
const [editor, {getTheme}] = useLexicalComposerContext();
const isEditable = useLexicalEditable();
const [isShownRow, setShownRow] = useState<boolean>(false);
const [isShownColumn, setShownColumn] = useState<boolean>(false);
Expand All @@ -50,7 +56,7 @@ function TableHoverActionsContainer({

const debouncedOnMouseMove = useDebounce(
(event: MouseEvent) => {
const {isOutside, tableDOMNode} = getMouseInfo(event);
const {isOutside, tableDOMNode} = getMouseInfo(event, getTheme);

if (isOutside) {
setShownRow(false);
Expand Down Expand Up @@ -256,14 +262,14 @@ function TableHoverActionsContainer({
<>
{isShownRow && (
<button
className={'PlaygroundEditorTheme__tableAddRows'}
className={`${getTheme()?.tableAddRows}`}
style={{...position}}
onClick={() => insertAction(true)}
/>
)}
{isShownColumn && (
<button
className={'PlaygroundEditorTheme__tableAddColumns'}
className={`${getTheme()?.tableAddColumns}`}
style={{...position}}
onClick={() => insertAction(false)}
/>
Expand All @@ -272,24 +278,28 @@ function TableHoverActionsContainer({
);
}

function getMouseInfo(event: MouseEvent): {
function getMouseInfo(
event: MouseEvent,
getTheme: () => EditorThemeClasses | null | undefined,
): {
tableDOMNode: HTMLElement | null;
isOutside: boolean;
} {
const target = event.target;
const tableCellClass = getThemeSelector(getTheme, 'tableCell');

if (isHTMLElement(target)) {
const tableDOMNode = target.closest<HTMLElement>(
'td.PlaygroundEditorTheme__tableCell, th.PlaygroundEditorTheme__tableCell',
`td${tableCellClass}, th${tableCellClass}`,
);

const isOutside = !(
tableDOMNode ||
target.closest<HTMLElement>(
'button.PlaygroundEditorTheme__tableAddRows',
`button${getThemeSelector(getTheme, 'tableAddRows')}`,
) ||
target.closest<HTMLElement>(
'button.PlaygroundEditorTheme__tableAddColumns',
`button${getThemeSelector(getTheme, 'tableAddColumns')}`,
) ||
target.closest<HTMLElement>('div.TableCellResizer__resizer')
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,8 @@ const theme: EditorThemeClasses = {
specialText: 'PlaygroundEditorTheme__specialText',
tab: 'PlaygroundEditorTheme__tabNode',
table: 'PlaygroundEditorTheme__table',
tableAddColumns: 'PlaygroundEditorTheme__tableAddColumns',
tableAddRows: 'PlaygroundEditorTheme__tableAddRows',
tableAlignment: {
center: 'PlaygroundEditorTheme__tableAlignmentCenter',
right: 'PlaygroundEditorTheme__tableAlignmentRight',
Expand Down
26 changes: 26 additions & 0 deletions packages/lexical-playground/src/utils/getThemeSelector.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
/**
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
*/

import {EditorThemeClasses} from 'lexical';
import invariant from 'shared/invariant';

export function getThemeSelector(
getTheme: () => EditorThemeClasses | null | undefined,
name: keyof EditorThemeClasses,
): string {
const className = getTheme()?.[name];
invariant(
typeof className === 'string',
'getThemeClass: required theme property %s not defined',
String(name),
);
return className
.split(/\s+/g)
.map((cls) => `.${cls}`)
.join();
}

0 comments on commit 90bc029

Please sign in to comment.