Skip to content
Open
Show file tree
Hide file tree
Changes from 10 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
FROM emscripten/emsdk:3.1.53
FROM emscripten/emsdk:4.0.6

# Avoid warnings by switching to noninteractive
ENV DEBIAN_FRONTEND=noninteractive
Expand Down Expand Up @@ -38,6 +38,7 @@ RUN apt-get update \
&& rm -rf /var/lib/apt/lists/*

RUN curl -fsSL https://deb.nodesource.com/setup_16.x | bash -
RUN apt-get install -y cmake ninja-build pkg-config doxygen graphviz
RUN apt-get install -y nodejs
RUN npm install --global yarn

Expand Down
4 changes: 4 additions & 0 deletions .gitmodules
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,7 @@
[submodule "packages/charls/extern/charls"]
path = packages/charls/extern/charls
url = https://github.com/cornerstonejs/charls.git
[submodule "packages/libjxl/extern/libjxl"]
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Uses the v0.11.x release tag so I don't think we need a custom version tag here.

path = packages/libjxl/extern/libjxl
url = https://github.com/libjxl/libjxl.git
branch = v0.11.x
3 changes: 2 additions & 1 deletion packages/dicom-codec/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,14 @@
"webpack-cli": "^4.5.0",
"webpack-merge": "^5.7.3"
},
"dependencies": {
"peerDependencies": {
"@cornerstonejs/codec-big-endian": ">=0.1.0",
"@cornerstonejs/codec-charls": ">=1.2.3",
"@cornerstonejs/codec-libjpeg-turbo-8bit": ">=1.2.2",
"@cornerstonejs/codec-little-endian": ">=0.0.6",
"@cornerstonejs/codec-openjpeg": ">=1.2.4",
"@cornerstonejs/codec-openjph": "^2.4.7",
"@cornerstonejs/codec-libjxl": ">=0.0.1",
"browser-or-node": "^2.0.0",
"jpeg-lossless-decoder-js": "^2.0.4"
}
Expand Down
4 changes: 2 additions & 2 deletions packages/dicom-codec/src/codecs/codecFactory.js
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,7 @@ async function runProcess(
function getTargetImageInfo(previousImageInfo, imageInfo) {
const { bitsPerSample, componentCount } = imageInfo;
const { height, width, signed } = imageInfo;

return {
...previousImageInfo,
...imageInfo,
Expand Down Expand Up @@ -208,7 +208,7 @@ function encode(context, codecConfig, imageFrame, imageInfo, options = {}) {

const { beforeEncode = () => {} } = options;

beforeEncode(encoderInstance);
beforeEncode(encoderInstance, codecConfig);

context.timer.init("To encode length: " + imageFrame.length);
for (let i = 0; i < iterations; i++) {
Expand Down
5 changes: 5 additions & 0 deletions packages/dicom-codec/src/codecs/htj2k.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,11 @@ const codecWrapper = {
Encoder: undefined,
encoderName: "HTJ2KEncoder",
decoderName: "HTJ2KDecoder",
setQuality: (encoder, {lossless=true, qualityFloat=-1}) => {
console.log("Setting HTJ2K quality to", lossless, qualityFloat);
encoder.setQuality(lossless, qualityFloat);
},

};

/**
Expand Down
11 changes: 9 additions & 2 deletions packages/dicom-codec/src/codecs/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ const rleLosslessCodec = require("./rleLossless");
const bigEndianCodec = require("./bigEndian");
const libjpegTurbo8BitCodec = require("./libjpegTurbo8bit");
const libjpegTurbo12BitCodec = require("./libjpegTurbo12bit");
const libjxl = require("./jpegxl");

/**
* Wrapper to codec. It holds current codec, encoder, decoder, name for each.
Expand Down Expand Up @@ -37,13 +38,18 @@ const codecsMap = {
"1.2.840.10008.1.2.4.81": jpeglsCodec,
"1.2.840.10008.1.2.4.90": jpeg2000Codec,
"1.2.840.10008.1.2.4.91": jpeg2000Codec,
// Private Transfer Syntax - update to final ID when released by WG-06
"3.2.840.10008.1.2.4.96": htj2kCodec,
"1.2.840.10008.1.2.4.110": libjxl,
"1.2.840.10008.1.2.4.111": libjxl,
"1.2.840.10008.1.2.4.112": libjxl,

// The three official HTJ2K transfer syntaxes
"1.2.840.10008.1.2.4.201": htj2kCodec,
"1.2.840.10008.1.2.4.202": htj2kCodec,
"1.2.840.10008.1.2.4.203": htj2kCodec,
"1.2.840.10008.1.2.5": rleLosslessCodec,

// Private Transfer Syntax - update to final ID when released by WG-06
"3.2.840.10008.1.2.4.96": htj2kCodec,
};

function hasCodec(transferSyntaxUID) {
Expand All @@ -53,6 +59,7 @@ function hasCodec(transferSyntaxUID) {
function getCodec(transferSyntaxUID) {
const codec = codecsMap[transferSyntaxUID];
if (!codec) {
console.log("codecsMap=", codecsMap);
throw new Error("unknown transfer syntax UID " + transferSyntaxUID);
}
return codec;
Expand Down
3 changes: 3 additions & 0 deletions packages/dicom-codec/src/codecs/jpegls.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,9 @@ const codecWrapper = {
Encoder: undefined,
encoderName: "JpegLSEncoder",
decoderName: "JpegLSDecoder",
setQuality: (encoder, { lossless = true, delta = 3 }) => {
encoder.setNearLossless(lossless ? 0 : delta);
},
};

/**
Expand Down
71 changes: 71 additions & 0 deletions packages/dicom-codec/src/codecs/jpegxl.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
const codecModule = require("@cornerstonejs/codec-libjxl");
const codecFactory = require("./codecFactory");

/**
* @type {CodecWrapper}
*/
const codecWrapper = {
codec: undefined,
Decoder: undefined,
Encoder: undefined,
encoderName: "JpegXLEncoder",
decoderName: "JpegXLDecoder",
};

