Last active
July 6, 2023 08:19
-
-
Save Nanguage/5209a950caf7b8ba3ec7b3b4601ab556 to your computer and use it in GitHub Desktop.
Image viewer ImJoy plugin
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<docs lang="markdown"> | |
The panel for upload the image file. | |
</docs> | |
<config lang="json"> | |
{ | |
"name": "upload-panel", | |
"type": "window", | |
"tags": [], | |
"ui": "", | |
"version": "0.1.0", | |
"cover": "", | |
"description": "[TODO: describe this plugin with one sentence.]", | |
"icon": "extension", | |
"inputs": null, | |
"outputs": null, | |
"api_version": "0.1.8", | |
"env": "", | |
"permissions": [], | |
"requirements": ["https://cdn.tailwindcss.com"], | |
"dependencies": ["https://gist.githubusercontent.com/Nanguage/5209a950caf7b8ba3ec7b3b4601ab556/raw/a64c1f57607c47efc807ef066b88795b9b6c7b57/viewer.imjoy.html"] | |
} | |
</config> | |
<script lang="javascript"> | |
class ImJoyPlugin { | |
async setup() { | |
const viewer_plugin = await api.getPlugin('viewer') | |
const fileInput = document.getElementById("file-input") | |
const fileChosen = document.getElementById('file-chosen'); | |
fileInput.addEventListener("change", async () => { | |
const file = fileInput.files[0] | |
fileChosen.textContent = file.name | |
if (!file) { | |
await api.alert("No file selected") | |
return | |
} | |
const reader = new FileReader() | |
reader.onload = async function() { | |
await api.log("viewer plugin loaded") | |
const content = this.result | |
await viewer_plugin.load_image_from_bytes(file.name, content) | |
} | |
reader.readAsArrayBuffer(file) | |
}) | |
const urlInput = document.getElementById("url-input") | |
const urlLoadButton = document.getElementById("url-load-button") | |
urlLoadButton.addEventListener("click", async () => { | |
const url = urlInput.value | |
if (!url) { | |
await api.alert("No URL provided") | |
return | |
} | |
await viewer_plugin.load_image_from_url(url) | |
}) | |
} | |
async run(ctx) {} | |
} | |
api.export(new ImJoyPlugin()) | |
</script> | |
<window lang="html"> | |
<div class="m-1"> | |
<h1 class="text-3xl font-bold"> | |
Upload then view the image | |
</h1> | |
<p class="mt-4">Load an PNG, JPG or TIFF file:</p> | |
<div class="flex"> | |
<span id="file-chosen" class="w-1/2 px-4 py-2 border border-gray-300 rounded-l-md text-gray-500">No file selected.</span> | |
<label for="file-input" class="py-2 px-3 bg-blue-500 text-white rounded-r-md cursor-pointer w-20 text-center"> | |
Browse | |
</label> | |
<input type="file" id="file-input" class="hidden" /> | |
</div> | |
<p class="mt-4">Or load from an URL. The URL to OME-Zarr are supported:</p> | |
<div class="flex"> | |
<input type="text" class="w-1/2 px-4 py-2 border border-gray-300 rounded-l-md text-gray-500" | |
placeholder="Target URL" | |
id="url-input" /> | |
<button | |
class="px-4 py-2 bg-blue-500 text-white rounded-r-md w-20" | |
id="url-load-button">Load</button> | |
</div> | |
</div> | |
</window> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<config lang="json"> | |
{ | |
"name": "viewer", | |
"type": "web-python", | |
"tags": [], | |
"flags": [], | |
"ui": "", | |
"version": "0.1.0", | |
"cover": "", | |
"description": "View your image", | |
"icon": "extension", | |
"inputs": null, | |
"outputs": null, | |
"api_version": "0.1.8", | |
"env": "", | |
"permissions": [], | |
"requirements": ["imageio"], | |
"dependencies": [] | |
} | |
</config> | |
<script lang="python"> | |
import io | |
from imjoy import api | |
import imageio | |
try: | |
import pyodide | |
is_pyodide = True | |
except ImportError: | |
is_pyodide = False | |
async def fetch_file_content(url) -> bytes: | |
"""Fetch file content from url, return bytes. | |
Compatible with both pyodide and native-python. | |
Reference: | |
https://github.com/imjoy-team/kaibu-utils/blob/ecc25337adb0c94e6345f09bba80aa0637ce9af0/kaibu_utils/__init__.py#L403-L425 | |
""" | |
await api.log("Fetch URL: " + url) | |
if is_pyodide: | |
from js import fetch | |
response = await fetch(url) | |
bytes_ = await response.arrayBuffer() | |
bytes_ = bytes_.to_py() | |
else: | |
import requests | |
bytes_ = requests.get(url) | |
await api.log("Fetched bytes: " + str(len(bytes_))) | |
return bytes_ | |
class Plugin(): | |
async def setup(self): | |
api.log("Viewer plugin is ready.") | |
async def show_image_vtk(self, image): | |
self.viewer = await api.createWindow( | |
src="https://oeway.github.io/itk-vtk-viewer/", | |
fullscreen=False | |
) | |
self.viewer.setImage(image) | |
async def show_image_avivator(self, url: str): | |
self.viewer = await api.createWindow( | |
src=f"https://avivator.gehlenborglab.org/?image_url={url}", | |
fullscreen=False | |
) | |
async def show_image_vizarr(self, url: str): | |
self.viewer = await api.createWindow( | |
src=f"https://oeway.github.io/vizarr/?source={url}", | |
fullscreen=False | |
) | |
async def load_image_from_bytes(self, file_name, img_bytes): | |
_file = io.BytesIO(img_bytes) | |
_file.name = file_name | |
if file_name.endswith(".tif") or file_name.endswith(".tiff"): | |
image = imageio.volread(_file) | |
else: | |
image = imageio.imread(_file) | |
await api.log( | |
"Image loaded with shape: " + str(image.shape) + | |
" and dtype: " + str(image.dtype) | |
) | |
await self.show_image_vtk(image) | |
async def load_image_from_url(self, url, zarr_viewer='vizarr'): | |
file_name = url.split("?")[0].rstrip('/').split("/")[-1] | |
await api.log(file_name) | |
if file_name.endswith(".zarr"): | |
if zarr_viewer == 'vizarr': | |
await self.show_image_vizarr(url) | |
else: | |
await self.show_image_avivator(url) | |
else: | |
bytes_ = await fetch_file_content(url) | |
await api.log(file_name) | |
await self.load_image_from_bytes(file_name, bytes_) | |
api.export(Plugin()) | |
</script> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment