How to Make a Robot Pet Cat

Part 1 - Brain

A three-tier learning stack that turns a Unitree Go1 into something that acts like a cat.

K. Jeff Rah
Independent ยท jeffrah89@gmail.com
5-minute autonomous rollout. No external command input โ€” the brain decides what to do moment by moment.

TL;DR

The cat-feel does not live in the locomotion layer and it does not live in the skill library. It lives in a small thing on top: a behavioral-mode attractor with a 6-dimensional mood latent and a stochastic decision period. Add those three to a vanilla PPO categorical head and a generic walker, and the rollout starts to look like a cat.

This page summarizes Part 1 โ€” Brain. It also describes the substrate the brain runs on (Tier 1 walker, Tier 2 skills) and documents the paradigms we tried and threw away.

The stack

brain (Tier 3) โ€” PPO + 6-D mood + 6-mode attractor, ~0.5 Hz โ†“ skill ID skills (Tier 2) โ€” { walk, crouch, lie_belly, stay } โ†“ velocity / joint targets motion (Tier 1) โ€” Go1 velocity-tracking walker (mjlab PPO), 50 Hz โ†“ joint torques MuJoCo + Unitree Go1

Each tier is independently trainable. The contribution of Part 1 is the brain layer plus the empirical observation that the skill set should be small โ€” four learned skills is enough, more skills do not help.

How it works

Mood Latent Attractor PPO Brain 6-dim OU process mode-transition policy MlpPolicy, Discrete(5) in: ε ~ N(0,I₆), dt out: state[0..5] in: mood weights, time_in_mode out: mode ∈ {REST,OBS,STALK, PLAY,GROOM,EXPLORE} in: 15-dim obs, reward weights, allowed skill mask out: skill ID, every 1.5–4 s state[0–2] (mode bias) skill mask (per-mode allow-list) state[3–5] → σ(2x) → (wₑ𝒗𝒗, wₐ𝒜𝒜, wₚ𝓁𝓎𝓎) walk / crouch / lie_belly / stay / get_up

Mood latent. A 6-dimensional Ornstein–Uhlenbeck process running at every physics step. The first three dimensions (energy, alertness, sociability) provide a continuous bias to the mode-transition softmax. The last three dimensions are passed through σ(2x) to produce the per-step reward weights (wcuriosity, wcomfort, wplay), making the reward landscape itself a function of internal state. The time constant is ~20 min, so mood evolves much slower than skill selection.

Attractor. A mode-transition policy over six behavioral modes. At each potential transition point it computes logits as a linear function of the current mood weights, then samples from softmax(logits / T). A transition is gated by a minimum dwell time, so the cat commits to a mode for tens of seconds before reconsidering. Each mode defines an allow-list of skills and a set of hard-blocked skills (e.g. walk is always blocked in RESTING and GROOMING). Out-of-allow-list actions are suppressed stochastically with a 70/30 soft-pass rather than a hard mask, preserving gradient flow.

PPO brain. An MlpPolicy over a 15-dim observation vector (mood state[6], XY position[2], cos/sin yaw[2], body height[1], horizontal speed[1], normalized time-in-skill[1], play-target Δxy[2]) with a Discrete(5) action head. Index 0 is HOLD; indices 1–5 map to the five skills. The policy is queried on a stochastic commitment schedule (T ~ U(1.5, 4.0) s) rather than every step, which eliminates high-frequency skill thrashing without modifying the policy architecture. Entropy regularization (ent_coef = 0.05) is critical to prevent collapse to a single dominant skill.

Skill library

Four learned skills. Earlier versions of the system carried fifteen named skills; we converged here after the faking-is-enough principle: scripted PD for postures, RL only where RL is necessary.

What we tried and removed

A paper that only reports the final design overstates how obvious that design was. These paradigms were tried, integrated, and removed:

AMP imitation track. Trained PPO + a style discriminator over ~20 retargeted cat motion clips. Under velocity commands, the resulting policy moved zero meters in five seconds. We moved cat-feel up to Tier 3.

Released weights

FileSizePurpose
models/mjlab_go1_walker_normal.pt4.6 MBTier 1 walker + walk skill
models/mjlab_go1_crouch.pt4.4 MBcrouch skill
checkpoints/brain/brain_4skill_v1.zip156 KBTier 3 PPO brain, Discrete(5)

All weights are MIT-licensed and hosted on GitHub.

Quickstart

git clone https://github.com/jeffrah00/robot-pet-cat.git
cd robot-pet-cat
python3.11 -m venv .venv && source .venv/bin/activate
pip install -e ".[dev]"

# Download released weights (~5 MB total)
python scripts/download_weights.py

# Run a 30-second autonomous rollout
python scripts/render_brain_3d.py \
    --checkpoint checkpoints/brain/brain_4skill_v1.zip \
    --duration 30 --output renders/demo.mp4

BibTeX

@article{rah2026brain,
  title   = {How to Make a Robot Pet Cat: Part 1 --- Brain},
  author  = {Rah, K. Jeff},
  journal = {arXiv preprint},
  year    = {2026}
}

What's next

Part 1 is the brain on top of a sim-only substrate. Future parts: