Skip to content
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

Visualize Hi-C files using Juicebox without relying on an iframe #2106

Draft
wants to merge 38 commits into
base: develop
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
56afecb
feat: able to render 3d models locally
luistoptal Nov 10, 2024
b65a3ab
feat: use jquery
luistoptal Nov 10, 2024
5d3bdd1
feat: scaffold model viewer refactor
luistoptal Nov 11, 2024
d16a28b
feat: able to visualize rendered models
luistoptal Nov 12, 2024
e572f03
feat: model looks similar to sketchfab
luistoptal Nov 12, 2024
7ced357
feat: adds multitud of small refactorings
luistoptal Nov 12, 2024
97bf32f
feat: load ply, obj and las models
luistoptal Nov 13, 2024
d76ca05
feat: responsive canvas and refactored ui code
luistoptal Nov 13, 2024
31d6c99
feat: improves help controls
luistoptal Nov 13, 2024
4c15ea4
feat: adds fullscreen btn
luistoptal Nov 13, 2024
ba975be
feat: refactors root ui script, colocates selectors, adds js docs
luistoptal Nov 13, 2024
33e4a05
feat: integrates model viewer into dataset page
luistoptal Nov 14, 2024
e83abd2
feat: improves a11y for model loading state
luistoptal Nov 14, 2024
5053b67
chore: remove debug logs
luistoptal Nov 14, 2024
f051629
chore: up log
luistoptal Nov 14, 2024
e858b73
chore: undoes ignored temp models folder
luistoptal Nov 14, 2024
e064ace
feat: adds jsdocs
luistoptal Nov 14, 2024
bd824ca
chore: Merge branch 'develop' into new-feature/2054-3d-image-viewer
luistoptal Nov 14, 2024
d3c9334
chore: update 3d models tab test
luistoptal Nov 20, 2024
6a8e1e7
feat: tests for model selector
luistoptal Nov 20, 2024
336b89a
fix: undoes bug introduced by trim func
luistoptal Nov 20, 2024
5bd9b1c
chore: add https://cdn.jsdelivr.net to nginx config
luistoptal Nov 20, 2024
bf0e900
feat: add 3d models to test db and tests
luistoptal Nov 21, 2024
d0e4167
chore: adds model source to nginx
luistoptal Nov 21, 2024
226be5f
chore: Merge branch 'develop' into new-feature/2054-3d-image-viewer
luistoptal Nov 21, 2024
3eb5306
chore: cleanup tests
luistoptal Nov 22, 2024
8eb66e9
feat: scaffold hic viewer
luistoptal Nov 22, 2024
b004b38
fix: displays 3d models only in 3d models tab panel
luistoptal Nov 22, 2024
2ce1f06
chore: Merge branch 'new-feature/2054-3d-image-viewer' into new-featu…
luistoptal Nov 22, 2024
60ae2f7
fix: render model viewer only once
luistoptal Nov 22, 2024
15ffbca
chore: Merge branch 'new-feature/2054-3d-image-viewer' into new-featu…
luistoptal Nov 22, 2024
0fcc304
feat: displays hic viewer only once
luistoptal Nov 22, 2024
8cc0311
feat: able to visualize hic files
luistoptal Nov 22, 2024
0874d46
feat: adds hic view wrapper to prevent overflow
luistoptal Nov 23, 2024
959c0d9
feat: refactor js code and fix layout issues
luistoptal Nov 23, 2024
ab0275a
chore: sets up testing remote hic files
luistoptal Nov 23, 2024
32ef63b
chore: up log
luistoptal Nov 23, 2024
01648a5
chore: adds juicebox test
luistoptal Nov 23, 2024
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
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -112,4 +112,4 @@ php-conf/appconfig.ini
params-local.php

# release related artefacts
VERSION
VERSION
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).

## Unreleased