/**
* Decode imageFrame using jpegls decoder.
*
* @param {TypedArray} imageFrame to decode.
* @param {ExtendedImageInfo} imageInfo image info options.
* @returns Object containing decoded image frame and imageInfo (current) data.
*/
async function decode(imageFrame, imageInfo) {
return codecFactory.runProcess(
codecWrapper,
codecModule,
// Base module loads it's own codecModule
undefined,
codecWrapper.decoderName,
(context) => {
return codecFactory.decode(context, codecWrapper, imageFrame, imageInfo);
}
);
}

/**
* Encode imageFrame to jpegls format.
*
* @param {TypedArray} imageFrame to encode.
* @param {ExtendedImageInfo} imageInfo image info options.
* @param {Object} options encode option.
* @returns Object containing encoded image frame and imageInfo (current) data
*/
async function encode(imageFrame, imageInfo, options = {}) {
return codecFactory.runProcess(
codecWrapper,
codecModule,
undefined,
codecWrapper.encoderName,
(context) => {
function beforeEncode(encoderInstance) {
encoderInstance.setNearLossless(0);
}

return codecFactory.encode(
context,
codecWrapper,
imageFrame,
imageInfo,
Object.assign({}, options, { beforeEncode })
);
}
);
}

function getPixelData(imageFrame, imageInfo) {
return codecFactory.getPixelData(imageFrame, imageInfo);
}

exports.decode = decode;
exports.encode = encode;
exports.getPixelData = getPixelData;
4 changes: 4 additions & 0 deletions packages/dicom-codec/src/codecs/libjpegTurbo8bit.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,10 @@ const codecWrapper = {
Encoder: undefined,
encoderName: "JPEGEncoder",
decoderName: "JPEGDecoder",
setQuality: (encoder, {qualityPercent=90}) => {
console.log("Setting JPEG quality to", qualityPercent);
encoder.setQuality(qualityPercent);
},
};

