#!/bin/sh # Requires: rofi, xclip, xdotool, a color emoji font (Noto Color Emoji) # Emoji and kaomoji picker: search by name, Enter copies the character to the # clipboard and pastes it into whatever window was focused before rofi opened. # Terminals don't bind plain ctrl+v to paste, so terminal window classes get # ctrl+shift+v instead; override the whole thing with ROFI_EMOJI_PASTE_KEYS. # Picks are remembered and float to the top, so the handful anyone actually # uses stop needing to be searched for. set -u DATA=${ROFI_EMOJI_DATA:-$(dirname "$0")/../emoji.txt} RECENT="${XDG_CACHE_HOME:-$HOME/.cache}/rofi-emoji-recent" RECENT_MAX=${ROFI_EMOJI_RECENT_MAX:-30} [ -f "$DATA" ] || { echo "rofi-emoji: no emoji data at $DATA" >&2; exit 1; } touch "$RECENT" # Two spaces between the character and its name: a kaomoji can contain single # spaces, so a single space would be ambiguous when splitting the choice back # apart. Names stay in the row because that is what the search filters on. rows() { cat "$RECENT" "$DATA" | awk -F'\t' '!seen[$1]++ { printf "%s %s\n", $1, $2 }' } TARGET_WIN=$(xdotool getactivewindow 2>/dev/null) || TARGET_WIN= CHOICE=$(rows | rofi -dmenu -i -no-custom -p "emoji" -matching normal) || exit 0 [ -n "$CHOICE" ] || exit 0 CHAR=${CHOICE%% *} NAME=${CHOICE#* } printf '%s' "$CHAR" | xclip -selection clipboard -i if [ -n "$TARGET_WIN" ]; then TARGET_CLASS=$(xdotool getwindowclassname "$TARGET_WIN" 2>/dev/null || echo) case "$TARGET_CLASS" in *[Tt]erm*|kitty|st|st-256color|foot|footclient|tilix|konsole) DEFAULT_PASTE_KEYS="ctrl+shift+v" ;; *) DEFAULT_PASTE_KEYS="ctrl+v" ;; esac PASTE_KEYS=${ROFI_EMOJI_PASTE_KEYS:-$DEFAULT_PASTE_KEYS} xdotool windowactivate --sync "$TARGET_WIN" 2>/dev/null xdotool key --clearmodifiers --window "$TARGET_WIN" "$PASTE_KEYS" 2>/dev/null fi # Rewrite the recents file with this pick first and its older copy dropped. tmp="$RECENT.$$" printf '%s\t%s\n' "$CHAR" "$NAME" > "$tmp" grep -Fxv "$(printf '%s\t%s' "$CHAR" "$NAME")" "$RECENT" >> "$tmp" 2>/dev/null head -n "$RECENT_MAX" "$tmp" > "$RECENT" rm -f "$tmp" command -v dunstify >/dev/null 2>&1 && dunstify -r 7302 "Pasted $CHAR" "$NAME" || notify-send "Pasted $CHAR" "$NAME"