본문 바로가기

Robotics/Software Tech.

조이스틱 컨트롤 에뮬레이션


로봇을 수동으로 조종할 수 있는 방법은 많이 있다. PC를 사용한다면, 키보드, 마우스, 조이스틱등등...
이밖에도 블루투스같은 통신이나 무선랜을 이용하여 수동제어 하는 방법들이 있다.
실제 마우스로 조종을 하지만, 조이스틱과 같은 UI를 가진 조종 프로그램이 있다면 어떨까..

실제로 많은 개발자들은 핵심적인 기능구현에 많은 시간을 투자한다. 사실 그게 맞다. 하지만 기능구현과 더불어 중요한것이 바로 GUI이다. 화려한 GUI를 요구하는 시스템은 분명 아닐것이라는 가정하에, GUI는 단순히 보여주는 그 이상의 기능을 해야한다. 로봇이나 컴퓨터가 사람에게 어떠한 정보를 전달 해 줄 수 있는 매개체가 무엇이겠는가... 사운드, 모니터뿐 아니겠는가...

최대한 사용자는 소프트웨어를 사용하기 쉬워야 하고, 복잡하지 않으며, 과정 또는 결과데이터를 한눈에 보여 줄 수 있어야 한다고 본인은 생각한다. 소프트웨어의 조작방법이 한눈에 들어오지 않고, 그 사용법이 모호하여 혼란을 준다면, 누가 그 프로그램을 밤새 익혀가며 사용하려고 하겠는가..
뭐, 세상에 그 프로그램만이 존재하고, 그 프로그램만이 자신에게 도움이 된다고 한다면 또 모를일이겠지만...

전문적으로 UI를 컴포넌트화하여 판매하는 회사도 있다.
본인이 아는 대표적인 제품이 IOCOMP이다.(http://www.iocomp.com)
다양한 UI들이 있고, 사용하기도 간편하기때문에 많이 사용한다. 하지만, 이 컴포넌트를 자신이 개발하고 있는 소프트웨어에 탑재하여 판매가 이루어질시에는 라이센스 비용을 물어야 한다는 점이 걸린다..

하지만, 코드구루나 구글링, 코드프로젝트를 통해 100% free 코드를 얻을 수 있지 않은가...(일부의 경우 상업용으로 사용할때 별도의 라이센스계약을 이뤄야 하는경우도 있다.)

이번에 찾은것은 마우스로 조작하는 조이스틱과 같은 컨트롤 UI를 가진 프로그램을 찾는 것이다. 조이스틱이 없을때 조이스틱과 유사하게 제어할 수 있도록 하기위함 이랄까...

이 프로그램도, 잘 다듬고 기능을 추가/변경한다면 쓸만한 UI 컴포넌트가 나오지 않을까 생각한다.



Velocity-Based Joystick Controller

Currently, I am working towards building an omni-directional autonomous mobile robot. Omni-directional refers to a vehicle that could translate (or move) and spin (or rotate) simultaneouly. Just for an example, your car is not an omni-directional vehicle. As part of this ongoing project, I was assigned the job of building an application that could control the robot's motion from a desktop, remotely, rather than using a physical joystick as a child would normally drive his "Remote Toy Car." The application should be able to spit commands for both the modes of action (move and spin), simultaneouly. So, I did one and called it the Joystick Controller. Here is a part of it that is developed as the user interface.

The Joystick Controller is built as a stand-alone subclass that is derived from CStatic. To use this in your application, all that needs to be done is subclass a static control (the placeholder for the joystick control) in the dialog with the provided CJoystickCtrl class. For testing and demonstration purposes, the provided application shows a pie-shaped wedge that moves and rotates (with respect to the center) in the left half of the window. The different modes of action for the joystick are mapped to the various mouse events.

NOTE: ALL THE GENERATED VALUES ARE WITH RESPECT TO THE CENTER OF THE JOYSTICK AND NOT WITH RESPECT TO THE CLIENT AREA OR THE WINDOW AREA.

For a mouse click event in the Stick region (the gradient filled region of figure above):

  • Left Mouse Button Down: Increases the velocity of movement by a value equal to the distance between the mouse click point and the center of the joystick. For generalization purposes, the value is mapped between 0 and 10. The direction of the line from the center of the joystick to the mouse click provides the direction of the movement.
  • Left Mouse Button Up: Brings back the joystick's stick region to the stand-alone mode. In this mode, it spits only zeros.
  • Right Mouse Button Down: Same as that of left mouse button down except that it does not move to the stand-alone mode on the Right Mouse Button Up event.

For a mouse click event in the Spin region (the arced region of the figure above):

  • Left Mouse Button Down: Increates the velocity of rotation by a value equal to the distance between the mouse click point and the point of half the arc-length. Again, for generalization purposes the values are mapped between -10 to +10. The sign of the generated value gives the direction of rotation. Negative for anti-clockwise and positive for clockwise rotation.
  • Left Mouse Button Up: Brings back the joystick's spin region to the stand alone-mode—so spits only zero.
  • Right Mouse Button Down: Same as that of left mouse button down except that it does not move to the stand-alone mode on the Right Mouse Button Up event.

The basic idea of the implementation is that we should be able to issue a rotation command while something is already moving or vise-versa. Moreover, it should be able to issue variable commands based on the desired velocity; in other words, the farther you drive from the center, the faster the dependent object moves.

The demo application (previewed in the picture above) shows a pie-shaped structure (the dependent) in the left half of the window—moving and rotating simulataneously. The speed by which the pie moves or rotates is totally controllable by the joystick on the other half of the window.

Steps to Add This to Your Project

Say, m_Joystick is the object you make for the IDC_JOYSTICK static-object in the dialog box. Add the following line in the InitDialog for a dialog-based application (or in the equivalent funtion in a window-based application):

m_Joystick.SubclassDlgItem(IDC_JOYSTICK, this);

This is all is required to get the joystick to show up on your window. To get the direction of movement, the velocity of movement, and rotation, one can use the following public functions provided as members of the CJoystickCtrl class.

// To get the move direction.
// this is with respect to the center (0, 0) of the joystick
CPoint GetMoveDir();

// To get the rate at which to move
// Is mapped between 0 to 10
int GetMoveRate();

// To get the rate at which to move
// Is mapped between -10 to 10
// Negative value indicates anti-clockwise rotation and
// Positive value indicates clockwise rotation
int GetAngle();
This control can easily be used to control the movement and orientation of moving objects in the real world. At least, for now it is successfully being used to control my ROBOTS.

Downloads

Download demo project - 29 Kb
Download source - 7 Kb