Merge main (tests changed x_x) and pass all constraints.spec tests (pain)

This commit is contained in:
49lf
2024-11-29 14:12:19 -05:00
parent 60e62d435e
commit 3c1c1303e1
12 changed files with 2113 additions and 1962 deletions

View File

@ -52,10 +52,12 @@ export class SceneFixture {
}
expectState = async (expected: SceneSerialised) => {
return expect.poll(async () => await this._serialiseScene(), {
return expect
.poll(async () => await this._serialiseScene(), {
intervals: [1_000, 2_000, 10_000],
timeout: 60000,
}).toEqual(expected)
})
.toEqual(expected)
}
reConstruct = (page: Page) => {

View File

@ -115,9 +115,7 @@ test.describe('Onboarding tests', () => {
await replayButton.click()
// Ensure we see the warning, and that the code has not yet updated
await expect(
page.getByText('Would you like to create')
).toBeVisible()
await expect(page.getByText('Would you like to create')).toBeVisible()
await expect(page.locator('.cm-content')).toHaveText(initialCode)
const nextButton = page.getByTestId('onboarding-next')
@ -263,7 +261,9 @@ test.describe('Onboarding tests', () => {
await page.setBodyDimensions({ width: 1200, height: 1080 })
await homePage.goToModelingScene()
await expect.poll(() => page.url()).toContain(onboardingPaths.PARAMETRIC_MODELING)
await expect
.poll(() => page.url())
.toContain(onboardingPaths.PARAMETRIC_MODELING)
const bracketNoNewLines = bracket.replace(/\n/g, '')

View File

@ -7,9 +7,14 @@ import path from 'node:path'
// test file is for testing point an click code gen functionality that's not sketch mode related
test(
'verify extruding circle works',
async ({ context, homePage, cmdBar, editor, toolbar, scene }) => {
test('verify extruding circle works', async ({
context,
homePage,
cmdBar,
editor,
toolbar,
scene,
}) => {
const file = await fs.readFile(
path.resolve(
__dirname,
@ -30,14 +35,22 @@ test(
await expect(toolbar.extrudeButton).toBeEnabled()
})
await test.step('check code model connection works and that button is still enable once circle is selected ', async () => {
await moveToCircle()
const circleSnippet =
'circle({ center: [318.33, 168.1], radius: 182.8 }, %)'
await editor.expectState({
activeLines: ["constsketch002=startSketchOn('XZ')"],
highlightedCode: circleSnippet,
diagnostics: [],
})
await test.step('check code model connection works and that button is still enable once circle is selected ', async () => {
await moveToCircle()
const circleSnippet =
'circle({ center = [318.33, 168.1], radius = 182.8 }, %)'
await editor.expectState({
activeLines: [
"constsketch002=startSketchOn('XZ')"
],
activeLines: ["constsketch002=startSketchOn('XZ')"],
highlightedCode: circleSnippet,
diagnostics: [],
})
@ -50,6 +63,8 @@ test(
})
await expect(toolbar.extrudeButton).toBeEnabled()
})
await expect(toolbar.extrudeButton).toBeEnabled()
})
await test.step('do extrude flow and check extrude code is added to editor', async () => {
await toolbar.extrudeButton.click()
@ -76,8 +91,7 @@ test(
await editor.expectEditor.toContain(expectString)
})
}
)
})
test.describe('verify sketch on chamfer works', () => {
const _sketchOnAChamfer =
@ -145,7 +159,9 @@ test.describe('verify sketch on chamfer works', () => {
pixelDiff: 50,
})
await rectangle2ndClick()
await editor.expectEditor.toContain(afterRectangle2ndClickSnippet, { shouldNormalise: true })
await editor.expectEditor.toContain(afterRectangle2ndClickSnippet, {
shouldNormalise: true,
})
})
await test.step('Clean up so that `_sketchOnAChamfer` util can be called again', async () => {
@ -160,9 +176,14 @@ test.describe('verify sketch on chamfer works', () => {
})
})
}
test(
'works on all edge selections and can break up multi edges in a chamfer array',
async ({ context, page, homePage, editor, toolbar, scene }) => {
test('works on all edge selections and can break up multi edges in a chamfer array', async ({
context,
page,
homePage,
editor,
toolbar,
scene,
}) => {
const file = await fs.readFile(
path.resolve(
__dirname,
@ -191,8 +212,7 @@ test.describe('verify sketch on chamfer works', () => {
getOppositeEdge(seg01)
]}, %)`,
afterChamferSelectSnippet:
'sketch002 = startSketchOn(extrude001, seg03)',
afterChamferSelectSnippet: 'sketch002 = startSketchOn(extrude001, seg03)',
afterRectangle1stClickSnippet: 'startProfileAt([160.39, 254.59], %)',
afterRectangle2ndClickSnippet: `angledLine([0, 11.39], %, $rectangleSegmentA002)
|> angledLine([
@ -223,8 +243,7 @@ test.describe('verify sketch on chamfer works', () => {
]
}, %)`,
afterChamferSelectSnippet:
'sketch003 = startSketchOn(extrude001, seg04)',
afterChamferSelectSnippet: 'sketch003 = startSketchOn(extrude001, seg04)',
afterRectangle1stClickSnippet: 'startProfileAt([-255.89, 255.28], %)',
afterRectangle2ndClickSnippet: `angledLine([0, 11.56], %, $rectangleSegmentA003)
|> angledLine([
@ -249,8 +268,7 @@ test.describe('verify sketch on chamfer works', () => {
getNextAdjacentEdge(seg02)
]
}, %)`,
afterChamferSelectSnippet:
'sketch003 = startSketchOn(extrude001, seg04)',
afterChamferSelectSnippet: 'sketch003 = startSketchOn(extrude001, seg04)',
afterRectangle1stClickSnippet: 'startProfileAt([37.95, 322.96], %)',
afterRectangle2ndClickSnippet: `angledLine([0, 11.56], %, $rectangleSegmentA003)
|> angledLine([
@ -273,8 +291,7 @@ test.describe('verify sketch on chamfer works', () => {
length = 30,
tags = [getNextAdjacentEdge(yo)]
}, %)`,
afterChamferSelectSnippet:
'sketch005 = startSketchOn(extrude001, seg06)',
afterChamferSelectSnippet: 'sketch005 = startSketchOn(extrude001, seg06)',
afterRectangle1stClickSnippet: 'startProfileAt([-59.83, 19.69], %)',
afterRectangle2ndClickSnippet: `angledLine([0, 9.1], %, $rectangleSegmentA005)
@ -376,12 +393,16 @@ test.describe('verify sketch on chamfer works', () => {
{ shouldNormalise: true }
)
})
}
)
})
test(
'Works on chamfers that are non in a pipeExpression can break up multi edges in a chamfer array',
async ({ context, page, homePage, editor, toolbar, scene }) => {
test('Works on chamfers that are non in a pipeExpression can break up multi edges in a chamfer array', async ({
context,
page,
homePage,
editor,
toolbar,
scene,
}) => {
const file = await fs.readFile(
path.resolve(
__dirname,
@ -396,8 +417,6 @@ test.describe('verify sketch on chamfer works', () => {
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
const sketchOnAChamfer = _sketchOnAChamfer(page, editor, toolbar, scene)
await sketchOnAChamfer({
clickCoords: { x: 570, y: 220 },
cameraPos: { x: 16020, y: -2000, z: 10500 },
@ -410,8 +429,7 @@ test.describe('verify sketch on chamfer works', () => {
getOppositeEdge(seg01)
]}, extrude001)`,
beforeChamferSnippetEnd: '}, extrude001)',
afterChamferSelectSnippet:
'sketch002 = startSketchOn(extrude001, seg03)',
afterChamferSelectSnippet: 'sketch002 = startSketchOn(extrude001, seg03)',
afterRectangle1stClickSnippet: 'startProfileAt([160.39, 254.59], %)',
afterRectangle2ndClickSnippet: `angledLine([0, 11.39], %, $rectangleSegmentA002)
|> angledLine([
@ -468,8 +486,7 @@ sketch002 = startSketchOn(extrude001, seg03)
`,
{ shouldNormalise: true }
)
}
)
})
})
test(`Verify axis, origin, and horizontal snapping`, async ({

View File

@ -56,7 +56,6 @@ test(
})
await expect(projectLinks).toHaveCount(0)
}
)
@ -64,7 +63,6 @@ test(
'click help/keybindings from home page',
{ tag: '@electron' },
async ({ page }, testInfo) => {
await page.setBodyDimensions({ width: 1200, height: 500 })
page.on('console', console.log)
@ -76,7 +74,6 @@ test(
await page.getByTestId('keybindings-button').click()
// Make sure the keyboard shortcuts modal is visible.
await expect(page.getByText('Enter Sketch Mode')).toBeVisible()
}
)
@ -114,7 +111,6 @@ test(
await page.getByTestId('keybindings-button').click()
// Make sure the keyboard shortcuts modal is visible.
await expect(page.getByText('Enter Sketch Mode')).toBeVisible()
}
)
@ -148,7 +144,6 @@ test(
await page.hover('.cm-lint-marker-error')
const crypticErrorText = `Expected a tag declarator`
await expect(page.getByText(crypticErrorText).first()).toBeVisible()
}
)
@ -240,7 +235,6 @@ test.describe('Can export from electron app', () => {
// clean up exported file
await fsp.rm(filepath)
})
}
)
}
@ -441,7 +435,6 @@ test(
// expect the name not to have changed
await expect(page.getByText('bracket')).toBeVisible()
})
}
)
@ -470,7 +463,6 @@ test(
// expect to still be on the home page
await expect(page.getByText('router-template-slate')).toBeVisible()
await expect(page.getByText('Your Projects')).toBeVisible()
}
)
@ -533,7 +525,6 @@ test.describe(`Project management commands`, () => {
await expect(projectHomeLink.first()).toBeVisible()
await expect(projectHomeLink.first()).toContainText(projectRenamedName)
})
}
)
@ -586,7 +577,6 @@ test.describe(`Project management commands`, () => {
await test.step(`Check the project was deleted and we navigated home`, async () => {
await expect(noProjectsMessage).toBeVisible()
})
}
)
test(
@ -642,7 +632,6 @@ test.describe(`Project management commands`, () => {
).toBeVisible()
await expect(projectHomeLink).not.toHaveText(projectName)
})
}
)
test(
@ -692,7 +681,6 @@ test.describe(`Project management commands`, () => {
await expect(projectHomeLink).not.toBeVisible()
await expect(noProjectsMessage).toBeVisible()
})
}
)
})
@ -738,7 +726,6 @@ test(
await expect(u.codeLocator).toContainText(
'A mounting bracket for the Focusrite Scarlett Solo audio interface'
)
}
)
@ -794,10 +781,11 @@ test(
).rejects.toThrow()
// eslint-disable-next-line jest/no-conditional-expect
await expect(
fsp.access(path.join(testDir, 'router-template-slate', 'nested', 'main.kcl'))
fsp.access(
path.join(testDir, 'router-template-slate', 'nested', 'main.kcl')
)
).rejects.toThrow()
}
}
)
@ -876,7 +864,6 @@ test.fixme(
page.getByTestId('project-link').filter({ hasText: 'project-000' })
).toBeVisible()
})
}
)
@ -914,7 +901,6 @@ test(
await expect(u.codeLocator).toContainText('routerDiameter')
await expect(u.codeLocator).toContainText('templateGap')
await expect(u.codeLocator).toContainText('minClampingDistance')
}
)
@ -1022,7 +1008,6 @@ test(
)
}
})
}
)
@ -1211,7 +1196,6 @@ test(
await expect(page.getByText('router-template-slate')).toBeVisible()
await expect(page.getByText('New Project')).toBeVisible()
})
}
)
@ -1271,9 +1255,9 @@ test(
await page.getByTestId('project-directory-button').click()
await handleFile
await expect.poll(() => page.locator('section#projectDirectory input').inputValue()).toContain(
newProjectDirName
)
await expect
.poll(() => page.locator('section#projectDirectory input').inputValue())
.toContain(newProjectDirName)
await page.getByTestId('settings-close-button').click()
@ -1291,7 +1275,6 @@ test(
await page.getByTestId('project-directory-settings-link').click()
const handleFile = electronApp.evaluate(
async ({ dialog }, filePaths) => {
dialog.showOpenDialog = () =>
@ -1369,7 +1352,6 @@ test(
await expect(page.getByText(name)).toBeVisible()
}
})
}
)
@ -1475,7 +1457,6 @@ test(
false
)
})
}
)
@ -1534,7 +1515,6 @@ test(
expect(selectedText.length).toBe(0)
await expect(u.codeLocator).toHaveText('')
})
}
)
@ -1554,7 +1534,6 @@ test(
await expect(page.getByTestId('app-theme')).toHaveValue('dark')
await page.getByTestId('app-theme').selectOption('light')
})
await test.step('Starting the app again and we can see the same theme', async () => {
@ -1563,7 +1542,6 @@ test(
page.on('console', console.log)
await expect(page.getByTestId('app-theme')).toHaveValue('light')
})
}
)
@ -1605,6 +1583,5 @@ test.fixme(
await expect(projectLink).toContainText(projectNames[index])
}
})
}
)

View File

@ -1,16 +1,18 @@
import { test, expect, Page } from './zoo-test'
import path from 'path'
import * as fsp from 'fs/promises'
import {
getUtils,
executorInputPath,
} from './test-utils'
import { getUtils, executorInputPath } from './test-utils'
import { TEST_CODE_TRIGGER_ENGINE_EXPORT_ERROR } from './storageStates'
import { bracket } from 'lib/exampleKcl'
test.describe('Regression tests', () => {
// bugs we found that don't fit neatly into other categories
test('bad model has inline error #3251', async ({ context, page, homePage }) => { // because the model has `line([0,0]..` it is valid code, but the model is invalid
test('bad model has inline error #3251', async ({
context,
page,
homePage,
}) => {
// because the model has `line([0,0]..` it is valid code, but the model is invalid
// regression test for https://github.com/KittyCAD/modeling-app/issues/3251
// Since the bad model also found as issue with the artifact graph, which in tern blocked the editor diognostics
const u = await getUtils(page)
@ -41,8 +43,13 @@ test.describe('Regression tests', () => {
// when https://github.com/KittyCAD/modeling-app/issues/3268 is closed
// this test will need updating
const crypticErrorText = `ApiError`
await expect(page.getByText(crypticErrorText).first()).toBeVisible() })
test('user should not have to press down twice in cmdbar', async ({ page, homePage }) => { // because the model has `line([0,0]..` it is valid code, but the model is invalid
await expect(page.getByText(crypticErrorText).first()).toBeVisible()
})
test('user should not have to press down twice in cmdbar', async ({
page,
homePage,
}) => {
// because the model has `line([0,0]..` it is valid code, but the model is invalid
// regression test for https://github.com/KittyCAD/modeling-app/issues/3251
// Since the bad model also found as issue with the artifact graph, which in tern blocked the editor diognostics
const u = await getUtils(page)
@ -76,8 +83,9 @@ extrude001 = extrude(50, sketch001)
await page.getByTestId('command-bar-open-button').hover()
await page.getByTestId('command-bar-open-button').click()
const floppy = page
.getByRole('option', { name: 'floppy disk arrow Export' })
const floppy = page.getByRole('option', {
name: 'floppy disk arrow Export',
})
await floppy.click()
@ -109,8 +117,10 @@ extrude001 = extrude(50, sketch001)
await expect(page.locator('[data-headlessui-state="active"]')).toHaveText(
'light'
)
}) })
test('executes on load', async ({ page, homePage }) => { const u = await getUtils(page)
})
})
test('executes on load', async ({ page, homePage }) => {
const u = await getUtils(page)
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
@ -140,9 +150,11 @@ extrude001 = extrude(50, sketch001)
})
await expect(
page.locator('.pretty-json-container >> text=sketch001')
).toBeVisible() })
).toBeVisible()
})
test('re-executes', async ({ page, homePage }) => { const u = await getUtils(page)
test('re-executes', async ({ page, homePage }) => {
const u = await getUtils(page)
await page.addInitScript(async () => {
localStorage.setItem('persistCode', `myVar = 5`)
})
@ -166,8 +178,10 @@ extrude001 = extrude(50, sketch001)
await expect(
page.locator('.pretty-json-container >> text=myVar:67')
).toBeVisible() })
test('ProgramMemory can be serialised', async ({ page, homePage }) => { const u = await getUtils(page)
).toBeVisible()
})
test('ProgramMemory can be serialised', async ({ page, homePage }) => {
const u = await getUtils(page)
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
@ -203,19 +217,29 @@ extrude001 = extrude(50, sketch001)
messages.forEach((message) => {
expect(message).not.toContain(forbiddenMessage)
})
}) })
})
})
// Not relevant to us anymore, or at least for the time being.
test.skip('ensure the Zoo logo is not a link in browser app', async ({ page, homePage }) => { const u = await getUtils(page)
test.skip('ensure the Zoo logo is not a link in browser app', async ({
page,
homePage,
}) => {
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
const zooLogo = page.locator('[data-testid="app-logo"]')
// Make sure it's not a link
await expect(zooLogo).not.toHaveAttribute('href') })
await expect(zooLogo).not.toHaveAttribute('href')
})
test('Position _ Is Out Of Range... regression test', { tag: ['@skipWin'] }, async ({ context, page, homePage }) => { // SKip on windows, its being weird.
test(
'Position _ Is Out Of Range... regression test',
{ tag: ['@skipWin'] },
async ({ context, page, homePage }) => {
// SKip on windows, its being weird.
test.skip(
process.platform === 'win32',
'This test is being weird on windows'
@ -240,7 +264,6 @@ extrude001 = extrude(50, sketch001)
})
await expect(async () => {
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -292,9 +315,15 @@ extrude001 = extrude(50, sketch001)
thing: "blah"`)
await expect(page.locator('.cm-lint-marker-error')).toBeVisible() })
await expect(page.locator('.cm-lint-marker-error')).toBeVisible()
}
)
test('when engine fails export we handle the failure and alert the user', async ({ page, homePage }) => { const u = await getUtils(page)
test('when engine fails export we handle the failure and alert the user', async ({
page,
homePage,
}) => {
const u = await getUtils(page)
await page.addInitScript(
async ({ code }) => {
localStorage.setItem('persistCode', code)
@ -390,8 +419,13 @@ extrude001 = extrude(50, sketch001)
await expect(engineErrorToastMessage).not.toBeVisible()
const successToastMessage = page.getByText(`Exported successfully`)
await expect(successToastMessage).toBeVisible() })
test('ensure you can not export while an export is already going', { tag: ['@skipLinux', '@skipWin'] }, async ({ page, homePage }) => { // This is being weird on ubuntu and windows.
await expect(successToastMessage).toBeVisible()
})
test(
'ensure you can not export while an export is already going',
{ tag: ['@skipLinux', '@skipWin'] },
async ({ page, homePage }) => {
// This is being weird on ubuntu and windows.
test.skip(
// eslint-disable-next-line jest/valid-title
process.platform === 'linux' || process.platform === 'win32',
@ -476,7 +510,9 @@ extrude001 = extrude(50, sketch001)
])
await expect(successToastMessage).toBeVisible()
}) })
})
}
)
test(
`Network health indicator only appears in modeling view`,
@ -520,7 +556,11 @@ extrude001 = extrude(50, sketch001)
}
)
test(`View gizmo stays visible even when zoomed out all the way`, async ({ page, homePage }) => { const u = await getUtils(page)
test(`View gizmo stays visible even when zoomed out all the way`, async ({
page,
homePage,
}) => {
const u = await getUtils(page)
// Constants and locators
const planeColor: [number, number, number] = [170, 220, 170]
@ -570,7 +610,8 @@ extrude001 = extrude(50, sketch001)
await test.step(`Check that the gizmo is still visible`, async () => {
await expect(gizmo).toBeVisible()
}) })
})
})
})
async function clickExportButton(page: Page) {

View File

@ -3,7 +3,11 @@ import { test, expect } from './zoo-test'
import { commonPoints, getUtils } from './test-utils'
test.describe('Test network and connection issues', () => {
test('simulate network down and network little widget', async ({ page, homePage }) => { const u = await getUtils(page)
test('simulate network down and network little widget', async ({
page,
homePage,
}) => {
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await homePage.goToModelingScene()
@ -71,9 +75,15 @@ test.describe('Test network and connection issues', () => {
).not.toBeDisabled({ timeout: 15000 })
// (Second check) expect the network to be up
await expect(networkToggle).toContainText('Connected') })
await expect(networkToggle).toContainText('Connected')
})
test('Engine disconnect & reconnect in sketch mode', async ({ page, browserName, homePage }) => { // TODO: Don't skip Mac for these. After `window.tearDown` is working in Safari, these should work on webkit
test('Engine disconnect & reconnect in sketch mode', async ({
page,
browserName,
homePage,
}) => {
// TODO: Don't skip Mac for these. After `window.tearDown` is working in Safari, these should work on webkit
const networkToggle = page.getByTestId('network-toggle')
const u = await getUtils(page)
@ -208,5 +218,6 @@ test.describe('Test network and connection issues', () => {
await page.keyboard.press('Escape')
await expect(
page.getByRole('button', { name: 'Exit Sketch' })
).not.toBeVisible() })
).not.toBeVisible()
})
})

View File

@ -1157,3 +1157,12 @@ export function getPixelRGBs(page: Page) {
})
}
}
export async function pollEditorLinesSelectedLength(page: Page, lines: number) {
return expect
.poll(async () => {
const lines = await page.locator('.cm-activeLine').all()
return lines.length
})
.toBe(lines)
}

View File

@ -1,7 +1,7 @@
import { test, expect } from './zoo-test'
import { EngineCommand } from 'lang/std/artifactGraph'
import { uuidv4 } from 'lib/utils'
import { getUtils, } from './test-utils'
import { getUtils } from './test-utils'
test.describe('Testing Camera Movement', () => {
test('Can move camera reliably', async ({ page, context, homePage }) => {
@ -169,9 +169,14 @@ test.describe('Testing Camera Movement', () => {
await bakeInRetries(async () => {
await page.mouse.move(700, 400)
await page.mouse.wheel(0, -100)
}, [0, -85, -85]) })
}, [0, -85, -85])
})
test('Zoom should be consistent when exiting or entering sketches', async ({ page, homePage }) => { // start new sketch pan and zoom before exiting, when exiting the sketch should stay in the same place
test('Zoom should be consistent when exiting or entering sketches', async ({
page,
homePage,
}) => {
// start new sketch pan and zoom before exiting, when exiting the sketch should stay in the same place
// than zoom and pan outside of sketch mode and enter again and it should not change from where it is
// than again for sketching
@ -328,9 +333,14 @@ test.describe('Testing Camera Movement', () => {
await page.mouse.move(855, y)
await expect(page.getByTestId('hover-highlight').first()).toBeVisible({
timeout: 10_000,
}) })
})
})
test(`Zoom by scroll should not fire while orbiting`, async ({ page, homePage }) => { /**
test(`Zoom by scroll should not fire while orbiting`, async ({
page,
homePage,
}) => {
/**
* Currently we only allow zooming by scroll when no other camera movement is happening,
* set within cameraMouseDragGuards in cameraControls.ts,
* until the engine supports unifying multiple camera movements.
@ -462,5 +472,6 @@ test.describe('Testing Camera Movement', () => {
.toEqual(expectedOrbitCamZPosition)
await page.mouse.up({ button: 'middle' })
})
} })
}
})
})

View File

@ -1,11 +1,14 @@
import { test, expect } from './zoo-test'
import { getUtils, TEST_COLORS } from './test-utils'
import {
getUtils,
TEST_COLORS,
pollEditorLinesSelectedLength,
} from './test-utils'
import { XOR } from 'lib/utils'
test.describe('Testing constraints', () => {
test('Can constrain line length', async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
@ -35,7 +38,9 @@ test.describe('Testing constraints', () => {
// enter sketch again
await page.getByRole('button', { name: 'Edit Sketch' }).click()
await page.waitForTimeout(500) // wait for animation
// Wait for overlays to populate
await page.waitForTimeout(1000)
const startXPx = 500
await page.mouse.move(startXPx + PUR * 15, 250 - PUR * 10)
@ -61,11 +66,15 @@ test.describe('Testing constraints', () => {
// Exit sketch
await page.mouse.move(startXPx + PUR * 15, 250 - PUR * 10)
await page.keyboard.press('Escape')
await expect(
page.getByRole('button', { name: 'Exit Sketch' })
).not.toBeVisible() })
test(`Remove constraints`, async ({ page, homePage }) => { await page.addInitScript(async () => {
await expect
.poll(async () => {
await page.keyboard.press('Escape', { delay: 500 })
return page.getByRole('button', { name: 'Exit Sketch' }).isVisible()
})
.toBe(true)
})
test(`Remove constraints`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 79
@ -84,7 +93,7 @@ test.describe('Testing constraints', () => {
)
})
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -92,6 +101,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %, $seg01)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const line3 = await u.getSegmentBodyCoords(`[data-overlay-index="${2}"]`)
await page.mouse.click(line3.x, line3.y)
@ -104,12 +116,13 @@ test.describe('Testing constraints', () => {
await page.getByRole('button', { name: 'remove constraints' }).click()
await page.getByText('line([39.13, 68.63], %)').click()
await pollEditorLinesSelectedLength(page, 1)
const activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent).toHaveLength(1)
await expect(activeLinesContent[0]).toHaveText('|> line([39.13, 68.63], %)')
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
test.describe('Test perpendicular distance constraint', () => {
const cases = [
{
@ -122,7 +135,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { testName, offset } of cases) {
test(`${testName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${testName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -150,11 +164,12 @@ test.describe('Testing constraints', () => {
.click()
// Wait for the codemod to take effect
await expect(page.locator('.cm-content')).toContainText(`angle = -57,`)
await expect(page.locator('.cm-content')).toContainText(`angle: -57,`)
await expect(page.locator('.cm-content')).toContainText(
`offset = ${offset},`
`offset: ${offset},`
)
await pollEditorLinesSelectedLength(page, 2)
const activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent[0]).toHaveText(
`|> line([74.36, 130.4], %, $seg01)`
@ -173,16 +188,22 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %, $seg01)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Give time for overlays to populate
await page.waitForTimeout(1000)
const [line1, line3] = await Promise.all([
u.getSegmentBodyCoords(`[data-overlay-index="${0}"]`),
u.getSegmentBodyCoords(`[data-overlay-index="${2}"]`),
])
await page.mouse.click(line1.x, line1.y)
await page.keyboard.down('Shift')
await page.mouse.click(line3.x, line3.y)
await page.waitForTimeout(100) // this wait is needed for webkit - not sure why
await page.keyboard.up('Shift')
await page.keyboard.down('Shift')
await page.waitForTimeout(100)
await page.mouse.click(line3.x, line3.y)
await page.waitForTimeout(100)
await page.keyboard.up('Shift')
await page.waitForTimeout(100)
await page
.getByRole('button', {
name: 'Length: open menu',
@ -205,11 +226,12 @@ test.describe('Testing constraints', () => {
.click()
// Wait for the codemod to take effect
await expect(page.locator('.cm-content')).toContainText(`angle: -57,`)
await expect(page.locator('.cm-content')).toContainText(`angle = -57,`)
await expect(page.locator('.cm-content')).toContainText(
`offset: ${offset},`
`offset = ${offset},`
)
await pollEditorLinesSelectedLength(page, 2)
const activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent[0]).toHaveText(
`|> line([74.36, 130.4], %, $seg01)`
@ -217,7 +239,8 @@ test.describe('Testing constraints', () => {
await expect(activeLinesContent[1]).toHaveText(`}, %)`)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
}
})
test.describe('Test distance between constraint', () => {
@ -244,7 +267,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { testName, value, constraint } of cases) {
test(`${constraint} - ${testName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${constraint} - ${testName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -263,7 +287,7 @@ test.describe('Testing constraints', () => {
)
})
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -271,6 +295,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const [line1, line3] = await Promise.all([
u.getSegmentBodyCoords(`[data-overlay-index="${0}"]`),
u.getSegmentBodyCoords(`[data-overlay-index="${2}"]`),
@ -318,7 +345,8 @@ test.describe('Testing constraints', () => {
)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
}
})
test.describe('Test ABS distance constraint', () => {
@ -349,7 +377,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { testName, addVariable, value, constraint } of cases) {
test(`${constraint} - ${testName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${constraint} - ${testName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -376,6 +405,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const [line3] = await Promise.all([
u.getSegmentBodyCoords(`[data-overlay-index="${2}"]`),
])
@ -386,9 +418,11 @@ test.describe('Testing constraints', () => {
await page.mouse.click(900, 250)
}
await page.keyboard.down('Shift')
await page.waitForTimeout(100)
await page.mouse.click(line3.x, line3.y)
await page.waitForTimeout(100) // this wait is needed for webkit - not sure why
await page.waitForTimeout(100)
await page.keyboard.up('Shift')
await page.waitForTimeout(100)
await page
.getByRole('button', {
name: 'Length: open menu',
@ -424,7 +458,8 @@ test.describe('Testing constraints', () => {
)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
}
})
test.describe('Test Angle constraint double segment selection', () => {
@ -455,7 +490,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { testName, addVariable, value, axisSelect } of cases) {
test(`${testName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${testName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -482,6 +518,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const [line1, line3] = await Promise.all([
u.getSegmentBodyCoords(`[data-overlay-index="${0}"]`),
u.getSegmentBodyCoords(`[data-overlay-index="${2}"]`),
@ -533,7 +572,8 @@ test.describe('Testing constraints', () => {
)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
}
})
test.describe('Test Angle/Length constraint single selection', () => {
@ -564,7 +604,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { testName, addVariable, value, constraint } of cases) {
test(`${testName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${testName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -583,7 +624,7 @@ test.describe('Testing constraints', () => {
)
})
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -591,6 +632,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const line3 = await u.getSegmentBodyCoords(
`[data-overlay-index="${2}"]`
)
@ -616,7 +660,8 @@ test.describe('Testing constraints', () => {
await expect(page.locator('.cm-activeLine')).toHaveText(changedCode)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(4) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(4)
})
}
})
test.describe('Many segments - no modal constraints', () => {
@ -639,7 +684,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { codeAfter, constraintName } of cases) {
test(`${constraintName}`, async ({ page, homePage }) => { await page.addInitScript(async (customCode) => {
test(`${constraintName}`, async ({ page, homePage }) => {
await page.addInitScript(async (customCode) => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -658,7 +704,7 @@ test.describe('Testing constraints', () => {
)
})
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -666,6 +712,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const line1 = await u.getSegmentBodyCoords(
`[data-overlay-index="${0}"]`
)
@ -684,8 +733,8 @@ test.describe('Testing constraints', () => {
await page.keyboard.up('Shift')
// check actives lines
await pollEditorLinesSelectedLength(page, codeAfter.length)
const activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent).toHaveLength(codeAfter.length)
const constraintMenuButton = page.getByRole('button', {
name: 'Length: open menu',
@ -712,7 +761,8 @@ test.describe('Testing constraints', () => {
// if the code is an active line then the cursor should be on that line
await expect(line).toHaveText(codeAfter[i])
})
) })
)
})
}
})
test.describe('Two segment - no modal constraints', () => {
@ -735,7 +785,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { codeAfter, constraintName } of cases) {
test(`${constraintName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${constraintName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -753,7 +804,7 @@ test.describe('Testing constraints', () => {
)
})
const u = await getUtils(page)
await page.setBodyDimensions({ width: 1200, height: 500 })
await page.setBodyDimensions({ width: 1000, height: 500 })
await homePage.goToModelingScene()
await u.waitForPageLoad()
@ -761,6 +812,9 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const line1 = await u.getBoundingBox(`[data-overlay-index="${0}"]`)
const line3 = await u.getBoundingBox(`[data-overlay-index="${2}"]`)
@ -787,14 +841,15 @@ test.describe('Testing constraints', () => {
// check there are still 2 cursors (they should stay on the same lines as before constraint was applied)
await expect(page.locator('.cm-cursor')).toHaveCount(2)
// check actives lines
await pollEditorLinesSelectedLength(page, 2)
const activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent).toHaveLength(2)
// check both cursors are where they should be after constraint is applied
await expect(activeLinesContent[0]).toHaveText(
'|> line([74.36, 130.4], %, $seg01)'
)
await expect(activeLinesContent[1]).toHaveText(codeAfter) })
await expect(activeLinesContent[1]).toHaveText(codeAfter)
})
}
})
test.describe('Axis & segment - no modal constraints', () => {
@ -811,7 +866,8 @@ test.describe('Testing constraints', () => {
},
] as const
for (const { codeAfter, constraintName, axisClick } of cases) {
test(`${constraintName}`, async ({ page, homePage }) => { await page.addInitScript(async () => {
test(`${constraintName}`, async ({ page, homePage }) => {
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
`yo = 5
@ -837,14 +893,20 @@ test.describe('Testing constraints', () => {
await page.getByText('line([74.36, 130.4], %)').click()
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
const line3 = await u.getBoundingBox(`[data-overlay-index="${2}"]`)
// select segment and axis by holding down shift
await page.mouse.click(line3.x - 3, line3.y + 20)
await page.waitForTimeout(100)
await page.keyboard.down('Shift')
await page.waitForTimeout(100)
await page.mouse.click(axisClick.x, axisClick.y)
await page.waitForTimeout(100)
await page.keyboard.up('Shift')
await page.waitForTimeout(100)
const constraintMenuButton = page.getByRole('button', {
name: 'Length: open menu',
})
@ -859,11 +921,16 @@ test.describe('Testing constraints', () => {
// check the cursor is where is should be after constraint is applied
await expect(page.locator('.cm-content')).toContainText(codeAfter)
await expect(page.locator('.cm-activeLine')).toHaveText(codeAfter) })
await expect(page.locator('.cm-activeLine')).toHaveText(codeAfter)
})
}
})
test('Horizontally constrained line remains selected after applying constraint', async ({ page, homePage }) => { test.setTimeout(70_000)
test('Horizontally constrained line remains selected after applying constraint', async ({
page,
homePage,
}) => {
test.setTimeout(70_000)
await page.addInitScript(async () => {
localStorage.setItem(
'persistCode',
@ -885,6 +952,9 @@ test.describe('Testing constraints', () => {
)
await page.getByRole('button', { name: 'Edit Sketch' }).click()
// Wait for overlays to populate
await page.waitForTimeout(1000)
await page.waitForTimeout(100)
const lineBefore = await u.getSegmentBodyCoords(
`[data-overlay-index="1"]`,
@ -905,11 +975,17 @@ test.describe('Testing constraints', () => {
name: 'Length: open menu',
})
.click()
await page.waitForTimeout(500)
await page.getByRole('button', { name: 'Horizontal', exact: true }).click()
await page.waitForTimeout(500)
await pollEditorLinesSelectedLength(page, 1)
let activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent[0]).toHaveText(`|> xLine(3.13, %)`)
// Wait for code editor to settle.
await page.waitForTimeout(2000)
// If the overlay-angle is updated the THREE.js scene is in a good state
await expect(
await page.locator('[data-overlay-index="1"]')
@ -919,11 +995,17 @@ test.describe('Testing constraints', () => {
`[data-overlay-index="1"]`,
0
)
expect(
await u.getGreatestPixDiff(lineAfter, TEST_COLORS.BLUE)
).toBeLessThan(3)
await page.waitForTimeout(300)
const linebb = await u.getBoundingBox('[data-overlay-index="1"]')
await page.mouse.move(linebb.x, linebb.y, { step: 25 })
await page.mouse.click(linebb.x, linebb.y)
expect
.poll(async () => await u.getGreatestPixDiff(lineAfter, TEST_COLORS.BLUE))
.toBeLessThan(3)
await page.waitForTimeout(500)
await page
.getByRole('button', {
name: 'Length: open menu',
@ -937,9 +1019,11 @@ test.describe('Testing constraints', () => {
await page.getByLabel('length Value').fill('10')
await page.getByRole('button', { name: 'Add constraining value' }).click()
await pollEditorLinesSelectedLength(page, 1)
activeLinesContent = await page.locator('.cm-activeLine').all()
await expect(activeLinesContent[0]).toHaveText(`|> xLine(length001, %)`)
// checking the count of the overlays is a good proxy check that the client sketch scene is in a good state
await expect(page.getByTestId('segment-overlay')).toHaveCount(2) })
await expect(page.getByTestId('segment-overlay')).toHaveCount(2)
})
})

View File

@ -132,10 +132,12 @@ test.describe('Testing Gizmo', () => {
expect(page.getByTestId('cam-z-target')).toHaveValue(
expectedCameraTarget.z.toString()
),
]) })
])
})
}
test('Context menu and popover menu', async ({ page, homePage }) => { const testCase = {
test('Context menu and popover menu', async ({ page, homePage }) => {
const testCase = {
testDescription: 'Right view',
expectedCameraPosition: { x: 5660.02, y: -152, z: 26 },
expectedCameraTarget: { x: 800, y: -152, z: 26 },
@ -238,7 +240,8 @@ test.describe('Testing Gizmo', () => {
})
await expect(gizmoPopoverButton).toBeVisible()
await gizmoPopoverButton.click()
await expect(buttonToTest).toBeVisible() })
await expect(buttonToTest).toBeVisible()
})
})
test.describe(`Testing gizmo, fixture-based`, () => {
@ -252,7 +255,9 @@ test.describe(`Testing gizmo, fixture-based`, () => {
scene,
}) => {
await context.addInitScript(() => {
localStorage.setItem('persistCode', `
localStorage.setItem(
'persistCode',
`
const sketch002 = startSketchOn('XZ')
|> startProfileAt([-108.83, -57.48], %)
|> angledLine([0, 105.13], %, $rectangleSegmentA001)
@ -271,7 +276,8 @@ test.describe(`Testing gizmo, fixture-based`, () => {
radius: 182.8
}, %)
|> extrude(50, %)
`)
`
)
})
await page.setBodyDimensions({ width: 1000, height: 500 })

View File

@ -1,18 +1,10 @@
import { test, expect } from '@playwright/test'
import { getUtils, setup, tearDown } from './test-utils'
import { test, expect } from './zoo-test'
import { getUtils } from './test-utils'
import { TEST_SETTINGS, TEST_SETTINGS_KEY } from './storageStates'
import * as TOML from '@iarna/toml'
test.beforeEach(async ({ context, page }, testInfo) => {
await setup(context, page, testInfo)
})
test.afterEach(async ({ page }, testInfo) => {
await tearDown(page, testInfo)
})
test.describe('Test toggling perspective', () => {
test('via command palette and toggle', async ({ page }) => {
test('via command palette and toggle', async ({ page, homePage }) => {
const u = await getUtils(page)
// Locators and constants
@ -40,8 +32,8 @@ test.describe('Test toggling perspective', () => {
})
await test.step('Setup', async () => {
await page.setViewportSize({ width: screenWidth, height: screenHeight })
await u.waitForAuthSkipAppStart()
await page.setBodyDimensions({ width: screenWidth, height: screenHeight })
await homePage.goToModelingScene()
await u.closeKclCodePanel()
await expect
.poll(async () => locationToHaveColor(backgroundColor), {
@ -87,7 +79,7 @@ test.describe('Test toggling perspective', () => {
}
)
await page.reload()
await u.waitForAuthSkipAppStart()
await homePage.goToModelingScene()
await expect
.poll(async () => locationToHaveColor(xzPlaneColor), {
timeout: 5000,

View File

@ -7,7 +7,8 @@ import packageJson from '../package.json'
import { MachinesListing } from 'components/MachineManagerProvider'
import chokidar from 'chokidar'
const resizeWindow = (width: number, height: number) => ipcRenderer.invoke('app.resizeWindow', [width, height])
const resizeWindow = (width: number, height: number) =>
ipcRenderer.invoke('app.resizeWindow', [width, height])
const open = (args: any) => ipcRenderer.invoke('dialog.showOpenDialog', args)
const save = (args: any) => ipcRenderer.invoke('dialog.showSaveDialog', args)
const openExternal = (url: any) => ipcRenderer.invoke('shell.openExternal', url)