8000 Grid mode using vispy ViewBox and linked cameras by brisvag · Pull Request #7870 · napari/napari · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

Grid mode using vispy ViewBox and linked cameras #7870

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 178 commits into
base: main
Choose a base branch
from

Conversation

brisvag
Copy link
Contributor
@brisvag brisvag commented Apr 29, 2025

References and relevant issues

Description

This PR replaces the current transform-based grid mode with a viewbox-based one using linked cameras.

Additionally, viewer canvas overlays (such as scale_bar) now have a gridded property which, when set to True, will make it so the overlay appears in every grid box instead that on the general canvas.

import napari
v = napari.Viewer(ndisplay=3)
l0, l1 = v.open_sample('napari', 'cells3d')
l1.bounding_box.visible = True
v.scale_bar.visible = True
v.axes.visible = True
v.grid.enabled = True

v.scale_bar.gridded = True

image

@brisvag brisvag requested review from melonora and a team as code owners April 29, 2025 14:35
@github-actions github-actions bot added the tests Something related to our tests label Apr 29, 2025
@brisvag brisvag marked this pull request as draft April 29, 2025 14:35
@github-actions github-actions bot added the qt Relates to qt label May 6, 2025
@brisvag brisvag force-pushed the feature/canvas-model branch from 443e246 to da63dc6 Compare May 6, 2025 12:58
@brisvag brisvag marked this pull request as ready for review May 6, 2025 13:56
@brisvag
Copy link
Contributor Author
brisvag commented May 6, 2025

Todo from pairing with @melonora:

  • fix camera getting stuck (and infinite event loops)
  • fix canvas overlays not being shown

@brisvag
Copy link
Contributor Author
brisvag commented Jun 22, 2025

The constrains are ok actually. It seems that maybe the problem is with vispy wheels missing for python 3.13?

Actually: the constraint for vispy in 3.12_docs is wrong, and stuck at 0.15.0, despite updating constraints. @Czaki do you know what's going on?

just kidding, the updated constraints were good, I'm just dumb :P

add test to ensure cameras are updated correctly on grid switch
@TimMonko
Copy link
Contributor

Great great work! Again, wish I had more time than a drive by. Earlier problem is fixed. Mostly everything is smoothed.

Reordering layers results in miscalculation of overlay position (until something like a mouse scroll event, which fixes it):
image

It also appears that removing layers such that there is an odd number left, but not even, also has the miscalculation. Adding layers (odd or even) does not result in the issue. I'm sure that's clue to where the layer updates aren't being called correctly, can look later tonight.

Tests are so close now!

Comment on lines 954 to 969
for napari_layer, vispy_layer in self.layer_to_visual.items():
row, col = self.viewer.grid.position(
# FIXME: the use of `len(self.viewer.layers) - 1 - idx` should be removed
# see https://github.com/napari/napari/pull/7870#issuecomment-2965031040
len(self.viewer.layers)
- 1
- self.viewer.layers.index(napari_layer),
len(self.viewer.layers),
)
view = self.grid[row, col]
# any border_color != None will add a padding of +1
# see https://github.com/vispy/vispy/issues/1492
view.border_width = 0
view.border_color = None

camera = VispyCamera(view, self.viewer.camera, self.viewer.dims)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this creating a new camera for each layer? wouldn't that mean with something like stride =2 that there are 2 cameras in the same grid? I dunno if that's the problem with the comment I had about overlay positioning or not

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, true, nice catch! I updated it to loop over viewboxes instead, I'm sure multiple cameras probably cause some of the weird issues we encountered so far 😓

@psobolewskiPhD
Copy link
Member
psobolewskiPhD commented Jun 22, 2025

I'm finding something odd with additive blending and stride, specifically negative stride.
It only happens with an odd number of layers.
Stride -2:
image
Note all layers are additive blending, but you cannot see the blue nuclei layer. If you change WGA opacity it fades to black.
Here's is stride +2:
image

Actually, it also happens with even number of layers if the negative stride is odd, e.g. with lilly:
image
Note the lack of the red layer when i fade the W and G:
image

Otherwise things appear to be working other than the issues noted above by Tim which can be triggered by changing stride.

@brisvag
Copy link
Contributor Author
brisvag commented Jun 22, 2025

@TimMonko both your issues should be fixed!

@psobolewskiPhD I think I had missed 1 spot where the inverted order of the grid causes issues. Can you check again?

@brisvag
Copy link
Contributor Author
brisvag commented Jun 22, 2025

