Spaces:
Runtime error
Runtime error
zy7_oldserver commited on
Commit ·
9b01cdb
1
Parent(s): 6c4bed1
- requirements.txt +1 -2
- seg2med_app/frankenstein/frankenstein.py +1 -1
- seg2med_app/streamlit_drawable_canvas/__init__.py +163 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/asset-manifest.json +20 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/index.html +1 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/css/main.8802268d.chunk.css +2 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/css/main.8802268d.chunk.css.map +1 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js +0 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js.LICENSE.txt +78 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js.map +0 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/main.80185090.chunk.js +2 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/main.80185090.chunk.js.map +1 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/runtime-main.3def19be.js +2 -0
- seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/runtime-main.3def19be.js.map +1 -0
requirements.txt
CHANGED
|
@@ -15,8 +15,7 @@ torchmetrics
|
|
| 15 |
tensorboard
|
| 16 |
|
| 17 |
# Streamlit UI
|
| 18 |
-
streamlit
|
| 19 |
-
streamlit-drawable-canvas
|
| 20 |
|
| 21 |
# Medical imaging
|
| 22 |
monai
|
|
|
|
| 15 |
tensorboard
|
| 16 |
|
| 17 |
# Streamlit UI
|
| 18 |
+
streamlit
|
|
|
|
| 19 |
|
| 20 |
# Medical imaging
|
| 21 |
monai
|
seg2med_app/frankenstein/frankenstein.py
CHANGED
|
@@ -5,7 +5,7 @@ import numpy as np
|
|
| 5 |
import streamlit as st
|
| 6 |
from PIL import Image
|
| 7 |
|
| 8 |
-
from streamlit_drawable_canvas import st_canvas
|
| 9 |
from seg2med_app.simulation.get_labels import get_labels
|
| 10 |
from seg2med_app.app_utils.image_utils import show_three_planes_interactive, show_label_overlay
|
| 11 |
import time
|
|
|
|
| 5 |
import streamlit as st
|
| 6 |
from PIL import Image
|
| 7 |
|
| 8 |
+
from seg2med_app.streamlit_drawable_canvas import st_canvas
|
| 9 |
from seg2med_app.simulation.get_labels import get_labels
|
| 10 |
from seg2med_app.app_utils.image_utils import show_three_planes_interactive, show_label_overlay
|
| 11 |
import time
|
seg2med_app/streamlit_drawable_canvas/__init__.py
ADDED
|
@@ -0,0 +1,163 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
import base64
|
| 2 |
+
import io
|
| 3 |
+
import os
|
| 4 |
+
from dataclasses import dataclass
|
| 5 |
+
from hashlib import md5
|
| 6 |
+
|
| 7 |
+
import numpy as np
|
| 8 |
+
import streamlit as st
|
| 9 |
+
import streamlit.components.v1 as components
|
| 10 |
+
import streamlit.elements.lib.image_utils as st_image
|
| 11 |
+
from PIL import Image
|
| 12 |
+
|
| 13 |
+
_RELEASE = True # on packaging, pass this to True
|
| 14 |
+
|
| 15 |
+
if not _RELEASE:
|
| 16 |
+
_component_func = components.declare_component(
|
| 17 |
+
"st_canvas",
|
| 18 |
+
url="http://localhost:3001",
|
| 19 |
+
)
|
| 20 |
+
else:
|
| 21 |
+
parent_dir = os.path.dirname(os.path.abspath(__file__))
|
| 22 |
+
build_dir = os.path.join(parent_dir, "frontend/build")
|
| 23 |
+
_component_func = components.declare_component("st_canvas", path=build_dir)
|
| 24 |
+
|
| 25 |
+
|
| 26 |
+
@dataclass
|
| 27 |
+
class CanvasResult:
|
| 28 |
+
"""Dataclass to store output of React Component
|
| 29 |
+
|
| 30 |
+
Attributes
|
| 31 |
+
----------
|
| 32 |
+
image_data: np.array
|
| 33 |
+
RGBA Matrix of Image Data.
|
| 34 |
+
json_data: dict
|
| 35 |
+
JSON string of canvas and objects.
|
| 36 |
+
"""
|
| 37 |
+
|
| 38 |
+
image_data: np.array = None
|
| 39 |
+
json_data: dict = None
|
| 40 |
+
|
| 41 |
+
|
| 42 |
+
def _data_url_to_image(data_url: str) -> Image:
|
| 43 |
+
"""Convert DataURL string to the image."""
|
| 44 |
+
_, _data_url = data_url.split(";base64,")
|
| 45 |
+
return Image.open(io.BytesIO(base64.b64decode(_data_url)))
|
| 46 |
+
|
| 47 |
+
|
| 48 |
+
def _resize_img(img: Image, new_height: int = 700, new_width: int = 700) -> Image:
|
| 49 |
+
"""Resize the image to the provided resolution."""
|
| 50 |
+
h_ratio = new_height / img.height
|
| 51 |
+
w_ratio = new_width / img.width
|
| 52 |
+
img = img.resize((int(img.width * w_ratio), int(img.height * h_ratio)))
|
| 53 |
+
return img
|
| 54 |
+
|
| 55 |
+
|
| 56 |
+
def st_canvas(
|
| 57 |
+
fill_color: str = "#eee",
|
| 58 |
+
stroke_width: int = 20,
|
| 59 |
+
stroke_color: str = "black",
|
| 60 |
+
background_color: str = "",
|
| 61 |
+
background_image: Image = None,
|
| 62 |
+
update_streamlit: bool = True,
|
| 63 |
+
height: int = 400,
|
| 64 |
+
width: int = 600,
|
| 65 |
+
drawing_mode: str = "freedraw",
|
| 66 |
+
initial_drawing: dict = None,
|
| 67 |
+
display_toolbar: bool = True,
|
| 68 |
+
point_display_radius: int = 3,
|
| 69 |
+
key=None,
|
| 70 |
+
) -> CanvasResult:
|
| 71 |
+
"""Create a drawing canvas in Streamlit app. Retrieve the RGBA image data into a 4D numpy array (r, g, b, alpha)
|
| 72 |
+
on mouse up event.
|
| 73 |
+
|
| 74 |
+
Parameters
|
| 75 |
+
----------
|
| 76 |
+
fill_color: str
|
| 77 |
+
Color of fill for Rect in CSS color property. Defaults to "#eee".
|
| 78 |
+
stroke_width: str
|
| 79 |
+
Width of drawing brush in CSS color property. Defaults to 20.
|
| 80 |
+
stroke_color: str
|
| 81 |
+
Color of drawing brush in hex. Defaults to "black".
|
| 82 |
+
background_color: str
|
| 83 |
+
Color of canvas background in CSS color property. Defaults to "" which is transparent.
|
| 84 |
+
Overriden by background_image.
|
| 85 |
+
Note: Changing background_color will reset the drawing.
|
| 86 |
+
background_image: Image
|
| 87 |
+
Pillow Image to display behind canvas.
|
| 88 |
+
Automatically resized to canvas dimensions.
|
| 89 |
+
Being behind the canvas, it is not sent back to Streamlit on mouse event.
|
| 90 |
+
update_streamlit: bool
|
| 91 |
+
Whenever True, send canvas data to Streamlit when object/selection is updated or mouse up.
|
| 92 |
+
height: int
|
| 93 |
+
Height of canvas in pixels. Defaults to 400.
|
| 94 |
+
width: int
|
| 95 |
+
Width of canvas in pixels. Defaults to 600.
|
| 96 |
+
drawing_mode: {'freedraw', 'transform', 'line', 'rect', 'circle', 'point', 'polygon'}
|
| 97 |
+
Enable free drawing when "freedraw", object manipulation when "transform", "line", "rect", "circle", "point", "polygon".
|
| 98 |
+
Defaults to "freedraw".
|
| 99 |
+
initial_drawing: dict
|
| 100 |
+
Redraw canvas with given initial_drawing. If changed to None then empties canvas.
|
| 101 |
+
Should generally be the `json_data` output from other canvas, which you can manipulate.
|
| 102 |
+
Beware: if importing from a bigger/smaller canvas, no rescaling is done in the canvas,
|
| 103 |
+
it should be ran on user's side.
|
| 104 |
+
display_toolbar: bool
|
| 105 |
+
Display the undo/redo/reset toolbar.
|
| 106 |
+
point_display_radius: int
|
| 107 |
+
The radius to use when displaying point objects. Defaults to 3.
|
| 108 |
+
key: str
|
| 109 |
+
An optional string to use as the unique key for the widget.
|
| 110 |
+
Assign a key so the component is not remount every time the script is rerun.
|
| 111 |
+
|
| 112 |
+
Returns
|
| 113 |
+
-------
|
| 114 |
+
result: CanvasResult
|
| 115 |
+
`image_data` contains reshaped RGBA image 4D numpy array (r, g, b, alpha),
|
| 116 |
+
`json_data` stores the canvas/objects JSON representation which you can manipulate, store
|
| 117 |
+
load and then reinject into another canvas through the `initial_drawing` argument.
|
| 118 |
+
"""
|
| 119 |
+
# Resize background_image to canvas dimensions by default
|
| 120 |
+
# Then override background_color
|
| 121 |
+
background_image_url = None
|
| 122 |
+
if background_image:
|
| 123 |
+
background_image = _resize_img(background_image, height, width)
|
| 124 |
+
# Reduce network traffic and cache when switch another configure, use streamlit in-mem filemanager to convert image to URL
|
| 125 |
+
background_image_url = st_image.image_to_url(
|
| 126 |
+
background_image, width, True, "RGB", "PNG", f"drawable-canvas-bg-{md5(background_image.tobytes()).hexdigest()}-{key}"
|
| 127 |
+
)
|
| 128 |
+
base_url_path: str = st._config.get_option("server.baseUrlPath").strip("/")
|
| 129 |
+
if base_url_path:
|
| 130 |
+
base_url_path = "/" + base_url_path
|
| 131 |
+
background_image_url = base_url_path + background_image_url
|
| 132 |
+
|
| 133 |
+
background_color = ""
|
| 134 |
+
|
| 135 |
+
# Clean initial drawing, override its background color
|
| 136 |
+
initial_drawing = (
|
| 137 |
+
{"version": "4.4.0"} if initial_drawing is None else initial_drawing
|
| 138 |
+
)
|
| 139 |
+
initial_drawing["background"] = background_color
|
| 140 |
+
|
| 141 |
+
component_value = _component_func(
|
| 142 |
+
fillColor=fill_color,
|
| 143 |
+
strokeWidth=stroke_width,
|
| 144 |
+
strokeColor=stroke_color,
|
| 145 |
+
backgroundColor=background_color,
|
| 146 |
+
backgroundImageURL=background_image_url,
|
| 147 |
+
realtimeUpdateStreamlit=update_streamlit and (drawing_mode != "polygon"),
|
| 148 |
+
canvasHeight=height,
|
| 149 |
+
canvasWidth=width,
|
| 150 |
+
drawingMode=drawing_mode,
|
| 151 |
+
initialDrawing=initial_drawing,
|
| 152 |
+
displayToolbar=display_toolbar,
|
| 153 |
+
displayRadius=point_display_radius,
|
| 154 |
+
key=key,
|
| 155 |
+
default=None,
|
| 156 |
+
)
|
| 157 |
+
if component_value is None:
|
| 158 |
+
return CanvasResult
|
| 159 |
+
|
| 160 |
+
return CanvasResult(
|
| 161 |
+
np.asarray(_data_url_to_image(component_value["data"])),
|
| 162 |
+
component_value["raw"],
|
| 163 |
+
)
|
seg2med_app/streamlit_drawable_canvas/frontend/build/asset-manifest.json
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
{
|
| 2 |
+
"files": {
|
| 3 |
+
"main.css": "./static/css/main.8802268d.chunk.css",
|
| 4 |
+
"main.js": "./static/js/main.80185090.chunk.js",
|
| 5 |
+
"main.js.map": "./static/js/main.80185090.chunk.js.map",
|
| 6 |
+
"runtime-main.js": "./static/js/runtime-main.3def19be.js",
|
| 7 |
+
"runtime-main.js.map": "./static/js/runtime-main.3def19be.js.map",
|
| 8 |
+
"static/js/2.3a63bcf0.chunk.js": "./static/js/2.3a63bcf0.chunk.js",
|
| 9 |
+
"static/js/2.3a63bcf0.chunk.js.map": "./static/js/2.3a63bcf0.chunk.js.map",
|
| 10 |
+
"index.html": "./index.html",
|
| 11 |
+
"static/css/main.8802268d.chunk.css.map": "./static/css/main.8802268d.chunk.css.map",
|
| 12 |
+
"static/js/2.3a63bcf0.chunk.js.LICENSE.txt": "./static/js/2.3a63bcf0.chunk.js.LICENSE.txt"
|
| 13 |
+
},
|
| 14 |
+
"entrypoints": [
|
| 15 |
+
"static/js/runtime-main.3def19be.js",
|
| 16 |
+
"static/js/2.3a63bcf0.chunk.js",
|
| 17 |
+
"static/css/main.8802268d.chunk.css",
|
| 18 |
+
"static/js/main.80185090.chunk.js"
|
| 19 |
+
]
|
| 20 |
+
}
|
seg2med_app/streamlit_drawable_canvas/frontend/build/index.html
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
<!doctype html><html lang="en"><head><meta charset="utf-8"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#000000"/><meta name="description" content="Streamlit Component"/><title>Streamlit Component</title><link href="./static/css/main.8802268d.chunk.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div><script>!function(e){function r(r){for(var n,a,l=r[0],f=r[1],i=r[2],p=0,s=[];p<l.length;p++)a=l[p],Object.prototype.hasOwnProperty.call(o,a)&&o[a]&&s.push(o[a][0]),o[a]=0;for(n in f)Object.prototype.hasOwnProperty.call(f,n)&&(e[n]=f[n]);for(c&&c(r);s.length;)s.shift()();return u.push.apply(u,i||[]),t()}function t(){for(var e,r=0;r<u.length;r++){for(var t=u[r],n=!0,l=1;l<t.length;l++){var f=t[l];0!==o[f]&&(n=!1)}n&&(u.splice(r--,1),e=a(a.s=t[0]))}return e}var n={},o={1:0},u=[];function a(r){if(n[r])return n[r].exports;var t=n[r]={i:r,l:!1,exports:{}};return e[r].call(t.exports,t,t.exports,a),t.l=!0,t.exports}a.m=e,a.c=n,a.d=function(e,r,t){a.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:t})},a.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},a.t=function(e,r){if(1&r&&(e=a(e)),8&r)return e;if(4&r&&"object"==typeof e&&e&&e.__esModule)return e;var t=Object.create(null);if(a.r(t),Object.defineProperty(t,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var n in e)a.d(t,n,function(r){return e[r]}.bind(null,n));return t},a.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return a.d(r,"a",r),r},a.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},a.p="./";var l=this.webpackJsonpdrawable_canvas=this.webpackJsonpdrawable_canvas||[],f=l.push.bind(l);l.push=r,l=l.slice();for(var i=0;i<l.length;i++)r(l[i]);var c=f;t()}([])</script><script src="./static/js/2.3a63bcf0.chunk.js"></script><script src="./static/js/main.80185090.chunk.js"></script></body></html>
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/css/main.8802268d.chunk.css
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
|
|
|
| 1 |
+
.CanvasToolbar_enabled__2bOtL{cursor:pointer;background:none}.CanvasToolbar_disabled__T9sX8{cursor:not-allowed;-webkit-filter:invert(95%) sepia(10%) saturate(657%) hue-rotate(184deg) brightness(92%) contrast(95%);filter:invert(95%) sepia(10%) saturate(657%) hue-rotate(184deg) brightness(92%) contrast(95%)}.CanvasToolbar_enabled__2bOtL:hover{-webkit-filter:invert(41%) sepia(62%) saturate(7158%) hue-rotate(344deg) brightness(101%) contrast(108%);filter:invert(41%) sepia(62%) saturate(7158%) hue-rotate(344deg) brightness(101%) contrast(108%)}.CanvasToolbar_invertx__2gc2O{-webkit-transform:scaleX(-1);transform:scaleX(-1)}:root{box-sizing:border-box}*,:after,:before{box-sizing:inherit}body{margin:0;background:transparent}
|
| 2 |
+
/*# sourceMappingURL=main.8802268d.chunk.css.map */
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/css/main.8802268d.chunk.css.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
{"version":3,"sources":["webpack://src/components/CanvasToolbar.module.css","webpack://src/index.css"],"names":[],"mappings":"AAAA,8BACE,cAAe,CACf,eACF,CAEA,+BACE,kBAAmB,CACnB,qGAC+B,CAD/B,6FAEF,CAEA,oCACE,wGACiC,CADjC,gGAEF,CAEA,8BACE,4BAAqB,CAArB,oBACF,CClBA,MACE,qBACF,CAEA,iBAGE,kBACF,CAEA,KACE,QAAS,CACT,sBACF","file":"main.8802268d.chunk.css","sourcesContent":[".enabled {\n cursor: pointer;\n background: none;\n}\n\n.disabled {\n cursor: not-allowed;\n filter: invert(95%) sepia(10%) saturate(657%) hue-rotate(184deg)\n brightness(92%) contrast(95%);\n}\n\n.enabled:hover {\n filter: invert(41%) sepia(62%) saturate(7158%) hue-rotate(344deg)\n brightness(101%) contrast(108%);\n}\n\n.invertx {\n transform: scaleX(-1);\n}\n",":root {\n box-sizing: border-box;\n}\n\n*,\n::before,\n::after {\n box-sizing: inherit;\n}\n\nbody {\n margin: 0;\n background: transparent;\n}\n"]}
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js.LICENSE.txt
ADDED
|
@@ -0,0 +1,78 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
/*
|
| 2 |
+
object-assign
|
| 3 |
+
(c) Sindre Sorhus
|
| 4 |
+
@license MIT
|
| 5 |
+
*/
|
| 6 |
+
|
| 7 |
+
/*!
|
| 8 |
+
* The buffer module from node.js, for the browser.
|
| 9 |
+
*
|
| 10 |
+
* @author Feross Aboukhadijeh <http://feross.org>
|
| 11 |
+
* @license MIT
|
| 12 |
+
*/
|
| 13 |
+
|
| 14 |
+
/*! Fabric.js Copyright 2008-2015, Printio (Juriy Zaytsev, Maxim Chernyak) */
|
| 15 |
+
|
| 16 |
+
/*! regenerator-runtime -- Copyright (c) 2014-present, Facebook, Inc. -- license (MIT): https://github.com/facebook/regenerator/blob/main/LICENSE */
|
| 17 |
+
|
| 18 |
+
/**
|
| 19 |
+
* @license
|
| 20 |
+
* Copyright 2018-2021 Streamlit Inc.
|
| 21 |
+
*
|
| 22 |
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
| 23 |
+
* you may not use this file except in compliance with the License.
|
| 24 |
+
* You may obtain a copy of the License at
|
| 25 |
+
*
|
| 26 |
+
* http://www.apache.org/licenses/LICENSE-2.0
|
| 27 |
+
*
|
| 28 |
+
* Unless required by applicable law or agreed to in writing, software
|
| 29 |
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
| 30 |
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
| 31 |
+
* See the License for the specific language governing permissions and
|
| 32 |
+
* limitations under the License.
|
| 33 |
+
*/
|
| 34 |
+
|
| 35 |
+
/**
|
| 36 |
+
* @license
|
| 37 |
+
* Lodash <https://lodash.com/>
|
| 38 |
+
* Copyright OpenJS Foundation and other contributors <https://openjsf.org/>
|
| 39 |
+
* Released under MIT license <https://lodash.com/license>
|
| 40 |
+
* Based on Underscore.js 1.8.3 <http://underscorejs.org/LICENSE>
|
| 41 |
+
* Copyright Jeremy Ashkenas, DocumentCloud and Investigative Reporters & Editors
|
| 42 |
+
*/
|
| 43 |
+
|
| 44 |
+
/** @license React v0.19.1
|
| 45 |
+
* scheduler.production.min.js
|
| 46 |
+
*
|
| 47 |
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
| 48 |
+
*
|
| 49 |
+
* This source code is licensed under the MIT license found in the
|
| 50 |
+
* LICENSE file in the root directory of this source tree.
|
| 51 |
+
*/
|
| 52 |
+
|
| 53 |
+
/** @license React v16.13.1
|
| 54 |
+
* react-dom.production.min.js
|
| 55 |
+
*
|
| 56 |
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
| 57 |
+
*
|
| 58 |
+
* This source code is licensed under the MIT license found in the
|
| 59 |
+
* LICENSE file in the root directory of this source tree.
|
| 60 |
+
*/
|
| 61 |
+
|
| 62 |
+
/** @license React v16.13.1
|
| 63 |
+
* react-is.production.min.js
|
| 64 |
+
*
|
| 65 |
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
| 66 |
+
*
|
| 67 |
+
* This source code is licensed under the MIT license found in the
|
| 68 |
+
* LICENSE file in the root directory of this source tree.
|
| 69 |
+
*/
|
| 70 |
+
|
| 71 |
+
/** @license React v16.13.1
|
| 72 |
+
* react.production.min.js
|
| 73 |
+
*
|
| 74 |
+
* Copyright (c) Facebook, Inc. and its affiliates.
|
| 75 |
+
*
|
| 76 |
+
* This source code is licensed under the MIT license found in the
|
| 77 |
+
* LICENSE file in the root directory of this source tree.
|
| 78 |
+
*/
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/2.3a63bcf0.chunk.js.map
ADDED
|
The diff for this file is too large to render.
See raw diff
|
|
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/main.80185090.chunk.js
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
|
|
|
| 1 |
+
(this.webpackJsonpdrawable_canvas=this.webpackJsonpdrawable_canvas||[]).push([[0],{21:function(t,e,n){t.exports={enabled:"CanvasToolbar_enabled__2bOtL",disabled:"CanvasToolbar_disabled__T9sX8",invertx:"CanvasToolbar_invertx__2gc2O"}},36:function(t,e){},37:function(t,e){},38:function(t,e){},40:function(t,e,n){},41:function(t,e,n){"use strict";n.r(e);var a=n(6),o=n.n(a),r=n(24),i=n.n(r),s=n(8),c=n(17),u=n(9),l=n(14),h=n(21),f=n.n(h),d="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAwwAAAMMBnc7+MwAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAEFSURBVEiJ7dSxLkRBFMbx31BIlkQlHoCap5BQLAXvQafV6DyLRLYSdkWv0dBQ0NAKkUhkj2bEzc3udW9xE5E9yVfNd85/5pyZSRGhzZhqtfoE8DcAKaVOqwD0mkBSSnNNAAmBAboR8V4qtoguVrNWMI9n3Gad4SQqHlRk9dHJvmns4qWwXqUrbESEspSMfazhekyhN9zhc8z6KWarAKN0jm0sI+WkmdyuPTyV/JdFSBXgATujjl3aYQf7+CjkXhTaPRYw+DbVETZLkMM6Leo3hGxhmHNfsVBnBk0hx4XcozqARpA8/GG+bQcJ6+rFTUQ81jGmlJYi4p6fa9da/IPvegL4Lb4A0uc9nRaYXwcAAAAASUVORK5CYII=",v=function(t){var e=t.imgUrl,n=t.altText,a=t.invertX,r=t.size,i=t.enabled,s=t.clickCallback;return o.a.createElement("img",{src:e,className:"\n ".concat(i?f.a.enabled:f.a.disabled," ").concat(a?"":f.a.invertx,"\n "),alt:n,title:n,height:"".concat(r,"px"),width:"".concat(r,"px"),onClick:s})};v.defaultProps={invertX:!1};var b=function(t){var e=t.topPosition,n=(t.leftPosition,t.canUndo),a=t.canRedo,r=t.downloadCallback,i=t.undoCallback,s=t.redoCallback,c=t.resetCallback,u=[{imgUrl:"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAsQAAALEBxi1JjQAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAEYSURBVEiJ7dS9SgNBFMXxX0y0NNpLqjQiKRRETON7aBMfwLfxDcRGC8HOTm21s7RIYZdniGiRO+6y5mNXVxD0wMBw58z532Fnh1+kFq5jNH8C0MFbjE7ZTUsVAEsz5rUBvqR/wB8CNLFeY+5aZH4ArjDCXsHYNv+vbWK1UNuNrMs8oGfyFGzmjDthvA9QUe1YG4U3aQvL2M4DpqkRHfZxU4C0o9aPxhpzcsDQ5I0ZFOpHGMfas+wtSvNxePIaxNpw0QngHIcR1M3Vu3jFcXhmqsw1vZCdJCmFny3a3CoBSBAm3TbKhlcBJEj6Vo9lN1UBwENF/yfAAVaqhhS0P614J7uCdY1bsh+kh1NsfLP7pBec4KmmvNl6B0BuQt0zCQ0xAAAAAElFTkSuQmCC",altText:"Send to Streamlit",invertX:!1,enabled:!0,clickCallback:r},{imgUrl:d,altText:"Undo",invertX:!0,enabled:n,clickCallback:n?i:function(){}},{imgUrl:d,altText:"Redo",invertX:!1,enabled:a,clickCallback:a?s:function(){}},{imgUrl:"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAhQAAAIUB4uz/wQAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAHUSURBVEiJtda9ahRRFAfw3xHFJCabFEkawcYiYKMWVmohBHwFOwsfQLCxthOENHZqKxZG8DHSxcJC0Qcw7AqSNSoGci3mznp3nP0K8cBlZs7X/5z//RopJeMGlrGL1Bi7WJ4Uf9pk2cQVPMDPrJvHVra9GRc8BBARS7iKU4X6cn5+wvf8vljbIuJr4XuEdyml/YGmoGIdX/xLxayji/U2iu5iJXfwa1zbY2QOOznXE4YpuoE93D5m8lr2cLMN4BWu4TF+4HDGxIEOeng90DaW5BkVj/fyd6dhP4u5hq6Tnxdz7GZpL1eLlNIhvmEtq7Yj4mHhsoWng5Ir23b+rGO6Zc62fdAtnFewUdjOqyaylo3sMxJgqIMsvcJ5X8XrKFlCvwHQmwRQdjArwH5K6fc0AKvHAFjVoGcUwCwUdbKPHNNrOpw0RVN10MVCRCz8T4A6oI/FiIiTBKh5XFN1EDnRkETEnGrnH2sOSoC60rbqoR8R8zg3bQe102oB0DYPAwB/l/VkgJTSgeo+KDtoA6h1fSN2Me1nUV3JOj7iOT5k/csi5jNe4D2uj+og8lE7rIx4hjt4hIMRRZRyX7UYLqWUjoYsI35VLuCt6tKZ5h7ewa22XH8AgjMTispa6ucAAAAASUVORK5CYII=",altText:"Reset canvas & history",invertX:!1,enabled:!0,clickCallback:c}];return o.a.createElement("div",{style:{position:"absolute",top:e+4,left:0,display:"flex",gap:4,zIndex:20}},u.map((function(t){return o.a.createElement(v,{key:t.altText,imgUrl:t.imgUrl,altText:t.altText,invertX:t.invertX,size:24,enabled:t.enabled,clickCallback:t.clickCallback})})))},S=function(t){var e=Object(a.useState)(new u.fabric.Canvas("")),n=Object(s.a)(e,2),r=n[0],i=n[1],l=function(t,e){var n=Object(a.useState)(t),o=Object(s.a)(n,2),r=o[0],i=o[1];return Object(a.useEffect)((function(){var n=setTimeout((function(){i(t)}),e);return function(){clearTimeout(n)}}),[t,e]),r}(t.stateToSendToStreamlit,200);return Object(a.useEffect)((function(){var t=new u.fabric.Canvas("canvas-to-streamlit",{enableRetinaScaling:!1});i(t)}),[]),Object(a.useEffect)((function(){l&&t.shouldSendToStreamlit&&r.loadFromJSON(l,(function(){!function(t){var e=t.getContext().canvas.toDataURL();c.a.setComponentValue({data:e,width:t.getWidth(),height:t.getHeight(),raw:t.toObject()})}(r)}))}),[r,t.shouldSendToStreamlit,l]),o.a.createElement("canvas",{id:"canvas-to-streamlit",width:t.canvasWidth,height:t.canvasHeight})},k=n(4),m=n(7),A={shouldReloadCanvas:!1,forceSendToStreamlit:!1},C={shouldReloadCanvas:!0,forceSendToStreamlit:!1},g={shouldReloadCanvas:!1,forceSendToStreamlit:!0},w={shouldReloadCanvas:!0,forceSendToStreamlit:!0},y=function(t,e){switch(e.type){case"save":if(e.state){if(Object(l.isEmpty)(t.currentState))return{history:{undoStack:[],redoStack:[]},action:Object(m.a)({},A),initialState:e.state,currentState:e.state};if(Object(l.isEqual)(e.state,t.currentState))return{history:Object(m.a)({},t.history),action:Object(m.a)({},A),initialState:t.initialState,currentState:t.currentState};var n=t.history.undoStack.length>=100;return{history:{undoStack:[].concat(Object(k.a)(t.history.undoStack.slice(n?1:0)),[t.currentState]),redoStack:[]},action:Object(m.a)({},A),initialState:null==t.initialState?t.currentState:t.initialState,currentState:e.state}}throw new Error("No action state to save");case"undo":if(Object(l.isEmpty)(t.currentState)||Object(l.isEqual)(t.initialState,t.currentState))return{history:Object(m.a)({},t.history),action:Object(m.a)({},A),initialState:t.initialState,currentState:t.currentState};var a=0===t.history.undoStack.length;return{history:{undoStack:t.history.undoStack.slice(0,-1),redoStack:[].concat(Object(k.a)(t.history.redoStack),[t.currentState])},action:Object(m.a)({},C),initialState:t.initialState,currentState:a?t.currentState:t.history.undoStack[t.history.undoStack.length-1]};case"redo":return t.history.redoStack.length>0?{history:{undoStack:[].concat(Object(k.a)(t.history.undoStack),[t.currentState]),redoStack:t.history.redoStack.slice(0,-1)},action:Object(m.a)({},C),initialState:t.initialState,currentState:t.history.redoStack[t.history.redoStack.length-1]}:{history:Object(m.a)({},t.history),action:Object(m.a)({},A),initialState:t.initialState,currentState:t.currentState};case"reset":if(!e.state)throw new Error("No action state to store in reset");return{history:{undoStack:[],redoStack:[]},action:Object(m.a)({},w),initialState:e.state,currentState:e.state};case"forceSendToStreamlit":return{history:Object(m.a)({},t.history),action:Object(m.a)({},g),initialState:t.initialState,currentState:t.currentState};default:throw new Error("TS should protect from this")}},M={history:{undoStack:[],redoStack:[]},action:{forceSendToStreamlit:!1,shouldReloadCanvas:!1},initialState:{},currentState:{}},p=Object(a.createContext)({}),O=function(t){var e=t.children,n=Object(a.useReducer)(y,M),r=Object(s.a)(n,2),i=r[0],c=r[1],u=Object(a.useCallback)((function(t){return c({type:"save",state:t})}),[c]),l=Object(a.useCallback)((function(){return c({type:"undo"})}),[c]),h=Object(a.useCallback)((function(){return c({type:"redo"})}),[c]),f=Object(a.useCallback)((function(){return c({type:"forceSendToStreamlit"})}),[c]),d=Object(a.useCallback)((function(t){return c({type:"reset",state:t})}),[c]),v=0!==i.history.undoStack.length,b=0!==i.history.redoStack.length;return o.a.createElement(p.Provider,{value:{canvasState:i,saveState:u,undo:l,redo:h,canUndo:v,canRedo:b,forceStreamlitUpdate:f,resetState:d}},e)},j=n(0),_=n(1),R=n(2),x=n(3),D=Object(_.a)((function t(e){Object(j.a)(this,t),this._canvas=void 0,this._canvas=e})),E=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){var t;Object(j.a)(this,n);for(var a=arguments.length,o=new Array(a),r=0;r<a;r++)o[r]=arguments[r];return(t=e.call.apply(e,[this].concat(o))).isMouseDown=!1,t.fillColor="#ffffff",t.strokeWidth=10,t.strokeColor="#ffffff",t.currentCircle=new u.fabric.Circle,t.currentStartX=0,t.currentStartY=0,t._minRadius=10,t.linearDistance=function(t,e){var n=e.x-t.x,a=e.y-t.y;return Math.sqrt(n*n+a*a)},t}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this,n=t.strokeWidth,a=t.strokeColor,o=t.fillColor;return this._canvas.isDrawingMode=!1,this._canvas.selection=!1,this._canvas.forEachObject((function(t){return t.selectable=t.evented=!1})),this.strokeWidth=n,this.strokeColor=a,this.fillColor=o,this._minRadius=n,this._canvas.on("mouse:down",(function(t){return e.onMouseDown(t)})),this._canvas.on("mouse:move",(function(t){return e.onMouseMove(t)})),this._canvas.on("mouse:up",(function(t){return e.onMouseUp(t)})),this._canvas.on("mouse:out",(function(t){return e.onMouseOut(t)})),function(){e._canvas.off("mouse:down"),e._canvas.off("mouse:move"),e._canvas.off("mouse:up"),e._canvas.off("mouse:out")}}},{key:"onMouseDown",value:function(t){var e=this._canvas,n=t.e.button;this.isMouseDown=!0;var a=e.getPointer(t.e);this.currentStartX=a.x,this.currentStartY=a.y,this.currentCircle=new u.fabric.Circle({left:this.currentStartX,top:this.currentStartY,originX:"left",originY:"center",strokeWidth:this.strokeWidth,stroke:this.strokeColor,fill:this.fillColor,selectable:!1,evented:!1,radius:this._minRadius}),0===n&&e.add(this.currentCircle)}},{key:"onMouseMove",value:function(t){if(this.isMouseDown){var e=this._canvas,n=e.getPointer(t.e),a=this.linearDistance({x:this.currentStartX,y:this.currentStartY},{x:n.x,y:n.y})/2;this.currentCircle.set({radius:Math.max(a,this._minRadius),angle:180*Math.atan2(n.y-this.currentStartY,n.x-this.currentStartX)/Math.PI}),this.currentCircle.setCoords(),e.renderAll()}}},{key:"onMouseUp",value:function(t){this.isMouseDown=!1}},{key:"onMouseOut",value:function(t){this.isMouseDown=!1}}]),n}(D),U=E,L=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){return Object(j.a)(this,n),e.apply(this,arguments)}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=t.strokeWidth,n=t.strokeColor;return this._canvas.isDrawingMode=!0,this._canvas.freeDrawingBrush.width=e,this._canvas.freeDrawingBrush.color=n,function(){}}}]),n}(D),B=L,X=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){var t;Object(j.a)(this,n);for(var a=arguments.length,o=new Array(a),r=0;r<a;r++)o[r]=arguments[r];return(t=e.call.apply(e,[this].concat(o))).isMouseDown=!1,t.strokeWidth=10,t.strokeColor="#ffffff",t.currentLine=new u.fabric.Line,t}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this,n=t.strokeWidth,a=t.strokeColor;return this._canvas.isDrawingMode=!1,this._canvas.selection=!1,this._canvas.forEachObject((function(t){return t.selectable=t.evented=!1})),this.strokeWidth=n,this.strokeColor=a,this._canvas.on("mouse:down",(function(t){return e.onMouseDown(t)})),this._canvas.on("mouse:move",(function(t){return e.onMouseMove(t)})),this._canvas.on("mouse:up",(function(t){return e.onMouseUp(t)})),this._canvas.on("mouse:out",(function(t){return e.onMouseOut(t)})),function(){e._canvas.off("mouse:down"),e._canvas.off("mouse:move"),e._canvas.off("mouse:up"),e._canvas.off("mouse:out")}}},{key:"onMouseDown",value:function(t){var e=this._canvas,n=t.e.button;this.isMouseDown=!0;var a=e.getPointer(t.e),o=[a.x,a.y,a.x,a.y];this.currentLine=new u.fabric.Line(o,{strokeWidth:this.strokeWidth,fill:this.strokeColor,stroke:this.strokeColor,originX:"center",originY:"center",selectable:!1,evented:!1}),0===n&&e.add(this.currentLine)}},{key:"onMouseMove",value:function(t){if(this.isMouseDown){var e=this._canvas,n=e.getPointer(t.e);this.currentLine.set({x2:n.x,y2:n.y}),this.currentLine.setCoords(),e.renderAll()}}},{key:"onMouseUp",value:function(t){this.isMouseDown=!1;var e=this._canvas;0===this.currentLine.width&&0===this.currentLine.height&&e.remove(this.currentLine)}},{key:"onMouseOut",value:function(t){this.isMouseDown=!1}}]),n}(D),W=X,Y=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){var t;Object(j.a)(this,n);for(var a=arguments.length,o=new Array(a),r=0;r<a;r++)o[r]=arguments[r];return(t=e.call.apply(e,[this].concat(o))).isMouseDown=!1,t.fillColor="#ffffff",t.strokeWidth=10,t.strokeColor="#ffffff",t.startCircle=new u.fabric.Circle,t.currentLine=new u.fabric.Line,t.currentPath=new u.fabric.Path,t._pathString="M ",t}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this,n=t.strokeWidth,a=t.strokeColor,o=t.fillColor;return this._canvas.isDrawingMode=!1,this._canvas.selection=!1,this._canvas.forEachObject((function(t){return t.selectable=t.evented=!1})),this.strokeWidth=n,this.strokeColor=a,this.fillColor=o,this._canvas.on("mouse:down",(function(t){return e.onMouseDown(t)})),this._canvas.on("mouse:move",(function(t){return e.onMouseMove(t)})),this._canvas.on("mouse:up",(function(t){return e.onMouseUp(t)})),this._canvas.on("mouse:out",(function(t){return e.onMouseOut(t)})),this._canvas.on("mouse:dblclick",(function(t){return e.onMouseDoubleClick(t)})),function(){e._canvas.off("mouse:down"),e._canvas.off("mouse:move"),e._canvas.off("mouse:up"),e._canvas.off("mouse:out"),e._canvas.off("mouse:dblclick")}}},{key:"onMouseDown",value:function(t){var e=this._canvas,n=t.e.button,a=!1;"M "===this._pathString&&(a=!0),this.isMouseDown=!0;var o=e.getPointer(t.e),r=[o.x,o.y,o.x,o.y];e.remove(this.currentLine),this.currentLine=new u.fabric.Line(r,{strokeWidth:this.strokeWidth,fill:this.strokeColor,stroke:this.strokeColor,originX:"center",originY:"center",selectable:!1,evented:!1}),0===n&&e.add(this.currentLine),a&&0===n?(this._pathString+="".concat(o.x," ").concat(o.y," "),this.startCircle=new u.fabric.Circle({left:o.x,top:o.y,originX:"center",originY:"center",strokeWidth:this.strokeWidth,stroke:this.strokeColor,fill:this.strokeColor,selectable:!1,evented:!1,radius:this.strokeWidth}),e.add(this.startCircle),a=!1):(e.remove(this.currentPath),0===n&&(this._pathString+="L ".concat(o.x," ").concat(o.y," ")),2===n&&(this._pathString+="z",e.remove(this.startCircle))),this.currentPath=new u.fabric.Path(this._pathString,{strokeWidth:this.strokeWidth,fill:this.fillColor,stroke:this.strokeColor,originX:"center",originY:"center",selectable:!1,evented:!1}),0!==this.currentPath.width&&0!==this.currentPath.height&&e.add(this.currentPath),2===n&&(this._pathString="M ")}},{key:"onMouseMove",value:function(t){if(this.isMouseDown){var e=this._canvas,n=e.getPointer(t.e);this.currentLine.set({x2:n.x,y2:n.y}),this.currentLine.setCoords(),e.renderAll()}}},{key:"onMouseUp",value:function(t){this.isMouseDown=!0}},{key:"onMouseOut",value:function(t){this.isMouseDown=!1}},{key:"onMouseDoubleClick",value:function(t){for(var e=this._canvas,n=0;n<3;n++){var a=this._pathString.lastIndexOf("L");-1===a?(this._pathString="M ",e.remove(this.startCircle)):this._pathString=this._pathString.slice(0,a)}e.remove(this.currentLine),e.remove(this.currentPath),this.currentPath=new u.fabric.Path(this._pathString,{strokeWidth:this.strokeWidth,fill:this.fillColor,stroke:this.strokeColor,originX:"center",originY:"center",selectable:!1,evented:!1}),e.add(this.currentPath)}}]),n}(D),N=Y,T=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){var t;Object(j.a)(this,n);for(var a=arguments.length,o=new Array(a),r=0;r<a;r++)o[r]=arguments[r];return(t=e.call.apply(e,[this].concat(o))).isMouseDown=!1,t.fillColor="#ffffff",t.strokeWidth=10,t.strokeColor="#ffffff",t.currentRect=new u.fabric.Rect,t.currentStartX=0,t.currentStartY=0,t._minLength=10,t}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this,n=t.strokeWidth,a=t.strokeColor,o=t.fillColor;return this._canvas.isDrawingMode=!1,this._canvas.selection=!1,this._canvas.forEachObject((function(t){return t.selectable=t.evented=!1})),this.strokeWidth=n,this.strokeColor=a,this.fillColor=o,this._minLength=n,this._canvas.on("mouse:down",(function(t){return e.onMouseDown(t)})),this._canvas.on("mouse:move",(function(t){return e.onMouseMove(t)})),this._canvas.on("mouse:up",(function(t){return e.onMouseUp(t)})),this._canvas.on("mouse:out",(function(t){return e.onMouseOut(t)})),function(){e._canvas.off("mouse:down"),e._canvas.off("mouse:move"),e._canvas.off("mouse:up"),e._canvas.off("mouse:out")}}},{key:"onMouseDown",value:function(t){var e=this._canvas,n=t.e.button;this.isMouseDown=!0;var a=e.getPointer(t.e);this.currentStartX=a.x,this.currentStartY=a.y,this.currentRect=new u.fabric.Rect({left:this.currentStartX,top:this.currentStartY,originX:"left",originY:"top",width:this._minLength,height:this._minLength,stroke:this.strokeColor,strokeWidth:this.strokeWidth,fill:this.fillColor,transparentCorners:!1,selectable:!1,evented:!1,strokeUniform:!0,noScaleCache:!1,angle:0}),0===n&&e.add(this.currentRect)}},{key:"onMouseMove",value:function(t){if(this.isMouseDown){var e=this._canvas,n=e.getPointer(t.e);this.currentStartX>n.x&&this.currentRect.set({left:Math.abs(n.x)}),this.currentStartY>n.y&&this.currentRect.set({top:Math.abs(n.y)});var a=Math.abs(this.currentStartX-n.x),o=Math.abs(this.currentStartY-n.y);this.currentRect.set({width:Math.max(a,2*this._minLength),height:Math.max(o,2*this._minLength)}),this.currentRect.setCoords(),e.renderAll()}}},{key:"onMouseUp",value:function(t){this.isMouseDown=!1}},{key:"onMouseOut",value:function(t){this.isMouseDown=!1}}]),n}(D),P=T,I=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){return Object(j.a)(this,n),e.apply(this,arguments)}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this._canvas;e.isDrawingMode=!1,e.selection=!0,e.forEachObject((function(t){return t.selectable=t.evented=!0}));var n=function(){e.remove(e.getActiveObject())};return e.on("mouse:dblclick",n),function(){e.off("mouse:dblclick",n)}}}]),n}(D),V=I,H=function(t){Object(R.a)(n,t);var e=Object(x.a)(n);function n(){var t;Object(j.a)(this,n);for(var a=arguments.length,o=new Array(a),r=0;r<a;r++)o[r]=arguments[r];return(t=e.call.apply(e,[this].concat(o))).isMouseDown=!1,t.fillColor="#ffffff",t.strokeWidth=10,t.strokeColor="#ffffff",t.currentCircle=new u.fabric.Circle,t.currentStartX=0,t.currentStartY=0,t.displayRadius=1,t}return Object(_.a)(n,[{key:"configureCanvas",value:function(t){var e=this,n=t.strokeWidth,a=t.strokeColor,o=t.fillColor,r=t.displayRadius;return this._canvas.isDrawingMode=!1,this._canvas.selection=!1,this._canvas.forEachObject((function(t){return t.selectable=t.evented=!1})),this.strokeWidth=n,this.strokeColor=a,this.fillColor=o,this.displayRadius=r,this._canvas.on("mouse:down",(function(t){return e.onMouseDown(t)})),this._canvas.on("mouse:move",(function(t){return e.onMouseMove(t)})),this._canvas.on("mouse:up",(function(t){return e.onMouseUp(t)})),this._canvas.on("mouse:out",(function(t){return e.onMouseOut(t)})),function(){e._canvas.off("mouse:down"),e._canvas.off("mouse:move"),e._canvas.off("mouse:up"),e._canvas.off("mouse:out")}}},{key:"onMouseDown",value:function(t){var e=this._canvas,n=t.e.button;this.isMouseDown=!0;var a=e.getPointer(t.e);this.currentStartX=a.x-(this.displayRadius+this.strokeWidth/2),this.currentStartY=a.y,this.currentCircle=new u.fabric.Circle({left:this.currentStartX,top:this.currentStartY,originX:"left",originY:"center",strokeWidth:this.strokeWidth,stroke:this.strokeColor,fill:this.fillColor,selectable:!1,evented:!1,radius:this.displayRadius}),0===n&&e.add(this.currentCircle)}},{key:"onMouseMove",value:function(t){if(this.isMouseDown){var e=this._canvas;this.currentCircle.setCoords(),e.renderAll()}}},{key:"onMouseUp",value:function(t){this.isMouseDown=!1}},{key:"onMouseOut",value:function(t){this.isMouseDown=!1}}]),n}(D),z={circle:U,freedraw:B,line:W,polygon:N,rect:P,transform:V,point:H};var F=Object(c.b)((function(t){var e=t.args,n=e.canvasWidth,r=e.canvasHeight,i=e.backgroundColor,h=e.backgroundImageURL,f=e.realtimeUpdateStreamlit,d=e.drawingMode,v=e.fillColor,k=e.strokeWidth,m=e.strokeColor,A=e.displayRadius,C=e.initialDrawing,g=e.displayToolbar,w=Object(a.useState)(new u.fabric.Canvas("")),y=Object(s.a)(w,2),M=y[0],O=y[1];M.stopContextMenu=!0,M.fireRightClick=!0;var j=Object(a.useState)(new u.fabric.StaticCanvas("")),_=Object(s.a)(j,2),R=_[0],x=_[1],D=Object(a.useContext)(p),E=D.canvasState,U=E.action,L=U.shouldReloadCanvas,B=U.forceSendToStreamlit,X=E.currentState,W=E.initialState,Y=D.saveState,N=D.undo,T=D.redo,P=D.canUndo,I=D.canRedo,V=D.forceStreamlitUpdate,H=D.resetState;return Object(a.useEffect)((function(){var t=new u.fabric.Canvas("canvas",{enableRetinaScaling:!1}),e=new u.fabric.StaticCanvas("backgroundimage-canvas",{enableRetinaScaling:!1});O(t),x(e),c.a.setFrameHeight()}),[]),Object(a.useEffect)((function(){Object(l.isEqual)(W,C)||M.loadFromJSON(C,(function(){M.renderAll(),H(C)}))}),[M,C,W,H]),Object(a.useEffect)((function(){if(h){var t,e=new Image;e.onload=function(){R.getContext().drawImage(e,0,0)};var n=null!==(t=function(){var t=new URLSearchParams(window.location.search).get("streamlitUrl");if(null==t)return null;try{return new URL(t).origin}catch(e){return null}}())&&void 0!==t?t:"";e.src=n+h}}),[M,R,r,n,i,h,Y]),Object(a.useEffect)((function(){L&&M.loadFromJSON(X,(function(){}))}),[M,L,X]),Object(a.useEffect)((function(){var t=new z[d](M).configureCanvas({fillColor:v,strokeWidth:k,strokeColor:m,displayRadius:A});return M.on("mouse:up",(function(t){Y(M.toJSON()),3===t.button&&V()})),M.on("mouse:dblclick",(function(){Y(M.toJSON())})),function(){t(),M.off("mouse:up"),M.off("mouse:dblclick")}}),[M,k,m,A,v,d,C,Y,V]),o.a.createElement("div",{style:{position:"relative"}},o.a.createElement("div",{style:{position:"absolute",top:0,left:0,zIndex:-10,visibility:"hidden"}},o.a.createElement(S,{canvasHeight:r,canvasWidth:n,shouldSendToStreamlit:f||B,stateToSendToStreamlit:X})),o.a.createElement("div",{style:{position:"absolute",top:0,left:0,zIndex:0}},o.a.createElement("canvas",{id:"backgroundimage-canvas",width:n,height:r})),o.a.createElement("div",{style:{position:"absolute",top:0,left:0,zIndex:10}},o.a.createElement("canvas",{id:"canvas",width:n,height:r,style:{border:"lightgrey 1px solid"}})),g&&o.a.createElement(b,{topPosition:r,leftPosition:n,canUndo:P,canRedo:I,downloadCallback:V,undoCallback:N,redoCallback:T,resetCallback:function(){H(W)}}))}));n(40);i.a.render(o.a.createElement(o.a.StrictMode,null,o.a.createElement(O,null,o.a.createElement(F,null))),document.getElementById("root"))}},[[41,1,2]]]);
|
| 2 |
+
//# sourceMappingURL=main.80185090.chunk.js.map
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/main.80185090.chunk.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
{"version":3,"sources":["components/CanvasToolbar.module.css","img/undo.png","components/CanvasToolbar.tsx","img/download.png","img/bin.png","components/UpdateStreamlit.tsx","DrawableCanvasState.tsx","lib/fabrictool.ts","lib/circle.ts","lib/freedraw.ts","lib/line.ts","lib/polygon.ts","lib/rect.ts","lib/transform.ts","lib/point.ts","lib/index.ts","DrawableCanvas.tsx","index.tsx"],"names":["module","exports","SquareIcon","_ref","imgUrl","altText","invertX","size","enabled","clickCallback","React","createElement","src","className","concat","styles","disabled","invertx","alt","title","height","width","onClick","defaultProps","CanvasToolbar","_ref2","topPosition","canUndo","leftPosition","canRedo","downloadCallback","undoCallback","redoCallback","resetCallback","iconElements","undo","style","position","top","left","display","gap","zIndex","map","e","key","UpdateStreamlit","props","_useState3","useState","fabric","Canvas","_useState4","_slicedToArray","stCanvas","setStCanvas","debouncedStateToSend","value","delay","_useState","_useState2","debouncedValue","setDebouncedValue","useEffect","handler","setTimeout","clearTimeout","useDebounce","stateToSendToStreamlit","stC","enableRetinaScaling","shouldSendToStreamlit","loadFromJSON","canvas","data","getContext","toDataURL","Streamlit","setComponentValue","getWidth","getHeight","raw","toObject","sendDataToStreamlit","id","canvasWidth","canvasHeight","NO_ACTION","shouldReloadCanvas","forceSendToStreamlit","RELOAD_CANVAS","SEND_TO_STREAMLIT","RELOAD_AND_SEND_TO_STREAMLIT","canvasStateReducer","state","action","type","isEmpty","currentState","history","undoStack","redoStack","_objectSpread","initialState","isEqual","undoOverHistoryMaxCount","length","_toConsumableArray","slice","Error","isUndoEmpty","CanvasStateContext","createContext","CanvasStateProvider","children","_useReducer","useReducer","_useReducer2","canvasState","dispatch","saveState","useCallback","redo","forceStreamlitUpdate","resetState","Provider","FabricTool","_createClass","_classCallCheck","_canvas","this","CircleTool","_FabricTool","_inherits","_super","_createSuper","_this","_len","arguments","args","Array","_key","call","apply","isMouseDown","fillColor","strokeWidth","strokeColor","currentCircle","Circle","currentStartX","currentStartY","_minRadius","linearDistance","point1","point2","xs","x","ys","y","Math","sqrt","_this2","isDrawingMode","selection","forEachObject","o","selectable","evented","on","onMouseDown","onMouseMove","onMouseUp","onMouseOut","off","_clicked","pointer","getPointer","originX","originY","stroke","fill","radius","add","_radius","set","max","angle","atan2","PI","setCoords","renderAll","FreedrawTool","freeDrawingBrush","color","LineTool","currentLine","Line","points","x2","y2","remove","PolygonTool","startCircle","currentPath","Path","_pathString","onMouseDoubleClick","_start","i","_last_pt_idx","lastIndexOf","RectTool","currentRect","Rect","_minLength","transparentCorners","strokeUniform","noScaleCache","abs","_width","_height","TransformTool","handleDoubleClick","getActiveObject","PointTool","displayRadius","tools","circle","freedraw","line","polygon","rect","transform","point","withStreamlitConnection","backgroundColor","backgroundImageURL","realtimeUpdateStreamlit","drawingMode","initialDrawing","displayToolbar","setCanvas","stopContextMenu","fireRightClick","StaticCanvas","backgroundCanvas","setBackgroundCanvas","_useCanvasState","useContext","_useCanvasState$canva","_useCanvasState$canva2","c","imgC","setFrameHeight","_getStreamlitBaseUrl","bgImage","Image","onload","drawImage","baseUrl","URLSearchParams","window","location","search","get","URL","origin","_unused","getStreamlitBaseUrl","cleanupToolEvents","configureCanvas","toJSON","visibility","border","ReactDOM","render","StrictMode","DrawableCanvas","document","getElementById"],"mappings":"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","file":"static/js/main.80185090.chunk.js","sourcesContent":["// extracted by mini-css-extract-plugin\nmodule.exports = {\"enabled\":\"CanvasToolbar_enabled__2bOtL\",\"disabled\":\"CanvasToolbar_disabled__T9sX8\",\"invertx\":\"CanvasToolbar_invertx__2gc2O\"};","export default \"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAwwAAAMMBnc7+MwAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAEFSURBVEiJ7dSxLkRBFMbx31BIlkQlHoCap5BQLAXvQafV6DyLRLYSdkWv0dBQ0NAKkUhkj2bEzc3udW9xE5E9yVfNd85/5pyZSRGhzZhqtfoE8DcAKaVOqwD0mkBSSnNNAAmBAboR8V4qtoguVrNWMI9n3Gad4SQqHlRk9dHJvmns4qWwXqUrbESEspSMfazhekyhN9zhc8z6KWarAKN0jm0sI+WkmdyuPTyV/JdFSBXgATujjl3aYQf7+CjkXhTaPRYw+DbVETZLkMM6Leo3hGxhmHNfsVBnBk0hx4XcozqARpA8/GG+bQcJ6+rFTUQ81jGmlJYi4p6fa9da/IPvegL4Lb4A0uc9nRaYXwcAAAAASUVORK5CYII=\"","import React from \"react\"\n\nimport styles from \"./CanvasToolbar.module.css\"\n\nimport bin from \"../img/bin.png\"\nimport undo from \"../img/undo.png\"\nimport download from \"../img/download.png\"\n\ninterface SquareIconProps {\n imgUrl: string\n altText: string\n invertX?: boolean\n size: number\n enabled: boolean\n clickCallback: () => void\n}\n\nconst SquareIcon = ({\n imgUrl,\n altText,\n invertX,\n size,\n enabled,\n clickCallback,\n}: SquareIconProps) => (\n <img\n src={imgUrl}\n className={`\n ${enabled ? styles.enabled : styles.disabled} ${\n invertX ? \"\" : styles.invertx\n }\n `}\n alt={altText}\n title={altText}\n height={`${size}px`}\n width={`${size}px`}\n onClick={clickCallback}\n />\n)\nSquareIcon.defaultProps = {\n invertX: false,\n}\n\ninterface CanvasToolbarProps {\n topPosition: number\n leftPosition: number\n canUndo: boolean\n canRedo: boolean\n downloadCallback: () => void\n undoCallback: () => void\n redoCallback: () => void\n resetCallback: () => void\n}\n\nconst CanvasToolbar = ({\n topPosition,\n leftPosition,\n canUndo,\n canRedo,\n downloadCallback,\n undoCallback,\n redoCallback,\n resetCallback,\n}: CanvasToolbarProps) => {\n const GAP_BETWEEN_ICONS = 4\n const ICON_SIZE = 24\n\n const iconElements = [\n {\n imgUrl: download,\n altText: \"Send to Streamlit\",\n invertX: false,\n enabled: true,\n clickCallback: downloadCallback,\n },\n {\n imgUrl: undo,\n altText: \"Undo\",\n invertX: true,\n enabled: canUndo,\n clickCallback: canUndo ? undoCallback : () => {},\n },\n {\n imgUrl: undo,\n altText: \"Redo\",\n invertX: false,\n enabled: canRedo,\n clickCallback: canRedo ? redoCallback : () => {},\n },\n {\n imgUrl: bin,\n altText: \"Reset canvas & history\",\n invertX: false,\n enabled: true,\n clickCallback: resetCallback,\n },\n ]\n\n return (\n <div\n style={{\n position: \"absolute\",\n top: topPosition + 4,\n left: 0,\n display: \"flex\",\n gap: GAP_BETWEEN_ICONS,\n zIndex: 20,\n }}\n >\n {iconElements.map((e) => (\n <SquareIcon\n key={e.altText}\n imgUrl={e.imgUrl}\n altText={e.altText}\n invertX={e.invertX}\n size={ICON_SIZE}\n enabled={e.enabled}\n clickCallback={e.clickCallback}\n />\n ))}\n </div>\n )\n}\n\nexport default CanvasToolbar\n","export default \"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAsQAAALEBxi1JjQAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAEYSURBVEiJ7dS9SgNBFMXxX0y0NNpLqjQiKRRETON7aBMfwLfxDcRGC8HOTm21s7RIYZdniGiRO+6y5mNXVxD0wMBw58z532Fnh1+kFq5jNH8C0MFbjE7ZTUsVAEsz5rUBvqR/wB8CNLFeY+5aZH4ArjDCXsHYNv+vbWK1UNuNrMs8oGfyFGzmjDthvA9QUe1YG4U3aQvL2M4DpqkRHfZxU4C0o9aPxhpzcsDQ5I0ZFOpHGMfas+wtSvNxePIaxNpw0QngHIcR1M3Vu3jFcXhmqsw1vZCdJCmFny3a3CoBSBAm3TbKhlcBJEj6Vo9lN1UBwENF/yfAAVaqhhS0P614J7uCdY1bsh+kh1NsfLP7pBec4KmmvNl6B0BuQt0zCQ0xAAAAAElFTkSuQmCC\"","export default \"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAAhQAAAIUB4uz/wQAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAAHUSURBVEiJtda9ahRRFAfw3xHFJCabFEkawcYiYKMWVmohBHwFOwsfQLCxthOENHZqKxZG8DHSxcJC0Qcw7AqSNSoGci3mznp3nP0K8cBlZs7X/5z//RopJeMGlrGL1Bi7WJ4Uf9pk2cQVPMDPrJvHVra9GRc8BBARS7iKU4X6cn5+wvf8vljbIuJr4XuEdyml/YGmoGIdX/xLxayji/U2iu5iJXfwa1zbY2QOOznXE4YpuoE93D5m8lr2cLMN4BWu4TF+4HDGxIEOeng90DaW5BkVj/fyd6dhP4u5hq6Tnxdz7GZpL1eLlNIhvmEtq7Yj4mHhsoWng5Ir23b+rGO6Zc62fdAtnFewUdjOqyaylo3sMxJgqIMsvcJ5X8XrKFlCvwHQmwRQdjArwH5K6fc0AKvHAFjVoGcUwCwUdbKPHNNrOpw0RVN10MVCRCz8T4A6oI/FiIiTBKh5XFN1EDnRkETEnGrnH2sOSoC60rbqoR8R8zg3bQe102oB0DYPAwB/l/VkgJTSgeo+KDtoA6h1fSN2Me1nUV3JOj7iOT5k/csi5jNe4D2uj+og8lE7rIx4hjt4hIMRRZRyX7UYLqWUjoYsI35VLuCt6tKZ5h7ewa22XH8AgjMTispa6ucAAAAASUVORK5CYII=\"","import React, { useEffect, useState } from \"react\"\nimport { Streamlit } from \"streamlit-component-lib\"\nimport { fabric } from \"fabric\"\n\nconst DELAY_DEBOUNCE = 200\n\n/**\n * Download image and JSON data from canvas to send back to Streamlit\n */\nconst sendDataToStreamlit = (canvas: fabric.Canvas): void => {\n const data = canvas\n .getContext()\n .canvas.toDataURL()\n Streamlit.setComponentValue({\n data: data,\n width: canvas.getWidth(),\n height: canvas.getHeight(),\n raw: canvas.toObject(),\n })\n}\n\n/**\n * This hook allows you to debounce any fast changing value.\n * The debounced value will only reflect the latest value when the useDebounce hook has not been called for the specified time period.\n * When used in conjunction with useEffect, you can easily ensure that expensive operations like API calls are not executed too frequently.\n * https://usehooks.com/useDebounce/\n * @param value value to debounce\n * @param delay delay of debounce in ms\n */\nconst useDebounce = (value: any, delay: number) => {\n const [debouncedValue, setDebouncedValue] = useState(value)\n\n useEffect(\n () => {\n // Update debounced value after delay\n const handler = setTimeout(() => {\n setDebouncedValue(value)\n }, delay)\n\n // Cancel the timeout if value changes (also on delay change or unmount)\n // This is how we prevent debounced value from updating if value is changed ...\n // .. within the delay period. Timeout gets cleared and restarted.\n return () => {\n clearTimeout(handler)\n }\n },\n [value, delay] // Only re-call effect if value or delay changes\n )\n return debouncedValue\n}\n\ninterface UpdateStreamlitProps {\n shouldSendToStreamlit: boolean\n stateToSendToStreamlit: Object\n canvasWidth: number\n canvasHeight: number\n}\n\n/**\n * Canvas whose sole purpose is to draw current state\n * to send image data to Streamlit.\n * Put it in the background or make it invisible!\n */\nconst UpdateStreamlit = (props: UpdateStreamlitProps) => {\n const [stCanvas, setStCanvas] = useState(new fabric.Canvas(\"\"))\n\n // Debounce fast changing canvas states\n // Especially when drawing lines and circles which continuously render while drawing\n const debouncedStateToSend = useDebounce(\n props.stateToSendToStreamlit,\n DELAY_DEBOUNCE\n )\n\n // Initialize canvas\n useEffect(() => {\n const stC = new fabric.Canvas(\"canvas-to-streamlit\", {\n enableRetinaScaling: false,\n })\n setStCanvas(stC)\n }, [])\n\n // Load state to canvas, then send content to Streamlit\n useEffect(() => {\n if (debouncedStateToSend && props.shouldSendToStreamlit) {\n stCanvas.loadFromJSON(debouncedStateToSend, () => {\n sendDataToStreamlit(stCanvas)\n })\n }\n }, [stCanvas, props.shouldSendToStreamlit, debouncedStateToSend])\n\n return (\n <canvas\n id=\"canvas-to-streamlit\"\n width={props.canvasWidth}\n height={props.canvasHeight}\n />\n )\n}\n\nexport default UpdateStreamlit\n","import React, {\n createContext,\n useReducer,\n useContext,\n useCallback,\n} from \"react\"\nimport { isEmpty, isEqual } from \"lodash\"\n\nconst HISTORY_MAX_COUNT = 100\n\ninterface CanvasHistory {\n undoStack: Object[] // store previous canvas states\n redoStack: Object[] // store undone canvas states\n}\n\ninterface CanvasAction {\n shouldReloadCanvas: boolean // reload currentState into app canvas, on undo/redo\n forceSendToStreamlit: boolean // send currentState back to Streamlit\n}\n\nconst NO_ACTION: CanvasAction = {\n shouldReloadCanvas: false,\n forceSendToStreamlit: false,\n}\n\nconst RELOAD_CANVAS: CanvasAction = {\n shouldReloadCanvas: true,\n forceSendToStreamlit: false,\n}\n\nconst SEND_TO_STREAMLIT: CanvasAction = {\n shouldReloadCanvas: false,\n forceSendToStreamlit: true,\n}\n\nconst RELOAD_AND_SEND_TO_STREAMLIT: CanvasAction = {\n shouldReloadCanvas: true,\n forceSendToStreamlit: true,\n}\n\ninterface CanvasState {\n history: CanvasHistory\n action: CanvasAction\n initialState: Object // first currentState for app\n currentState: Object // current canvas state as canvas.toJSON()\n}\n\ninterface Action {\n type: \"save\" | \"undo\" | \"redo\" | \"reset\" | \"forceSendToStreamlit\"\n state?: Object\n}\n\n/**\n * Reducer takes 5 actions: save, undo, redo, reset, forceSendToStreamlit\n *\n * On reset, clear everything, set initial and current state to cleared canvas\n *\n * On save:\n * - First, if there is no initial state, set it to current\n * Since we don't reset history on component initialization\n * As backgroundColor/image are applied after component init\n * and wouldn't be stored in initial state\n * - If the sent state is same as current state, then nothing has changed so don't save\n * - Clear redo stack\n * - Push current state to undo stack, delete oldest if necessary\n * - Set new current state\n *\n * On undo:\n * - Push state to redoStack if it's not the initial\n * - Pop state from undoStack into current state\n *\n * On redo:\n * - Pop state from redoStack into current state\n *\n * For undo/redo/reset, set shouldReloadCanvas to inject currentState into user facing canvas\n */\nconst canvasStateReducer = (\n state: CanvasState,\n action: Action\n): CanvasState => {\n switch (action.type) {\n case \"save\":\n if (!action.state) throw new Error(\"No action state to save\")\n else if (isEmpty(state.currentState)) {\n return {\n history: {\n undoStack: [],\n redoStack: [],\n },\n action: { ...NO_ACTION },\n initialState: action.state,\n currentState: action.state,\n }\n } else if (isEqual(action.state, state.currentState))\n return {\n history: { ...state.history },\n action: { ...NO_ACTION },\n initialState: state.initialState,\n currentState: state.currentState,\n }\n else {\n const undoOverHistoryMaxCount =\n state.history.undoStack.length >= HISTORY_MAX_COUNT\n return {\n history: {\n undoStack: [\n ...state.history.undoStack.slice(undoOverHistoryMaxCount ? 1 : 0),\n state.currentState,\n ],\n redoStack: [],\n },\n action: { ...NO_ACTION },\n initialState:\n state.initialState == null\n ? state.currentState\n : state.initialState,\n currentState: action.state,\n }\n }\n case \"undo\":\n if (\n isEmpty(state.currentState) ||\n isEqual(state.initialState, state.currentState)\n ) {\n return {\n history: { ...state.history },\n action: { ...NO_ACTION },\n initialState: state.initialState,\n currentState: state.currentState,\n }\n } else {\n const isUndoEmpty = state.history.undoStack.length === 0\n return {\n history: {\n undoStack: state.history.undoStack.slice(0, -1),\n redoStack: [...state.history.redoStack, state.currentState],\n },\n action: { ...RELOAD_CANVAS },\n initialState: state.initialState,\n currentState: isUndoEmpty\n ? state.currentState\n : state.history.undoStack[state.history.undoStack.length - 1],\n }\n }\n case \"redo\":\n if (state.history.redoStack.length > 0) {\n // TODO: test currentState empty too ?\n return {\n history: {\n undoStack: [...state.history.undoStack, state.currentState],\n redoStack: state.history.redoStack.slice(0, -1),\n },\n action: { ...RELOAD_CANVAS },\n initialState: state.initialState,\n currentState:\n state.history.redoStack[state.history.redoStack.length - 1],\n }\n } else {\n return {\n history: { ...state.history },\n action: { ...NO_ACTION },\n initialState: state.initialState,\n currentState: state.currentState,\n }\n }\n case \"reset\":\n if (!action.state) throw new Error(\"No action state to store in reset\")\n return {\n history: {\n undoStack: [],\n redoStack: [],\n },\n action: { ...RELOAD_AND_SEND_TO_STREAMLIT },\n initialState: action.state,\n currentState: action.state,\n }\n case \"forceSendToStreamlit\":\n return {\n history: { ...state.history },\n action: { ...SEND_TO_STREAMLIT },\n initialState: state.initialState,\n currentState: state.currentState,\n }\n default:\n throw new Error(\"TS should protect from this\")\n }\n}\n\nconst initialState: CanvasState = {\n history: {\n undoStack: [],\n redoStack: [],\n },\n action: {\n forceSendToStreamlit: false,\n shouldReloadCanvas: false,\n },\n initialState: {},\n currentState: {},\n}\n\ninterface CanvasStateContextProps {\n canvasState: CanvasState\n saveState: (state: Object) => void\n undo: () => void\n redo: () => void\n forceStreamlitUpdate: () => void\n canUndo: boolean\n canRedo: boolean\n resetState: (state: Object) => void\n}\n\nconst CanvasStateContext = createContext<CanvasStateContextProps>(\n {} as CanvasStateContextProps\n)\n\nexport const CanvasStateProvider = ({\n children,\n}: React.PropsWithChildren<{}>) => {\n const [canvasState, dispatch] = useReducer(canvasStateReducer, initialState)\n\n // Setup our callback functions\n // We memoize with useCallback to prevent unnecessary re-renders\n const saveState = useCallback(\n (state) => dispatch({ type: \"save\", state: state }),\n [dispatch]\n )\n const undo = useCallback(() => dispatch({ type: \"undo\" }), [dispatch])\n const redo = useCallback(() => dispatch({ type: \"redo\" }), [dispatch])\n const forceStreamlitUpdate = useCallback(\n () => dispatch({ type: \"forceSendToStreamlit\" }),\n [dispatch]\n )\n const resetState = useCallback(\n (state) => dispatch({ type: \"reset\", state: state }),\n [dispatch]\n )\n\n const canUndo = canvasState.history.undoStack.length !== 0\n const canRedo = canvasState.history.redoStack.length !== 0\n\n return (\n <CanvasStateContext.Provider\n value={{\n canvasState,\n saveState,\n undo,\n redo,\n canUndo,\n canRedo,\n forceStreamlitUpdate,\n resetState,\n }}\n >\n {children}\n </CanvasStateContext.Provider>\n )\n}\n\n/**\n * Hook to get data out of context\n */\nexport const useCanvasState = () => {\n return useContext(CanvasStateContext)\n}\n","import { fabric } from \"fabric\"\n\nexport interface ConfigureCanvasProps {\n fillColor: string\n strokeWidth: number\n strokeColor: string\n displayRadius: number\n}\n\n/**\n * Base class for any fabric tool that configures and draws on canvas\n */\nabstract class FabricTool {\n protected _canvas: fabric.Canvas\n\n /**\n * Pass Fabric canvas by reference so tools can configure it\n */\n constructor(canvas: fabric.Canvas) {\n this._canvas = canvas\n }\n\n /**\n * Configure canvas and return a callback to clean eventListeners\n * @param args\n */\n abstract configureCanvas(args: ConfigureCanvasProps): () => void\n}\n\nexport default FabricTool\n","import { fabric } from \"fabric\"\nimport FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass CircleTool extends FabricTool {\n isMouseDown: boolean = false\n fillColor: string = \"#ffffff\"\n strokeWidth: number = 10\n strokeColor: string = \"#ffffff\"\n currentCircle: fabric.Circle = new fabric.Circle()\n currentStartX: number = 0\n currentStartY: number = 0\n _minRadius: number = 10\n\n configureCanvas({\n strokeWidth,\n strokeColor,\n fillColor,\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = false\n this._canvas.selection = false\n this._canvas.forEachObject((o) => (o.selectable = o.evented = false))\n\n this.strokeWidth = strokeWidth\n this.strokeColor = strokeColor\n this.fillColor = fillColor\n this._minRadius = strokeWidth\n\n this._canvas.on(\"mouse:down\", (e: any) => this.onMouseDown(e))\n this._canvas.on(\"mouse:move\", (e: any) => this.onMouseMove(e))\n this._canvas.on(\"mouse:up\", (e: any) => this.onMouseUp(e))\n this._canvas.on(\"mouse:out\", (e: any) => this.onMouseOut(e))\n return () => {\n this._canvas.off(\"mouse:down\")\n this._canvas.off(\"mouse:move\")\n this._canvas.off(\"mouse:up\")\n this._canvas.off(\"mouse:out\")\n }\n }\n\n onMouseDown(o: any) {\n let canvas = this._canvas\n let _clicked = o.e[\"button\"]\n this.isMouseDown = true\n let pointer = canvas.getPointer(o.e)\n this.currentStartX = pointer.x\n this.currentStartY = pointer.y\n this.currentCircle = new fabric.Circle({\n left: this.currentStartX,\n top: this.currentStartY,\n originX: \"left\",\n originY: \"center\",\n strokeWidth: this.strokeWidth,\n stroke: this.strokeColor,\n fill: this.fillColor,\n selectable: false,\n evented: false,\n radius: this._minRadius,\n })\n if (_clicked === 0) {\n canvas.add(this.currentCircle)\n }\n }\n\n onMouseMove(o: any) {\n if (!this.isMouseDown) return\n let canvas = this._canvas\n let pointer = canvas.getPointer(o.e)\n let _radius =\n this.linearDistance(\n { x: this.currentStartX, y: this.currentStartY },\n { x: pointer.x, y: pointer.y }\n ) / 2\n this.currentCircle.set({\n radius: Math.max(_radius, this._minRadius),\n angle:\n (Math.atan2(\n pointer.y - this.currentStartY,\n pointer.x - this.currentStartX\n ) *\n 180) /\n Math.PI,\n })\n this.currentCircle.setCoords()\n canvas.renderAll()\n }\n\n onMouseUp(o: any) {\n this.isMouseDown = false\n }\n\n onMouseOut(o: any) {\n this.isMouseDown = false\n }\n\n /**\n * Calculate the distance of two x,y points\n *\n * @param point1 an object with x,y attributes representing the start point\n * @param point2 an object with x,y attributes representing the end point\n *\n * @returns {number}\n */\n linearDistance = (point1: any, point2: any) => {\n let xs = point2.x - point1.x\n let ys = point2.y - point1.y\n return Math.sqrt(xs * xs + ys * ys)\n }\n}\n\nexport default CircleTool\n","import FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass FreedrawTool extends FabricTool {\n configureCanvas({\n strokeWidth,\n strokeColor,\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = true\n this._canvas.freeDrawingBrush.width = strokeWidth\n this._canvas.freeDrawingBrush.color = strokeColor\n return () => {}\n }\n}\n\nexport default FreedrawTool\n","import { fabric } from \"fabric\"\nimport FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass LineTool extends FabricTool {\n isMouseDown: boolean = false\n strokeWidth: number = 10\n strokeColor: string = \"#ffffff\"\n currentLine: fabric.Line = new fabric.Line()\n\n configureCanvas({\n strokeWidth,\n strokeColor,\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = false\n this._canvas.selection = false\n this._canvas.forEachObject((o) => (o.selectable = o.evented = false))\n\n this.strokeWidth = strokeWidth\n this.strokeColor = strokeColor\n\n this._canvas.on(\"mouse:down\", (e: any) => this.onMouseDown(e))\n this._canvas.on(\"mouse:move\", (e: any) => this.onMouseMove(e))\n this._canvas.on(\"mouse:up\", (e: any) => this.onMouseUp(e))\n this._canvas.on(\"mouse:out\", (e: any) => this.onMouseOut(e))\n return () => {\n this._canvas.off(\"mouse:down\")\n this._canvas.off(\"mouse:move\")\n this._canvas.off(\"mouse:up\")\n this._canvas.off(\"mouse:out\")\n }\n }\n\n onMouseDown(o: any) {\n let canvas = this._canvas\n let _clicked = o.e[\"button\"]\n this.isMouseDown = true\n var pointer = canvas.getPointer(o.e)\n var points = [pointer.x, pointer.y, pointer.x, pointer.y]\n this.currentLine = new fabric.Line(points, {\n strokeWidth: this.strokeWidth,\n fill: this.strokeColor,\n stroke: this.strokeColor,\n originX: \"center\",\n originY: \"center\",\n selectable: false,\n evented: false,\n })\n if (_clicked === 0) {\n canvas.add(this.currentLine)\n }\n }\n\n onMouseMove(o: any) {\n if (!this.isMouseDown) return\n let canvas = this._canvas\n var pointer = canvas.getPointer(o.e)\n this.currentLine.set({ x2: pointer.x, y2: pointer.y })\n this.currentLine.setCoords()\n canvas.renderAll()\n }\n\n onMouseUp(o: any) {\n this.isMouseDown = false\n let canvas = this._canvas\n if (this.currentLine.width === 0 && this.currentLine.height === 0) {\n canvas.remove(this.currentLine)\n }\n }\n\n onMouseOut(o: any) {\n this.isMouseDown = false\n }\n}\n\nexport default LineTool\n","import { fabric } from \"fabric\"\nimport FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass PolygonTool extends FabricTool {\n isMouseDown: boolean = false\n fillColor: string = \"#ffffff\"\n strokeWidth: number = 10\n strokeColor: string = \"#ffffff\"\n startCircle: fabric.Circle = new fabric.Circle()\n currentLine: fabric.Line = new fabric.Line()\n currentPath: fabric.Path = new fabric.Path()\n _pathString: string = \"M \"\n\n configureCanvas({\n strokeWidth,\n strokeColor,\n fillColor,\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = false\n this._canvas.selection = false\n this._canvas.forEachObject((o) => (o.selectable = o.evented = false))\n\n this.strokeWidth = strokeWidth\n this.strokeColor = strokeColor\n this.fillColor = fillColor\n\n this._canvas.on(\"mouse:down\", (e: any) => this.onMouseDown(e))\n this._canvas.on(\"mouse:move\", (e: any) => this.onMouseMove(e))\n this._canvas.on(\"mouse:up\", (e: any) => this.onMouseUp(e))\n this._canvas.on(\"mouse:out\", (e: any) => this.onMouseOut(e))\n this._canvas.on(\"mouse:dblclick\", (e: any) => this.onMouseDoubleClick(e))\n return () => {\n this._canvas.off(\"mouse:down\")\n this._canvas.off(\"mouse:move\")\n this._canvas.off(\"mouse:up\")\n this._canvas.off(\"mouse:out\")\n this._canvas.off(\"mouse:dblclick\")\n }\n }\n\n onMouseDown(o: any) {\n let canvas = this._canvas\n let _clicked = o.e[\"button\"]\n let _start = false\n if (this._pathString === \"M \") {\n _start = true\n }\n\n this.isMouseDown = true\n var pointer = canvas.getPointer(o.e)\n\n var points = [pointer.x, pointer.y, pointer.x, pointer.y]\n canvas.remove(this.currentLine)\n this.currentLine = new fabric.Line(points, {\n strokeWidth: this.strokeWidth,\n fill: this.strokeColor,\n stroke: this.strokeColor,\n originX: \"center\",\n originY: \"center\",\n selectable: false,\n evented: false,\n })\n if (_clicked === 0) {\n canvas.add(this.currentLine)\n }\n\n if (_start && _clicked === 0) {\n // Initialize pathString\n this._pathString += `${pointer.x} ${pointer.y} `\n this.startCircle = new fabric.Circle({\n left: pointer.x,\n top: pointer.y,\n originX: \"center\",\n originY: \"center\",\n strokeWidth: this.strokeWidth,\n stroke: this.strokeColor,\n fill: this.strokeColor,\n selectable: false,\n evented: false,\n radius: this.strokeWidth,\n })\n canvas.add(this.startCircle)\n\n _start = false\n } else {\n canvas.remove(this.currentPath)\n if (_clicked === 0) {\n // Update pathString\n this._pathString += `L ${pointer.x} ${pointer.y} `\n }\n if (_clicked === 2) {\n // Close pathString\n this._pathString += \"z\"\n canvas.remove(this.startCircle)\n }\n }\n this.currentPath = new fabric.Path(this._pathString, {\n strokeWidth: this.strokeWidth,\n fill: this.fillColor,\n stroke: this.strokeColor,\n originX: \"center\",\n originY: \"center\",\n selectable: false,\n evented: false,\n })\n if (this.currentPath.width !== 0 && this.currentPath.height !== 0) {\n canvas.add(this.currentPath)\n }\n if (_clicked === 2) {\n this._pathString = \"M \"\n }\n }\n\n onMouseMove(o: any) {\n if (!this.isMouseDown) return\n let canvas = this._canvas\n var pointer = canvas.getPointer(o.e)\n this.currentLine.set({ x2: pointer.x, y2: pointer.y })\n this.currentLine.setCoords()\n canvas.renderAll()\n }\n\n onMouseUp(o: any) {\n this.isMouseDown = true\n }\n\n onMouseOut(o: any) {\n this.isMouseDown = false\n }\n\n onMouseDoubleClick(o: any) {\n let canvas = this._canvas\n // Double click adds two more points at the end, so we have to move back twice more...\n for (let i = 0; i < 3; i++) {\n let _last_pt_idx = this._pathString.lastIndexOf(\"L\")\n if (_last_pt_idx === -1) {\n this._pathString = \"M \"\n canvas.remove(this.startCircle)\n } else {\n this._pathString = this._pathString.slice(0, _last_pt_idx)\n }\n }\n\n canvas.remove(this.currentLine)\n canvas.remove(this.currentPath)\n this.currentPath = new fabric.Path(this._pathString, {\n strokeWidth: this.strokeWidth,\n fill: this.fillColor,\n stroke: this.strokeColor,\n originX: \"center\",\n originY: \"center\",\n selectable: false,\n evented: false,\n })\n canvas.add(this.currentPath)\n }\n}\nexport default PolygonTool\n","import { fabric } from \"fabric\"\nimport FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass RectTool extends FabricTool {\n isMouseDown: boolean = false\n fillColor: string = \"#ffffff\"\n strokeWidth: number = 10\n strokeColor: string = \"#ffffff\"\n currentRect: fabric.Rect = new fabric.Rect()\n currentStartX: number = 0\n currentStartY: number = 0\n _minLength: number = 10\n\n configureCanvas({\n strokeWidth,\n strokeColor,\n fillColor,\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = false\n this._canvas.selection = false\n this._canvas.forEachObject((o) => (o.selectable = o.evented = false))\n\n this.strokeWidth = strokeWidth\n this.strokeColor = strokeColor\n this.fillColor = fillColor\n this._minLength = strokeWidth\n\n this._canvas.on(\"mouse:down\", (e: any) => this.onMouseDown(e))\n this._canvas.on(\"mouse:move\", (e: any) => this.onMouseMove(e))\n this._canvas.on(\"mouse:up\", (e: any) => this.onMouseUp(e))\n this._canvas.on(\"mouse:out\", (e: any) => this.onMouseOut(e))\n return () => {\n this._canvas.off(\"mouse:down\")\n this._canvas.off(\"mouse:move\")\n this._canvas.off(\"mouse:up\")\n this._canvas.off(\"mouse:out\")\n }\n }\n\n onMouseDown(o: any) {\n let canvas = this._canvas\n let _clicked = o.e[\"button\"]\n this.isMouseDown = true\n let pointer = canvas.getPointer(o.e)\n this.currentStartX = pointer.x\n this.currentStartY = pointer.y\n this.currentRect = new fabric.Rect({\n left: this.currentStartX,\n top: this.currentStartY,\n originX: \"left\",\n originY: \"top\",\n width: this._minLength,\n height: this._minLength,\n stroke: this.strokeColor,\n strokeWidth: this.strokeWidth,\n fill: this.fillColor,\n transparentCorners: false,\n selectable: false,\n evented: false,\n strokeUniform: true,\n noScaleCache: false,\n angle: 0,\n })\n if (_clicked === 0) {\n canvas.add(this.currentRect)\n }\n }\n\n onMouseMove(o: any) {\n if (!this.isMouseDown) return\n let canvas = this._canvas\n let pointer = canvas.getPointer(o.e)\n if (this.currentStartX > pointer.x) {\n this.currentRect.set({ left: Math.abs(pointer.x) })\n }\n if (this.currentStartY > pointer.y) {\n this.currentRect.set({ top: Math.abs(pointer.y) })\n }\n let _width = Math.abs(this.currentStartX - pointer.x)\n let _height = Math.abs(this.currentStartY - pointer.y)\n this.currentRect.set({\n width: Math.max(_width, this._minLength * 2),\n height: Math.max(_height, this._minLength * 2),\n })\n this.currentRect.setCoords()\n canvas.renderAll()\n }\n\n onMouseUp(o: any) {\n this.isMouseDown = false\n }\n\n onMouseOut(o: any) {\n this.isMouseDown = false\n }\n}\n\nexport default RectTool\n","import FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass TransformTool extends FabricTool {\n configureCanvas(args: ConfigureCanvasProps): () => void {\n let canvas = this._canvas\n canvas.isDrawingMode = false\n canvas.selection = true\n canvas.forEachObject((o) => (o.selectable = o.evented = true))\n\n // instead of looking for target of double click,\n // assume double click on object clears the selected object\n const handleDoubleClick = () => {\n canvas.remove(canvas.getActiveObject())\n }\n\n canvas.on(\"mouse:dblclick\", handleDoubleClick)\n return () => {\n canvas.off(\"mouse:dblclick\", handleDoubleClick)\n }\n }\n}\n\nexport default TransformTool\n","import { fabric } from \"fabric\"\nimport FabricTool, { ConfigureCanvasProps } from \"./fabrictool\"\n\nclass PointTool extends FabricTool {\n isMouseDown: boolean = false\n fillColor: string = \"#ffffff\"\n strokeWidth: number = 10\n strokeColor: string = \"#ffffff\"\n currentCircle: fabric.Circle = new fabric.Circle()\n currentStartX: number = 0\n currentStartY: number = 0\n displayRadius: number = 1\n\n configureCanvas({\n strokeWidth,\n strokeColor,\n fillColor,\n displayRadius\n }: ConfigureCanvasProps): () => void {\n this._canvas.isDrawingMode = false\n this._canvas.selection = false\n this._canvas.forEachObject((o) => (o.selectable = o.evented = false))\n\n this.strokeWidth = strokeWidth\n this.strokeColor = strokeColor\n this.fillColor = fillColor\n this.displayRadius = displayRadius\n\n this._canvas.on(\"mouse:down\", (e: any) => this.onMouseDown(e))\n this._canvas.on(\"mouse:move\", (e: any) => this.onMouseMove(e))\n this._canvas.on(\"mouse:up\", (e: any) => this.onMouseUp(e))\n this._canvas.on(\"mouse:out\", (e: any) => this.onMouseOut(e))\n return () => {\n this._canvas.off(\"mouse:down\")\n this._canvas.off(\"mouse:move\")\n this._canvas.off(\"mouse:up\")\n this._canvas.off(\"mouse:out\")\n }\n }\n\n onMouseDown(o: any) {\n let canvas = this._canvas\n let _clicked = o.e[\"button\"]\n this.isMouseDown = true\n let pointer = canvas.getPointer(o.e)\n this.currentStartX = pointer.x - (this.displayRadius + this.strokeWidth / 2.)\n this.currentStartY = pointer.y //- (this._minRadius + this.strokeWidth)\n this.currentCircle = new fabric.Circle({\n left: this.currentStartX,\n top: this.currentStartY,\n originX: \"left\",\n originY: \"center\",\n strokeWidth: this.strokeWidth,\n stroke: this.strokeColor,\n fill: this.fillColor,\n selectable: false,\n evented: false,\n radius: this.displayRadius,\n })\n if (_clicked === 0) {\n canvas.add(this.currentCircle)\n }\n }\n\n onMouseMove(o: any) {\n if (!this.isMouseDown) return\n let canvas = this._canvas\n this.currentCircle.setCoords()\n canvas.renderAll()\n }\n\n onMouseUp(o: any) {\n this.isMouseDown = false\n }\n\n onMouseOut(o: any) {\n this.isMouseDown = false\n }\n\n}\n\nexport default PointTool\n","import CircleTool from \"./circle\"\nimport FabricTool from \"./fabrictool\"\nimport FreedrawTool from \"./freedraw\"\nimport LineTool from \"./line\"\nimport PolygonTool from \"./polygon\"\nimport RectTool from \"./rect\"\nimport TransformTool from \"./transform\"\nimport PointTool from \"./point\"\n\n// TODO: Should make TS happy on the Map of selectedTool --> FabricTool\nconst tools: any = {\n circle: CircleTool,\n freedraw: FreedrawTool,\n line: LineTool,\n polygon: PolygonTool,\n rect: RectTool,\n transform: TransformTool,\n point: PointTool\n}\n\nexport { tools, FabricTool }\n","import React, { useEffect, useState } from \"react\"\nimport {\n ComponentProps,\n Streamlit,\n withStreamlitConnection,\n} from \"streamlit-component-lib\"\nimport { fabric } from \"fabric\"\nimport { isEqual } from \"lodash\"\n\nimport CanvasToolbar from \"./components/CanvasToolbar\"\nimport UpdateStreamlit from \"./components/UpdateStreamlit\"\n\nimport { useCanvasState } from \"./DrawableCanvasState\"\nimport { tools, FabricTool } from \"./lib\"\n\nfunction getStreamlitBaseUrl(): string | null {\n const params = new URLSearchParams(window.location.search)\n const baseUrl = params.get(\"streamlitUrl\")\n if (baseUrl == null) {\n return null\n }\n\n try {\n return new URL(baseUrl).origin\n } catch {\n return null\n }\n}\n\n/**\n * Arguments Streamlit receives from the Python side\n */\nexport interface PythonArgs {\n fillColor: string\n strokeWidth: number\n strokeColor: string\n backgroundColor: string\n backgroundImageURL: string\n realtimeUpdateStreamlit: boolean\n canvasWidth: number\n canvasHeight: number\n drawingMode: string\n initialDrawing: Object\n displayToolbar: boolean\n displayRadius: number\n}\n\n/**\n * Define logic for the canvas area\n */\nconst DrawableCanvas = ({ args }: ComponentProps) => {\n const {\n canvasWidth,\n canvasHeight,\n backgroundColor,\n backgroundImageURL,\n realtimeUpdateStreamlit,\n drawingMode,\n fillColor,\n strokeWidth,\n strokeColor,\n displayRadius,\n initialDrawing,\n displayToolbar,\n }: PythonArgs = args\n\n /**\n * State initialization\n */\n const [canvas, setCanvas] = useState(new fabric.Canvas(\"\"))\n canvas.stopContextMenu = true\n canvas.fireRightClick = true\n\n const [backgroundCanvas, setBackgroundCanvas] = useState(\n new fabric.StaticCanvas(\"\")\n )\n const {\n canvasState: {\n action: { shouldReloadCanvas, forceSendToStreamlit },\n currentState,\n initialState,\n },\n saveState,\n undo,\n redo,\n canUndo,\n canRedo,\n forceStreamlitUpdate,\n resetState,\n } = useCanvasState()\n\n /**\n * Initialize canvases on component mount\n * NB: Remount component by changing its key instead of defining deps\n */\n useEffect(() => {\n const c = new fabric.Canvas(\"canvas\", {\n enableRetinaScaling: false,\n })\n const imgC = new fabric.StaticCanvas(\"backgroundimage-canvas\", {\n enableRetinaScaling: false,\n })\n setCanvas(c)\n setBackgroundCanvas(imgC)\n Streamlit.setFrameHeight()\n }, [])\n\n /**\n * Load user drawing into canvas\n * Python-side is in charge of initializing drawing with background color if none provided\n */\n useEffect(() => {\n if (!isEqual(initialState, initialDrawing)) {\n canvas.loadFromJSON(initialDrawing, () => {\n canvas.renderAll()\n resetState(initialDrawing)\n })\n }\n }, [canvas, initialDrawing, initialState, resetState])\n\n /**\n * Update background image\n */\n useEffect(() => {\n if (backgroundImageURL) {\n var bgImage = new Image();\n bgImage.onload = function() {\n backgroundCanvas.getContext().drawImage(bgImage, 0, 0);\n };\n const baseUrl = getStreamlitBaseUrl() ?? \"\"\n bgImage.src = baseUrl + backgroundImageURL\n }\n }, [\n canvas,\n backgroundCanvas,\n canvasHeight,\n canvasWidth,\n backgroundColor,\n backgroundImageURL,\n saveState,\n ])\n\n /**\n * If state changed from undo/redo/reset, update user-facing canvas\n */\n useEffect(() => {\n if (shouldReloadCanvas) {\n canvas.loadFromJSON(currentState, () => {})\n }\n }, [canvas, shouldReloadCanvas, currentState])\n\n /**\n * Update canvas with selected tool\n * PS: add initialDrawing in dependency so user drawing update reinits tool\n */\n useEffect(() => {\n // Update canvas events with selected tool\n const selectedTool = new tools[drawingMode](canvas) as FabricTool\n const cleanupToolEvents = selectedTool.configureCanvas({\n fillColor: fillColor,\n strokeWidth: strokeWidth,\n strokeColor: strokeColor,\n displayRadius: displayRadius\n })\n\n canvas.on(\"mouse:up\", (e: any) => {\n saveState(canvas.toJSON())\n if (e[\"button\"] === 3) {\n forceStreamlitUpdate()\n }\n })\n\n canvas.on(\"mouse:dblclick\", () => {\n saveState(canvas.toJSON())\n })\n\n // Cleanup tool + send data to Streamlit events\n return () => {\n cleanupToolEvents()\n canvas.off(\"mouse:up\")\n canvas.off(\"mouse:dblclick\")\n }\n }, [\n canvas,\n strokeWidth,\n strokeColor,\n displayRadius,\n fillColor,\n drawingMode,\n initialDrawing,\n saveState,\n forceStreamlitUpdate,\n ])\n\n /**\n * Render canvas w/ toolbar\n */\n return (\n <div style={{ position: \"relative\" }}>\n <div\n style={{\n position: \"absolute\",\n top: 0,\n left: 0,\n zIndex: -10,\n visibility: \"hidden\",\n }}\n >\n <UpdateStreamlit\n canvasHeight={canvasHeight}\n canvasWidth={canvasWidth}\n shouldSendToStreamlit={\n realtimeUpdateStreamlit || forceSendToStreamlit\n }\n stateToSendToStreamlit={currentState}\n />\n </div>\n <div\n style={{\n position: \"absolute\",\n top: 0,\n left: 0,\n zIndex: 0,\n }}\n >\n <canvas\n id=\"backgroundimage-canvas\"\n width={canvasWidth}\n height={canvasHeight}\n />\n </div>\n <div\n style={{\n position: \"absolute\",\n top: 0,\n left: 0,\n zIndex: 10,\n }}\n >\n <canvas\n id=\"canvas\"\n width={canvasWidth}\n height={canvasHeight}\n style={{ border: \"lightgrey 1px solid\" }}\n />\n </div>\n {displayToolbar && (\n <CanvasToolbar\n topPosition={canvasHeight}\n leftPosition={canvasWidth}\n canUndo={canUndo}\n canRedo={canRedo}\n downloadCallback={forceStreamlitUpdate}\n undoCallback={undo}\n redoCallback={redo}\n resetCallback={() => {\n resetState(initialState)\n }}\n />\n )}\n </div>\n )\n}\n\nexport default withStreamlitConnection(DrawableCanvas)\n","import React from \"react\"\nimport ReactDOM from \"react-dom\"\nimport DrawableCanvas from \"./DrawableCanvas\"\nimport { CanvasStateProvider } from \"./DrawableCanvasState\"\n\nimport \"./index.css\"\n\nReactDOM.render(\n <React.StrictMode>\n <CanvasStateProvider>\n <DrawableCanvas />\n </CanvasStateProvider>\n </React.StrictMode>,\n document.getElementById(\"root\")\n)\n"],"sourceRoot":""}
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/runtime-main.3def19be.js
ADDED
|
@@ -0,0 +1,2 @@
|
|
|
|
|
|
|
|
|
|
| 1 |
+
!function(e){function r(r){for(var n,a,l=r[0],f=r[1],i=r[2],p=0,s=[];p<l.length;p++)a=l[p],Object.prototype.hasOwnProperty.call(o,a)&&o[a]&&s.push(o[a][0]),o[a]=0;for(n in f)Object.prototype.hasOwnProperty.call(f,n)&&(e[n]=f[n]);for(c&&c(r);s.length;)s.shift()();return u.push.apply(u,i||[]),t()}function t(){for(var e,r=0;r<u.length;r++){for(var t=u[r],n=!0,l=1;l<t.length;l++){var f=t[l];0!==o[f]&&(n=!1)}n&&(u.splice(r--,1),e=a(a.s=t[0]))}return e}var n={},o={1:0},u=[];function a(r){if(n[r])return n[r].exports;var t=n[r]={i:r,l:!1,exports:{}};return e[r].call(t.exports,t,t.exports,a),t.l=!0,t.exports}a.m=e,a.c=n,a.d=function(e,r,t){a.o(e,r)||Object.defineProperty(e,r,{enumerable:!0,get:t})},a.r=function(e){"undefined"!==typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},a.t=function(e,r){if(1&r&&(e=a(e)),8&r)return e;if(4&r&&"object"===typeof e&&e&&e.__esModule)return e;var t=Object.create(null);if(a.r(t),Object.defineProperty(t,"default",{enumerable:!0,value:e}),2&r&&"string"!=typeof e)for(var n in e)a.d(t,n,function(r){return e[r]}.bind(null,n));return t},a.n=function(e){var r=e&&e.__esModule?function(){return e.default}:function(){return e};return a.d(r,"a",r),r},a.o=function(e,r){return Object.prototype.hasOwnProperty.call(e,r)},a.p="./";var l=this.webpackJsonpdrawable_canvas=this.webpackJsonpdrawable_canvas||[],f=l.push.bind(l);l.push=r,l=l.slice();for(var i=0;i<l.length;i++)r(l[i]);var c=f;t()}([]);
|
| 2 |
+
//# sourceMappingURL=runtime-main.3def19be.js.map
|
seg2med_app/streamlit_drawable_canvas/frontend/build/static/js/runtime-main.3def19be.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
|
|
|
|
| 1 |
+
{"version":3,"sources":["../webpack/bootstrap"],"names":["webpackJsonpCallback","data","moduleId","chunkId","chunkIds","moreModules","executeModules","i","resolves","length","Object","prototype","hasOwnProperty","call","installedChunks","push","modules","parentJsonpFunction","shift","deferredModules","apply","checkDeferredModules","result","deferredModule","fulfilled","j","depId","splice","__webpack_require__","s","installedModules","exports","module","l","m","c","d","name","getter","o","defineProperty","enumerable","get","r","Symbol","toStringTag","value","t","mode","__esModule","ns","create","key","bind","n","object","property","p","jsonpArray","this","oldJsonpFunction","slice"],"mappings":"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","file":"static/js/runtime-main.3def19be.js","sourcesContent":[" \t// install a JSONP callback for chunk loading\n \tfunction webpackJsonpCallback(data) {\n \t\tvar chunkIds = data[0];\n \t\tvar moreModules = data[1];\n \t\tvar executeModules = data[2];\n\n \t\t// add \"moreModules\" to the modules object,\n \t\t// then flag all \"chunkIds\" as loaded and fire callback\n \t\tvar moduleId, chunkId, i = 0, resolves = [];\n \t\tfor(;i < chunkIds.length; i++) {\n \t\t\tchunkId = chunkIds[i];\n \t\t\tif(Object.prototype.hasOwnProperty.call(installedChunks, chunkId) && installedChunks[chunkId]) {\n \t\t\t\tresolves.push(installedChunks[chunkId][0]);\n \t\t\t}\n \t\t\tinstalledChunks[chunkId] = 0;\n \t\t}\n \t\tfor(moduleId in moreModules) {\n \t\t\tif(Object.prototype.hasOwnProperty.call(moreModules, moduleId)) {\n \t\t\t\tmodules[moduleId] = moreModules[moduleId];\n \t\t\t}\n \t\t}\n \t\tif(parentJsonpFunction) parentJsonpFunction(data);\n\n \t\twhile(resolves.length) {\n \t\t\tresolves.shift()();\n \t\t}\n\n \t\t// add entry modules from loaded chunk to deferred list\n \t\tdeferredModules.push.apply(deferredModules, executeModules || []);\n\n \t\t// run deferred modules when all chunks ready\n \t\treturn checkDeferredModules();\n \t};\n \tfunction checkDeferredModules() {\n \t\tvar result;\n \t\tfor(var i = 0; i < deferredModules.length; i++) {\n \t\t\tvar deferredModule = deferredModules[i];\n \t\t\tvar fulfilled = true;\n \t\t\tfor(var j = 1; j < deferredModule.length; j++) {\n \t\t\t\tvar depId = deferredModule[j];\n \t\t\t\tif(installedChunks[depId] !== 0) fulfilled = false;\n \t\t\t}\n \t\t\tif(fulfilled) {\n \t\t\t\tdeferredModules.splice(i--, 1);\n \t\t\t\tresult = __webpack_require__(__webpack_require__.s = deferredModule[0]);\n \t\t\t}\n \t\t}\n\n \t\treturn result;\n \t}\n\n \t// The module cache\n \tvar installedModules = {};\n\n \t// object to store loaded and loading chunks\n \t// undefined = chunk not loaded, null = chunk preloaded/prefetched\n \t// Promise = chunk loading, 0 = chunk loaded\n \tvar installedChunks = {\n \t\t1: 0\n \t};\n\n \tvar deferredModules = [];\n\n \t// The require function\n \tfunction __webpack_require__(moduleId) {\n\n \t\t// Check if module is in cache\n \t\tif(installedModules[moduleId]) {\n \t\t\treturn installedModules[moduleId].exports;\n \t\t}\n \t\t// Create a new module (and put it into the cache)\n \t\tvar module = installedModules[moduleId] = {\n \t\t\ti: moduleId,\n \t\t\tl: false,\n \t\t\texports: {}\n \t\t};\n\n \t\t// Execute the module function\n \t\tmodules[moduleId].call(module.exports, module, module.exports, __webpack_require__);\n\n \t\t// Flag the module as loaded\n \t\tmodule.l = true;\n\n \t\t// Return the exports of the module\n \t\treturn module.exports;\n \t}\n\n\n \t// expose the modules object (__webpack_modules__)\n \t__webpack_require__.m = modules;\n\n \t// expose the module cache\n \t__webpack_require__.c = installedModules;\n\n \t// define getter function for harmony exports\n \t__webpack_require__.d = function(exports, name, getter) {\n \t\tif(!__webpack_require__.o(exports, name)) {\n \t\t\tObject.defineProperty(exports, name, { enumerable: true, get: getter });\n \t\t}\n \t};\n\n \t// define __esModule on exports\n \t__webpack_require__.r = function(exports) {\n \t\tif(typeof Symbol !== 'undefined' && Symbol.toStringTag) {\n \t\t\tObject.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });\n \t\t}\n \t\tObject.defineProperty(exports, '__esModule', { value: true });\n \t};\n\n \t// create a fake namespace object\n \t// mode & 1: value is a module id, require it\n \t// mode & 2: merge all properties of value into the ns\n \t// mode & 4: return value when already ns object\n \t// mode & 8|1: behave like require\n \t__webpack_require__.t = function(value, mode) {\n \t\tif(mode & 1) value = __webpack_require__(value);\n \t\tif(mode & 8) return value;\n \t\tif((mode & 4) && typeof value === 'object' && value && value.__esModule) return value;\n \t\tvar ns = Object.create(null);\n \t\t__webpack_require__.r(ns);\n \t\tObject.defineProperty(ns, 'default', { enumerable: true, value: value });\n \t\tif(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key));\n \t\treturn ns;\n \t};\n\n \t// getDefaultExport function for compatibility with non-harmony modules\n \t__webpack_require__.n = function(module) {\n \t\tvar getter = module && module.__esModule ?\n \t\t\tfunction getDefault() { return module['default']; } :\n \t\t\tfunction getModuleExports() { return module; };\n \t\t__webpack_require__.d(getter, 'a', getter);\n \t\treturn getter;\n \t};\n\n \t// Object.prototype.hasOwnProperty.call\n \t__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };\n\n \t// __webpack_public_path__\n \t__webpack_require__.p = \"./\";\n\n \tvar jsonpArray = this[\"webpackJsonpdrawable_canvas\"] = this[\"webpackJsonpdrawable_canvas\"] || [];\n \tvar oldJsonpFunction = jsonpArray.push.bind(jsonpArray);\n \tjsonpArray.push = webpackJsonpCallback;\n \tjsonpArray = jsonpArray.slice();\n \tfor(var i = 0; i < jsonpArray.length; i++) webpackJsonpCallback(jsonpArray[i]);\n \tvar parentJsonpFunction = oldJsonpFunction;\n\n\n \t// run deferred modules from other chunks\n \tcheckDeferredModules();\n"],"sourceRoot":""}
|