mirror of
https://github.com/gradio-app/gradio.git
synced 2024-12-27 02:30:17 +08:00
Merge branch 'master' of https://github.com/gradio-app/gradio
This commit is contained in:
commit
bc69139099
@ -11,7 +11,7 @@ def sentiment_analysis(text):
|
||||
del scores["compound"]
|
||||
return scores
|
||||
|
||||
iface = gr.Interface(sentiment_analysis, "textbox", "label", allow_screenshot=False, allow_flagging=False)
|
||||
iface = gr.Interface(sentiment_analysis, "textbox", "label", interpretation="default")
|
||||
|
||||
iface.test_launch()
|
||||
if __name__ == "__main__":
|
||||
|
@ -85,7 +85,6 @@ iface = gr.Interface(
|
||||
["third", True, 30, ["Child"], 20, "S"],
|
||||
],
|
||||
interpretation="default",
|
||||
live=True
|
||||
)
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
@ -65,6 +65,8 @@ export class GradioInterface extends React.Component {
|
||||
this.clear = this.clear.bind(this);
|
||||
this.submit = this.submit.bind(this);
|
||||
this.flag = this.flag.bind(this);
|
||||
this.interpret = this.interpret.bind(this);
|
||||
this.removeInterpret = this.removeInterpret.bind(this);
|
||||
this.handleExampleChange = this.handleExampleChange.bind(this);
|
||||
this.state = this.get_default_state();
|
||||
this.state["examples_page"] = 0;
|
||||
@ -82,6 +84,7 @@ export class GradioInterface extends React.Component {
|
||||
state["submitting"] = false;
|
||||
state["error"] = false;
|
||||
state["complete"] = false;
|
||||
state["interpretation"] = null;
|
||||
state["just_flagged"] = false;
|
||||
state["has_changed"] = false;
|
||||
state["example_id"] = null;
|
||||
@ -99,13 +102,13 @@ export class GradioInterface extends React.Component {
|
||||
input_state[i] = this.state[i];
|
||||
}
|
||||
this.setState({ "submitting": true, "has_changed": false, "error": false });
|
||||
this.props.fn(input_state, "predict").then((output) => {
|
||||
this.props.fn(input_state, "predict").then(output => {
|
||||
let index_start = this.props.input_components.length;
|
||||
for (let [i, value] of output["data"].entries()) {
|
||||
this.setState({ [index_start + i]: value });
|
||||
}
|
||||
this.setState({ "submitting": false, "complete": true });
|
||||
if (this.state.has_changed) {
|
||||
if (this.props.live && this.state.has_changed) {
|
||||
this.submit();
|
||||
}
|
||||
}).catch(e => {
|
||||
@ -133,6 +136,31 @@ export class GradioInterface extends React.Component {
|
||||
}, 1000)
|
||||
this.props.fn(component_state, "flag");
|
||||
}
|
||||
interpret() {
|
||||
if (!this.state.complete) {
|
||||
return;
|
||||
}
|
||||
let input_state = [];
|
||||
for (let i = 0; i < this.props.input_components.length; i++) {
|
||||
if (this.state[i] === null) {
|
||||
return;
|
||||
}
|
||||
input_state[i] = this.state[i];
|
||||
}
|
||||
this.setState({ "submitting": true, "has_changed": false, "error": false });
|
||||
this.props.fn(input_state, "interpret").then(output => {
|
||||
this.setState({ "interpretation": output["interpretation_scores"], "submitting": false })
|
||||
}).catch(e => {
|
||||
console.error(e);
|
||||
this.setState({
|
||||
"error": true,
|
||||
"submitting": false
|
||||
});
|
||||
});
|
||||
}
|
||||
removeInterpret() {
|
||||
this.setState({ "interpretation": null });
|
||||
}
|
||||
handleChange(_id, value) {
|
||||
let state_change = { [_id]: value, "has_changed": true };
|
||||
if (this.props.live && !(this.state.submitting)) {
|
||||
@ -176,7 +204,7 @@ export class GradioInterface extends React.Component {
|
||||
return (
|
||||
<div className="component" key={index}>
|
||||
<div className="panel_header">{component.label}</div>
|
||||
<Component {...component} handleChange={this.handleChange.bind(this, index)} value={this.state[index]} />
|
||||
<Component {...component} handleChange={this.handleChange.bind(this, index)} value={this.state[index]} interpretation={this.state["interpretation"] === null ? null : this.state["interpretation"][index]} />
|
||||
</div>);
|
||||
})}
|
||||
</div>
|
||||
@ -203,21 +231,13 @@ export class GradioInterface extends React.Component {
|
||||
</div>
|
||||
<div className="panel_buttons">
|
||||
{this.props.allow_interpretation ?
|
||||
<button className="panel_button">Interpret</button> : false
|
||||
(this.state.interpretation === null ?
|
||||
<button className={classNames("panel_button", { "disabled": this.state.complete === false })} onClick={this.interpret}>Interpret</button> :
|
||||
<button className="panel_button" onClick={this.removeInterpret}>Hide</button>)
|
||||
: false
|
||||
}
|
||||
{this.props.allow_screenshot ?
|
||||
<div className="screenshot_set">
|
||||
<button className="panel_button left_panel_button">Screenshot</button>
|
||||
<button className="panel_button right_panel_button">GIF</button>
|
||||
{this.state.screenshot_mode ?
|
||||
<div className="screenshot_logo">
|
||||
<img src="/static/img/logo_inline.png" alt="Gradio" />
|
||||
<button className='record_stop'>
|
||||
<div className='record_square'></div>
|
||||
</button>
|
||||
</div>
|
||||
: false}
|
||||
</div>
|
||||
<button className="panel_button hidden">Screenshot</button>
|
||||
: false}
|
||||
{this.props.allow_flagging ?
|
||||
<button className={classNames("panel_button", { "disabled": this.state.complete === false })}
|
||||
|
@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import { DataURLComponentExample } from '../component_example';
|
||||
import AudioReactRecorder, { RecordState } from 'audio-react-recorder'
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class AudioInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -46,6 +47,13 @@ class AudioInput extends React.Component {
|
||||
<audio controls key={this.key}>
|
||||
<source src={this.props.value}></source>
|
||||
</audio>
|
||||
{this.props.interpretation === null ? false :
|
||||
<div class="interpret_range">
|
||||
{this.props.interpretation.map(value =>
|
||||
<div style={{ 'background-color': getSaliencyColor(value) }}>
|
||||
</div>
|
||||
)}
|
||||
</div>}
|
||||
</div>);
|
||||
} else {
|
||||
if (this.props.source === "microphone") {
|
||||
@ -59,7 +67,7 @@ class AudioInput extends React.Component {
|
||||
} else if (this.props.source === "upload") {
|
||||
let no_action = (evt) => {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
evt.stopPropagation();
|
||||
}
|
||||
return (
|
||||
<div className="input_image" onDrag={no_action} onDragStart={no_action} onDragEnd={no_action} onDragOver={no_action} onDragEnter={no_action} onDragLeave={no_action} onDrop={no_action} >
|
||||
|
@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import classNames from "classnames";
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class CheckboxInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -15,12 +16,23 @@ class CheckboxInput extends React.Component {
|
||||
<div className={classNames("checkbox_item", {
|
||||
"selected": this.props.value
|
||||
})} onClick={this.handleChange}>
|
||||
<div className="checkbox">
|
||||
<svg className="check" viewBox="-10 -10 20 20">
|
||||
<line x1="-7.5" y1="0" x2="-2.5" y2="5"></line>
|
||||
<line x1="-2.5" y1="5" x2="7.5" y2="-7.5"></line>
|
||||
</svg>
|
||||
</div>
|
||||
{this.props.interpretation === null ?
|
||||
<div className="checkbox">
|
||||
<svg className="check" viewBox="-10 -10 20 20">
|
||||
<line x1="-7.5" y1="0" x2="-2.5" y2="5"></line>
|
||||
<line x1="-2.5" y1="5" x2="7.5" y2="-7.5"></line>
|
||||
</svg>
|
||||
</div>
|
||||
:
|
||||
<div class="interpretation">
|
||||
<div class="interpretation_box" style={{ "backgroundColor": getSaliencyColor(this.props.interpretation[0]) }}></div>
|
||||
<div class="interpretation_box" style={{ "backgroundColor": getSaliencyColor(this.props.interpretation[1]) }}>
|
||||
<svg className="interpret_check" viewBox="-10 -10 20 20">
|
||||
<line x1="-7.5" y1="0" x2="-2.5" y2="5"></line>
|
||||
<line x1="-2.5" y1="5" x2="7.5" y2="-7.5"></line>
|
||||
</svg>
|
||||
</div>
|
||||
</div>}
|
||||
</div>
|
||||
</div>)
|
||||
}
|
||||
@ -32,4 +44,4 @@ class CheckboxInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {CheckboxInput, CheckboxInputExample};
|
||||
export { CheckboxInput, CheckboxInputExample };
|
@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import classNames from "classnames";
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class CheckboxGroupInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -17,21 +18,32 @@ class CheckboxGroupInput extends React.Component {
|
||||
this.props.handleChange(all_selected);
|
||||
}
|
||||
render() {
|
||||
return (<div className="input_checkbox_group">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <div className={classNames("checkbox_item", {
|
||||
"selected": this.props.value.includes(item)
|
||||
})} onClick={this.handleChange.bind(this, item)} key={index}>
|
||||
return (<div className="input_checkbox_group">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <div className={classNames("checkbox_item", {
|
||||
"selected": this.props.value.includes(item)
|
||||
})} onClick={this.handleChange.bind(this, item)} key={index}>
|
||||
{this.props.interpretation === null ?
|
||||
<div className="checkbox">
|
||||
<svg className="check" viewBox="-10 -10 20 20">
|
||||
<line x1="-7.5" y1="0" x2="-2.5" y2="5"></line>
|
||||
<line x1="-2.5" y1="5" x2="7.5" y2="-7.5"></line>
|
||||
</svg>
|
||||
</div>
|
||||
{item}
|
||||
</div>
|
||||
})}
|
||||
</div>)
|
||||
:
|
||||
<div class="interpretation">
|
||||
<div class="interpretation_box" style={{ "backgroundColor": getSaliencyColor(this.props.interpretation[index][0]) }}></div>
|
||||
<div class="interpretation_box" style={{ "backgroundColor": getSaliencyColor(this.props.interpretation[index][1]) }}>
|
||||
<svg className="interpret_check" viewBox="-10 -10 20 20">
|
||||
<line x1="-7.5" y1="0" x2="-2.5" y2="5"></line>
|
||||
<line x1="-2.5" y1="5" x2="7.5" y2="-7.5"></line>
|
||||
</svg>
|
||||
</div>
|
||||
</div>}
|
||||
{item}
|
||||
</div>
|
||||
})}
|
||||
</div>)
|
||||
}
|
||||
}
|
||||
|
||||
@ -41,4 +53,4 @@ class CheckboxGroupInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {CheckboxGroupInput, CheckboxGroupInputExample};
|
||||
export { CheckboxGroupInput, CheckboxGroupInputExample };
|
||||
|
@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import classNames from "classnames";
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class DropdownInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -12,21 +13,28 @@ class DropdownInput extends React.Component {
|
||||
}
|
||||
render() {
|
||||
return (<div className="input_dropdown">
|
||||
<div className="dropdown inline-block relative">
|
||||
<button className="selector ">
|
||||
<span className="current">{this.props.value}</span>
|
||||
<svg className="caret" viewBox="0 0 20 20"><path d="M9.293 12.95l.707.707L15.657 8l-1.414-1.414L10 10.828 5.757 6.586 4.343 8z" /> </svg>
|
||||
</button>
|
||||
<ul className="dropdown_menu">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <li className={classNames("dropdown_item", {
|
||||
"selected": item === this.props.value
|
||||
})} onClick={this.handleChange.bind(this, item)} key={index}>
|
||||
{item}
|
||||
</li>
|
||||
})}
|
||||
</ul>
|
||||
</div>
|
||||
{this.props.interpretation === null ?
|
||||
<div className="dropdown inline-block relative">
|
||||
<button className="selector ">
|
||||
<span className="current">{this.props.value}</span>
|
||||
<svg className="caret" viewBox="0 0 20 20"><path d="M9.293 12.95l.707.707L15.657 8l-1.414-1.414L10 10.828 5.757 6.586 4.343 8z" /> </svg>
|
||||
</button>
|
||||
<ul className="dropdown_menu">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <li className={classNames("dropdown_item", {
|
||||
"selected": item === this.props.value
|
||||
})} onClick={this.handleChange.bind(this, item)} key={index}>
|
||||
{item}
|
||||
</li>
|
||||
})}
|
||||
</ul>
|
||||
</div>
|
||||
:
|
||||
<div class="interpretation">
|
||||
{this.props.interpretation.map((value, index) =>
|
||||
<div class="interpretation_box" key={index} style={{ "backgroundColor": getSaliencyColor(value) }}>{this.props.choices[index]}</div>
|
||||
)}
|
||||
</div>}
|
||||
</div>)
|
||||
}
|
||||
}
|
||||
@ -37,4 +45,4 @@ class DropdownInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {DropdownInput, DropdownInputExample};
|
||||
export { DropdownInput, DropdownInputExample };
|
||||
|
@ -2,6 +2,7 @@ import React from 'react';
|
||||
import { DataURLComponentExample } from '../component_example';
|
||||
import Webcam from "react-webcam";
|
||||
import { SketchField, Tools } from '../../vendor/ReactSketch';
|
||||
import { getObjectFitSize, paintSaliency } from '../utils';
|
||||
|
||||
class ImageInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -9,11 +10,13 @@ class ImageInput extends React.Component {
|
||||
this.handleChange = this.handleChange.bind(this);
|
||||
this.uploader = React.createRef();
|
||||
this.openFileUpload = this.openFileUpload.bind(this);
|
||||
this.onImgLoad = this.onImgLoad.bind(this);
|
||||
this.load_preview_from_files = this.load_preview_from_files.bind(this);
|
||||
this.load_preview_from_upload = this.load_preview_from_upload.bind(this);
|
||||
this.load_preview_from_drop = this.load_preview_from_drop.bind(this);
|
||||
this.snapshot = this.snapshot.bind(this);
|
||||
this.getSketch = this.getSketch.bind(this);
|
||||
this.imgRef = React.createRef();
|
||||
this.webcamRef = React.createRef();
|
||||
this.sketchRef = React.createRef();
|
||||
this.sketchKey = 0;
|
||||
@ -32,17 +35,39 @@ class ImageInput extends React.Component {
|
||||
let imageSrc = this.sketchRef.current.toDataURL();
|
||||
this.handleChange(imageSrc);
|
||||
}
|
||||
onImgLoad({target:img}) {
|
||||
this.setState({dimensions:{height:img.offsetHeight,
|
||||
width:img.offsetWidth}});
|
||||
}
|
||||
render() {
|
||||
let no_action = (evt) => {
|
||||
evt.preventDefault();
|
||||
evt.stopPropagation();
|
||||
}
|
||||
if (this.props.value !== null && this.props.source !== "canvas") {
|
||||
let interpretation = false;
|
||||
if (this.props.interpretation !== null) {
|
||||
let img = this.imgRef.current;
|
||||
let size = getObjectFitSize(true, img.width, img.height, img.naturalWidth, img.naturalHeight);
|
||||
if (this.props.shape) {
|
||||
size = getObjectFitSize(true, size.width, size.height, this.props.shape[0], this.props.shape[1])
|
||||
}
|
||||
let width = size.width;
|
||||
let height = size.height;
|
||||
let canvas = document.createElement("canvas")
|
||||
canvas.setAttribute("height", height);
|
||||
canvas.setAttribute("width", width);
|
||||
paintSaliency(this.props.interpretation, canvas.getContext("2d"), width, height);
|
||||
interpretation = (<div class="interpretation">
|
||||
<img src={canvas.toDataURL()}></img>
|
||||
</div>)
|
||||
}
|
||||
return (
|
||||
<div className="input_image">
|
||||
<div className="image_preview_holder">
|
||||
<img className="image_preview" alt="" src={this.props.value} />
|
||||
<img ref={this.imgRef} onLoad={this.onImgLoad} className="image_preview" alt="" src={this.props.value} />
|
||||
</div>
|
||||
{interpretation}
|
||||
</div>)
|
||||
} else {
|
||||
if (this.props.source === "upload") {
|
||||
|
@ -1,5 +1,6 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class NumberInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -14,7 +15,16 @@ class NumberInput extends React.Component {
|
||||
}
|
||||
}
|
||||
render() {
|
||||
return <input type="text" className="input_number" onChange={this.handleChange} value={this.props.value === null ? "" : this.props.value}></input>
|
||||
return <div className="input_number">
|
||||
{this.props.interpretation === null ?
|
||||
<input type="text" onChange={this.handleChange} value={this.props.value === null ? "" : this.props.value}></input>
|
||||
:
|
||||
<div class="interpretation">
|
||||
{this.props.interpretation.map((value, index) =>
|
||||
<div class="interpretation_box" key={index} style={{ "backgroundColor": getSaliencyColor(value[1]) }}>{value[0]}</div>
|
||||
)}
|
||||
</div>}
|
||||
</div>
|
||||
}
|
||||
}
|
||||
|
||||
@ -25,4 +35,4 @@ class NumberInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {NumberInput, NumberInputExample};
|
||||
export { NumberInput, NumberInputExample };
|
||||
|
@ -1,6 +1,7 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import classNames from "classnames";
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class RadioInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -11,16 +12,21 @@ class RadioInput extends React.Component {
|
||||
this.props.handleChange(selected_item);
|
||||
}
|
||||
render() {
|
||||
return (<div className="input_radio">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <div className={classNames("radio_item", {
|
||||
return (<div className="input_radio">
|
||||
{this.props.choices.map((item, index) => {
|
||||
return <div key={index}>
|
||||
<div className={classNames("radio_item", {
|
||||
"selected": item === this.props.value
|
||||
})} onClick={this.handleChange.bind(this, item)} key={index}>
|
||||
<div className="radio_circle"></div>
|
||||
})} onClick={this.handleChange.bind(this, item)}>
|
||||
{this.props.interpretation === null ?
|
||||
<div className="radio_circle"></div> :
|
||||
<div className="radio_circle" style={{"backgroundColor": getSaliencyColor(this.props.interpretation[index])}}></div>
|
||||
}
|
||||
{item}
|
||||
</div>
|
||||
})}
|
||||
</div>)
|
||||
</div>
|
||||
})}
|
||||
</div>)
|
||||
}
|
||||
}
|
||||
|
||||
@ -30,4 +36,4 @@ class RadioInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {RadioInput, RadioInputExample};
|
||||
export { RadioInput, RadioInputExample };
|
||||
|
@ -1,5 +1,6 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class SliderInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -10,10 +11,20 @@ class SliderInput extends React.Component {
|
||||
this.props.handleChange(parseFloat(evt.target.value));
|
||||
}
|
||||
render() {
|
||||
return (<div className="input_slider">
|
||||
<input type="range" className="range" onChange={this.handleChange} value={this.props.value} min={this.props.minimum} max={this.props.maximum} step={this.props.step}></input>
|
||||
<div className="value">{this.props.value}</div>
|
||||
</div>)
|
||||
return (<div className="input_slider">
|
||||
{this.props.interpretation === null ?
|
||||
<>
|
||||
<input type="range" className="range" onChange={this.handleChange} value={this.props.value} min={this.props.minimum} max={this.props.maximum} step={this.props.step}></input>
|
||||
<div className="value">{this.props.value}</div>
|
||||
</>
|
||||
:
|
||||
<div class="interpret_range">
|
||||
{this.props.interpretation.map(value =>
|
||||
<div style={{ 'background-color': getSaliencyColor(value) }}>
|
||||
</div>
|
||||
)}
|
||||
</div>}
|
||||
</div>)
|
||||
}
|
||||
}
|
||||
|
||||
@ -23,4 +34,4 @@ class SliderInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {SliderInput, SliderInputExample};
|
||||
export { SliderInput, SliderInputExample };
|
||||
|
@ -1,5 +1,6 @@
|
||||
import React from 'react';
|
||||
import ComponentExample from '../component_example';
|
||||
import { getSaliencyColor } from '../utils';
|
||||
|
||||
class TextboxInput extends React.Component {
|
||||
constructor(props) {
|
||||
@ -10,15 +11,25 @@ class TextboxInput extends React.Component {
|
||||
this.props.handleChange(evt.target.value);
|
||||
}
|
||||
render() {
|
||||
if (this.props.lines > 1) {
|
||||
if (this.props.interpretation !== null) {
|
||||
return (
|
||||
<div>
|
||||
<textarea className="input_text" value={this.props.value || ""} onChange={this.handleChange}>
|
||||
<div className="input_text">
|
||||
<div class="interpretation">
|
||||
{this.props.interpretation.map((item, index) => <div class="interpretation_box" key={index} style={{ "backgroundColor": getSaliencyColor(item[1]) }}>{item[0]}</div>)}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
} else if (this.props.lines > 1) {
|
||||
return (
|
||||
<div className="input_text">
|
||||
<textarea value={this.props.value || ""} onChange={this.handleChange}>
|
||||
</textarea>
|
||||
</div>
|
||||
)
|
||||
} else {
|
||||
return <input type="text" className="input_text" onChange={this.handleChange} value={this.props.value || ""}></input>
|
||||
return (<div className="input_text">
|
||||
<input type="text" onChange={this.handleChange} value={this.props.value || ""}></input>
|
||||
</div>)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -29,4 +40,4 @@ class TextboxInputExample extends ComponentExample {
|
||||
}
|
||||
}
|
||||
|
||||
export {TextboxInput, TextboxInputExample};
|
||||
export { TextboxInput, TextboxInputExample };
|
||||
|
@ -7,4 +7,69 @@ export function prettyBytes(bytes) {
|
||||
}
|
||||
let unit = units[i];
|
||||
return bytes.toFixed(1) + " " + unit;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
export function getSaliencyColor(value) {
|
||||
if (value < 0) {
|
||||
var color = [52, 152, 219];
|
||||
} else {
|
||||
var color = [231, 76, 60];
|
||||
}
|
||||
return colorToString(interpolate(Math.abs(value), [255, 255, 255], color));
|
||||
}
|
||||
|
||||
function interpolate(val, rgb1, rgb2) {
|
||||
if (val > 1) {
|
||||
val = 1;
|
||||
}
|
||||
val = Math.sqrt(val);
|
||||
var rgb = [0, 0, 0];
|
||||
var i;
|
||||
for (i = 0; i < 3; i++) {
|
||||
rgb[i] = Math.round(rgb1[i] * (1.0 - val) + rgb2[i] * val);
|
||||
}
|
||||
return rgb;
|
||||
}
|
||||
|
||||
function colorToString(rgb) {
|
||||
return "rgb(" + rgb[0] + ", " + rgb[1] + ", " + rgb[2] + ")";
|
||||
}
|
||||
|
||||
export function getObjectFitSize(contains /* true = contain, false = cover */, containerWidth, containerHeight, width, height) {
|
||||
var doRatio = width / height;
|
||||
var cRatio = containerWidth / containerHeight;
|
||||
var targetWidth = 0;
|
||||
var targetHeight = 0;
|
||||
var test = contains ? (doRatio > cRatio) : (doRatio < cRatio);
|
||||
|
||||
if (test) {
|
||||
targetWidth = containerWidth;
|
||||
targetHeight = targetWidth / doRatio;
|
||||
} else {
|
||||
targetHeight = containerHeight;
|
||||
targetWidth = targetHeight * doRatio;
|
||||
}
|
||||
|
||||
return {
|
||||
width: targetWidth,
|
||||
height: targetHeight,
|
||||
x: (containerWidth - targetWidth) / 2,
|
||||
y: (containerHeight - targetHeight) / 2
|
||||
};
|
||||
}
|
||||
|
||||
export function paintSaliency(data, ctx, width, height) {
|
||||
var cell_width = width / data[0].length
|
||||
var cell_height = height / data.length
|
||||
var r = 0
|
||||
data.forEach(function(row) {
|
||||
var c = 0
|
||||
row.forEach(function(cell) {
|
||||
ctx.fillStyle = getSaliencyColor(cell);
|
||||
ctx.fillRect(c * cell_width, r * cell_height, cell_width, cell_height);
|
||||
c++;
|
||||
})
|
||||
r++;
|
||||
})
|
||||
}
|
@ -35,7 +35,7 @@
|
||||
@apply mb-1 uppercase text-sm font-semibold;
|
||||
}
|
||||
.panel_button {
|
||||
@apply flex-grow p-3 rounded bg-gray-50 hover:bg-gray-100 transition font-semibold focus:outline-none;
|
||||
@apply flex-1 p-3 rounded bg-gray-50 hover:bg-gray-100 transition font-semibold focus:outline-none;
|
||||
}
|
||||
.panel_button.disabled {
|
||||
@apply text-gray-400 cursor-not-allowed;
|
||||
@ -92,17 +92,32 @@
|
||||
}
|
||||
}
|
||||
/* Input Components */
|
||||
textarea.input_text {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1 resize-none;
|
||||
}
|
||||
input.input_text {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1;
|
||||
}
|
||||
.input_text {
|
||||
textarea {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1 resize-none;
|
||||
}
|
||||
input {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1;
|
||||
}
|
||||
.interpretation {
|
||||
.interpretation_box {
|
||||
@apply inline-block whitespace-pre-wrap;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_number {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1;
|
||||
input {
|
||||
@apply w-full bg-white border-gray-400 rounded box-border p-1;
|
||||
}
|
||||
.interpretation {
|
||||
@apply flex h-6;
|
||||
.interpretation_box {
|
||||
@apply flex-grow;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_image {
|
||||
@apply w-full h-80;
|
||||
@apply w-full h-80 relative;
|
||||
.upload_zone {
|
||||
@apply border-8 border-gray-300 border-dashed w-full h-full flex justify-center items-center text-3xl text-gray-400 text-center cursor-pointer leading-10;
|
||||
}
|
||||
@ -119,6 +134,9 @@
|
||||
.snapshot {
|
||||
@apply absolute bottom-0 w-full bg-white bg-opacity-90 py-3 font-bold text-lg text-center;
|
||||
}
|
||||
.interpretation {
|
||||
@apply w-full h-full absolute top-0 left-0 flex justify-center items-center opacity-90 hover:opacity-20 transition;
|
||||
}
|
||||
}
|
||||
.input_image_example {
|
||||
@apply h-24;
|
||||
@ -163,6 +181,20 @@
|
||||
stroke-width: 4;
|
||||
stroke-linecap: round;
|
||||
}
|
||||
.interpretation {
|
||||
@apply flex;
|
||||
.interpretation_box {
|
||||
@apply flex-grow h-4 w-4;
|
||||
}
|
||||
.interpret_check {
|
||||
@apply w-full h-full;
|
||||
}
|
||||
.interpret_check line {
|
||||
stroke: gray;
|
||||
stroke-width: 4;
|
||||
stroke-linecap: round;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_checkbox {
|
||||
@apply flex flex-wrap gap-2;
|
||||
@ -189,6 +221,20 @@
|
||||
stroke-width: 4;
|
||||
stroke-linecap: round;
|
||||
}
|
||||
.interpretation {
|
||||
@apply flex;
|
||||
.interpretation_box {
|
||||
@apply flex-grow h-4 w-4;
|
||||
}
|
||||
.interpret_check {
|
||||
@apply w-full h-full;
|
||||
}
|
||||
.interpret_check line {
|
||||
stroke: gray;
|
||||
stroke-width: 4;
|
||||
stroke-linecap: round;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_dropdown {
|
||||
@apply inline-block relative;
|
||||
@ -216,6 +262,9 @@
|
||||
:hover .dropdown_menu {
|
||||
@apply block;
|
||||
}
|
||||
.interpretation_box {
|
||||
@apply p-1;
|
||||
}
|
||||
}
|
||||
.input_slider {
|
||||
@apply text-center;
|
||||
@ -232,6 +281,12 @@
|
||||
.value {
|
||||
@apply inline-block mx-auto mt-1 px-2 py-0.5 bg-gray-200 rounded text-gray-700;
|
||||
}
|
||||
.interpret_range {
|
||||
@apply flex h-6;
|
||||
div {
|
||||
@apply flex-grow;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_audio {
|
||||
.audio-react-recorder {
|
||||
@ -246,6 +301,12 @@
|
||||
audio {
|
||||
@apply w-full border-2 border-gray-300 rounded;
|
||||
}
|
||||
.interpret_range {
|
||||
@apply flex h-4;
|
||||
div {
|
||||
@apply flex-grow h-full;
|
||||
}
|
||||
}
|
||||
}
|
||||
.input_video {
|
||||
@apply w-full h-80;
|
||||
|
@ -86,13 +86,13 @@
|
||||
}
|
||||
}
|
||||
/* Input Components */
|
||||
textarea.input_text {
|
||||
.input_text textarea {
|
||||
@apply w-full p-3 border rounded-lg shadow-inner outline-none focus:ring-1 focus:ring-inset focus:ring-indigo-200 focus:shadow-inner placeholder-gray-400;
|
||||
}
|
||||
input.input_text {
|
||||
.input_text input {
|
||||
@apply w-full p-3 border rounded-lg shadow-inner outline-none focus:ring-1 focus:ring-inset focus:ring-indigo-200 focus:shadow-inner placeholder-gray-400;
|
||||
}
|
||||
.input_number {
|
||||
.input_number input {
|
||||
@apply w-full p-3 border rounded-lg shadow-inner outline-none focus:ring-1 focus:ring-inset focus:ring-indigo-200 focus:shadow-inner placeholder-gray-400;
|
||||
}
|
||||
.input_image {
|
||||
|
@ -33,6 +33,8 @@ gradio/frontend/static/bundle.js.LICENSE.txt
|
||||
gradio/frontend/static/bundle.js.map
|
||||
gradio/frontend/static/css/main.20be28ac.css
|
||||
gradio/frontend/static/css/main.20be28ac.css.map
|
||||
gradio/frontend/static/css/main.2b64a968.css
|
||||
gradio/frontend/static/css/main.2b64a968.css.map
|
||||
gradio/frontend/static/css/main.380e3222.css
|
||||
gradio/frontend/static/css/main.380e3222.css.map
|
||||
gradio/frontend/static/css/main.4aea80f8.css
|
||||
|
@ -1,17 +1,17 @@
|
||||
{
|
||||
"files": {
|
||||
"main.css": "/static/css/main.4aea80f8.css",
|
||||
"main.css": "/static/css/main.2b64a968.css",
|
||||
"main.js": "/static/bundle.js",
|
||||
"main.js.map": "/static/bundle.js.map",
|
||||
"index.html": "/index.html",
|
||||
"static/bundle.css.map": "/static/bundle.css.map",
|
||||
"static/bundle.js.LICENSE.txt": "/static/bundle.js.LICENSE.txt",
|
||||
"static/css/main.4aea80f8.css.map": "/static/css/main.4aea80f8.css.map",
|
||||
"static/css/main.2b64a968.css.map": "/static/css/main.2b64a968.css.map",
|
||||
"static/media/logo_loading.e93acd82.jpg": "/static/media/logo_loading.e93acd82.jpg"
|
||||
},
|
||||
"entrypoints": [
|
||||
"static/bundle.css",
|
||||
"static/css/main.4aea80f8.css",
|
||||
"static/css/main.2b64a968.css",
|
||||
"static/bundle.js"
|
||||
]
|
||||
}
|
@ -8,4 +8,4 @@
|
||||
window.config = {{ config|tojson }};
|
||||
} catch (e) {
|
||||
window.config = {};
|
||||
}</script><title>Gradio</title><link href="https://fonts.googleapis.com/css?family=Open+Sans" rel="stylesheet"><link href="static/bundle.css" rel="stylesheet"><link href="static/css/main.4aea80f8.css" rel="stylesheet"></head><body><div id="root"></div><script src="static/bundle.js"></script></body></html>
|
||||
}</script><title>Gradio</title><link href="https://fonts.googleapis.com/css?family=Open+Sans" rel="stylesheet"><link href="static/bundle.css" rel="stylesheet"><link href="static/css/main.2b64a968.css" rel="stylesheet"></head><body><div id="root"></div><script src="static/bundle.js"></script></body></html>
|
@ -258,6 +258,7 @@ class Number(InputComponent):
|
||||
return self
|
||||
|
||||
def get_interpretation_neighbors(self, x):
|
||||
x = float(x)
|
||||
neighbors = []
|
||||
if self.interpretation_delta_type == "percent":
|
||||
delta = 1.0 * self.interpretation_delta * x / 100
|
||||
|
Loading…
Reference in New Issue
Block a user