#include <stdio.h>
#include <stdlib.h>
#include <Application.h>
#include <Message.h>
#include <Button.h>
#include <View.h>
#include <Window.h>
enum {
TRACKING_NONE = 0,
TRACKING_ALL,
TRACKING_RIGHT,
TRACKING_BOTTOM,
TRACKING_RIGHT_BOTTOM,
};
class TestView : public BView {
public:
TestView(BRect frame, const char* name,
uint32 resizeFlags, uint32 flags)
: BView(frame, name, resizeFlags, flags),
fTracking(TRACKING_NONE),
fLastMousePos(0.0, 0.0)
{
rgb_color color;
color.red = rand() / 256;
color.green = rand() / 256;
color.blue = rand() / 256;
color.alpha = 255;
SetViewColor(color);
SetLowColor(color);
}
virtual void Draw(BRect updateRect);
virtual void MouseDown(BPoint where);
virtual void MouseUp(BPoint where);
virtual void MouseMoved(BPoint where, uint32 transit,
const BMessage* dragMessage);
private:
uint32 fTracking;
BPoint fLastMousePos;
};
void
TestView::Draw(BRect updateRect)
{
SetHighColor(0, 0, 0, 255);
const char* message = "Click and drag to move this view!";
DrawString(message, BPoint(20.0, 30.0));
BRect r(Bounds());
r.right -= 15.0;
r.bottom -= 15.0;
StrokeLine(r.RightTop(), BPoint(r.right, Bounds().bottom));
StrokeLine(r.LeftBottom(), BPoint(Bounds().right, r.bottom));
}
void
TestView::MouseDown(BPoint where)
{
BRect r(Bounds());
r.right -= 15.0;
r.bottom -= 15.0;
if (r.Contains(where))
fTracking = TRACKING_ALL;
else if (r.bottom < where.y && r.right < where.x)
fTracking = TRACKING_RIGHT_BOTTOM;
else if (r.bottom < where.y)
fTracking = TRACKING_BOTTOM;
else if (r.right < where.x)
fTracking = TRACKING_RIGHT;
fLastMousePos = where;
SetMouseEventMask(B_POINTER_EVENTS, B_LOCK_WINDOW_FOCUS);
}
void
TestView::MouseUp(BPoint where)
{
fTracking = TRACKING_NONE;
}
void
TestView::MouseMoved(BPoint where, uint32 transit,
const BMessage* dragMessage)
{
BPoint offset = where - fLastMousePos;
switch (fTracking) {
case TRACKING_ALL:
MoveBy(offset.x, offset.y);
break;
case TRACKING_RIGHT:
ResizeBy(offset.x, 0.0);
fLastMousePos = where;
break;
case TRACKING_BOTTOM:
ResizeBy(0.0, offset.y);
fLastMousePos = where;
break;
case TRACKING_RIGHT_BOTTOM:
ResizeBy(offset.x, offset.y);
fLastMousePos = where;
break;
}
}
void
show_window(BRect frame, const char* name)
{
BWindow* window = new BWindow(frame, name,
B_TITLED_WINDOW,
B_ASYNCHRONOUS_CONTROLS | B_QUIT_ON_WINDOW_CLOSE);
BView* view = new TestView(window->Bounds(), "test 1", B_FOLLOW_ALL,
B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE);
window->AddChild(view);
BRect bounds = view->Bounds();
bounds.InsetBy(20, 20);
BView* view1 = new TestView(bounds, "test 2", B_FOLLOW_RIGHT | B_FOLLOW_BOTTOM,
B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE);
view->AddChild(view1);
bounds = view1->Bounds();
bounds.InsetBy(20, 20);
BView* view2 = new TestView(bounds, "test 3", B_FOLLOW_NONE,
B_WILL_DRAW | B_FULL_UPDATE_ON_RESIZE);
view1->AddChild(view2);
window->Show();
}
int
main(int argc, char** argv)
{
BApplication* app = new BApplication("application/x.vnd-Haiku.Following");
BRect frame(50.0, 50.0, 300.0, 250.0);
show_window(frame, "Following Test");
app->Run();
delete app;
return 0;
}