Skip to content

Commit

Permalink
Release v0.8.2
Browse files Browse the repository at this point in the history
  • Loading branch information
lucalianas committed Jan 21, 2022
2 parents eb7285b + 72ef0d2 commit 1837456
Show file tree
Hide file tree
Showing 4 changed files with 114 additions and 20 deletions.
26 changes: 19 additions & 7 deletions dzi_adapter/tiledb_dzi_adapter.py
Original file line number Diff line number Diff line change
Expand Up @@ -183,21 +183,33 @@ def _apply_palette(self, slice, palette):
raise InvalidColorPalette('%s is not a valid color palette' % palette)
p_colors = copy(p_obj.colors)
p_colors.insert(0, [255, 255, 255]) # TODO: check if actually necessary
norm_slice = np.asarray(np.uint8(slice*len(p_colors))).reshape(-1)
colored_slice = np.full((*slice.shape, 4), [0, 0, 0, 0]).reshape(-1, 4)
norm_slice = np.asarray(np.float16(slice*len(p_colors))).reshape(-1)
# extend the p_colors array to avoid an issue related to probabilities with a value of 1.0
p_colors.append(p_colors[-1])
colored_slice = [p_colors[int(y)] for y in norm_slice]
return np.array(colored_slice).reshape(*slice.shape, 3)
for i, prob in enumerate(norm_slice):
try:
colored_slice[i] = [*p_colors[int(prob)], 255]
except ValueError:
pass
colored_tile = colored_slice.reshape(*slice.shape, 4)
return colored_tile

def _tile_to_img(self, tile, mode='RGB'):
def _tile_to_img(self, tile, mode='RGBA'):
img = Image.fromarray(np.uint8(tile), mode)
return img

def _get_expected_tile_size(self, dzi_tile_size, zoom_scale_factor, dataset_tile_size):
return max(int((dzi_tile_size*zoom_scale_factor)/dataset_tile_size), 1)

def _apply_threshold(self, slice, threshold):
slice[slice<threshold] = np.nan
return slice

def _slice_to_tile(self, slice, tile_size, zoom_scale_factor, dataset_tile_size, palette):
def _slice_to_tile(self, slice, tile_size, zoom_scale_factor, dataset_tile_size, palette, threshold):
expected_tile_size = self._get_expected_tile_size(tile_size, zoom_scale_factor, dataset_tile_size)
if threshold:
slice = self._apply_threshold(slice, float(threshold))
tile = self._apply_palette(slice, palette)
tile = self._tile_to_img(tile)
# self.logger.debug(f'Tile width: {tile.width} --- Tile Height: {tile.height}')
Expand Down Expand Up @@ -235,7 +247,7 @@ def get_dzi_description(self, tile_size=None, attribute_label=None):
return etree.tostring(dzi_root)


def get_tile(self, level, row, column, palette, attribute_label=None, tile_size=None):
def get_tile(self, level, row, column, palette, threshold=None, attribute_label=None, tile_size=None):
self.logger.debug('Loading tile')
tile_size = tile_size if tile_size is not None else settings.DEEPZOOM_TILE_SIZE
self.logger.debug('Setting tile size to %dpx', tile_size)
Expand All @@ -250,4 +262,4 @@ def get_tile(self, level, row, column, palette, attribute_label=None, tile_size=
slice, zoom_scale_factor = self._slice_by_attribute(attribute, int(level), int(row), int(column), tile_size)
return self._slice_to_tile(slice, tile_size, zoom_scale_factor,
self._get_meta_attribute('{0}.tile_size'.format(attribute)),
palette)
palette, threshold)
37 changes: 31 additions & 6 deletions src/js/viewport_controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -319,20 +319,45 @@ function ViewerController(div_id, prefix_url, tile_sources, viewer_config, image

this.initOverlaysLayer = function(overlays, opacity) {
this.default_overlay_opacity = opacity;
this.current_overlay_opacity = this.default_overlay_opacity;
this.overlays = overlays;
};

this.addOverlayToViewer = function(overlay_url, opacity) {
this.viewer.addTiledImage({
tileSource: overlay_url,
opacity: opacity,
index: 1,
replace: true
});
};

this.activateOverlay = function(label) {
if (label in this.overlays) {
console.log("Activating overlay " + label);
this.viewer.addTiledImage({
tileSource: this.overlays[label],
opacity: this.default_overlay_opacity,
index: 1,
replace: true
});
this.addOverlayToViewer(this.overlays[label], this.current_overlay_opacity);
} else {
console.error("There is no overlay registered with label " + label);
}
};

this.setOverlay = function(overlay_base_url, palette, threshold) {
if (overlay_base_url !== undefined && palette !== undefined) {
var th = (threshold === undefined) ? 0 : threshold;
var overlay_url = overlay_base_url + "?palette=" + palette + "&threshold=" + th;
console.log("Setting overlay URL to " + overlay_url);
this.addOverlayToViewer(overlay_url, this.current_overlay_opacity);
} else {
console.error("Missing mandatory parameter");
}
}

this.setOverlayOpacity = function(opacity) {
this.current_overlay_opacity = opacity;
this.viewer.world.getItemAt(1).setOpacity(this.current_overlay_opacity);
}

this.setOverlayDefaultOpacity = function(opacity) {
this.setOverlayOpacity(this.default_overlay_opacity);
}
}
61 changes: 58 additions & 3 deletions templates/ome_seadragon/test/test_overlay_viewer.html
Original file line number Diff line number Diff line change
Expand Up @@ -81,20 +81,75 @@
viewer.setMinDZILevel(8);
});

