ひとしれずひっそり

主にソフトに関することをメモしていきます。過程をそのまま書いていたりするので間違いが含まれます。鵜呑みしない様に。

M5でmruby/c (5)

クラスは作れたんだけどメソッド呼び出しがうまくいかない。

https://github.com/mrubyc/mrubyc/blob/master/src/class.c#L131-L155

メソッドの定義はこちらで処理されている。

void mrbc_define_method(struct VM *vm, mrbc_class *cls, const char *name, mrbc_func_t cfunc)

前回最初の引数を0にしていたがVMへのポインターを渡す様だ。
関数ポインターmrbc_func_t という型になる。

typedef void (*mrbc_func_t)(struct VM *vm, struct RObject *v, int argc);

https://github.com/mrubyc/mrubyc/blob/master/src/value.h#L62

るびまの記事を参考にする。

https://github.com/kishima/libmrubycForWioLTEArduino/blob/master/src/hal/ext_wio.cpp#L15-L30

static void class_wio_control_led(mrb_vm *vm, mrb_value *v, int argc )
{
    if(argc!=3){
        SET_FALSE_RETURN();
        return;
    }
    if(wio==NULL){
        DEBUG_PRINT("wio==NULL\n");
        return;
    }
    int r=GET_INT_ARG(1);
    int g=GET_INT_ARG(2);
    int b=GET_INT_ARG(3);
    wio->LedSetRGB(r, g, b);
    SET_TRUE_RETURN();
}
  • 引数の数をチェック
  • 操作するデバイスが存在するか確認
  • GET_INT_ARG()で引数から値を取得している
  • SET_TRUE_RETURN()で戻り値をセット

という感じだろうか。

それに倣ってこうしてみる.

static void
class_display_set_text_size(mrb_vm *vm, mrb_value *v, int argc)
{
  mrb_int i;
    if(argc!=1){
        SET_FALSE_RETURN();
        return;
    }
    i = GET_INT_ARG(1);
  M5.Lcd.setTextSize((uint8_t)i);
    SET_TRUE_RETURN();
}

rubyコードは

Display.set_text_size(3)

実行してみると

Exception(vm_id=1): undefined local variable or method '3' for Display (NoMethodError)

引数の3が認識されていないみたいだ。

そもそもmrbcでコンパイルする時にDisplayがクラスだとどうやって認識するんだ。