警告

現在、このドキュメントは古いバージョンをご覧いただいています。 最新の情報をご希望の場合は、下記をご参照してください 5.1 .

(例)ベッコフTwinCAT

ここでは、ベッコフTwinCATバージョン3.1のEtherCATモジュールに EYE+ を簡単に統合する例を紹介します。

前提条件

始める前に、以下のファイルが既にダウンロードされていることを確認してください。
  • EYE+ EtherCAT ESIファイル(電子データシート)

  • 容易な統合を可能にするEYE+ TwinCATプロジェクトテンプレート(事前に宣言された変数を含む)【オプション】

これらのファイルは、 EtherCAT ダウンロード からダウンロードできます。

必要なファイルをダウンロードしたら、ベッコフTwinCATのインストールフォルダにESIファイルを必ずインストールしてください。

<path_to_twincat_install>\3.1\Config\Io\EtherCAT

<path_to_twincat_install> は、通常 C:\TwinCAT\ です。

ESIファイルを正しいフォルダにインストールしたら、ベッコフTwinCATを再起動したことを確認してください。

基本的な統合

すべての準備が整ったら、新しいベッコフTwinCATプロジェクトの作成に進みます。そして、左上の部分にある以下のアイコンを押して、Co設定モード(Configuration Mode)になっていることを確認してください。

../../../_images/twincat_config_mode.png

その後、EtherCATバスをスキャンして EYE+ とマスターデバイスを認識し、位置を特定する準備が整いました。スキャンオプションは、左ペインにあるデバイス(Devices)を右クリックすることで利用できます。

../../../_images/twincat_scan.png

スキャンプロセスには数秒かかるかもしれませんが、現在バスに接続されているすべてのデバイスが検出されます。

注釈

スキャンが終了してもお使いの EYE+ がリストに表示されない場合は、正しく接続され、電源が入っていることを確認してください。それでも問題が解決しない場合は、サポートチームまでお問い合わせください。

正しくスキャンが完了できると、デバイス(Devices)の下のリストに EYE+ のボックスも表示されます。

../../../_images/twincat_scan_complete.png

オプションのテンプレートをダウンロードされた方は、次のステップに進んでください。テンプレートをインポートすることで、 EYE+ を完全に活用するために必要なすべての変数が作成されます。テンプレートのインポートは簡単で、PLCプロジェクトを右クリックして、ZIPからインポート(Import From ZIP)をクリックします。

../../../_images/twincat_import_template.png

正しくインポートできていれば、変数の構造全体が利用できるようになります。

../../../_images/twincat_variables.png

TwinCAT内で変数を利用できるようにプロジェクトを構築する必要があります。変数を EYE+ の変数にマッピングするには、マルチリンク機能(Multi Link functionality)を使うと簡単に行うことができます。

../../../_images/twincat_variables_built.png
../../../_images/twincat_multilink.png

変数のマッピングが完了し、ランニングモードで再起動すると、レジスタのライブフィードバックが得られるはずです。

../../../_images/twincat_prod.png

次のサンプルコードでは、 EYE+ コントローラで以前作成したレシピの自動運転を開始し、最初のパーツを取得することができます。これを行うには、 udRecipeID をそのレシピの ID に設定し、 boStart を True に設定してください。認識されたパーツの座標は reRobotTargetXreRobotTargetYreRobotTargetRz で返されます。

