Skip to content

Commit 526bfa1

Browse files
committed
Updates
1 parent 8a0c27b commit 526bfa1

File tree

7 files changed

+68
-15
lines changed

7 files changed

+68
-15
lines changed

plugins/breakpoint-split-view/src/BreakpointSplitView/components/useRangeSelect.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,10 @@ export function useRangeSelect(
9494
}
9595

9696
function mouseMove(event: React.MouseEvent<HTMLDivElement>) {
97+
// If we have a rubberband selection active (menu is open), don't update guideX
98+
if (anchorPosition) {
99+
return
100+
}
97101
setGuideX(getRelativeX(event, ref.current))
98102
}
99103

plugins/linear-comparative-view/src/LinearComparativeView/components/useRangeSelect.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,10 @@ export function useRangeSelect(
9898
}
9999

100100
function mouseMove(event: React.MouseEvent<HTMLDivElement>) {
101+
// If we have a rubberband selection active (menu is open), don't update guideX
102+
if (anchorPosition) {
103+
return
104+
}
101105
setGuideX(getRelativeX(event, ref.current))
102106
}
103107

plugins/linear-genome-view/src/LinearGenomeView/components/HeaderRegionWidth.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,10 @@ const HeaderRegionWidth = observer(function HeaderRegionWidth({
1919
model: LinearGenomeViewModel
2020
}) {
2121
const { classes } = useStyles()
22-
const { coarseTotalBpDisplayStr } = model
22+
const { effectiveTotalBpDisplayStr } = model
2323
return (
2424
<Typography variant="body2" color="textSecondary" className={classes.bp}>
25-
{coarseTotalBpDisplayStr}
25+
{effectiveTotalBpDisplayStr}
2626
</Typography>
2727
)
2828
})

