Nattapong Tapachoom
CC
c7cb155
raw
history blame
9.45 kB
import gradio as gr
from transformers import pipeline
# รายชื่อโมเดลที่ให้เลือก
MODEL_LIST = [
"SandboxBhh/sentiment-thai-text-model",
"poom-sci/WangchanBERTa-finetuned-sentiment",
"Thaweewat/wangchanberta-hyperopt-sentiment-01",
"cardiffnlp/twitter-xlm-roberta-base-sentiment",
"phoner45/wangchan-sentiment-thai-text-model",
"ZombitX64/Sentiment-01",
"ZombitX64/Sentiment-02",
"ZombitX64/Sentiment-03",
"ZombitX64/MultiSent-E5-Pro",
"ZombitX64/MultiSent-E5",
"ZombitX64/Thai-sentiment-e5",
"ZombitX64/sentiment-103",
"nlptown/bert-base-multilingual-uncased-sentiment"
]
from functools import lru_cache
# ใช้ cache เพื่อไม่ต้องโหลดโมเดลซ้ำ
@lru_cache(maxsize=2)
def get_nlp(model_name):
return pipeline("sentiment-analysis", model=model_name)
label_map = {
"LABEL_0": 0,
"LABEL_1": 1,
"LABEL_2": 2,
"LABEL_3": 3
}
label_name_map = {
"LABEL_0": "question",
"LABEL_1": "negative",
"LABEL_2": "neutral",
"LABEL_3": "positive"
}
def analyze_text(text, model_name):
# แยกประโยคโดยใช้ \n หรือจุด
import re
sentences = [s.strip() for s in re.split(r'[.\n]', text) if s.strip()]
if not sentences:
return "❗ กรุณาใส่ข้อความที่ต้องการวิเคราะห์"
# สีและไอคอนสำหรับแต่ละ sentiment
sentiment_style = {
"positive": {"emoji": "😊", "color": "#4CAF50", "bg": "#E8F5E8"},
"negative": {"emoji": "😔", "color": "#F44336", "bg": "#FFEBEE"},
"neutral": {"emoji": "😐", "color": "#FF9800", "bg": "#FFF3E0"},
"question": {"emoji": "❓", "color": "#2196F3", "bg": "#E3F2FD"}
}
results = []
results.append("📊 **ผลการวิเคราะห์ความรู้สึก**\n" + "="*50 + "\n")
nlp = get_nlp(model_name)
for i, sentence in enumerate(sentences, 1):
result = nlp(sentence)[0]
label = result['label']
score = result['score']
code = label_map.get(label, -1)
label_name = label_name_map.get(label, label)
style = sentiment_style.get(label_name, {"emoji": "🔍", "color": "#666666", "bg": "#F5F5F5"})
bar_length = int(score * 20)
progress_bar = "█" * bar_length + "░" * (20 - bar_length)
result_text = f"""
🔸 **ประโยคที่ {i}:** "{sentence}"
{style['emoji']} **ผลวิเคราะห์:** {label_name.upper()} (รหัส: {code})
📈 **ความมั่นใจ:** {score:.2f} ({score*100:.1f}%)
{progress_bar} {score:.2f}
{'─' * 60}
"""
results.append(result_text)
# เพิ่มสรุปผลรวม
total_sentences = len(sentences)
results.append(f"\n📋 **สรุป:** วิเคราะห์ทั้งหมด {total_sentences} ประโยค")
return "\n".join(results)
with gr.Blocks(
theme=gr.themes.Soft(primary_hue="blue", secondary_hue="purple", neutral_hue="gray"),
css="""
.gradio-container {
max-width: 900px !important;
margin: auto !important;
background: #f4f7fa !important;
border-radius: 18px !important;
box-shadow: 0 4px 24px 0 #bdbdbd33;
}
.main-card {
background: white;
border-radius: 16px;
box-shadow: 0 2px 12px 0 #bdbdbd22;
padding: 32px 32px 24px 32px;
margin: 32px 0 24px 0;
}
.output-markdown {
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif !important;
}
.gr-button {
font-size: 1.1em;
padding: 0.7em 2em;
border-radius: 8px;
}
.gr-textbox textarea {
font-size: 1.1em;
min-height: 120px;
}
.gr-dropdown input {
font-size: 1.1em;
}
"""
) as demo:
gr.Markdown("""
<div style="text-align: center; padding: 32px 0 12px 0;">
<h1 style="font-size:2.5em; margin-bottom: 0.2em; color:#3b3b6d;">🧠 Thai Sentiment Analyzer</h1>
<div style="font-size:1.2em; color:#666;">AI วิเคราะห์ความรู้สึกในข้อความภาษาไทย รองรับหลายโมเดลและหลายประโยค</div>
</div>
""")
with gr.Row():
with gr.Column():
gr.Markdown("""
<div class='main-card'>
<h3 style='color:#4a4a7d; margin-bottom:10px;'>� เลือกโมเดลวิเคราะห์ความรู้สึก</h3>
</div>
""")
model_dropdown = gr.Dropdown(
choices=MODEL_LIST,
value="ZombitX64/MultiSent-E5",
label="โมเดลที่ต้องการใช้"
)
gr.Markdown("""
<div class='main-card' style='margin-top:18px;'>
<h3 style='color:#4a4a7d; margin-bottom:10px;'>� ตัวอย่างข้อความ</h3>
</div>
""")
with gr.Column():
gr.Markdown("""
<div class='main-card'>
<h3 style='color:#4a4a7d; margin-bottom:10px;'>📝 ข้อความที่ต้องการวิเคราะห์</h3>
<div style='color:#888; font-size:1em;'>
💬 พิมพ์ข้อความหลายประโยคที่นี่<br>
<span style='font-size:0.95em;'>• แยกแต่ละประโยคด้วยจุด (.) หรือขึ้นบรรทัดใหม่<br>• รองรับข้อความภาษาไทยและหลายประโยคพร้อมกัน</span>
</div>
</div>
""")
text_input = gr.Textbox(
lines=7,
placeholder="ตัวอย่าง: วันนี้อากาศดีมาก. ฉันมีความสุขมาก\nหรือ\nวันนี้อากาศดีมาก\nฉันมีความสุขมาก",
label=""
)
analyze_btn = gr.Button("� วิเคราะห์ข้อความ", elem_id="analyze-btn")
output_box = gr.Textbox(
label="📊 ผลการวิเคราะห์ความรู้สึก",
lines=15,
show_copy_button=True
)
# ต้องสร้างตัวอย่างหลัง text_input ถูกนิยามแล้ว
examples = gr.Examples(
examples=[
["วันนี้อากาศดีมาก ฉันรู้สึกมีความสุขมาก"],
["ฉันไม่ชอบอาหารนี้ รสชาติแปลกมาก"],
["วันนี้เป็นยังไง\nเรียนหนังสือกันไหม"],
["บริการดีมาก พนักงานใจดี\nแต่ของมีราคาแพงไปหน่อย\nโดยรวมแล้วพอใจ"]
],
inputs=[text_input],
label="คลิกเพื่อใส่ตัวอย่างในกล่องข้อความ"
)
gr.Markdown("""
<div class='main-card' style='margin-top:24px; background: #f8f9fa;'>
<div style="display: flex; justify-content: space-around; padding: 10px 0;">
<div style="text-align: center;">
<div style="font-size: 24px;">😊</div>
<strong>Positive</strong><br>
<small>ความรู้สึกเชิงบวก</small>
</div>
<div style="text-align: center;">
<div style="font-size: 24px;">😔</div>
<strong>Negative</strong><br>
<small>ความรู้สึกเชิงลบ</small>
</div>
<div style="text-align: center;">
<div style="font-size: 24px;">😐</div>
<strong>Neutral</strong><br>
<small>ความรู้สึกเป็นกลาง</small>
</div>
<div style="text-align: center;">
<div style="font-size: 24px;">❓</div>
<strong>Question</strong><br>
<small>ประโยคคำถาม</small>
</div>
</div>
</div>
""")
def analyze_wrapper(text, model_name):
return analyze_text(text, model_name)
analyze_btn.click(analyze_wrapper, inputs=[text_input, model_dropdown], outputs=output_box)
text_input.submit(analyze_wrapper, inputs=[text_input, model_dropdown], outputs=output_box)
model_dropdown.change(analyze_wrapper, inputs=[text_input, model_dropdown], outputs=output_box)
# ตัวอย่าง: คลิกแล้วใส่ข้อความในกล่อง
examples.dataset.click(lambda x: x[0] if isinstance(x, list) and x else "", outputs=text_input)