mirror of
https://github.com/yu-i-i/overleaf-cep.git
synced 2026-11-14 22:23:42 +01:00
Merge pull request #33687 from overleaf/mj-temporary-tabs-fix
[web] Only consider real key presses to make tab permanent GitOrigin-RevId: 50ab453445e111de2b317f50470f9f4eec39a66f
This commit is contained in:
committed by
Copybot
parent
6538c00742
commit
ac961f1d40
@@ -1,4 +1,4 @@
|
||||
import React, { FC, useEffect, useRef } from 'react'
|
||||
import React, { FC, useEffect, useRef, useState } from 'react'
|
||||
import { EditorProviders } from '../../../helpers/editor-providers'
|
||||
import { TabsContainer } from '../../../../../frontend/js/features/source-editor/components/tabs/tabs-container'
|
||||
import {
|
||||
@@ -11,6 +11,13 @@ import {
|
||||
} from '@/features/ide-react/context/editor-manager-context'
|
||||
import { TAB_TRANSFER_TYPE } from '@/features/ide-react/context/tabs-context'
|
||||
import { useFileTreeOpenContext } from '@/features/ide-react/context/file-tree-open-context'
|
||||
import {
|
||||
EditorViewContext,
|
||||
useEditorViewContext,
|
||||
} from '@/features/ide-react/context/editor-view-context'
|
||||
import { EditorView } from '@codemirror/view'
|
||||
import { EditorState, Transaction } from '@codemirror/state'
|
||||
import { tabsListener } from '@/features/source-editor/extensions/tabs-listener'
|
||||
|
||||
const DOC_IDS = {
|
||||
main: 'doc-main-id',
|
||||
@@ -120,6 +127,53 @@ function makeEditorManagerProvider() {
|
||||
return EditorManagerProvider
|
||||
}
|
||||
|
||||
function makeEditorViewProvider() {
|
||||
const EditorViewProvider: FC<React.PropsWithChildren> = ({ children }) => {
|
||||
const parentRef = useRef<HTMLDivElement>(null)
|
||||
const [view, setView] = useState<EditorView | null>(null)
|
||||
useEffect(() => {
|
||||
if (!parentRef.current) return
|
||||
const editorView = new EditorView({
|
||||
state: EditorState.create({
|
||||
extensions: [
|
||||
tabsListener(),
|
||||
EditorView.contentAttributes.of({
|
||||
'data-testid': 'mock-editor-view',
|
||||
}),
|
||||
],
|
||||
}),
|
||||
parent: parentRef.current,
|
||||
})
|
||||
setView(editorView)
|
||||
return () => editorView.destroy()
|
||||
}, [])
|
||||
return (
|
||||
<EditorViewContext.Provider value={{ view, setView: () => {} }}>
|
||||
{children}
|
||||
<div ref={parentRef} />
|
||||
</EditorViewContext.Provider>
|
||||
)
|
||||
}
|
||||
return EditorViewProvider
|
||||
}
|
||||
|
||||
function RemoteChangeButton() {
|
||||
const { view } = useEditorViewContext()
|
||||
return (
|
||||
<button
|
||||
type="button"
|
||||
onClick={() =>
|
||||
view?.dispatch({
|
||||
changes: { from: 0, insert: 'remote text' },
|
||||
annotations: Transaction.remote.of(true),
|
||||
})
|
||||
}
|
||||
>
|
||||
Add a remote change
|
||||
</button>
|
||||
)
|
||||
}
|
||||
|
||||
// Rendered inside the provider tree to call handleFileTreeSelect() when a
|
||||
// custom DOM event fires. Also triggers handleFileTreeInit() on mount.
|
||||
function FileSelectionDriver({
|
||||
@@ -188,10 +242,12 @@ describe('File Tabs', function () {
|
||||
userSettings={options?.userSettings}
|
||||
providers={{
|
||||
EditorManagerProvider: makeEditorManagerProvider(),
|
||||
EditorViewProvider: makeEditorViewProvider(),
|
||||
}}
|
||||
>
|
||||
<FileSelectionDriver />
|
||||
<TabsContainer />
|
||||
<RemoteChangeButton />
|
||||
</EditorProviders>
|
||||
)
|
||||
}
|
||||
@@ -216,6 +272,8 @@ describe('File Tabs', function () {
|
||||
})
|
||||
|
||||
mountTabs()
|
||||
|
||||
cy.findByTestId('mock-editor-view').as('editorView')
|
||||
})
|
||||
|
||||
describe('Initial file selection', function () {
|
||||
@@ -228,6 +286,7 @@ describe('File Tabs', function () {
|
||||
rootDocId={DOC_IDS.main}
|
||||
providers={{
|
||||
EditorManagerProvider: makeEditorManagerProvider(),
|
||||
EditorViewProvider: makeEditorViewProvider(),
|
||||
}}
|
||||
>
|
||||
<FileSelectionDriver
|
||||
@@ -266,7 +325,7 @@ describe('File Tabs', function () {
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should('exist')
|
||||
|
||||
// Make main permanent (keypress) so selecting another file doesn't replace it
|
||||
cy.get('body').type('a')
|
||||
cy.get('@editorView').type('a')
|
||||
|
||||
// Select another file
|
||||
cy.then(() => selectDoc(DOC_IDS.intro))
|
||||
@@ -307,7 +366,7 @@ describe('File Tabs', function () {
|
||||
'tab-temporary'
|
||||
)
|
||||
|
||||
cy.get('body').type('a')
|
||||
cy.get('@editorView').type('a')
|
||||
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should(
|
||||
'not.have.class',
|
||||
@@ -321,7 +380,7 @@ describe('File Tabs', function () {
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should('exist')
|
||||
|
||||
// Make main permanent
|
||||
cy.get('body').type('a')
|
||||
cy.get('@editorView').type('a')
|
||||
|
||||
// Open intro (temporary)
|
||||
cy.then(() => selectDoc(DOC_IDS.intro))
|
||||
@@ -338,6 +397,21 @@ describe('File Tabs', function () {
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should('exist')
|
||||
})
|
||||
|
||||
it('does not make a temporary tab permanent on remote changes', function () {
|
||||
cy.then(() => selectDoc(DOC_IDS.main))
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should(
|
||||
'have.class',
|
||||
'tab-temporary'
|
||||
)
|
||||
|
||||
cy.findByRole('button', { name: 'Add a remote change' }).click()
|
||||
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should(
|
||||
'have.class',
|
||||
'tab-temporary'
|
||||
)
|
||||
})
|
||||
|
||||
it('makes a temporary tab permanent on double-click', function () {
|
||||
cy.then(() => selectDoc(DOC_IDS.main))
|
||||
cy.findByRole('tab', { name: /main\.tex/ }).should(
|
||||
@@ -902,7 +976,7 @@ describe('File Tabs', function () {
|
||||
for (let i = 1; i <= 10; i++) {
|
||||
const id = `ch${i}`
|
||||
cy.then(() => selectEntity(makeDocEntity(id, `chapter-${i}.tex`)))
|
||||
cy.get('body').type('a')
|
||||
cy.get('@editorView').type('a')
|
||||
cy.findByRole('tab', { name: new RegExp(`chapter-${i}.tex`) }).should(
|
||||
'be.visible'
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user