window.overlay_base_url = "{{ host_name }}/ome_seadragon/arrays/deepzoom/get/{{ dataset_label }}.dzi";
window.overlay_default_palette = 'Greens_9';
window.overlay_default_threshold = '0.6';

viewer.initOverlaysLayer(
{
"greens_9": "{{ host_name }}/ome_seadragon/arrays/deepzoom/get/{{ dataset_label }}.dzi?palette=Greens_9",
"blues_9": "{{ host_name }}/ome_seadragon/arrays/deepzoom/get/{{ dataset_label }}.dzi?palette=Blues_9",
"reds_9": "{{ host_name }}/ome_seadragon/arrays/deepzoom/get/{{ dataset_label }}.dzi?palette=Reds_9"
"greens_9": overlay_base_url + "?palette=Greens_9&threshold=0.6",
"blues_9": overlay_base_url + "?palette=Blues_9&threshold=0.6",
"reds_9": overlay_base_url + "?palette=Reds_9&threshold=0.6"
}, 0.5
);

viewer.activateOverlay("greens_9");
});
});

function changeOverlayOpacity(value) {
window.viewer.setOverlayOpacity(value);
}

function changeOverlayThreshold(value) {
window.viewer.setOverlay(window.overlay_base_url, window.overlay_default_palette, value);
}
</script>
</head>
<body>
<div class="container-fluid" id="overlay_controls" style="padding-top: 10px;">
<div class="col-md-2">
<div class="row">
<label for="overlay_opacity">Overlay opacity</label>
<input type="range" id="overlay_opacity" min="0.0" max="1.0" step="0.01" value="0.5"
oninput="changeOverlayOpacity(this.value)" list="op_tickmarks">
<datalist id="op_tickmarks">
<option value="0" label="0%"></option>
<option value="0.1"></option>
<option value="0.2"></option>
<option value="0.3"></option>
<option value="0.4"></option>
<option value="0.5" label="50%"></option>
<option value="0.6"></option>
<option value="0.7"></option>
<option value="0.8"></option>
<option value="0.9"></option>
<option value="1" label="100%"></option>
</datalist>
</div>
</div>
<div class="col-md-1"></div>
<div class="col-md-2">
<div class="row">
<label for="overlay_threshold">Overlay threshold</label>
<input type="range" id="overlay_threshold" min="0.0" max="1.0" step="0.1" value="0.6"
onchange="changeOverlayThreshold(this.value)" list="th_tickmarks">
<datalist id="th_tickmarks">
<option value="0" label="0%"></option>
<option value="0.1"></option>
<option value="0.2"></option>
<option value="0.3"></option>
<option value="0.4"></option>
<option value="0.5" label="50%"></option>
<option value="0.6"></option>
<option value="0.7"></option>
<option value="0.8"></option>
<option value="0.9"></option>
<option value="1" label="100%"></option>
</datalist>
</div>
</div>
</div>
<div class="container-fluid">
<div class="col-md-12" id="openseadragon_viewer" style="height:1px; padding-top:10px; padding-bottom: 10px;"></div>
</div>
Expand Down
10 changes: 6 additions & 4 deletions views.py
Original file line number Diff line number Diff line change
Expand Up @@ -580,22 +580,23 @@ def get_array_dataset_dzi_by_id(request, dataset_id, conn=None, **kwargs):
return HttpResponseNotFound(f'There is not a valid array dataset with ID {dataset_id}')


def _get_tile_from_dataset(original_file, level, row, column, color_palette):
def _get_tile_from_dataset(original_file, level, row, column, color_palette, threshold):
if original_file and original_file.mimetype == 'dataset-folder/tiledb':
dzi_adapter = DZIAdapterFactory('TILEDB').get_adapter(original_file.name)
return dzi_adapter.get_tile(level, int(row), int(column), color_palette)
return dzi_adapter.get_tile(level, int(row), int(column), color_palette, threshold)
else:
return None


@login_required()
def get_array_dataset_tile_by_label(request, dataset_label, level, row, column, conn=None, **kwargs):
color_palette = request.GET.get('palette')
threshold = request.GET.get('threshold')
if color_palette is None:
return HttpResponseBadRequest('Missing mandatory palette value to complete the request')
try:
original_file = get_original_file(conn, dataset_label)
tile = _get_tile_from_dataset(original_file, level, row, column, color_palette)
tile = _get_tile_from_dataset(original_file, level, row, column, color_palette, threshold)
if tile:
response = HttpResponse(content_type='image/png')
tile.save(response, 'png')
Expand All @@ -613,11 +614,12 @@ def get_array_dataset_tile_by_label(request, dataset_label, level, row, column,
@login_required()
def get_array_dataset_tile_by_id(request, dataset_id, level, row, column, conn=None, **kwargs):
color_palette = request.GET.get('palette')
threshold = request.GET.get('threshold')
if color_palette is None:
return HttpResponseBadRequest('Missing mandatory palette value to complete the request')
try:
original_file = get_original_file_by_id(conn, dataset_id)
tile = _get_tile_from_dataset(original_file, level, row, column, color_palette)
tile = _get_tile_from_dataset(original_file, level, row, column, color_palette, threshold)
if tile:
response = HttpResponse(content_type='image/png')
tile.save(response, 'png')
Expand Down

0 comments on commit 1837456

Please sign in to comment.