Skip to content

Commit

Permalink
Don't modify state when setting identical selection
Browse files Browse the repository at this point in the history
  • Loading branch information
jsnajdr committed Mar 6, 2024
1 parent c5e643a commit fbf5ac9
Showing 1 changed file with 47 additions and 42 deletions.
89 changes: 47 additions & 42 deletions packages/block-editor/src/store/reducer.js
Original file line number Diff line number Diff line change
Expand Up @@ -1336,14 +1336,14 @@ function selectionHelper( state = {}, action ) {
if (
! action.clientIds ||
! action.clientIds.length ||
action.clientIds.indexOf( state.clientId ) === -1
! action.clientIds.includes( state.clientId )
) {
return state;
}

return {};
case 'REPLACE_BLOCKS': {
if ( action.clientIds.indexOf( state.clientId ) === -1 ) {
if ( ! action.clientIds.includes( state.clientId ) ) {
return state;
}

Expand All @@ -1366,6 +1366,20 @@ function selectionHelper( state = {}, action ) {
return state;
}

function selectionEqual( sel1, sel2 ) {
if ( sel1 === sel2 ) {
return true;
}
if ( ! sel1 || ! sel2 ) {
return false;
}
return (
sel1.clientId === sel2.clientId &&
sel1.attributeKey === sel2.attributeKey &&
sel1.offset === sel2.offset
);
}

/**
* Reducer returning the selection state.
*
Expand All @@ -1375,33 +1389,30 @@ function selectionHelper( state = {}, action ) {
* @return {boolean} Updated state.
*/
export function selection( state = {}, action ) {
let { selectionStart, selectionEnd } = state;

switch ( action.type ) {
case 'SELECTION_CHANGE':
if ( action.clientId ) {
return {
selectionStart: {
clientId: action.clientId,
attributeKey: action.attributeKey,
offset: action.startOffset,
},
selectionEnd: {
clientId: action.clientId,
attributeKey: action.attributeKey,
offset: action.endOffset,
},
selectionStart = {
clientId: action.clientId,
attributeKey: action.attributeKey,
offset: action.startOffset,
};
selectionEnd = {
clientId: action.clientId,
attributeKey: action.attributeKey,
offset: action.endOffset,
};
} else {
selectionStart = action.start || selectionStart;
selectionEnd = action.end || selectionEnd;
}

return {
selectionStart: action.start || state.selectionStart,
selectionEnd: action.end || state.selectionEnd,
};
break;
case 'RESET_SELECTION':
const { selectionStart, selectionEnd } = action;
return {
selectionStart,
selectionEnd,
};
selectionStart = action.selectionStart;
selectionEnd = action.selectionEnd;
break;
case 'MULTI_SELECT':
const { start, end } = action;

Expand All @@ -1412,10 +1423,9 @@ export function selection( state = {}, action ) {
return state;
}

return {
selectionStart: { clientId: start },
selectionEnd: { clientId: end },
};
selectionStart = { clientId: start };
selectionEnd = { clientId: end };
break;
case 'RESET_BLOCKS':
const startClientId = state?.selectionStart?.clientId;
const endClientId = state?.selectionEnd?.clientId;
Expand All @@ -1431,31 +1441,26 @@ export function selection( state = {}, action ) {
( block ) => block.clientId === startClientId
)
) {
return {
selectionStart: {},
selectionEnd: {},
};
selectionStart = {};
selectionEnd = {};
}

// If the end of the selection won't exist after reset, collapse selection.
if (
else if (
! action.blocks.some(
( block ) => block.clientId === endClientId
)
) {
return {
...state,
selectionEnd: state.selectionStart,
};
selectionEnd = selectionStart;
}
break;
default:
selectionStart = selectionHelper( state.selectionStart, action );
selectionEnd = selectionHelper( state.selectionEnd, action );
}

const selectionStart = selectionHelper( state.selectionStart, action );
const selectionEnd = selectionHelper( state.selectionEnd, action );

if (
selectionStart === state.selectionStart &&
selectionEnd === state.selectionEnd
selectionEqual( selectionStart, state.selectionStart ) &&
selectionEqual( selectionEnd, state.selectionEnd )
) {
return state;
}
Expand Down

0 comments on commit fbf5ac9

Please sign in to comment.