Spaces:
Sleeping
Sleeping
| import random | |
| import re | |
| import gradio as gr | |
| import emoji | |
| # ------------------------- | |
| # Config | |
| # ------------------------- | |
| ELIGIBLE = ("NOUN", "ADJ") # for clarity; used by our simple tagger | |
| WORD2EMOJI = { | |
| # Nouns | |
| "heart":"β€οΈ","love":"β€οΈ","car":"π","bike":"π²","bicycle":"π²","bus":"π","train":"π","plane":"βοΈ", | |
| "pizza":"π","burger":"π","coffee":"β","tea":"π΅","book":"π","laptop":"π»","computer":"π₯οΈ", | |
| "phone":"π±","camera":"π·","money":"π°","cash":"π΅","rain":"π§οΈ","sun":"βοΈ","moon":"π","star":"β", | |
| "fire":"π₯","party":"π","gift":"π","music":"π΅","dog":"πΆ","cat":"π±","bird":"π¦","flower":"πΈ", | |
| "tree":"π³","house":"π ","home":"π ","school":"π«","office":"π’","hospital":"π₯","food":"π½οΈ", | |
| "cake":"π°","cookie":"πͺ","chocolate":"π«","icecream":"π¨","beach":"ποΈ","mountain":"β°οΈ","city":"ποΈ", | |
| "rocket":"π","earth":"π","globe":"π","world":"π","mail":"βοΈ","letter":"βοΈ","football":"π", | |
| "soccer":"β½","basketball":"π","tennis":"πΎ","medal":"π ","trophy":"π","alarm":"β°","clock":"β°", | |
| "idea":"π‘","lightbulb":"π‘","check":"β ","cross":"β","warning":"β οΈ", | |
| # Adjectives | |
| "happy":"π","sad":"π’","angry":"π‘","tired":"π΄","sleepy":"π΄","cool":"π","loveable":"π₯°", | |
| "lovely":"π₯°","beautiful":"π","pretty":"π","handsome":"π€΅","smart":"π§ ","brilliant":"π§ ", | |
| "fast":"β‘","quick":"β‘","slow":"π’","hot":"π₯","cold":"βοΈ","sweet":"π¬","salty":"π§", | |
| "spicy":"πΆοΈ","fresh":"π«§","strong":"πͺ","weak":"π«€","shiny":"β¨","clean":"π«§","dirty":"π§Ή", | |
| "busy":"π","rich":"π°","poor":"πͺ","lucky":"π","fun":"π","romantic":"π","scary":"π±" | |
| } | |
| ADJECTIVE_WORDS = { | |
| "happy","sad","angry","tired","sleepy","cool","loveable","lovely","beautiful","pretty", | |
| "handsome","smart","brilliant","fast","quick","slow","hot","cold","sweet","salty","spicy", | |
| "fresh","strong","weak","shiny","clean","dirty","busy","rich","poor","lucky","fun","romantic","scary" | |
| } | |
| # Heuristic suffixes | |
| _ADJ_SUFFIXES = ("y","ive","ful","less","ous","al","ic","able","ible","ish") | |
| _NOUN_SUFFIXES = ("tion","ment","ness","ity","er","or","ship","age","ance","ence","ism","ist") | |
| # ------------------------- | |
| # Utilities | |
| # ------------------------- | |
| def try_emojize_alias(word): | |
| """Try alias-based emojization without using 'strict' (for older emoji libs).""" | |
| lemma = word.lower() | |
| for cand in (f":{lemma}:", f":{lemma}_face:", f":{lemma}_emoji:", f":{lemma}_button:"): | |
| try: | |
| em = emoji.emojize(cand, language="alias") | |
| except TypeError: | |
| # very old emoji versions: no language kw; still OK | |
| em = emoji.emojize(cand) | |
| if em != cand: | |
| return em | |
| return None | |
| def tokenize(text): | |
| # Keep punctuation as separate tokens; include emojis as tokens | |
| return re.findall(r"\w+|[^\w\s]", text, flags=re.UNICODE) | |
| def simple_tag(tokens): | |
| """Return list of (token, tag) where tag is 'NOUN', 'ADJ', or 'OTHER'.""" | |
| tagged = [] | |
| for t in tokens: | |
| # Non-letters (punct/emoji) -> OTHER | |
| if not re.search(r"[A-Za-z]", t): | |
| tagged.append((t, "OTHER")) | |
| continue | |
| low = t.lower() | |
| if low in WORD2EMOJI: | |
| tagged.append((t, "ADJ" if low in ADJECTIVE_WORDS else "NOUN")) | |
| continue | |
| # Heuristics | |
| if low.endswith(_ADJ_SUFFIXES): | |
| tagged.append((t, "ADJ")) | |
| elif low.endswith(_NOUN_SUFFIXES) or t[:1].isupper(): | |
| tagged.append((t, "NOUN")) | |
| else: | |
| tagged.append((t, "OTHER")) | |
| return tagged | |
| # ------------------------- | |
| # Core function | |
| # ------------------------- | |
| def translate_text(text, mode="Replace", replacement_rate=1.0, keep_case=True, dedupe=True): | |
| try: | |
| text = (text or "").strip() | |
| if not text: | |
| return "" | |
| tokens = tokenize(text) | |
| tagged = simple_tag(tokens) | |
| out = [] | |
| for tok, tag in tagged: | |
| eligible = (tag in ELIGIBLE) and re.search(r"[A-Za-z]", tok) | |
| if eligible and random.random() <= replacement_rate: | |
| key = tok.lower() | |
| em = WORD2EMOJI.get(key) or try_emojize_alias(key) | |
| if em: | |
| if mode == "Replace": | |
| out.append(em) | |
| else: | |
| out.append(f"{tok} {em}" if not dedupe else f"{tok} {em}") | |
| continue | |
| out.append(tok) | |
| # No space before , . ! ? ; : ) ] } | |
| result = "" | |
| for i, t in enumerate(out): | |
| result += t | |
| if i < len(out) - 1: | |
| nxt = out[i + 1] | |
| if not re.match(r"^[,\.!\?;:\)\]\}]+$", nxt): | |
| result += " " | |
| if not keep_case: | |
| result = re.sub(r"[A-Za-z]+", lambda m: m.group(0).lower(), result) | |
| return result | |
| except Exception as e: | |
| # Show error message in UI instead of throwing | |
| return f"[Error in translate_text: {e}]" | |
| # ------------------------- | |
| # UI | |
| # ------------------------- | |
| EXAMPLES = [ | |
| "I love spicy pizza and hot coffee on a rainy day.", | |
| "The smart dog chased a happy cat around the house.", | |
| "We had a beautiful view of the city from the mountain.", | |
| "She wrote a brilliant idea in her notebook.", | |
| "This is a strong team with a cool product.", | |
| ] | |
| with gr.Blocks(title="Emoji Translator πβ‘οΈπππ") as demo: | |
| gr.Markdown( | |
| """ | |
| # Emoji Translator πβ‘οΈπππ | |
| Type a sentence β Iβll replace **nouns/adjectives** with matching emojis. | |
| **Mode** | |
| - **Replace**: swap eligible words with emojis | |
| - **Append**: keep words and add emojis right after | |
| **Tips** | |
| - Use the *Replacement rate* to control how many words get emojis. | |
| - Try examples below! | |
| """ | |
| ) | |
| with gr.Row(): | |
| with gr.Column(): | |
| inp = gr.Textbox(label="Your sentence", placeholder="Type hereβ¦", lines=4) | |
| mode = gr.Radio(choices=["Replace", "Append"], value="Replace", label="Mode") | |
| rate = gr.Slider(0.0, 1.0, value=1.0, step=0.05, label="Replacement rate") | |
| keep_case = gr.Checkbox(value=True, label="Preserve original capitalization") | |
| dedupe = gr.Checkbox(value=True, label="Avoid duplicate emojis when appending") | |
| btn = gr.Button("Translate β¨", variant="primary") | |
| with gr.Column(): | |
| out = gr.Textbox(label="Emoji-fied text", lines=4) | |
| gr.Examples(EXAMPLES, inputs=inp, label="Examples") | |
| btn.click(translate_text, inputs=[inp, mode, rate, keep_case, dedupe], outputs=out) | |
| if __name__ == "__main__": | |
| demo.launch() | |