File size: 2,919 Bytes
dda6bed | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 | """
ui/components.py — reusable Gradio input widgets.
Each function returns (component, …) tuples so app.py stays declarative.
"""
import gradio as gr
from config import (
MODELS,
DEFAULT_PROMPT,
DEFAULT_MAX_TOKENS,
DEFAULT_TEMPERATURE,
)
PROMPT_EXAMPLES = [
["Describe this image in detail."],
["List every object you can see."],
["What is the mood or atmosphere of this image?"],
["What text, if any, appears in this image?"],
["Explain this image to someone who cannot see it."],
["What is unusual or interesting about this image?"],
]
def image_upload() -> gr.Image:
return gr.Image(type="pil", label="📷 Input Image", height=320)
def prompt_box() -> gr.Textbox:
return gr.Textbox(
value=DEFAULT_PROMPT,
label="💬 Prompt",
lines=3,
placeholder="Ask anything about the image…",
)
def model_selector() -> gr.Radio:
return gr.Radio(
choices=list(MODELS.keys()),
value=list(MODELS.keys())[0],
label="🤖 Model",
)
def generation_settings() -> tuple[gr.Slider, gr.Slider]:
"""Returns (max_tokens_slider, temperature_slider)."""
with gr.Accordion("⚙️ Generation settings", open=False):
max_tokens = gr.Slider(
64, 2048, value=DEFAULT_MAX_TOKENS, step=64, label="Max tokens"
)
temperature = gr.Slider(
0.0, 1.5, value=DEFAULT_TEMPERATURE, step=0.05, label="Temperature"
)
return max_tokens, temperature
def api_key_field() -> gr.Textbox:
with gr.Accordion("🔑 API Key", open=False):
box = gr.Textbox(
label="Your API key (optional)",
type="password",
lines=1,
placeholder="sk-… leave blank to use the free public key",
)
gr.Markdown(
"A **free public key** is used when this field is blank. \n"
"It is shared and rate-limited — paste your own key from "
"[modelbest.cn](https://modelbest.cn) for unlimited use."
)
return box
def prompt_examples(prompt_input: gr.Textbox) -> gr.Examples:
return gr.Examples(
examples=PROMPT_EXAMPLES,
inputs=[prompt_input],
label="📝 Examples",
)
def output_box() -> gr.Textbox:
return gr.Textbox(
label="📄 Model Description (streaming)",
lines=22,
placeholder="Response streams here token-by-token…",
)
def info_panel() -> None:
gr.Markdown(
"---\n"
"**API details**\n"
"- Endpoint: `https://api.modelbest.cn/v1/chat/completions`\n"
"- Protocol: OpenAI-compatible (SSE streaming)\n"
"- Auth: Bearer token\n\n"
"**Models**\n"
"| Model | Params | Best for |\n"
"|---|---|---|\n"
"| Instruct | 1.3 B | Fast Q&A, descriptions |\n"
"| Thinking | 1.3 B | Complex reasoning, OCR |\n"
)
|