/**
Expand Down
32 changes: 32 additions & 0 deletions packages/libjxl/.devcontainer/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
FROM debian:stable

RUN apt update
RUN apt install -y cmake clang doxygen g++ extra-cmake-modules \
libgif-dev libjpeg-dev ninja-build libgoogle-perftools-dev \
graphviz
RUN apt install -y qt6-base-dev libwebp-dev libgimp2.0-dev libopenexr-dev \
libgtest-dev libgmock-dev libbenchmark-dev libbenchmark-tools
RUN apt install -y git

WORKDIR $OPT

# Get the emsdk repo.
RUN git clone https://github.com/emscripten-core/emsdk.git

# Enter that directory.
WORKDIR $OPT/emsdk

# Download and install the latest SDK tools.
RUN ./emsdk install latest

# Make the "latest" SDK "active" for the current user. (writes ~/.emscripten file)
RUN ./emsdk activate latest

# Install node
RUN apt install -y nodejs

RUN echo "NODE_JS='/usr/bin/node'" >> $OPT/emsdk/.emscripten

WORKDIR /workspaces/libjxl

CMD /bin/bash
27 changes: 27 additions & 0 deletions packages/libjxl/.devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
// For format details, see https://aka.ms/vscode-remote/devcontainer.json or this file's README at:
// https://github.com/microsoft/vscode-dev-containers/tree/v0.112.0/containers/cpp
{
"name": "C++",
"dockerFile": "Dockerfile",

// Set *default* container specific settings.json values on container create.
"settings": {
"terminal.integrated.shell.linux": "/bin/bash"
},

// Add the IDs of extensions you want installed when the container is created.
"extensions": [
"ms-vscode.cpptools",
"twxs.cmake",
"flixs.vs-code-http-server-and-html-preview"
]

// Use 'forwardPorts' to make a list of ports inside the container available locally.
// "forwardPorts": [],

// Use 'postCreateCommand' to run commands after the container is created.
// "postCreateCommand": "gcc -v",

// Uncomment to connect as a non-root user. See https://aka.ms/vscode-remote/containers/non-root.
// "remoteUser": "emscripten"
}
109 changes: 109 additions & 0 deletions packages/libjxl/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
build/
build-native/
test/node/*.jxl

.DS_Store

# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
lerna-debug.log*

# Diagnostic reports (https://nodejs.org/api/report.html)
report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json

# Runtime data
pids
*.pid
*.seed
*.pid.lock

# Directory for instrumented libs generated by jscoverage/JSCover
lib-cov

# Coverage directory used by tools like istanbul
coverage
*.lcov

# nyc test coverage
.nyc_output

# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files)
.grunt

# Bower dependency directory (https://bower.io/)
bower_components

# node-waf configuration
.lock-wscript

# Compiled binary addons (https://nodejs.org/api/addons.html)
build/Release

# Dependency directories
node_modules/
jspm_packages/

# TypeScript v1 declaration files
typings/

# TypeScript cache
*.tsbuildinfo

# Optional npm cache directory
.npm

# Optional eslint cache
.eslintcache

# Microbundle cache
.rpt2_cache/
.rts2_cache_cjs/
.rts2_cache_es/
.rts2_cache_umd/

# Optional REPL history
.node_repl_history

# Output of 'npm pack'
*.tgz

# Yarn Integrity file
.yarn-integrity

# dotenv environment variables file
.env
.env.test

# parcel-bundler cache (https://parceljs.org/)
.cache

# Next.js build output
.next

# Nuxt.js build / generate output
.nuxt

# Gatsby files
.cache/
# Comment in the public line in if your project uses Gatsby and *not* Next.js
# https://nextjs.org/blog/next-9-1#public-directory-support
# public

# vuepress build output
.vuepress/dist

# Serverless directories
.serverless/

# FuseBox cache
.fusebox/

# DynamoDB Local files
.dynamodb/

# TernJS port file
.tern-port
3 changes: 3 additions & 0 deletions packages/libjxl/.gitmodules
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
[submodule "extern/libjxl"]
path = extern/libjxl
url = https://github.com/libjxl/libjxl.git
Loading