Move a Fanuc robot remotely using the SDK. There are several approaches depending on your application requirements.

## RMI : TP-like motion commands

RMI (Remote Motion Interface) sends motion instructions similar to a TP program. Best for pick-and-place, welding paths, and multi-waypoint trajectories.

**C# : RmiMotion**
```csharp
using System;
using UnderAutomation.Fanuc;
using UnderAutomation.Fanuc.Common;
using UnderAutomation.Fanuc.Rmi.Data;
using UnderAutomation.Fanuc.Rmi.TpInstructions;

public class RmiMotion
{
    static void Main()
    {
        FanucRobot robot = new FanucRobot();
        ConnectionParameters parameters = new ConnectionParameters("192.168.0.1");
        parameters.Rmi.Enable = true;
        robot.Connect(parameters);

        // Check status
        RmiControllerStatusResponse status = robot.Rmi.GetStatus();
        if (status.TPEnabled)
        {
            Console.WriteLine("Turn off the teach pendant before proceeding.");
            return;
        }
        if (!status.ServoReady)
        {
            Console.WriteLine("Servos are not ready.");
            return;
        }

        // Initialize RMI_MOVE
        robot.Rmi.Initialize();

        // Set speed override
        robot.Rmi.SetOverride(80);

        // Move to a start position
        robot.Rmi.SendTpInstruction(new JointMotionJRepTpInstruction
        {
            SpeedType = RmiJointSpeedType.Percent,
            Speed = 10,
            TermType = RmiTerminationType.Fine,
            Joints = new JointsPosition(0, 0, 0, 0, 0, 0)
        }).WaitForCompletion();

        // Approach
        robot.Rmi.SendTpInstruction(new LinearMotionTpInstruction
        {
            SpeedType = RmiLinearSpeedType.MmSec,
            Speed = 200,
            TermType = RmiTerminationType.Cnt,
            TermValue = 50,
            Target = new CartesianPositionWithUserFrame(500, 200, 350, 0, 90, 0, 1, 0)
        });

        // Descend to pick position
        robot.Rmi.SendTpInstruction(new LinearMotionTpInstruction
        {
            SpeedType = RmiLinearSpeedType.MmSec,
            Speed = 50,
            TermType = RmiTerminationType.Fine,
            Target = new CartesianPositionWithUserFrame(500, 200, 300, 0, 90, 0, 1, 0)
        }).WaitForCompletion();

        // Activate gripper
        robot.Rmi.SendTpInstruction(new CallProgramTpInstruction { ProgramName = "GRIP_ON" })
             .WaitForCompletion();

        // Retract
        robot.Rmi.SendTpInstruction(new LinearMotionTpInstruction
        {
            SpeedType = RmiLinearSpeedType.MmSec,
            Speed = 100,
            TermType = RmiTerminationType.Fine,
            Target = new CartesianPositionWithUserFrame(500, 200, 400, 0, 90, 0, 1, 0)
        }).WaitForCompletion();

        // Check HOLD state
        if (robot.Rmi.IsInHoldState)
        {
            Console.WriteLine("Controller in HOLD. Calling Reset...");
            robot.Rmi.Reset();
        }

        robot.Rmi.Abort();
        robot.Disconnect();
    }
}
```

