google / neuroglancer

WebGL-based viewer for volumetric data
Apache License 2.0
1.09k stars 299 forks source link

How to view a SWC file on Neuroglancer? #207

Open manoaman opened 4 years ago

manoaman commented 4 years ago

Hi,

I am trying to view a SWC file but cannot seem to figure out how to configure or required steps to view it. I am getting unsupported data source error. Could you please help me to a good example to look at? I am also sharing a sample SWC file. Thanks.

https://drive.google.com/file/d/1zOWpYvHtxArdXTO8Q3FGZ8DugmdCu8d5/view?usp=sharing

Screen Shot 2020-03-10 at 5 31 10 PM

{ "dimensions": { "x": [ 0.01309425, "m" ], "y": [ 0.02506075, "m" ], "z": [ 0.000219, "m" ] }, "crossSectionScale": 0.04566210045662101, "projectionOrientation": [ -0.18240146338939667, -0.22431287169456482, 0.6762499809265137, 0.6775687336921692 ], "projectionScale": 93.51598173515983, "layers": [ { "type": "image", "source": { "url": "swc://http://localhost:9000/test.swc", "subsources": { "default": true, "bounds": true }, "enableDefaultSubsources": false }, "tab": "source", "opacity": 1, "blend": "default", "shader": "#uicontrol vec3 color color(default=\"white\")\n#uicontrol float min slider(default=0, min=0, max=1, step=0.01)\n#uicontrol float max slider(default=1, min=0, max=1, step=0.01)\n#uicontrol float brightness slider(default=0, min=-1, max=1, step=0.1)\n#uicontrol float contrast slider(default=0, min=-3, max=3, step=0.1)\n\nfloat scale(float x) {\n return (x - min) / (max - min);\n}\n\nvoid main() {\n emitRGB(\n color vec3(\n scale(\n toNormalized(getDataValue()))\n + brightness) exp(contrast)\n );\n}", "shaderControls": { "color": "#fff7f6", "min": 0.52, "max": 0.68, "brightness": 0.4, "contrast": 0.2 }, "name": "swc" } ], "selectedLayer": { "layer": "Nissl", "visible": true, "size": 612 }, "layout": "4panel", "statistics": { "visible": true } }

jbms commented 4 years ago

Unfortunately Neuroglancer does not yet support viewing SWC files directly (only via the DVID data source), but if you are interested it would be relatively easy to add such support.

manoaman commented 4 years ago

Yes, I would be interested in testing out. I did see some interactions here https://github.com/google/neuroglancer/issues/169 but I wasn't clear what changes were made. Would you be able to point me out the change?

Is is basically changing url to point locally served swc file?

https://github.com/google/neuroglancer/blob/master/src/neuroglancer/datasource/dvid/backend.ts

@registerSharedObject() export class DVIDSkeletonSource extends
(WithParameters(SkeletonSource, SkeletonSourceParameters)) {
  download(chunk: SkeletonChunk, cancellationToken: CancellationToken) {
    const {parameters} = this;
    let bodyid = `${chunk.objectId}`;
    const url = `${parameters.baseUrl}/api/node/${parameters['nodeKey']}` +
        `/${parameters['dataInstanceKey']}/key/` + bodyid + '_swc';
    return cancellableFetchOk(url, {}, responseArrayBuffer, cancellationToken)
        .then(response => {
          let enc = new TextDecoder('utf-8');
          decodeSwcSkeletonChunk(chunk, enc.decode(response));
        });
  }
}
jbms commented 4 years ago

To create an SWC source, you would want to copy an existing data source directory to e.g. datasource/swc, then copy in the DVID skeleton source and modify it.

Neuroglancer expects skeletons to be associated with numeric segment ids, so you would need to decide on a naming scheme, e.g. .swc

manoaman commented 4 years ago

I attempted to create SWC source and I'm still not seeing this SWC provider registered in default_provider.ts. (registerProvider) Where could I still be missing to register?

jbms commented 4 years ago

You have to also add the datasource to config/webpack_helpers.js to have it included in the build.

manoaman commented 4 years ago

I thought I added to const DEFAULT_DATA_SOURCES = exports.DEFAULT_DATA_SOURCES but still seems not as a provider. Could there be other places I'm missing out?

  {
    source: 'neuroglancer/datasource/swc',
    asyncComputation: [
      'neuroglancer/async_computation/decode_jpeg',
    ],
  },
jbms commented 4 years ago

If you can point me to your repository (or make a pull request if you want to contribute it here) I can take a look.

manoaman commented 4 years ago

Yes, I'll make a pull request. Thanks! https://github.com/google/neuroglancer/pull/212

manoaman commented 4 years ago

Just pushed the code but I'm still struggling with this error that I'm facing. Any feedbacks would be appreciated for further fixes. Thanks!

Screen Shot 2020-04-08 at 2 05 27 PM

jbms commented 4 years ago

Change the layer type to "segmentation" rather than "image" (use the drop down at the top left of the layer side panel).

manoaman commented 4 years ago

Seems to be still failing to load. Could I be missing anything?

Screen Shot 2020-04-09 at 5 24 07 PM

jbms commented 4 years ago

In Neuroglancer, a skeleton data source does not provide just a single skeleton but rather a map of uint64 -> skeleton.

You can select the set of uint64 ids that are displayed using the "Seg" tab in the side panel. You can type in a number, e.g. 42, in the input box and press enter.

With how your code is currently, this will cause it to attempt to load:

"${parameters.baseUrl}/swc/42"

If that is not correct, you can adjust the code.

manoaman commented 4 years ago

Hi again,

swc files seem to load up in spheres so at least I got these files loaded ok. I tried emitDefault() for the shader part. Not sure if I'm on a right track with shader code for skeleton. Where should I be tweaking?

Screen Shot 2020-04-10 at 1 54 54 PM Screen Shot 2020-04-10 at 2 07 13 PM

jbms commented 4 years ago

For skeletons you don't necessarily need to modify the shader at all. If you have additional vertex attributes, you can compute the color based on them, but the swc format does not support them.

If your skeletons are displaying as a single point, it might be because you are so far zoomed out. You can try zooming in or fixing the scaling in your datasource implementation.

manoaman commented 4 years ago

I thought I am far zoomed and tried setting lower upper scale to (200um,200um,200um) or (2um,2um,2um) or (1nm,1nm,1nm). And I'm still getting the same one filled circle. I also tried tweaking skeleton line widths. Am I not scaling correctly in the datasource tab?

Screen Shot 2020-04-10 at 5 16 12 PM

jbms commented 4 years ago

If you push your updated code and send me one of your swc files, I can take a look.

manoaman commented 4 years ago

Hi, latest updates are here. https://github.com/google/neuroglancer/pull/212/commits/1e32661101c4997b3d5602eb8e04a9aeb80dc485

jbms commented 4 years ago

Can you also send me or point me to an SWC file you are trying it with?

manoaman commented 4 years ago

Here is a shared link of SWC files. https://drive.google.com/drive/folders/1hPY8O_xOJw0UYCvohEK49mM0pyhLE5Sd?usp=sharing

I am also trying to see if I could use a generic file name stored in an arbitrary nested folders. e.g.) /swc/reconstructed/ch0/reconstructed_ch0.swc . Could this be done from tweaking this url?

    let bodyid = `${chunk.objectId}`;
    const url = `${parameters.baseUrl}/api/node/${parameters['nodeKey']}` +
        `/${parameters['dataInstanceKey']}/key/` + bodyid + '_swc';

Maybe this is an off topic. Because .swc files are usually not stored in a standard numeric names (object id) and they could be stored in nested folders, should the files be organized to match the url format defined in Neuroglancer?

jbms commented 4 years ago

Once I fixed the issue of the scales vector being all zero as I commented in the pull request, I am able to view skeletons successfully.

As far as the URL format --- I also added a comment to the pull request regarding supporting arbitrary patterns rather than requiring a particular directory structure.

manoaman commented 4 years ago

Hi, I think I managed to load swc files. Thank you for the feedbacks.

And I think I need to better understand the use case of segmentation ids and source tabs. I didn't realize I could load up multiple segmentations (swc files) in a single tab as opposed to loading up a single segmentation (swc) per tab.

It seems that I can group segmentations (swc files) in a tab from one source, and another group of segmentations (swc files) to another tab, and so on.

Tab1: http://localhost/swc/path/*.swc Tab2: http://localhost/swc/another/path/*.swc Tab3: http://localhost/swc/another/nested/path/*.swc

What is an expected use case of using more tabs over loading all the segmentation in a single tab? Also, what is "Enable default subsource set" used for?

Screen Shot 2020-04-17 at 8 07 08 PM

Screen Shot 2020-04-17 at 8 11 33 PM

jbms commented 4 years ago

You can use whatever method is most convenient. If you have a large number of skeletons that are related in some way, it is probably more convenient to have them all part of the same "layer" (what you are calling a "tab"), because neuroglancer could display thousands of skeletons at once but isn't really set up to have thousands of layers. If you have several sets of skeletons from different sources (e.g. auto-generated vs manually created) or something like that, you may want to have them in separate layers.

manoaman commented 4 years ago

Hi jbms,

I recently found out that CloudVolume can decode a SWC file and convert it to precomputed format. The data seems to load on Neuroglancer but the skeleton does not seem to show up. Could I be missing something? Tested files are https://drive.google.com/drive/folders/1kzuH9mNl2r22K70A_1xDJkzfMO32s1X2?usp=sharing

Thank you, -m

jbms commented 4 years ago

It works for me. If using a webserver that doesn't automatically handle the .gz extension, you will need to gunzip the skeleton file first. Also you will need to rotate around in the 3d view to see the skeletons.

See link below (you will need to change the datasource url to point to your webserver):

https://neuroglancer-demo.appspot.com/#!%7B%22dimensions%22:%7B%22x%22:%5B1e-9%2C%22m%22%5D%2C%22y%22:%5B1e-9%2C%22m%22%5D%2C%22z%22:%5B1e-9%2C%22m%22%5D%7D%2C%22position%22:%5B849.36279296875%2C1019.5581665039062%2C75.639892578125%5D%2C%22crossSectionScale%22:1%2C%22projectionOrientation%22:%5B0.09868691116571426%2C0.3405956029891968%2C0.6517659425735474%2C0.6704152822494507%5D%2C%22projectionScale%22:1024%2C%22layers%22:%5B%7B%22type%22:%22segmentation%22%2C%22source%22:%22precomputed://http://localhost:8081%22%2C%22tab%22:%22source%22%2C%22segments%22:%5B%2212345%22%5D%2C%22segmentQuery%22:%2212345%22%2C%22name%22:%22skeletons%22%7D%5D%2C%22showSlices%22:false%2C%22selectedLayer%22:%7B%22layer%22:%22skeletons%22%2C%22visible%22:true%7D%2C%22layout%22:%224panel%22%2C%22partialViewport%22:%5B0%2C0%2C1%2C1%5D%7D

manoaman commented 4 years ago

Thank you jbms! It seems that gunzip the file was the solution to visualize skeletons. I would have to check if nginx allows to serve .gz extension.

manoaman commented 4 years ago

In fact, .gz worked fine too. I think I simple had to type in the identifier I assigned. I wonder if there is a way to pull up a list of segmentation ids without knowing them. Do you currently support such a feature @jbms ? I did realize there is regex support for grouping segmentations.

jbms commented 4 years ago

There isn't a way to see a list of all the segment IDs unless you provide labels via segment_properties: https://github.com/google/neuroglancer/blob/master/src/neuroglancer/datasource/precomputed/segment_properties.md