Toggle annotations layers
advancedviewportannotationsclassification
Console
PMA.UI version: 2.43.3
Toggle annotations layers using classification.
annotation_classes.html
1<!doctype >
2<html lang="en">
3
4<head>
5 <meta charset="utf-8">
6 <meta http-equiv="X-UA-Compatible" content="IE=10">
7 <meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
8
9 <!-- Include PMA.UI required libraries downloaded or from CDN -->
10 <script src="./pma.ui/jquery-3.1.0.js"></script>
11 <link href="./pma.ui/font-awesome.min.css" type="text/css" rel="stylesheet">
12
13 <!-- Include optional libraries downloaded or from CDN -->
14 <link rel="stylesheet" href="./pma.ui/bootstrap.min.css">
15 <script src="./pma.ui/bootstrap.bundle.min.js"></script>
16
17 <!-- Include PMA.UI script & css -->
18 <script src="./pma.ui/pma.ui.js"></script>
19 <link href="./pma.ui/pma.ui.css" type="text/css" rel="stylesheet">
20
21 <!-- Include custom script & css -->
22 <script src="./js/annotation_classes.js"></script>
23 <link href="./css/annotation_classes.css" type="text/css" rel="stylesheet">
24
25 <title>Toggle annotations layers</title>
26</head>
27
28<body>
29 <div class="container-fluid">
30 <div class="row">
31 <div class="col-8 px-0">
32 <!-- The element that will host the viewport -->
33 <div id="viewer"></div>
34 </div>
35 <div class="col-4 py-1 border-left overflow-auto vh-100">
36 <div class="d-flex justify-content-center h-100" id="loader">
37 <div class="spinner-border my-auto" role="status">
38 <span class="sr-only">Loading...</span>
39 </div>
40 </div>
41 <form>
42 <fieldset id="classes">
43
44 </fieldset>
45 </form>
46 </div>
47 </div>
48 </div>
49</body>
50
51</html>
annotation_classes.css
1html,
2body
3{
4 height: 100%;
5 padding: 0px;
6 margin: 0px;
7}
8
9#viewer
10{
11 height: 100vh;
12}
annotation_classes.js
1// Initial declarations
2var serverUrl = "https://host.pathomation.com/pma.core.2/";
3var serverUsername = "PMA_UI_demo";
4var serverPassword = "PMA_UI_demo";
5var imagePath = "mitosis_wsi/066c94c4c161224077a9.svs";
6var viewerElementSelector = "#viewer";
7var caller = "DemoPortal";
8var context = null;
9var slideLoader = null;
10var annotationManager = null;
11var annotations = [];
12var classes = [];
13var classesToShow = [];
14
15jQuery(function () {
16 console.log(`PMA.UI version: ${PMA.UI.getVersion()}`);
17
18 // Create a context
19 context = new PMA.UI.Components.Context({ caller: caller });
20
21 // Add an autologin authentication provider
22 new PMA.UI.Authentication.AutoLogin(context, [{ serverUrl: serverUrl, username: serverUsername, password: serverPassword }]);
23
24 // Create an image loader that will allow us to load images easily
25 slideLoader = new PMA.UI.Components.SlideLoader(context, {
26 element: viewerElementSelector,
27 annotations: {
28 visible: false,
29 showMeasurements: false,
30 labels: false,
31 },
32 });
33
34 // Listen for the slide loaded event by the slide loader
35 slideLoader.listen(PMA.UI.Components.Events.SlideLoaded, function (args) {
36 annotations = slideLoader.mainViewport.getAnnotations();
37 if (annotations.length > 0) {
38 classes = [...new Set(annotations.map(ann => ann.metaData.Classification))];
39 if (classes.length > 0) {
40 annotations.forEach(ann => slideLoader.mainViewport.showAnnotation(ann.metaData.AnnotationID, false));
41 slideLoader.mainViewport.showAnnotations(true);
42 $("#loader").remove();
43 classes.map(cl => $("#classes").append(
44 `<div class="form-group row">
45 <button type="button" class="btn btn-danger btn-sm mx-2 filter-button" data-id="${cl}">
46 <i class="fa fa-eye-slash" aria-hidden="true"></i>
47 </button>
48 <label for="${cl}"
49 class="col-form-label col-form-label-sm font-weight-bolder">${cl} [${annotations.filter((ann) => ann.metaData.Classification === cl).length}]</label>
50 </div>`
51 ));
52
53 $(".filter-button").on("click", function () {
54 var id = $(this).data("id");
55 var len = annotations.length;
56 if (classesToShow.includes(id)) {
57 var index = classesToShow.indexOf(id);
58 if (index !== -1) {
59 classesToShow.splice(index, 1);
60 }
61 $(this).removeClass("btn-primary");
62 $(this).addClass("btn-danger");
63 $(this.firstElementChild).removeClass("fa-eye");
64 $(this.firstElementChild).addClass("fa-eye-slash");
65 while (len--) {
66 if (annotations[len].metaData.Classification === id) {
67 slideLoader.mainViewport.showAnnotation(annotations[len].metaData.AnnotationID, false)
68 }
69 }
70 } else {
71 classesToShow.push(id);
72 $(this).removeClass("btn-danger");
73 $(this).addClass("btn-primary");
74 $(this.firstElementChild).removeClass("fa-eye-slash");
75 $(this.firstElementChild).addClass("fa-eye");
76 while (len--) {
77 if (annotations[len].metaData.Classification === id) {
78 slideLoader.mainViewport.showAnnotation(annotations[len].metaData.AnnotationID, true)
79 }
80 }
81 }
82 });
83 }
84 }
85 });
86
87 // Load the image with the context
88 slideLoader.load(serverUrl, imagePath);
89});