(*
 * This sample code is distributed under the license CC0 1.0 Universal,
 * you can get a copy of the license at https://creativecommons.org/publicdomain/zero/1.0/
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
 * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 *)

 VAR
         udRecipeID: UDINT;
         boStart: BOOL;
         R_TRIG_Start: R_TRIG;
         boStop: BOOL;
         R_TRIG_Stop: R_TRIG;
         boClearError : BOOL;
         inLastErrorID: UDINT;
         eState: UDINT;
         reRobotTargetX: REAL;
         reRobotTargetY: REAL;
         reRobotTargetRz: REAL;
 END_VAR

 VAR CONSTANT
         STATE_IDLE: UDINT := 0;
         STATE_START_PRODUCTION: UDINT := 10;
         STATE_ROBOT_MOVE_OUT_FOV: UDINT := 20;
         STATE_GET_PART: UDINT := 30;
         STATE_ROBOT_PICK_PLACE: UDINT := 50;
         STATE_STOP_PRODUCTION: UDINT := 60;
         STATE_ERROR: UDINT := 100;
 END_VAR

 R_TRIG_Start(CLK:= boStart);
 R_TRIG_Stop(CLK:= boStop);

 CASE eState OF

         STATE_IDLE:
                 IF R_TRIG_Start.Q THEN
                         eState := STATE_START_PRODUCTION;
                 END_IF

         STATE_START_PRODUCTION:
                 EYEplus.suEYEplusOutputGLO.udRecipeIDGOU := udRecipeID;
                 EYEplus.suEYEplusOutputGLO.boStartProductionTriggerGOU := TRUE;

                 IF EYEplus.suEYEplusInputGLO.boStartProductionDoneGIN AND NOT EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.boStartProductionTriggerGOU := FALSE;
                         eState := STATE_ROBOT_MOVE_OUT_FOV;
                 ELSIF EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.boStartProductionTriggerGOU := FALSE;
                         eState := STATE_ERROR;
                 END_IF

         STATE_ROBOT_MOVE_OUT_FOV:
                 //Robot move out of field of view
                 //Check that the movement is done before to go first get_part
                 eState := STATE_GET_PART;

         STATE_GET_PART:
                 EYEplus.suEYEplusOutputGLO.boGetPartTriggerGOU := TRUE;

                 IF EYEplus.suEYEplusInputGLO.boGetPartDoneGIN AND NOT EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         reRobotTargetX  := EYEplus.suEYEplusInputGLO.rePose1XGIN;
                         reRobotTargetY  := EYEplus.suEYEplusInputGLO.rePose1YGIN;
                         reRobotTargetRz := EYEplus.suEYEplusInputGLO.rePose1RzGIN;
                         EYEplus.suEYEplusOutputGLO.boGetPartTriggerGOU := FALSE;
                         eState := STATE_ROBOT_PICK_PLACE;
                 ELSIF EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.boGetPartTriggerGOU := FALSE;
                         eState := STATE_ERROR;
                 END_IF

         STATE_ROBOT_PICK_PLACE:
                 //Robot pick and place the part
                 //Check that the movement is done before to go make another get_part
                 eState := STATE_GET_PART;

         STATE_STOP_PRODUCTION:
                 EYEplus.suEYEplusOutputGLO.udStopStateGOU := 16#FF;

                 IF EYEplus.suEYEplusInputGLO.boStopStateDoneGIN AND NOT EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.udStopStateGOU := 16#00;
                         eState := STATE_IDLE;
                 ELSIF EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.udStopStateGOU := 16#00;
                         eState := STATE_ERROR;
                 END_IF

         STATE_ERROR:
                 EYEplus.suEYEplusOutputGLO.udStopStateGOU := 16#00;
                 EYEplus.suEYEplusOutputGLO.boStartProductionTriggerGOU := FALSE;
                 EYEplus.suEYEplusOutputGLO.boGetPartTriggerGOU := FALSE;

                 inLastErrorID := EYEplus.suEYEplusInputGLO.udErrorIDGIN;
                 EYEplus.suEYEplusOutputGLO.boClearErrorTriggerGOU := boClearError;

                 IF NOT EYEplus.suEYEplusInputGLO.boIsErrorGIN THEN
                         EYEplus.suEYEplusOutputGLO.boClearErrorTriggerGOU := FALSE;
                         eState := STATE_STOP_PRODUCTION;
                 END_IF;
 END_CASE

 IF R_TRIG_Stop.Q THEN
         EYEplus.suEYEplusOutputGLO.boStartProductionTriggerGOU := FALSE;
         EYEplus.suEYEplusOutputGLO.boGetPartTriggerGOU := FALSE;
         EYEplus.suEYEplusOutputGLO.boClearErrorTriggerGOU := FALSE;

         eState := STATE_STOP_PRODUCTION;
 END_IF