**Python : RmiMotion**
```python
from underautomation.fanuc.fanuc_robot import FanucRobot
from underautomation.fanuc.connection_parameters import ConnectionParameters
from underautomation.fanuc.rmi.tp_instructions.cartesian_linear_instructions import LinearMotionTpInstruction
from underautomation.fanuc.rmi.tp_instructions.cartesian_joint_instructions import JointMotionTpInstruction
from underautomation.fanuc.rmi.tp_instructions.j_rep_joint_instructions import JointMotionJRepTpInstruction
from underautomation.fanuc.rmi.tp_instructions.simple_instructions import (
    WaitDinTpInstruction, WaitTimeTpInstruction,
    SetPayloadTpInstruction, CallProgramTpInstruction
)
from underautomation.fanuc.rmi.data.enums import (
    RmiLinearSpeedType, RmiJointSpeedType, RmiTerminationType, RmiOnOff
)
from underautomation.fanuc.common.cartesian_position_with_user_frame import CartesianPositionWithUserFrame
from underautomation.fanuc.common.joints_position import JointsPosition

robot = FanucRobot()
parameters = ConnectionParameters("192.168.0.1")
parameters.rmi.enable = True
robot.connect(parameters)

# Check status before initializing
status = robot.rmi.get_status()
if status.tp_enabled:
    print("Turn off the teach pendant before proceeding.")
    robot.disconnect()
    exit()

robot.rmi.initialize()
robot.rmi.set_override(80)

# Move to home using joint motion with joint-angle target
home = JointMotionJRepTpInstruction()
home.speed_type = RmiJointSpeedType.PERCENT
home.speed = 10
home.term_type = RmiTerminationType.FINE
home.joints = JointsPosition(0, 0, 0, 0, 0, 0)
robot.rmi.send_tp_instruction(home).wait_for_completion()

# Approach
approach = LinearMotionTpInstruction()
approach.speed_type = RmiLinearSpeedType.MM_SEC
approach.speed = 200
approach.term_type = RmiTerminationType.CNT
approach.term_value = 50
approach.target = CartesianPositionWithUserFrame(500, 200, 350, 0, 90, 0, 1, 0)
robot.rmi.send_tp_instruction(approach)

# Descend to pick position
pick = LinearMotionTpInstruction()
pick.speed_type = RmiLinearSpeedType.MM_SEC
pick.speed = 50
pick.term_type = RmiTerminationType.FINE
pick.target = CartesianPositionWithUserFrame(500, 200, 300, 0, 90, 0, 1, 0)
robot.rmi.send_tp_instruction(pick).wait_for_completion()

# Activate gripper
grip = CallProgramTpInstruction()
grip.program_name = "GRIP_ON"
robot.rmi.send_tp_instruction(grip).wait_for_completion()

# Retract
retract = LinearMotionTpInstruction()
retract.speed_type = RmiLinearSpeedType.MM_SEC
retract.speed = 100
retract.term_type = RmiTerminationType.FINE
retract.target = CartesianPositionWithUserFrame(500, 200, 400, 0, 90, 0, 1, 0)
robot.rmi.send_tp_instruction(retract).wait_for_completion()

# Handle HOLD state
if robot.rmi.is_in_hold_state:
    print("Controller in HOLD. Calling reset...")
    robot.rmi.reset()

robot.rmi.abort()
robot.disconnect()
```

**Requirements**: J992 (Remote Motion Interface) robot option.

See also: [RMI Motion commands](/fanuc/documentation/rmi-motion)

## Stream Motion : Real-time streaming (J519)

Stream Motion sends joint or Cartesian positions at up to 250 Hz via UDP. Best for real-time control, force feedback, and adaptive paths.

**C# : MoveRobotRemotelyStreamMotion**
```csharp
using System;
using UnderAutomation.Fanuc;
using UnderAutomation.Fanuc.StreamMotion;
using UnderAutomation.Fanuc.StreamMotion.Data;

public class MoveRobotRemotelyStreamMotion
{
    static void Main()
    {
        FanucRobot robot = new FanucRobot();

        /**/
        // Connect and start streaming
        var parameters = new ConnectionParameters("192.168.0.1");
        parameters.StreamMotion.Enable = true;
        robot.Connect(parameters);
        robot.StreamMotion.Start();

        // Send a joint command
        robot.StreamMotion.SendJointCommand(new MotionData
        {
            J1 = 0,
            J2 = -30,
            J3 = 45,
            J4 = 0,
            J5 = 60,
            J6 = 0
        });

        // React to state updates (~125–250 Hz)
        robot.StreamMotion.StateReceived += (s, e) =>
        {
            StatePacket state = e.State;
            // state.JointPosition, state.CartesianPosition, state.Status...
        };
        /**/
    }
}
```

**Python : MoveRobotRemotelyStreamMotion**
```python
from underautomation.fanuc.fanuc_robot import FanucRobot

robot = FanucRobot()

##
# Connect and start streaming
robot.stream_motion.connect("192.168.0.1")
robot.stream_motion.start()

# Send a joint command
robot.stream_motion.send_joint_command(j1=0, j2=-30, j3=45, j4=0, j5=60, j6=0)

# React to state updates (~125-250 Hz)
def on_state_received(sender, e):
    state = e.State
    # state.joint_position, state.cartesian_position, state.status...

robot.stream_motion.state_received += on_state_received
##
```

**Requirements**: J519 (Stream Motion) robot option.

See also: [Stream Motion](/fanuc/documentation/stream-motion)

## SNPX + DPM : Position register handshake

See : [Move Robot with Mouse](/fanuc/documentation/move-robot-with-mouse)

# FTP

If you have option ASCII Upload, you can build th TP program .ls file, download it via FTP and execute the task with Telnet, SNPX. or CGTP

See : [TP editor with breakpoints](/fanuc/documentation/tp-editor-with-breakpoints)

## CGTP

CGTP allows you to create a new program, insert instructions, and execute it.