- Feat #329: Visualize Hi-C files using Juicebox without relying on an iframe
- Feat #2054: Visualize 3D models locally without relying on sketchfab iframe
- Fix #2094: Make Semgrep-based SAST analyzer available in tagged release
- Feat #701: Code refactoring to separate upload status transitions and notifications to prepare for upload status overhaul
- Security #1867: Update the gitlab static application security testing (SAST) job using the Semgrep-based analyzer
Expand Down
6 changes: 6 additions & 0 deletions data/dev/external_link.csv
Original file line number Diff line number Diff line change
Expand Up @@ -9,3 +9,9 @@ id,dataset_id,url,external_link_type_id
36,144,https://github.com/ShashaankV/GD,1
1525,2342,https://scicrunch.org/resolver/RRID:SCR_021313,1
1526,2342,https://github.com/cihga39871/Atria,7
1527,8,https://s3.ap-northeast-1.wasabisys.com/gigadb-datasets/dev/tests/3d-models/100006/leaf_01.las,5
1528,8,https://s3.ap-northeast-1.wasabisys.com/gigadb-datasets/dev/tests/3d-models/100006/beet_03.stl,5
1529,8,https://s3.ap-northeast-1.wasabisys.com/gigadb-datasets/dev/tests/3d-models/100006/GeoB8502_865cm_Shell-4.obj,5
1230,22,https://www.encodeproject.org/files/ENCFF718AWL/@@download/ENCFF718AWL.hic,9
1231,22,https://www.encodeproject.org/files/ENCFF406HHC/@@download/ENCFF406HHC.hic,9
1532,22,https://s3.ap-northeast-1.wasabisys.com/gigadb-datasets/dev/tests/3d-models/100006/GeoB8502_865cm_Shell-4.obj,5
3 changes: 2 additions & 1 deletion data/dev/external_link_type.csv
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,5 @@ id,name
5,3D Models
6,Code Ocean
7,Github links
8,USCS Tumour Map Viewer
8,USCS Tumour Map Viewer
9,Juicebox
5 changes: 1 addition & 4 deletions features/bootstrap/DatasetViewContext.php
Original file line number Diff line number Diff line change
Expand Up @@ -413,10 +413,7 @@ public function iShouldNotSeeTabWithTable($arg1, TableNode $table)
*/
public function iHaveAddedLinkToDataset($arg1, $arg2, $arg3)
{
if ("3D Viewer" == $arg1 ) {
$this->gigadbWebsiteContext->loadUserData("3D_Viewer_${arg3}_test_data");
}
elseif ("Code Ocean" == $arg1 ) {
if ("Code Ocean" == $arg1 ) {
$this->gigadbWebsiteContext->loadUserData("Code_Ocean_${arg3}_test_data");
}
else {
Expand Down
7 changes: 0 additions & 7 deletions features/dataset-view.feature
Original file line number Diff line number Diff line change
Expand Up @@ -152,13 +152,6 @@ Feature: a user visit the dataset page
| Funding body | Awardee | Award ID | Comments |
| National Science Foundation | Matthew W. Hahn | DEB-1249633 | Matthew W Hahn |

@ok
Scenario: 3D Viewer
Given I am not logged in to Gigadb web site
And I have added "3D Viewer" link "https://sketchfab.com/models/ea49d0dd500647cbb4b61ad5ca9e659a" to dataset "101001"
When I go to "/dataset/101001"
Then I should see "3D Models" tab with text "3D Models:"

@ok
Scenario: Protocols.io
Given I am not logged in to Gigadb web site
Expand Down
5 changes: 4 additions & 1 deletion less/index.less
Original file line number Diff line number Diff line change
Expand Up @@ -64,4 +64,7 @@
@import "modules/team-grid.less";
@import "modules/map.less";
@import "modules/lists.less";
@import "modules/tooltip.less";
@import "modules/tooltip.less";
@import "modules/model-viewer.less";
@import "modules/hic-viewer.less";

10 changes: 10 additions & 0 deletions less/modules/datatables.less
Original file line number Diff line number Diff line change
Expand Up @@ -28,3 +28,13 @@ table.dataTable thead {
.tab-content {
overflow: hidden;
}

.dataset-tab-content {
overflow: visible;
[role="tabpanel"] {
overflow: hidden;
&.visible {
overflow: visible;
}
}
}
4 changes: 4 additions & 0 deletions less/modules/hic-viewer.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
.hic-viewer-root {
max-height: 970px;
margin-bottom: 20px;
}
304 changes: 304 additions & 0 deletions less/modules/model-viewer.less
Original file line number Diff line number Diff line change
@@ -0,0 +1,304 @@
// stack order
@stack-order-controls-info: 1;
@stack-order-play-button: 2;
@stack-order-loading-overlay: 3;
@stack-order-error-display: 4;
@stack-order-help-modal: 5;
@stack-order-fullscreen: 9999;
@stack-order-fullscreen-controls: 10000;
@stack-order-fullscreen-help-modal: 10001;


.model-selector {
width: 450px;
margin-bottom: 20px;
}

.model-viewer-container {
position: relative;
width: 912px;
height: 512px;
background: transparent;
}

@media (max-width: 912px) {
.model-viewer-container {
width: 100%;
height: auto;
aspect-ratio: 1.78;
}
}

.canvas-container {
width: 100%;
height: 100%;
background-color: @color-light-gray;
display: block;
}

// controls info

.controls {
position: absolute;
background: transparent;
color: @color-true-white;
bottom: 0;
right: 0;
padding: 12px;
z-index: @stack-order-controls-info;
display: flex;
gap: 6px;
}

.controls .controls-btn {
text-decoration: none;
color: @color-warm-black;
background: transparent;
font-size: 18px;
opacity: 0.8;
transition: opacity 0.2s ease, background 0.2s ease;
border-radius: 50%;
width: 36px;
height: 36px;
display: flex;
align-items: center;
justify-content: center;

&:hover {
opacity: 1;
color: @color-true-white;
text-decoration: none;
background: rgba(0, 0, 0, 0.5);
}
}

// help modal

.help-modal {
position: absolute;
inset: 0;
z-index: @stack-order-help-modal;
background: rgba(0, 0, 0, 0.7);
display: flex;
justify-content: center;
align-items: center;
color: @color-true-white;

.help-modal-content {
background: rgba(0, 0, 0, 0.9);
border-radius: 8px;
padding: 24px;
min-width: 300px;
max-width: 90%;
}

.help-modal-header {
display: flex;
justify-content: space-between;
align-items: center;
margin-bottom: 20px;

.help-modal-title {
margin: 0;
font-size: 18px;
font-weight: bold;
}

.help-modal-close {
background: transparent;
border: none;
color: @color-true-white;
font-size: 20px;
padding: 4px;
cursor: pointer;
opacity: 0.8;

&:hover {
opacity: 1;
}
}
}

.help-modal-body {
h3 {
font-size: 14px;
margin: 0 0 16px 0;
opacity: 0.8;
}

.help-control {
display: flex;
align-items: center;
gap: 16px;
margin-bottom: 16px;

i {
font-size: 24px;
width: 24px;
text-align: center;
}

.help-control-text {
div:first-child {
font-weight: bold;
margin-bottom: 4px;
}

.help-control-detail {
font-size: 14px;
opacity: 0.8;
}
}
}
}
}

.model-viewer-container.fullscreen {
.canvas-container {
width: 100vw;
height: 100vh;
position: fixed;
top: 0;
left: 0;
z-index: @stack-order-fullscreen;
}

.controls {
position: fixed;
bottom: 0;
right: 0;
z-index: @stack-order-fullscreen-controls;
}

.help-modal {
width: 100vw;
height: 100vh;
position: fixed;
top: 0;
left: 0;
z-index: @stack-order-fullscreen-help-modal;
}
}

// play button

.play-button-overlay {
position: absolute;
inset: 0;
display: flex;
justify-content: center;
align-items: center;
z-index: @stack-order-play-button;
background: rgba(0, 0, 0, 0.3);
}

.play-button {
width: 150px;
height: 150px;
background: rgba(0, 0, 0, 0.5);
color: @color-true-white;
border: none;
border-radius: 50%;
padding: 20px;
display: flex;
justify-content: center;
align-items: center;
transition: transform 0.2s ease-in-out, background 0.3s ease-in-out;
}

.play-button:hover {
transform: scale(1.1);
background: @color-gigadb-green;
box-shadow: 0 0 40px rgba(255, 255, 255, 0.5),
0 0 20px fade(@color-gigadb-green, 60%);
}

.play-button:focus {
outline: none;
box-shadow: 0 0 0 4px @color-true-white,
0 0 0 8px @color-gigadb-green,
0 0 0 12px fade(@color-gigadb-green, 30%);
}

.play-button-icon {
font-size: 70px;
position: relative;
/* make button look visually centered */
left: 6px;
}

@media (max-width: 768px) {
.play-button {
width: 120px;
height: 120px;
padding: 16px;

.play-button-icon {
font-size: 50px;
}
}
}

// loading overlay

.loading-overlay {
position: absolute;
inset: 0;
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
z-index: @stack-order-loading-overlay;
background: rgba(0, 0, 0, 0.1);
backdrop-filter: blur(5px);
}

.loading-overlay.active {
display: flex;
}

.loading-spinner {
width: 40px;
height: 40px;
border: 4px solid transparent;
border-top: 4px solid @color-gigadb-green;
border-radius: 50%;
animation: spin 0.8s cubic-bezier(0.4, 0, 0.2, 1) infinite;
margin-bottom: 8px;
}

@keyframes spin {
0% {
transform: rotate(0deg);
}

100% {
transform: rotate(360deg);
}
}

.loading-text {
font-size: 18px;
color: @color-warm-black;
opacity: 1;
text-align: center;
margin-top: 5px;
font-weight: 500;
}

// error display

.error-display {
max-width: 100%;
position: absolute;
inset-inline: 12px;
bottom: 12px;
margin: 0;
z-index: @stack-order-error-display;
}

// model description
.model-description {
// avoid layout shift
height: 22px;
}
Loading