mirror of
https://github.com/gradio-app/gradio.git
synced 2025-02-23 11:39:17 +08:00
Add show_download_button
to gr.Image() (#4959)
* add show_download_button param * add static image story * chlog * fix test * typo * add default value Co-authored-by: Abubakar Abid <abubakar@huggingface.co> * fix test * fix another test --------- Co-authored-by: Abubakar Abid <abubakar@huggingface.co>
This commit is contained in:
parent
fdc9ca2ddf
commit
a0efc1180d
@ -4,7 +4,7 @@ No changes to highlight.
|
|||||||
|
|
||||||
## New Features:
|
## New Features:
|
||||||
|
|
||||||
No changes to highlight.
|
- Add `show_download_button` param to allow the download button in static Image components to be hidden by [@hannahblair](https://github.com/hannahblair) in [PR 4959](https://github.com/gradio-app/gradio/pull/4959)
|
||||||
|
|
||||||
## Bug Fixes:
|
## Bug Fixes:
|
||||||
|
|
||||||
|
@ -70,6 +70,7 @@ class Image(
|
|||||||
label: str | None = None,
|
label: str | None = None,
|
||||||
every: float | None = None,
|
every: float | None = None,
|
||||||
show_label: bool | None = None,
|
show_label: bool | None = None,
|
||||||
|
show_download_button: bool = True,
|
||||||
container: bool = True,
|
container: bool = True,
|
||||||
scale: int | None = None,
|
scale: int | None = None,
|
||||||
min_width: int = 160,
|
min_width: int = 160,
|
||||||
@ -97,6 +98,7 @@ class Image(
|
|||||||
label: component name in interface.
|
label: component name in interface.
|
||||||
every: If `value` is a callable, run the function 'every' number of seconds while the client connection is open. Has no effect otherwise. Queue must be enabled. The event can be accessed (e.g. to cancel it) via this component's .load_event attribute.
|
every: If `value` is a callable, run the function 'every' number of seconds while the client connection is open. Has no effect otherwise. Queue must be enabled. The event can be accessed (e.g. to cancel it) via this component's .load_event attribute.
|
||||||
show_label: if True, will display label.
|
show_label: if True, will display label.
|
||||||
|
show_download_button: If True, will display button to download image.
|
||||||
container: If True, will place the component in a container - providing some extra padding around the border.
|
container: If True, will place the component in a container - providing some extra padding around the border.
|
||||||
scale: relative width compared to adjacent Components in a Row. For example, if Component A has scale=2, and Component B has scale=1, A will be twice as wide as B. Should be an integer.
|
scale: relative width compared to adjacent Components in a Row. For example, if Component A has scale=2, and Component B has scale=1, A will be twice as wide as B. Should be an integer.
|
||||||
min_width: minimum pixel width, will wrap if not sufficient screen space to satisfy this value. If a certain scale value results in this Component being narrower than min_width, the min_width parameter will be respected first.
|
min_width: minimum pixel width, will wrap if not sufficient screen space to satisfy this value. If a certain scale value results in this Component being narrower than min_width, the min_width parameter will be respected first.
|
||||||
@ -133,6 +135,7 @@ class Image(
|
|||||||
self.tool = tool
|
self.tool = tool
|
||||||
self.invert_colors = invert_colors
|
self.invert_colors = invert_colors
|
||||||
self.streaming = streaming
|
self.streaming = streaming
|
||||||
|
self.show_download_button = show_download_button
|
||||||
if streaming and source != "webcam":
|
if streaming and source != "webcam":
|
||||||
raise ValueError("Image streaming only available if source is 'webcam'.")
|
raise ValueError("Image streaming only available if source is 'webcam'.")
|
||||||
self.select: EventListenerMethod
|
self.select: EventListenerMethod
|
||||||
@ -177,6 +180,7 @@ class Image(
|
|||||||
"brush_radius": self.brush_radius,
|
"brush_radius": self.brush_radius,
|
||||||
"selectable": self.selectable,
|
"selectable": self.selectable,
|
||||||
"show_share_button": self.show_share_button,
|
"show_share_button": self.show_share_button,
|
||||||
|
"show_download_button": self.show_download_button,
|
||||||
**IOComponent.get_config(self),
|
**IOComponent.get_config(self),
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -187,6 +191,7 @@ class Image(
|
|||||||
width: int | None = None,
|
width: int | None = None,
|
||||||
label: str | None = None,
|
label: str | None = None,
|
||||||
show_label: bool | None = None,
|
show_label: bool | None = None,
|
||||||
|
show_download_button: bool | None = None,
|
||||||
container: bool | None = None,
|
container: bool | None = None,
|
||||||
scale: int | None = None,
|
scale: int | None = None,
|
||||||
min_width: int | None = None,
|
min_width: int | None = None,
|
||||||
@ -200,6 +205,7 @@ class Image(
|
|||||||
"width": width,
|
"width": width,
|
||||||
"label": label,
|
"label": label,
|
||||||
"show_label": show_label,
|
"show_label": show_label,
|
||||||
|
"show_download_button": show_download_button,
|
||||||
"container": container,
|
"container": container,
|
||||||
"scale": scale,
|
"scale": scale,
|
||||||
"min_width": min_width,
|
"min_width": min_width,
|
||||||
|
@ -64,6 +64,7 @@ XRAY_CONFIG = {
|
|||||||
"min_width": 160,
|
"min_width": 160,
|
||||||
"name": "image",
|
"name": "image",
|
||||||
"show_share_button": False,
|
"show_share_button": False,
|
||||||
|
"show_download_button": True,
|
||||||
"visible": True,
|
"visible": True,
|
||||||
},
|
},
|
||||||
"serializer": "ImgSerializable",
|
"serializer": "ImgSerializable",
|
||||||
@ -136,6 +137,7 @@ XRAY_CONFIG = {
|
|||||||
"min_width": 160,
|
"min_width": 160,
|
||||||
"name": "image",
|
"name": "image",
|
||||||
"show_share_button": False,
|
"show_share_button": False,
|
||||||
|
"show_download_button": True,
|
||||||
"visible": True,
|
"visible": True,
|
||||||
},
|
},
|
||||||
"serializer": "ImgSerializable",
|
"serializer": "ImgSerializable",
|
||||||
@ -382,6 +384,7 @@ XRAY_CONFIG_DIFF_IDS = {
|
|||||||
"min_width": 160,
|
"min_width": 160,
|
||||||
"name": "image",
|
"name": "image",
|
||||||
"show_share_button": False,
|
"show_share_button": False,
|
||||||
|
"show_download_button": True,
|
||||||
"visible": True,
|
"visible": True,
|
||||||
},
|
},
|
||||||
"serializer": "ImgSerializable",
|
"serializer": "ImgSerializable",
|
||||||
@ -454,6 +457,7 @@ XRAY_CONFIG_DIFF_IDS = {
|
|||||||
"min_width": 160,
|
"min_width": 160,
|
||||||
"name": "image",
|
"name": "image",
|
||||||
"show_share_button": False,
|
"show_share_button": False,
|
||||||
|
"show_download_button": True,
|
||||||
"visible": True,
|
"visible": True,
|
||||||
},
|
},
|
||||||
"serializer": "ImgSerializable",
|
"serializer": "ImgSerializable",
|
||||||
|
@ -9,14 +9,15 @@
|
|||||||
import type { LoadingStatus } from "../StatusTracker/types";
|
import type { LoadingStatus } from "../StatusTracker/types";
|
||||||
import UploadText from "../UploadText.svelte";
|
import UploadText from "../UploadText.svelte";
|
||||||
|
|
||||||
export let elem_id: string = "";
|
export let elem_id = "";
|
||||||
export let elem_classes: Array<string> = [];
|
export let elem_classes: string[] = [];
|
||||||
export let visible: boolean = true;
|
export let visible = true;
|
||||||
export let value: null | string = null;
|
export let value: null | string = null;
|
||||||
export let source: "canvas" | "webcam" | "upload" = "upload";
|
export let source: "canvas" | "webcam" | "upload" = "upload";
|
||||||
export let tool: "editor" | "select" | "sketch" | "color-sketch" = "editor";
|
export let tool: "editor" | "select" | "sketch" | "color-sketch" = "editor";
|
||||||
export let label: string;
|
export let label: string;
|
||||||
export let show_label: boolean;
|
export let show_label: boolean;
|
||||||
|
export let show_download_button: boolean;
|
||||||
export let streaming: boolean;
|
export let streaming: boolean;
|
||||||
export let pending: boolean;
|
export let pending: boolean;
|
||||||
export let height: number | undefined;
|
export let height: number | undefined;
|
||||||
@ -24,13 +25,13 @@
|
|||||||
export let mirror_webcam: boolean;
|
export let mirror_webcam: boolean;
|
||||||
export let shape: [number, number];
|
export let shape: [number, number];
|
||||||
export let brush_radius: number;
|
export let brush_radius: number;
|
||||||
export let selectable: boolean = false;
|
export let selectable = false;
|
||||||
export let container: boolean = true;
|
export let container = true;
|
||||||
export let scale: number | null = null;
|
export let scale: number | null = null;
|
||||||
export let min_width: number | undefined = undefined;
|
export let min_width: number | undefined = undefined;
|
||||||
export let loading_status: LoadingStatus;
|
export let loading_status: LoadingStatus;
|
||||||
export let mode: "static" | "dynamic";
|
export let mode: "static" | "dynamic";
|
||||||
export let show_share_button: boolean = false;
|
export let show_share_button = false;
|
||||||
|
|
||||||
const dispatch = createEventDispatcher<{
|
const dispatch = createEventDispatcher<{
|
||||||
change: undefined;
|
change: undefined;
|
||||||
@ -70,6 +71,7 @@
|
|||||||
{value}
|
{value}
|
||||||
{label}
|
{label}
|
||||||
{show_label}
|
{show_label}
|
||||||
|
{show_download_button}
|
||||||
{selectable}
|
{selectable}
|
||||||
{show_share_button}
|
{show_share_button}
|
||||||
/>
|
/>
|
||||||
|
50
js/image/src/Image.stories.svelte
Normal file
50
js/image/src/Image.stories.svelte
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
<script>
|
||||||
|
import { Meta, Template, Story } from "@storybook/addon-svelte-csf";
|
||||||
|
import StaticImage from "./StaticImage.svelte";
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<Meta
|
||||||
|
title="Components/Image"
|
||||||
|
component={Image}
|
||||||
|
argTypes={{
|
||||||
|
value: {
|
||||||
|
control: "text",
|
||||||
|
description: "The image URL or file to display",
|
||||||
|
name: "value",
|
||||||
|
value: "https://i.ibb.co/6BgKdSj/groot.jpg"
|
||||||
|
},
|
||||||
|
show_download_button: {
|
||||||
|
options: [true, false],
|
||||||
|
description: "If false, the download button will not be visible",
|
||||||
|
control: { type: "boolean" },
|
||||||
|
defaultValue: true
|
||||||
|
},
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<Template let:args>
|
||||||
|
<div class="image-container" style="width: 300px; position: relative;border-radius: var(--radius-lg);overflow: hidden;">
|
||||||
|
<StaticImage {...args} />
|
||||||
|
</div>
|
||||||
|
</Template>
|
||||||
|
|
||||||
|
<Story
|
||||||
|
name="Static Image with label and download button"
|
||||||
|
args={{
|
||||||
|
value: "https://i.ibb.co/6BgKdSj/groot.jpg",
|
||||||
|
show_label: true,
|
||||||
|
show_download_button: true
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<Story
|
||||||
|
name="Static Image with no label or download button"
|
||||||
|
args={{
|
||||||
|
value: "https://i.ibb.co/6BgKdSj/groot.jpg",
|
||||||
|
show_label: false,
|
||||||
|
show_download_button: false
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -3,7 +3,7 @@
|
|||||||
import type { SelectData } from "@gradio/utils";
|
import type { SelectData } from "@gradio/utils";
|
||||||
import { uploadToHuggingFace } from "@gradio/utils";
|
import { uploadToHuggingFace } from "@gradio/utils";
|
||||||
import { BlockLabel, Empty, IconButton, ShareButton } from "@gradio/atoms";
|
import { BlockLabel, Empty, IconButton, ShareButton } from "@gradio/atoms";
|
||||||
import { Download, Community } from "@gradio/icons";
|
import { Download } from "@gradio/icons";
|
||||||
import { get_coordinates_of_clicked_image } from "./utils";
|
import { get_coordinates_of_clicked_image } from "./utils";
|
||||||
|
|
||||||
import { Image } from "@gradio/icons";
|
import { Image } from "@gradio/icons";
|
||||||
@ -11,8 +11,9 @@
|
|||||||
export let value: null | string;
|
export let value: null | string;
|
||||||
export let label: string | undefined = undefined;
|
export let label: string | undefined = undefined;
|
||||||
export let show_label: boolean;
|
export let show_label: boolean;
|
||||||
export let selectable: boolean = false;
|
export let show_download_button = true;
|
||||||
export let show_share_button: boolean = false;
|
export let selectable = false;
|
||||||
|
export let show_share_button = false;
|
||||||
|
|
||||||
const dispatch = createEventDispatcher<{
|
const dispatch = createEventDispatcher<{
|
||||||
change: string;
|
change: string;
|
||||||
@ -21,7 +22,7 @@
|
|||||||
|
|
||||||
$: value && dispatch("change", value);
|
$: value && dispatch("change", value);
|
||||||
|
|
||||||
const handle_click = (evt: MouseEvent) => {
|
const handle_click = (evt: MouseEvent): void => {
|
||||||
let coordinates = get_coordinates_of_clicked_image(evt);
|
let coordinates = get_coordinates_of_clicked_image(evt);
|
||||||
if (coordinates) {
|
if (coordinates) {
|
||||||
dispatch("select", { index: coordinates, value: null });
|
dispatch("select", { index: coordinates, value: null });
|
||||||
@ -34,6 +35,7 @@
|
|||||||
<Empty unpadded_box={true} size="large"><Image /></Empty>
|
<Empty unpadded_box={true} size="large"><Image /></Empty>
|
||||||
{:else}
|
{:else}
|
||||||
<div class="icon-buttons">
|
<div class="icon-buttons">
|
||||||
|
{#if show_download_button}
|
||||||
<a
|
<a
|
||||||
href={value}
|
href={value}
|
||||||
target={window.__is_colab__ ? "_blank" : null}
|
target={window.__is_colab__ ? "_blank" : null}
|
||||||
@ -41,6 +43,7 @@
|
|||||||
>
|
>
|
||||||
<IconButton Icon={Download} label="Download" />
|
<IconButton Icon={Download} label="Download" />
|
||||||
</a>
|
</a>
|
||||||
|
{/if}
|
||||||
{#if show_share_button}
|
{#if show_share_button}
|
||||||
<ShareButton
|
<ShareButton
|
||||||
on:share
|
on:share
|
||||||
|
@ -665,6 +665,7 @@ class TestImage:
|
|||||||
"tool": "editor",
|
"tool": "editor",
|
||||||
"name": "image",
|
"name": "image",
|
||||||
"show_share_button": False,
|
"show_share_button": False,
|
||||||
|
"show_download_button": True,
|
||||||
"streaming": False,
|
"streaming": False,
|
||||||
"show_label": True,
|
"show_label": True,
|
||||||
"label": "Upload Your Image",
|
"label": "Upload Your Image",
|
||||||
|
Loading…
Reference in New Issue
Block a user