Skip to content

Commit

Permalink
fix: 修复 2k 显示器切换到 MacBook 后表格渲染模糊 close #2072
Browse files Browse the repository at this point in the history
  • Loading branch information
lijinke666 committed Feb 13, 2023
1 parent 4602b42 commit 30feb66
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 12 deletions.
29 changes: 20 additions & 9 deletions packages/s2-core/__tests__/unit/ui/hd-adapter/index-spec.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,17 @@
import { createFakeSpreadSheet, sleep } from 'tests/util/helpers';
import { createPivotSheet, sleep } from 'tests/util/helpers';
import type { S2Options } from '../../../../src';
import type { SpreadSheet } from '@/sheet-type/spread-sheet';
import { HdAdapter } from '@/ui/hd-adapter';

jest.mock('@/interaction/event-controller');
jest.mock('@/interaction/root');

// eslint-disable-next-line jest/no-disabled-tests
describe.skip('HD Adapter Tests', () => {
describe('HD Adapter Tests', () => {
const DPR = 2;
const s2Options: S2Options = {
width: 600,
height: 600,
};

let s2: SpreadSheet;
let hdAdapter: HdAdapter;
Expand All @@ -25,7 +29,7 @@ describe.skip('HD Adapter Tests', () => {
configurable: true,
});

s2 = createFakeSpreadSheet();
s2 = createPivotSheet(s2Options);
hdAdapter = new HdAdapter(s2);
hdAdapter.init();

Expand All @@ -36,7 +40,7 @@ describe.skip('HD Adapter Tests', () => {
s2.options.height * DPR,
],
) => {
const canvas: HTMLCanvasElement = s2.container.get('el');
const canvas = s2.getCanvasElement();
expect(canvas.style.width).toEqual(`${width}px`);
expect(canvas.style.height).toEqual(`${height}px`);
expect(canvas.width).toEqual(updatedWidth);
Expand All @@ -46,6 +50,7 @@ describe.skip('HD Adapter Tests', () => {

afterEach(() => {
hdAdapter.destroy();
s2.destroy();

Object.defineProperty(visualViewport, 'scale', {
value: 1,
Expand All @@ -59,11 +64,12 @@ describe.skip('HD Adapter Tests', () => {
});

test('should not be update container size when zoom scale changed, but scale less than current DPR', async () => {
const render = jest.spyOn(s2, 'render').mockImplementationOnce(() => {});
visualViewport.dispatchEvent(new Event('resize'));
await sleep(500);

expectContainerSize();
expect(s2.render).not.toHaveBeenCalled();
expect(render).not.toHaveBeenCalled();
});

// eslint-disable-next-line jest/expect-expect
Expand All @@ -85,17 +91,20 @@ describe.skip('HD Adapter Tests', () => {
});

test('should use DPR for update container size when zoom scale changed, and scale less than current DPR', async () => {
const render = jest.spyOn(s2, 'render').mockImplementationOnce(() => {});
Object.defineProperty(visualViewport, 'scale', {
value: 1,
configurable: true,
});
visualViewport.dispatchEvent(new Event('resize'));

await sleep(500);
expect(s2.render).not.toHaveBeenCalled();
expect(render).not.toHaveBeenCalled();
});

test('should not rerender when zoom event destroyed', async () => {
const render = jest.spyOn(s2, 'render').mockImplementationOnce(() => {});

hdAdapter.destroy();
Object.defineProperty(visualViewport, 'scale', {
value: 3,
Expand All @@ -104,10 +113,12 @@ describe.skip('HD Adapter Tests', () => {
visualViewport.dispatchEvent(new Event('resize'));

await sleep(500);
expect(s2.render).not.toHaveBeenCalled();
expect(render).not.toHaveBeenCalled();
});

test('should not rerender when zoom event destroyed on mobile device', async () => {
const render = jest.spyOn(s2, 'render').mockImplementationOnce(() => {});

hdAdapter.destroy();
Object.defineProperty(navigator, 'userAgent', {
value: 'iPhone',
Expand All @@ -119,6 +130,6 @@ describe.skip('HD Adapter Tests', () => {
await sleep(500);

expectContainerSize();
expect(s2.render).not.toHaveBeenCalled();
expect(render).not.toHaveBeenCalled();
});
});
20 changes: 17 additions & 3 deletions packages/s2-core/src/ui/hd-adapter/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ export class HdAdapter {

private spreadsheet: SpreadSheet;

private isDevicePixelRatioChange = false;

constructor(spreadsheet: SpreadSheet) {
this.spreadsheet = spreadsheet;
}
Expand Down Expand Up @@ -60,7 +62,7 @@ export class HdAdapter {
// VisualViewport support browser zoom & mac touch tablet
this.viewport?.visualViewport?.addEventListener(
'resize',
this.renderByZoomScale,
this.renderByZoomScaleWithoutResizeEffect,
);
};

Expand All @@ -70,11 +72,23 @@ export class HdAdapter {
}
this.viewport?.visualViewport?.removeEventListener(
'resize',
this.renderByZoomScale,
this.renderByZoomScaleWithoutResizeEffect,
);
};

/**
* DPR改变也会触发 visualViewport 的 resize 事件, 预期是只监听双指缩放, 所以这里规避掉
* @see https://github.com/antvis/S2/issues/2072
*/
private renderByZoomScaleWithoutResizeEffect = (
event: Event & { target: VisualViewport },
) => {
this.isDevicePixelRatioChange = false;
this.renderByZoomScale(event);
};

private renderByDevicePixelRatioChanged = () => {
this.isDevicePixelRatioChange = true;
this.renderByDevicePixelRatio();
};

Expand Down Expand Up @@ -107,7 +121,7 @@ export class HdAdapter {
private renderByZoomScale = debounce(
(event: Event & { target: VisualViewport }) => {
const ratio = Math.ceil(event.target.scale);
if (ratio >= 1) {
if (ratio >= 1 && !this.isDevicePixelRatioChange) {
this.renderByDevicePixelRatio(ratio);
}
},
Expand Down

0 comments on commit 30feb66

Please sign in to comment.