How to Add “Convert to GIF” to Thunar on Linux (XFCE)

Add a right-click Convert to GIF action to the Thunar file manager on Linux XFCE using FFmpeg and a shell script — turn any video into a GIF in two clicks.

1152_convert-to-gif-hero

I wanted to right-click a video file and instantly turn it into a GIF without opening a video editor or typing long ffmpeg commands (I have no idea how to use ffmpeg btw).

This is for me to remember in the future how to do this if I ever lose the configuration that I have at the moment, so it’s more like a memento than a tutorial.


🧰 What You’ll Need

We’ll use three small tools:

  • FFmpeg – does the actual conversion
  • Zenity – provides a small graphical prompt for options
  • libnotify-bin – sends a desktop notification when the GIF is ready

Install them with:

sudo apt update
sudo apt install -y ffmpeg zenity libnotify-bin

⚙️ Step 1 — Create the conversion script

Create a folder for user scripts (if it doesn’t exist):

mkdir -p ~/.local/bin

Then create the script file:

nano ~/.local/bin/mp4-to-gif

Paste the following:

#!/usr/bin/env bash
set -euo pipefail

have() { command -v "$1" >/dev/null 2>&1; }
notify_ok() { have notify-send && notify-send "GIF created" "$1"; }

FPS_DEFAULT=12
WIDTH_DEFAULT=640
START_DEFAULT=0
DUR_DEFAULT=""

USE_ZENITY=false
if have zenity; then
  CHOICE=$(zenity --list --radiolist --width=420 --height=260 \
    --title="MP4 → GIF options" \
    --text="Choose a preset (you can tweak values after picking one):" \
    --column="" --column="Preset" --column="Details" \
    TRUE "Standard" "FPS 12, width 640, full clip" \
    FALSE "First 10s" "FPS 12, width 640, duration 10s" \
    FALSE "Smooth" "FPS 24, width 720" 2>/dev/null || echo "")

  case "$CHOICE" in
    "First 10s") DUR_DEFAULT=10 ;;
    "Smooth") FPS_DEFAULT=24; WIDTH_DEFAULT=720 ;;
  esac

  FPS=$(zenity --entry --title="FPS" --text="Frames per second" --entry-text="$FPS_DEFAULT" 2>/dev/null || echo "$FPS_DEFAULT")
  WIDTH=$(zenity --entry --title="Width" --text="Output width" --entry-text="$WIDTH_DEFAULT" 2>/dev/null || echo "$WIDTH_DEFAULT")
  START=$(zenity --entry --title="Start time (sec)" --entry-text="$START_DEFAULT" 2>/dev/null || echo "$START_DEFAULT")
  DUR=$(zenity --entry --title="Duration (sec)" --entry-text="$DUR_DEFAULT" 2>/dev/null || echo "$DUR_DEFAULT")
  USE_ZENITY=true
else
  FPS="$FPS_DEFAULT"; WIDTH="$WIDTH_DEFAULT"; START="$START_DEFAULT"; DUR="$DUR_DEFAULT"
fi

if [ $# -lt 1 ]; then
  echo "Usage: mp4-to-gif file1.mp4 [file2.mp4 ...]" >&2
  exit 1
fi

for inpath in "$@"; do
  [ ! -f "$inpath" ] && continue
  base="${inpath%.*}"
  outgif="${base}.gif"
  palette="$(mktemp --suffix=.png)"
  vf="fps=${FPS},scale=${WIDTH}:-1:flags=lanczos"
  ss_args=(); t_args=()
  [ "$START" != "0" ] && ss_args=(-ss "$START")
  [ -n "$DUR" ] && t_args=(-t "$DUR")

  ffmpeg -v warning "${ss_args[@]}" "${t_args[@]}" -i "$inpath" \
    -vf "$vf,palettegen=stats_mode=full" -y "$palette"

  ffmpeg -v warning "${ss_args[@]}" "${t_args[@]}" -i "$inpath" -i "$palette" \
    -lavfi "$vf [x]; [x][1:v] paletteuse=dither=sierra2_4a" \
    -y "$outgif"

  rm -f "$palette"
  notify_ok "$outgif"
  have xclip && printf "%s" "$outgif" | xclip -selection clipboard
done

$USE_ZENITY && zenity --info --text="GIF conversion complete!" --timeout=2 2>/dev/null || true

Make it executable:

chmod +x ~/.local/bin/mp4-to-gif

🖱️ Step 2 — Add the Thunar Context Menu Action

  1. Open Thunar → Edit → Configure Custom Actions → “+”
  2. Name: Convert to GIF
  3. Command:
    mp4-to-gif %F
  4. Switch to Appearance Conditions tab:
    • File pattern: *.mp4;*.mov;*.mkv
    • Check “Video files” (and optionally “Other files”)

🚀 Step 3 — Test It!

Right-click any video file in Thunar and choose Convert to GIF.

You’ll see a Zenity dialog to set FPS, width, and duration. When done, you’ll get a desktop notification and your new .gif will appear next to the original file.


💡 Optional Enhancements

  • Add a “Convert to WebP” action for smaller, modern animated files.
  • Add an “Extract Clip” action to trim videos.
  • Add a “Mute Video” action to strip audio tracks.

Each action can reuse this same structure with a different ffmpeg command.


🧠 Why Palettegen?

Using FFmpeg’s palettegen + paletteuse creates the highest-quality GIFs possible, because it generates a custom 256-color palette for each video frame range. This avoids the grainy, banded look typical of single-pass conversions.


✨ Final Thoughts

This tiny workflow turns Thunar into a lightweight media studio. With a bit of shell scripting, Linux gives you power, automation, and simplicity — no heavy apps are needed.

Save this guide for your future self. The next time you reinstall your system, you’ll have your “Convert to GIF” shortcut ready in minutes.

Happy converting 🎥✨

PS
This page was generated by ChatGPT because I want to keep this on my blog, and I don’t have time to write a proper old-school fancy blog post. So get off my shoulders; it’s 2025.


About the Author

Ivan Morgillo is a freelance software developer and technical trainer with 15+ years of experience. He has worked with Google, JetBrains, Bending Spoons, Deutsche Bahn, OneFootball, and The Body Coach. He specialises in Android, Flutter, Ruby on Rails, and AI integration. Follow him on Twitter @hamen or watch his coding content on YouTube @codewiththeitalians.