[C++] 237 FLTK : マウスをドラッグして四角形を描く その3 フレーム描画 Fl_Box

[M1 Mac, Monterey 12.6.3, clang 13.0.0, FLTK 3.8.1, NO IDE]

FLTKのfl_frame関数でフレームを描くと残像が重なって使えなかったのですが、最新のフレームだけ表示すると正常になりました。

また前のコードでは拡げたエリアを縮小することはできませんでした。このコードでは伸縮自在です。

ただし複数のフレームを描くと直前のフレームが消えてしまうので、これを残す方法を考える必要があります。あくまで見た目の問題であって、フレームの座標自体は保存できるようになっています。

課題はありますが、かなり前進したと言えるでしょう。

#pragma once
#include <FLstd.h>
#include "cppstd.h"

class BoxXY : public Fl_Box {
    Fl_Input* inputFrame1;
    Fl_Input* inputFrame2;
    Fl_Input* inputFrame3;
    Fl_Input* inputFrame4;

    public:
        BoxXY(int x, int y, int width_input, int height_input, Fl_Input* input1,Fl_Input* input2, Fl_Input* input3,Fl_Input* input4);
        void draw();
    private:
        int handle(int);
};
#include "BoxXY.h"

extern Fl_Box *show_box;
int xx1, yy1, xx2, yy2, xx0, yy0;

BoxXY::BoxXY(int x, int y, int width_input, int height_input, Fl_Input* input1,Fl_Input* input2, Fl_Input* input3,Fl_Input* input4) : Fl_Box(FL_FLAT_BOX, x, y, width_input, height_input, "") 
{
    this->inputFrame1 = input1;
    this->inputFrame2 = input2;
    this->inputFrame3 = input3;
    this->inputFrame4 = input4;
}

void BoxXY::draw(){
    // 線の色(第1引数)はAからXの24段階グレースケール4値(top, left, bottom, rightの順)
    // 灰色線
    fl_frame("LLLL",xx1+65, yy1+190, xx0-xx1, yy0-yy1);
    // 白線
    // fl_frame("XXXX",xx1+65, yy1+190, xx0-xx1, yy0-yy1);
    // 黒線
    // fl_frame("AAAA",xx1+65, yy1+190, xx0-xx1, yy0-yy1);
}

int BoxXY::handle(int event){
    switch (event) {
        case FL_PUSH:{
            xx1 = Fl::event_x() - 65;
            yy1 = Fl::event_y() - 190;

            inputFrame1->value(to_string(xx1).c_str());
            inputFrame1->textsize(12);

            inputFrame2->value(to_string(yy1).c_str());
            inputFrame2->textsize(12);

            return 1;
        }
        case FL_RELEASE:{
            xx2 = Fl::event_x() - 65;
            yy2 = Fl::event_y() - 190;

            inputFrame3->value(to_string(xx2).c_str());
            inputFrame3->textsize(12);

            inputFrame4->value(to_string(yy2).c_str());
            inputFrame4->textsize(12);

            return 1;
        }
        case FL_DRAG:{
            xx0 = Fl::event_x() - 65;
            yy0 = Fl::event_y() - 190;

            inputFrame3->value(to_string(xx0).c_str());
            inputFrame3->textsize(12);

            inputFrame4->value(to_string(yy0).c_str());
            inputFrame4->textsize(12);

            show_box -> redraw(); // この行を追加
            this->redraw();

            return 1;
        }
        default:
            return Fl_Box::handle(event);
    }
}

[C++] 236 FLTK : マウスをドラッグして四角形を描く その2 図形の削除 Fl_Box

[M1 Mac, Monterey 12.6.3, clang 13.0.0, FLTK 3.8.1, NO IDE]

前回の続きです。

fl_draw_box関数で描いた図形はキャンバスに相当するFl_Boxをredrawすると削除できます。