plugins/linear-genome-view/src/LinearGenomeView/components/HeaderZoomControls.tsx

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -48,13 +48,16 @@ const HeaderZoomControls = observer(function HeaderZoomControls({
4848
model: LinearGenomeViewModel
4949
}) {
5050
const { classes } = useStyles()
51-
const { width, maxBpPerPx, minBpPerPx, bpPerPx } = model
51+
const { width, maxBpPerPx, minBpPerPx, bpPerPx, effectiveBpPerPx } = model
52+
53+
// local state needed for slider drag: onChange updates this for visual
54+
// feedback, onChangeCommitted syncs to model
5255
const [value, setValue] = useState(-Math.log2(bpPerPx) * 100)
5356
useEffect(() => {
54-
setValue(-Math.log2(bpPerPx) * 100)
55-
}, [bpPerPx])
56-
const zoomInDisabled = bpPerPx <= minBpPerPx + 0.0001
57-
const zoomOutDisabled = bpPerPx >= maxBpPerPx - 0.0001
57+
setValue(-Math.log2(effectiveBpPerPx) * 100)
58+
}, [effectiveBpPerPx])
59+
const zoomInDisabled = effectiveBpPerPx <= minBpPerPx + 0.0001
60+
const zoomOutDisabled = effectiveBpPerPx >= maxBpPerPx - 0.0001
5861
return (
5962
<div className={classes.container}>
6063
<Tooltip title="Zoom out 2x">

plugins/linear-genome-view/src/LinearGenomeView/components/MiniControls.tsx

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,8 @@ const MiniControls = observer(function MiniControls({
2929
model: LinearGenomeViewModel
3030
}) {
3131
const { classes } = useStyles()
32-
const { id, bpPerPx, maxBpPerPx, minBpPerPx, hideHeader } = model
32+
const { id, bpPerPx, maxBpPerPx, minBpPerPx, hideHeader, effectiveBpPerPx } =
33+
model
3334
const { focusedViewId } = getSession(model)
3435
return hideHeader ? (
3536
<Paper className={classes.background}>
@@ -44,7 +45,7 @@ const MiniControls = observer(function MiniControls({
4445
onClick={() => {
4546
model.zoom(bpPerPx * 2)
4647
}}
47-
disabled={bpPerPx >= maxBpPerPx - 0.0001}
48+
disabled={effectiveBpPerPx >= maxBpPerPx - 0.0001}
4849
>
4950
<ZoomOut fontSize="small" />
5051
</IconButton>
@@ -53,7 +54,7 @@ const MiniControls = observer(function MiniControls({
5354
onClick={() => {
5455
model.zoom(bpPerPx / 2)
5556
}}
56-
disabled={bpPerPx <= minBpPerPx + 0.0001}
57+
disabled={effectiveBpPerPx <= minBpPerPx + 0.0001}
5758
>
5859
<ZoomIn fontSize="small" />
5960
</IconButton>

plugins/linear-genome-view/src/LinearGenomeView/components/useRangeSelect.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,11 @@ export function useRangeSelect(
117117
}
118118

119119
function mouseMove(event: React.MouseEvent<HTMLDivElement>) {
120+
// If we have a rubberband selection active (menu is open from a drag, not a click),
121+
// don't update guideX - let the rubberband stay visible
122+
if (anchorPosition?.isClick === false) {
123+
return
124+
}
120125
if (mouseDragging) {
121126
setGuideX(undefined)
122127
} else if (shiftOnly) {

plugins/linear-genome-view/src/LinearGenomeView/model.ts

Lines changed: 41 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -256,6 +256,11 @@ export function stateModelFactory(pluginManager: PluginManager) {
256256
* #volatile
257257
*/
258258
scaleFactor: 1,
259+
/**
260+
* #volatile
261+
* target bpPerPx during zoom animation, used for immediate UI feedback
262+
*/
263+
targetBpPerPx: undefined as number | undefined,
259264
/**
260265
* #volatile
261266
*/
@@ -1089,6 +1094,13 @@ export function stateModelFactory(pluginManager: PluginManager) {
10891094
self.scaleFactor = factor
10901095
},
10911096

1097+
/**
1098+
* #action
1099+
*/
1100+
setTargetBpPerPx(target: number | undefined) {
1101+
self.targetBpPerPx = target
1102+
},
1103+
10921104
/**
10931105
* #action
10941106
* this "clears the view" and makes the view return to the import form
@@ -1152,7 +1164,6 @@ export function stateModelFactory(pluginManager: PluginManager) {
11521164
})
11531165
.actions(self => {
11541166
let cancelLastAnimation = () => {}
1155-
let pendingTargetBpPerPx: number | undefined
11561167

11571168
/**
11581169
* #action
@@ -1166,7 +1177,7 @@ export function stateModelFactory(pluginManager: PluginManager) {
11661177

11671178
// Apply that factor to the pending target (if mid-animation) or current bpPerPx
11681179
// This allows rapid clicks to accumulate
1169-
const effectiveBase = pendingTargetBpPerPx ?? self.bpPerPx
1180+
const effectiveBase = self.targetBpPerPx ?? self.bpPerPx
11701181
let effectiveTarget = effectiveBase * intendedFactor
11711182

11721183
// Clamp to zoom limits
@@ -1175,14 +1186,15 @@ export function stateModelFactory(pluginManager: PluginManager) {
11751186
Math.min(self.maxBpPerPx, effectiveTarget),
11761187
)
11771188

1178-
const currentTarget = pendingTargetBpPerPx ?? self.bpPerPx
1189+
const currentTarget = self.targetBpPerPx ?? self.bpPerPx
11791190

11801191
// If already at limit (or effectively no change), do nothing
11811192
if (effectiveTarget === currentTarget) {
11821193
return
11831194
}
11841195

1185-
pendingTargetBpPerPx = effectiveTarget
1196+
// Set target immediately for UI feedback
1197+
self.setTargetBpPerPx(effectiveTarget)
11861198

11871199
// Calculate target scale factor relative to committed bpPerPx
11881200
// Don't update bpPerPx until animation completes - keeps blocks stable
@@ -1196,7 +1208,7 @@ export function stateModelFactory(pluginManager: PluginManager) {
11961208
() => {
11971209
self.zoomTo(effectiveTarget)
11981210
self.setScaleFactor(1)
1199-
pendingTargetBpPerPx = undefined
1211+
self.setTargetBpPerPx(undefined)
12001212
},
12011213
0,
12021214
1000,
@@ -1325,6 +1337,30 @@ export function stateModelFactory(pluginManager: PluginManager) {
13251337
get coarseTotalBpDisplayStr() {
13261338
return getBpDisplayStr(self.coarseTotalBp)
13271339
},
1340+
1341+
/**
1342+
* #getter
1343+
* effective bpPerPx accounting for pending zoom target
1344+
*/
1345+
get effectiveBpPerPx() {
1346+
return self.targetBpPerPx ?? self.bpPerPx
1347+
},
1348+
1349+
/**
1350+
* #getter
1351+
* total bp based on effective bpPerPx (updates immediately on zoom click)
1352+
*/
1353+
get effectiveTotalBp() {
1354+
return this.effectiveBpPerPx * self.width
1355+
},
1356+
1357+
/**
1358+
* #getter
1359+
* display string for effective total bp (updates immediately on zoom click)
1360+
*/
1361+
get effectiveTotalBpDisplayStr() {
1362+
return getBpDisplayStr(this.effectiveTotalBp)
1363+
},
13281364
}
13291365
})
13301366
.actions(self => ({

0 commit comments

Comments
 (0)