Skip to content

Commit 97de550

Browse files
committed
fix: rangeMap and scroll
1 parent 6d38ea9 commit 97de550

File tree

6 files changed

+47
-73
lines changed

6 files changed

+47
-73
lines changed

packages/demo/src/index.tsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ async function initView() {
2828
doc,
2929
});
3030
controller.setCurrentSheetId(controller.getCurrentSheetId());
31+
(window as any).controller = controller;
32+
(window as any).doc = doc;
3133

3234
createRoot(document.getElementById('root')!).render(
3335
<StrictMode>

packages/react/src/collaboration/index.ts

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,7 @@ function shouldSkip(isServer: boolean, tran: Y.Transaction) {
1111
return false;
1212
}
1313

14-
export async function initCollaboration(
15-
doc: Y.Doc,
16-
): Promise<{
14+
export async function initCollaboration(doc: Y.Doc): Promise<{
1715
provider: CollaborationProvider;
1816
isServer: boolean;
1917
isInit: boolean;
@@ -24,7 +22,7 @@ export async function initCollaboration(
2422
if (shouldSkip(isServer, tran)) {
2523
return;
2624
}
27-
collaborationLog('doc update', tran);
25+
collaborationLog('doc update', tran.doc.clientID, tran);
2826
provider.addHistory(update);
2927
});
3028
provider.subscribe();

packages/react/src/controller/Controller.ts

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,11 @@ import {
4141
IMAGE_FORMAT,
4242
formatCustomData,
4343
} from '@excel/shared';
44-
import { numberFormat, isDateFormat, convertDateToNumber } from '@excel/formula';
44+
import {
45+
numberFormat,
46+
isDateFormat,
47+
convertDateToNumber,
48+
} from '@excel/formula';
4549
import { transaction } from './decorator';
4650

4751
const defaultScrollValue: Omit<ScrollValue, 'row' | 'col'> = {
@@ -97,7 +101,6 @@ export class Controller implements IController {
97101
getActiveRange(r?: IRange) {
98102
return this.model.getActiveRange(r);
99103
}
100-
@transaction()
101104
setNextActiveCell(direction: 'left' | 'right' | 'down' | 'up') {
102105
const { range, isMerged } = this.getActiveRange();
103106
let startCol = range.col;
@@ -150,7 +153,6 @@ export class Controller implements IController {
150153
}
151154
this.setActiveRange(result);
152155
}
153-
@transaction()
154156
setActiveRange(range: IRange): void {
155157
this.model.setActiveRange(range);
156158
this.changeSet.add('rangeMap');

packages/react/src/model/Model.ts

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ export class Model implements IModel {
9494
for (const item of this.changeSet.keys()) {
9595
changeSet.add(item);
9696
}
97-
modelLog('observeDeep', event, changeSet);
97+
modelLog('observeDeep', doc.clientID, event[0], changeSet);
9898
this.render(changeSet);
9999
this.changeSet = new Set<ChangeEventType>();
100100
});
@@ -131,7 +131,13 @@ export class Model implements IModel {
131131
eventEmitter.emit('modelChange', { changeSet });
132132
}
133133
async emitChange(changeSet: Set<ChangeEventType>) {
134-
const localChangeList: ChangeEventType[] = ['antLine', 'undo', 'redo'];
134+
const localChangeList: ChangeEventType[] = [
135+
'antLine',
136+
'undo',
137+
'redo',
138+
'scroll',
139+
'rangeMap',
140+
];
135141
if (changeSet.has('customHeight') || changeSet.has('customWidth')) {
136142
this.computeViewSize();
137143
}
@@ -258,7 +264,11 @@ export class Model implements IModel {
258264

259265
result[key] = typeof v === 'undefined' ? {} : v;
260266
}
261-
return result;
267+
return {
268+
...result,
269+
rangeMap: this.rangeMapManager.toJSON(),
270+
scroll: this.scrollManager.toJSON(),
271+
};
262272
};
263273

264274
setCell(

packages/react/src/model/rangeMap.ts

Lines changed: 11 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,11 @@
1-
import type { ModelJSON, IRangeMap, IRange, IModel, YjsModelJson } from '@excel/shared';
2-
import { isSameRange, toIRange } from '@excel/shared';
3-
import * as Y from 'yjs';
1+
import type { ModelJSON, IRangeMap, IRange, IModel } from '@excel/shared';
42

53
export class RangeMap implements IRangeMap {
64
private model: IModel;
5+
private rangeMap: ModelJSON['rangeMap'] = {};
76
constructor(model: IModel) {
87
this.model = model;
98
}
10-
private get rangeMap() {
11-
return this.model.getRoot().get('rangeMap');
12-
}
139
validateRange(range: IRange) {
1410
if (!range) {
1511
return false;
@@ -37,20 +33,23 @@ export class RangeMap implements IRangeMap {
3733
}
3834
fromJSON(json: ModelJSON): void {
3935
const data = json.rangeMap || {};
40-
const rangeMap = new Y.Map() as YjsModelJson['rangeMap'];
36+
const rangeMap: ModelJSON['rangeMap'] = {};
4137
for (const range of Object.values(data)) {
4238
range.sheetId = range.sheetId || this.model.getCurrentSheetId();
4339
if (!this.model.validateRange(range)) {
4440
continue;
4541
}
46-
rangeMap.set(range.sheetId, range);
42+
rangeMap[range.sheetId] = { ...range };
4743
}
48-
this.model.getRoot().set('rangeMap', rangeMap);
44+
this.rangeMap = rangeMap;
45+
}
46+
toJSON() {
47+
return {...this.rangeMap}
4948
}
5049
getActiveRange() {
5150
const id = this.model.getCurrentSheetId();
5251

53-
const range = this.rangeMap?.get(id);
52+
const range = this.rangeMap[id];
5453
if (range) {
5554
range.sheetId = range.sheetId || id;
5655
return {
@@ -74,18 +73,9 @@ export class RangeMap implements IRangeMap {
7473
if (!this.validateRange(newRange)) {
7574
return;
7675
}
77-
let rangeMap = this.rangeMap;
78-
if (!rangeMap) {
79-
rangeMap = new Y.Map() as YjsModelJson['rangeMap'];
80-
this.model.getRoot().set('rangeMap', rangeMap);
81-
}
82-
const oldValue = rangeMap.get(newRange.sheetId);
83-
if (oldValue && isSameRange(oldValue, newRange)) {
84-
return;
85-
}
86-
rangeMap.set(newRange.sheetId, toIRange(newRange));
76+
this.rangeMap[newRange.sheetId] = { ...newRange };
8777
}
8878
deleteAll(sheetId?: string): void {
89-
this.rangeMap?.delete(sheetId || this.model.getCurrentSheetId());
79+
delete this.rangeMap[sheetId || this.model.getCurrentSheetId()];
9080
}
9181
}

packages/react/src/model/scroll.ts

Lines changed: 14 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -1,50 +1,38 @@
1-
import type {
2-
ModelJSON,
3-
IScroll,
4-
IModel,
5-
YjsModelJson,
6-
ModelScroll,
7-
TypedMap,
8-
} from '@excel/shared';
9-
import * as Y from 'yjs';
1+
import type { ModelJSON, IScroll, IModel, ModelScroll } from '@excel/shared';
102

113
export class ScrollManager implements IScroll {
124
private model: IModel;
5+
private scroll: ModelJSON['scroll'] = {};
136
constructor(model: IModel) {
147
this.model = model;
158
}
16-
private get scroll() {
17-
return this.model.getRoot().get('scroll');
18-
}
199
fromJSON(json: ModelJSON): void {
2010
const data = json.scroll || {};
21-
const scroll = new Y.Map() as YjsModelJson['scroll'];
11+
const scroll: ModelJSON['scroll'] = {};
2212
for (const [sheetId, value] of Object.entries(data)) {
2313
if (!sheetId || value.row < 0 || value.col < 0) {
2414
continue;
2515
}
26-
scroll.set(
27-
sheetId,
28-
new Y.Map(Object.entries(value)) as TypedMap<ModelScroll>,
29-
);
16+
scroll[sheetId] = value;
3017
}
31-
this.model.getRoot().set('scroll', scroll);
18+
this.scroll = scroll;
19+
}
20+
toJSON() {
21+
return { ...this.scroll };
3222
}
3323
deleteAll(sheetId?: string): void {
34-
this.scroll?.delete(sheetId || this.model.getCurrentSheetId());
24+
const id = sheetId || this.model.getCurrentSheetId();
25+
delete this.scroll[id];
3526
}
3627
getScroll(sheetId?: string): ModelScroll {
37-
const t = this.scroll?.get(sheetId || this.model.getCurrentSheetId());
28+
const t = this.scroll[sheetId || this.model.getCurrentSheetId()];
3829
if (!t) {
3930
return { row: 0, col: 0 };
4031
}
41-
return t.toJSON();
32+
return { ...t };
4233
}
4334
setScroll(value: ModelScroll, sheetId?: string) {
4435
const id = sheetId || this.model.getCurrentSheetId();
45-
if (!this.scroll) {
46-
this.model.getRoot().set('scroll', new Y.Map() as YjsModelJson['scroll']);
47-
}
4836
const sheetInfo = this.model.getSheetInfo(id);
4937
if (!sheetInfo) {
5038
return false;
@@ -61,23 +49,7 @@ export class ScrollManager implements IScroll {
6149
} else if (value.col < 0) {
6250
value.col = 0;
6351
}
64-
const item = this.scroll?.get(id);
65-
if (!item) {
66-
this.scroll!.set(
67-
id,
68-
new Y.Map(Object.entries(value)) as TypedMap<ModelScroll>,
69-
);
70-
return false;
71-
}
72-
let check = false;
73-
if (item.get('row') !== value.row) {
74-
check = true;
75-
item.set('row', value.row);
76-
}
77-
if (item.get('col') !== value.col) {
78-
check = true;
79-
item.set('col', value.col);
80-
}
81-
return check;
52+
this.scroll[id] = { ...value };
53+
return true;
8254
}
8355
}

0 commit comments

Comments
 (0)