四角形ではなくフレームを描く方法も試しましたが、残像が何個も重なるため実用には至りませんでした。

あとは図形を透過させれば出来上がりです。

clearBtn = new Fl_Button(565,190,50,30,"矩形\nクリア");
clearBtn->color(fl_rgb_color(112,128,144));
clearBtn->labelcolor(fl_rgb_color(208,207,207));
clearBtn->labelsize(12);
clearBtn->callback(clearCB);

--------------------------------------------------
void clearCB(Fl_Widget*, void*) {
    x1_input -> value(0);
    y1_input -> value(0);
    x2_input -> value(0);
    y2_input -> value(0);

    show_box -> redraw();
}

[C++] 235 FLTK : マウスをドラッグして四角形を描く その1 Fl_Box

[M1 Mac, Monterey 12.6.3, clang 13.0.0, FLTK 3.8.1, NO IDE]

動画にモザイクをかける範囲を指定する際、同時に四角形の枠が表示されるようにすると作業しやすくなります。

今のところ四角形自体は描けていますが、透明度が設定できないため描画した範囲の内容が隠れて全く見えません。

Fl_GL_Windowではアルファ値を設定できるようなのでそのうちテストしたいです。

記事とは関係ないですが、今日からMacOS Montereyを再度試しています。現時点の最新版はVentura 13.2です。

#pragma once
#include <FLstd.h>
#include "cppstd.h"
#include "Box.h"
#include <Line.h>

class BoxXY : public Fl_Box {
    Fl_Input* inputA1;
    Fl_Input* inputA2;
    Fl_Input* inputA3;
    Fl_Input* inputA4;

    public:
        BoxXY(int x, int y, int width_input, int height_input, Fl_Input* input1,Fl_Input* input2, Fl_Input* input3,Fl_Input* input4);
        void draw();
    private:
        int handle(int);
};
#include "BoxXY.h"

int xx1, yy1, xx2, yy2, xx0, yy0;

BoxXY::BoxXY(int x, int y, int width_input, int height_input, Fl_Input* input1,Fl_Input* input2, Fl_Input* input3,Fl_Input* input4) : Fl_Box(FL_FLAT_BOX, x, y, width_input, height_input, "") 
{
    this->inputA1 = input1;
    this->inputA2 = input2;
    this->inputA3 = input3;
    this->inputA4 = input4;
}

void BoxXY::draw(){
    fl_rectf(xx1+65, yy1+190, xx0-xx1, yy0-yy1, fl_rgb_color(255,250,240));

    // または
    // fl_draw_box(FL_FLAT_BOX, xx1+65, yy1+190, xx0-xx1, yy0-yy1, fl_rgb_color(255,250,240));

    // 以下の方法では残像が出る
    // fl_frame("XXXX",xx1+65, yy1+190, xx0-xx1, yy0-yy1);
    
}

int BoxXY::handle(int event){
    switch (event) {
        case FL_PUSH:{
            xx1 = Fl::event_x() - 65;
            yy1 = Fl::event_y() - 190;

            inputA1->value(to_string(xx1).c_str());
            inputA1->textsize(12);

            inputA2->value(to_string(yy1).c_str());
            inputA2->textsize(12);

            return 1;
        }
        case FL_RELEASE:{
            xx2 = Fl::event_x() - 65;
            yy2 = Fl::event_y() - 190;

            inputA3->value(to_string(xx2).c_str());
            inputA3->textsize(12);

            inputA4->value(to_string(yy2).c_str());
            inputA4->textsize(12);

            return 1;
        }
        case FL_DRAG:{
            xx0 = Fl::event_x() - 65;
            yy0 = Fl::event_y() - 190;

            inputA3->value(to_string(xx0).c_str());
            inputA3->textsize(12);

            inputA4->value(to_string(yy0).c_str());
            inputA4->textsize(12);

            this->redraw();

            return 1;
        }
        default:
            return Fl_Box::handle(event);
    }
}