@TimMonko my last commit should hopefuly fix the remaining test and might also fix #8033!

@psobolewskiPhD
Copy link
Member

@brisvag indeed, you also fixed a severe issue with multiscale layers, which are now properly rendered. 🎉

@TimMonko
Copy link
Contributor
TimMonko commented Jun 23, 2025

@TimMonko my last commit should hopefuly fix the remaining test and might also fix #8033!

Unfortunately does not solve #8033. What test were you trying to solve? I don't see any in the recent commits that are screenshot related, just multiscale. The screenshot test in d41bf35 (#7870) looks fixed in 0590cb6 (#7870)

@TimMonko
Copy link
Contributor

Ok, I've figured out the multiscale test fails. The _data_level is correctly 0 at the zoom which the data gets zoomed to in the viewer for the tests, resulting in the test failing. Therefore, the test previously incorrectly had the wrong data level --and this behavior was likely fixed by this PR. But if I force the data level to 1, then the corner pixels still seem the 0 level. I'll let someone more knowledgeable figure this out.
So, I think the tests need changing, but I'm not sure how to correctly do that because I have little experience with multi scale data. It's definitely related the corner pixel stuff you mentioned earlier.

I'm approving :) I tried really hard to break this, and couldn't.

@brisvag
Copy link
Contributor Author
brisvag commented Jun 23, 2025

The screenshot test in d41bf35 (#7870) looks fixed in 0590cb6 (#7870)

Uhm, I thought I solved it in 1372ed9, which is why I thought it might also solve your problem, by updating the canvas before screenshotting. But I might have misunderstood the test, I thought the divide by zero was failing due to the image being denegerate. Maybe we should revert that commit then?

Yeah those multiscale are the same as mentioned in these comments, I should mark xfail!

EDIT: actually, these might be more fixable than the above. Unfortunately, I'm not gonna be able to come back to this for a couple of days, sorry for the bad timing 😅 I'll let you decide what to do!

@TimMonko
Copy link
Contributor
TimMonko commented Jun 23, 2025

The plot thickens. Apparently the screenshot on_draw is needed for ubuntu 3.10. https://github.com/napari/napari/actions/runs/15829545543/job/44618484006?pr=7870#logs Interestingly, again, this doesn't fix it for Windows. Seems like tracking down the solution for #8033 is going to be a pain.

Edit: and it thickens more. it still fails with 954db3c (#7870) for ...

  1. ubuntu-latest py 3.10 pyside2
  2. windows-latest py 3.11 pyqt5
  3. maco-13 py 3.13 pyqt5
  4. macos-latest py 3.13 pyqt5

Maybe it's flaky? I'll try rerunning. Locally it passes for me.

Edit2: Yes it's flaky, so it's not this PR, per-se. It is in the sense we change the draw mechanism, but not a blocker to the PR. I'll still put in a resolution or x-fail here.

@TimMonko
Copy link
Contributor

Ok, so here's my final decision. This test is actually still an issue on main (localy), and is the same issue as #8033.

Without fully processing (like in the tests), we get just the canvas (hence the divide by zero, because the data doesn't ever show up). Hopefully this just means we are slightly slower in displaying the image, but it must be ever so slight, since this is the only test issue. And I mean the change in event processing must be so slight since itss flaky, so I'm not worried about performance. But I do think trying to fix #8033 is high because now it also probably effects others OSes. For that reason, I'm going to add the processing into this test only. I'm guessing this is probably the root of so much of our screenshot test flakiness....
image

Once the whole loop is processed is loaded, the figures/screenshots look good (as expected)
image

Comment on lines -323 to -324
center = tuple(np.round(np.divide(screenshot.shape[:2], 2)).astype(int))
np.testing.assert_almost_equal(screenshot[center], [0, 255, 255, 255])
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

maybe here and above, comment out the code and add a note, as you did with other tests above, so that we know to revive the test as soon as we can?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will do, good catch! Didn't realize Lorenzo commented these out too ... another lead on how this issue is happening. 😬

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

or, why does it need commented out? the test passes?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok actually I'm just confused on what I'm looking at. Is this the most recent commit? It's not what I see locally and I think it's the most recent commit. But this does look like a diff that has this code removed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
highlight PR that should be mentioned in next release notes preferences qt Relates to qt tests Something related to our tests UI/UX
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Grid is not correctly calculated when dim order is not default (in 3D only?) multicanvas grid display for layers in Napari
7 participants
0