bazaar: CtrlFinder, CtrlMover, cleaning + Test cases, new CtrlPos, a better way to live reposition Ctrl, RectCtrl code cleaning and exposing common code

git-svn-id: svn://ultimatepp.org/upp/trunk@3117 f0d560ea-af0d-0410-9eb7-867de7ffcac7
This commit is contained in:
kohait 2011-01-28 14:52:37 +00:00
parent 6364702911
commit 4ec748ce9b
34 changed files with 842 additions and 136 deletions

View file

@ -1,24 +1,59 @@
#include "CtrlFinder.h"
Ctrl* GetCtrl(Ctrl* parent, Point p, dword keyflags)
Ctrl* GetCtrl(Ctrl& c, Point p, dword keyflags, bool ignoreframe)
{
Ctrl* c = parent->GetFirstChild();
while(c)
Ctrl* q = c.GetFirstChild();
while(q)
{
Rect r = c->GetRect();
if(r.Contains(p)) return c;
c = c->GetNext();
if(!q->InFrame() || !ignoreframe)
{
Rect r = q->GetRect();
if(r.Contains(p)) return q;
}
q = q->GetNext();
}
return NULL;
}
void CtrlFinder::Reload()
{
if(IsEmpty()) return;
V::Reload();
Remove();
Get().Add(SizePos());
}
void CtrlFinder::Visit(Ctrl& c)
{
V::Visit(c);
Enable();
}
void CtrlFinder::Clear()
{
c = NULL;
Remove();
V::Clear();
}
void CtrlFinder::OnCtrlLeft(Point p, dword keyflags)
{
Ctrl* c = GetCtrlFromParent(p, keyflags);
c = NULL;
if(IsEmpty()) return;
c = ::GetCtrl(Get(), p, keyflags, ignoreframe);
if(c == this) c = NULL;
if(c) WhenLeftDown(*c, p, keyflags);
else WhenMissed(p, keyflags);
Action();
}
void CtrlFinder::OnCtrlRight(Point p, dword keyflags)
{
Ctrl* c = GetCtrlFromParent(p, keyflags);
c = NULL;
if(IsEmpty()) return;
c = ::GetCtrl(Get(), p, keyflags, ignoreframe);
if(c == this) c = NULL;
if(c) WhenRightDown(*c, p, keyflags);
else WhenMissed(p, keyflags);
Action();
}

View file

@ -5,16 +5,12 @@
using namespace Upp;
#include <Gen/Gen.h>
class MouseHookCtrl : public ParentCtrl
{
public:
typedef MouseHookCtrl CLASSNAME;
MouseHookCtrl() : minsize(Null) { Update(); }
void SetMinSize(Size sz) { minsize = sz; }
virtual Rect GetVoidRect()const { return GetSize(); }
virtual Size GetStdSize() const { return GetMinSize(); }
virtual Size GetMinSize() const { return IsNull(minsize) ? Ctrl::GetMinSize() : minsize; }
virtual void LeftDown(Point p, dword keyflags) { WhenLeftDown(p,keyflags); }
virtual void RightDown(Point p, dword keyflags) { WhenRightDown(p,keyflags); }
@ -24,8 +20,6 @@ public:
virtual void LeftRepeat(Point p, dword keyflags) { WhenLeftRepeat(p,keyflags); }
virtual void RightRepeat(Point p, dword keyflags) { WhenRightRepeat(p,keyflags); }
virtual void Updated() { IgnoreMouse(!IsEnabled()); }
Callback2<Point, dword> WhenLeftDown;
Callback2<Point, dword> WhenRightDown;
Callback2<Point, dword> WhenLeftUp;
@ -33,27 +27,34 @@ public:
Callback2<Point, dword> WhenMouseMove;
Callback2<Point, dword> WhenLeftRepeat;
Callback2<Point, dword> WhenRightRepeat;
protected:
Size minsize;
};
Ctrl* GetCtrl(Ctrl* parent, Point p, dword keyflags);
Ctrl* GetCtrl(Ctrl& c, Point p, dword keyflags, bool ignoreframe);
class CtrlFinder : public MouseHookCtrl
class CtrlFinder : public MouseHookCtrl, public Visiting<Ctrl>
{
public:
typedef CtrlFinder CLASSNAME;
typedef MouseHookCtrl R;
CtrlFinder() { R::WhenLeftDown = THISBACK(OnCtrlLeft); R::WhenRightDown = THISBACK(OnCtrlRight);}
typedef Visiting<Ctrl> V;
Ctrl* GetCtrl(Point p, dword keyflags) { return ::GetCtrl(this, p, keyflags); }
Ctrl* GetCtrlFromParent(Point p, dword keyflags) { return ::GetCtrl(GetParent(), p, keyflags); }
CtrlFinder() : ignoreframe(true) { R::WhenLeftDown = THISBACK(OnCtrlLeft); R::WhenRightDown = THISBACK(OnCtrlRight);}
virtual void Visit(Ctrl& c);
virtual void Reload();
virtual void Clear();
Callback3<Ctrl&, Point, dword> WhenLeftDown;
Callback3<Ctrl&, Point, dword> WhenRightDown;
Callback2<Point, dword> WhenMissed;
virtual Value GetData() const { return RawToValue(~c); }
Ctrl* GetCtrl() const { return c; }
bool ignoreframe;
protected:
Ptr<Ctrl> c;
void OnCtrlLeft(Point p, dword keyflags);
void OnCtrlRight(Point p, dword keyflags);
};

View file

@ -1,7 +1,8 @@
description "Find a Ctrl using a transparent Hook Ctrl, see CtrlPropTest\377";
uses
CtrlLib;
CtrlLib,
Gen;
file
CtrlFinder.h,

View file

@ -1,4 +1,5 @@
#ifndef _CtrlFinder_icpp_init_stub
#define _CtrlFinder_icpp_init_stub
#include "CtrlLib/init"
#include "Gen/init"
#endif

View file

@ -0,0 +1,32 @@
#ifndef _CtrlFinderTest_CtrlFinderTest_h
#define _CtrlFinderTest_CtrlFinderTest_h
#include <CtrlLib/CtrlLib.h>
using namespace Upp;
#define LAYOUTFILE <CtrlFinderTest/CtrlFinderTest.lay>
#include <CtrlCore/lay.h>
#include <CtrlFinder/CtrlFinder.h>
class CtrlFinderTest : public WithCtrlFinderTestLayout<TopWindow> {
public:
typedef CtrlFinderTest CLASSNAME;
CtrlFinderTest();
void VisitCB();
void ClearCB();
void EnableCB();
void DisableCB();
void ToInfo(const String& s);
void OnSelect(Ctrl& c, Point p, dword keyflags);
void OnMissed(Point p, dword keyflags);
CtrlFinder hk;
FrameTop<WithControlLay<ParentCtrl> > ft;
};
#endif

View file

@ -0,0 +1,14 @@
LAYOUT(CtrlFinderTestLayout, 412, 196)
ITEM(DropList, dv___0, LeftPosZ(336, 64).TopPosZ(48, 19))
ITEM(SliderCtrl, dv___1, LeftPosZ(336, 64).TopPosZ(84, 24))
ITEM(EditString, dv___2, LeftPosZ(336, 64).TopPosZ(12, 19))
ITEM(DocEdit, info, LeftPosZ(12, 292).TopPosZ(12, 148))
END_LAYOUT
LAYOUT(ControlLay, 264, 24)
ITEM(Button, visit, SetLabel(t_("Visit")).LeftPosZ(4, 56).VSizePosZ(4, 5))
ITEM(Button, clear, SetLabel(t_("Clear")).LeftPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, enable, SetLabel(t_("Enable")).RightPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, disable, SetLabel(t_("Disable")).RightPosZ(4, 56).VSizePosZ(4, 5))
END_LAYOUT

View file

@ -0,0 +1,12 @@
uses
CtrlLib,
CtrlFinder;
file
CtrlFinderTest.h,
main.cpp,
CtrlFinderTest.lay;
mainconfig
"" = "GUI MT";

View file

@ -0,0 +1,5 @@
#ifndef _CtrlFinderTest_icpp_init_stub
#define _CtrlFinderTest_icpp_init_stub
#include "CtrlLib/init"
#include "CtrlFinder/init"
#endif

View file

@ -0,0 +1,61 @@
#include "CtrlFinderTest.h"
void CtrlFinderTest::ToInfo(const String& s)
{
info.Insert(info.GetLength(), s + "\n");
info.SetCursor(info.GetLength());
}
void CtrlFinderTest::OnSelect(Ctrl& c, Point p, dword keyflags)
{
String inf = "Selected: ";
inf << String(typeid(c).name());
ToInfo(inf);
}
void CtrlFinderTest::OnMissed(Point p, dword keyflags)
{
String inf = ("Missed!");
ToInfo(inf);
}
void CtrlFinderTest::VisitCB()
{
hk.Visit(*this);
}
void CtrlFinderTest::ClearCB()
{
hk.Clear();
}
void CtrlFinderTest::EnableCB()
{
hk.Enable();
}
void CtrlFinderTest::DisableCB()
{
hk.Disable();
}
CtrlFinderTest::CtrlFinderTest()
{
CtrlLayout(*this, "Window title");
CtrlLayout(ft);
ft.Height(40);
AddFrame(ft);
ft.visit <<= THISBACK(VisitCB);
ft.clear <<= THISBACK(ClearCB);
ft.enable <<= THISBACK(EnableCB);
ft.disable <<= THISBACK(DisableCB);
hk.WhenLeftDown = THISBACK(OnSelect);
hk.WhenMissed = THISBACK(OnMissed);
hk.Visit(*this);
}
GUI_APP_MAIN
{
CtrlFinderTest().Run();
}

View file

@ -2,41 +2,45 @@
void CtrlMover::OnCtrlLeft(Ctrl& c, Point p, dword keyflags)
{
if(&c == &rc) return;
if(&c == this) return;
Visit(c);
if(&c == &rc) { rc.Remove(); return;}
rc.Remove();
Add(rc.SizePos());
rc.SetData(c.GetRect());
Action();
}
void CtrlMover::OnRectChange()
{
if(IsEmpty()) return;
Get().SetRect(rc.GetData());
if(IsEmpty()) { rc.Remove(); return; }
Ctrl* c = GetCtrl();
if(!c) return;
c->SetRect(rc.GetData());
Action();
}
void CtrlMover::OnMissed(Point p, dword keyflags)
{
Clear();
rc.Remove();
c = NULL; //from CtrlFinder
Action();
LeftDown(p, keyflags);
}
void CtrlMover::Updated()
{
Reload();
Ctrl* c = GetCtrl();
if(!c) return;
rc.SetData(c->GetRect());
}
void CtrlMover::State(int reason)
{
if(reason != ENABLE) return;
if(!IsEnabled()) Clear();
if(!IsEnabled()) rc.Remove();
}
void CtrlMover::Visit(Ctrl& c)
{
rc.Remove();
Add(rc.SizePos());
V::Visit(c);
}
@ -48,14 +52,14 @@ void CtrlMover::Clear()
void CtrlMover::Reload()
{
if(IsEmpty()) return;
V::Reload();
rc.SetData(Get().GetRect());
}
CtrlMover::CtrlMover()
{
WhenLeftDown = THISBACK(OnCtrlLeft);
WhenMissed = THISBACK(OnMissed);
rcst = RectCtrl::StyleDefault();
rcst.rectcol = Null;
rc.SetStyle(rcst);

View file

@ -7,15 +7,12 @@ using namespace Upp;
#include <CtrlFinder/CtrlFinder.h>
#include <RectCtrl/RectCtrl.h>
#include <Gen/Gen.h>
//the control mover is a layer on top of other ctrl surfaces, and can grab their Ctrls to move them.
class CtrlMover : public CtrlFinder, public Visiting<Ctrl>
class CtrlMover : public CtrlFinder
{
public:
typedef CtrlMover CLASSNAME;
typedef Visiting<Ctrl> V;
typedef CtrlFinder V;
CtrlMover();
virtual void Visit(Ctrl& c);

View file

@ -1,13 +1,9 @@
uses
CtrlLib,
CtrlFinder,
RectCtrl,
Gen;
RectCtrl;
file
CtrlMover.h,
CtrlMover.cpp;
mainconfig
"" = "GUI MT";

View file

@ -3,5 +3,4 @@
#include "CtrlLib/init"
#include "CtrlFinder/init"
#include "RectCtrl/init"
#include "Gen/init"
#endif

View file

@ -0,0 +1,32 @@
#ifndef _CtrlMoverTest_CtrlMoverTest_h
#define _CtrlMoverTest_CtrlMoverTest_h
#include <CtrlLib/CtrlLib.h>
using namespace Upp;
#define LAYOUTFILE <CtrlMoverTest/CtrlMoverTest.lay>
#include <CtrlCore/lay.h>
#include <CtrlMover/CtrlMover.h>
class CtrlMoverTest : public WithCtrlMoverTestLayout<TopWindow> {
public:
typedef CtrlMoverTest CLASSNAME;
CtrlMoverTest();
void VisitCB();
void ClearCB();
void EnableCB();
void DisableCB();
void ToInfo(const String& s);
void OnSelect(Ctrl& c, Point p, dword keyflags);
void OnMissed(Point p, dword keyflags);
CtrlMover hk;
FrameTop<WithControlLay<ParentCtrl> > ft;
};
#endif

View file

@ -0,0 +1,14 @@
LAYOUT(CtrlMoverTestLayout, 412, 196)
ITEM(DropList, dv___0, LeftPosZ(336, 64).TopPosZ(48, 19))
ITEM(SliderCtrl, dv___1, LeftPosZ(336, 64).TopPosZ(84, 24))
ITEM(EditString, dv___2, LeftPosZ(336, 64).TopPosZ(12, 19))
ITEM(DocEdit, info, LeftPosZ(12, 292).TopPosZ(12, 148))
END_LAYOUT
LAYOUT(ControlLay, 264, 24)
ITEM(Button, visit, SetLabel(t_("Visit")).LeftPosZ(4, 56).VSizePosZ(4, 5))
ITEM(Button, clear, SetLabel(t_("Clear")).LeftPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, enable, SetLabel(t_("Enable")).RightPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, disable, SetLabel(t_("Disable")).RightPosZ(4, 56).VSizePosZ(4, 5))
END_LAYOUT

View file

@ -0,0 +1,12 @@
uses
CtrlLib,
CtrlMover;
file
CtrlMoverTest.h,
main.cpp,
CtrlMoverTest.lay;
mainconfig
"" = "GUI MT";

View file

@ -0,0 +1,5 @@
#ifndef _CtrlMoverTest_icpp_init_stub
#define _CtrlMoverTest_icpp_init_stub
#include "CtrlLib/init"
#include "CtrlMover/init"
#endif

View file

@ -0,0 +1,61 @@
#include "CtrlMoverTest.h"
void CtrlMoverTest::ToInfo(const String& s)
{
info.Insert(info.GetLength(), s + "\n");
info.SetCursor(info.GetLength());
}
void CtrlMoverTest::OnSelect(Ctrl& c, Point p, dword keyflags)
{
String inf = "Selected: ";
inf << String(typeid(c).name());
ToInfo(inf);
}
void CtrlMoverTest::OnMissed(Point p, dword keyflags)
{
String inf = ("Missed!");
ToInfo(inf);
}
void CtrlMoverTest::VisitCB()
{
hk.Visit(*this);
}
void CtrlMoverTest::ClearCB()
{
hk.Clear();
}
void CtrlMoverTest::EnableCB()
{
hk.Enable();
}
void CtrlMoverTest::DisableCB()
{
hk.Disable();
}
CtrlMoverTest::CtrlMoverTest()
{
CtrlLayout(*this, "Window title");
CtrlLayout(ft);
ft.Height(40);
AddFrame(ft);
ft.visit <<= THISBACK(VisitCB);
ft.clear <<= THISBACK(ClearCB);
ft.enable <<= THISBACK(EnableCB);
ft.disable <<= THISBACK(DisableCB);
//hk.WhenLeftDown = THISBACK(OnSelect);
//hk.WhenMissed = THISBACK(OnMissed);
hk.Visit(*this);
}
GUI_APP_MAIN
{
CtrlMoverTest().Run();
}

212
bazaar/CtrlPos/CtrlPos.cpp Normal file
View file

@ -0,0 +1,212 @@
#include "CtrlPos.h"
void CtrlPos::DrawAlignHandle(Draw& w, const Size& sz, const Rect&r, const Ctrl::LogPos& pos, const Color& col)
{
Point p;
bool q;
Size rz = r.GetSize();
Color col2 = Blend(col, Black);
p = r.CenterLeft();
p.y -= rz.cy/4;
q = (pos.x.GetAlign()&Ctrl::LEFT);
w.DrawLine(p, Point(0, p.y), (q)?(PEN_SOLID):(PEN_DOT), (q)?(col):(col2));
p = r.CenterRight();
p.y += rz.cy/4;
q = (pos.x.GetAlign()&Ctrl::RIGHT);
w.DrawLine(p, Point(sz.cx, p.y), (q)?(PEN_SOLID):(PEN_DOT), (q)?(col):(col2));
p = r.TopCenter();
p.x -= rz.cx/4;
q = (pos.y.GetAlign()&Ctrl::TOP);
w.DrawLine(p, Point(p.x, 0), (q)?(PEN_SOLID):(PEN_DOT), (q)?(col):(col2));
p = r.BottomCenter();
p.x += rz.cx/4;
q = (pos.y.GetAlign()&Ctrl::BOTTOM);
w.DrawLine(p, Point(p.x, sz.cy), (q)?(PEN_SOLID):(PEN_DOT), (q)?(col):(col2));
}
bool CtrlPos::GetAlignMode(const Size& sz, const Rect& r, const Point& pp, Ctrl::LogPos& pos, int handsize)
{
int size = handsize+2;
Rect c;
Point p;
int q;
Size rz = r.GetSize();
q = pos.x.GetAlign();
p = r.CenterLeft();
p.y -= rz.cy/4;
c = Rect(p, Point(0, p.y)); c.InflateVert(size); c.Normalize();
if(c.Contains(pp)) { q&= ~Ctrl::LEFT; q|= (pos.x.GetAlign()&Ctrl::LEFT)?(0):(Ctrl::LEFT); pos.x.SetAlign(q); return true; }
p = r.CenterRight();
p.y += rz.cy/4;
c = Rect(p, Point(sz.cx, p.y)); c.InflateVert(size); c.Normalize();
if(c.Contains(pp)) { q&= ~Ctrl::RIGHT; q|= (pos.x.GetAlign()&Ctrl::RIGHT)?(0):(Ctrl::RIGHT); pos.x.SetAlign(q); return true; }
q = pos.y.GetAlign();
p = r.TopCenter();
p.x -= rz.cx/4;
c = Rect(p, Point(p.x, 0)); c.InflateHorz(size); c.Normalize();
if(c.Contains(pp)) { q&= ~Ctrl::TOP; q|= (pos.y.GetAlign()&Ctrl::TOP)?(0):(Ctrl::TOP); pos.y.SetAlign(q); return true; }
p = r.BottomCenter();
p.x += rz.cx/4;
c = Rect(p, Point(p.x, sz.cy)); c.InflateHorz(size); c.Normalize();
if(c.Contains(pp)) { q&= ~Ctrl::BOTTOM; q|= (pos.y.GetAlign()&Ctrl::BOTTOM)?(0):(Ctrl::BOTTOM); pos.y.SetAlign(q); return true; }
return false;
}
void CtrlPos::Paint(Draw& w)
{
Size sz = GetSize();
if(!IsTransparent())
w.DrawRect(0,0,sz.cx,sz.cy, SColorFace());
if(IsEnabled() && !IsEmpty())
{
Ctrl* c = Get().GetFirstChild();
while(c)
{
if(!c->InFrame())
{
Rect r = c->GetRect();
r.Inflate(1);
RectCtrl::DrawHandleFrame(w, r, LtGray, 1);
}
c = c->GetNext();
}
}
Ctrl* c = GetCtrl();
if(!c) return;
Rect r = c->GetRect();
RectCtrl::DrawHandleFrame(w, r, style->framecol, style->framesize);
DrawAlignHandle(w, sz, r, c->GetPos(), style->framecol);
RectCtrl::DrawHandle(w, r, style->handcol, style->handsize);
if(pressed)// && moving)
RectCtrl::DrawRectInfo(w, Point(10,10), r, style->framecol, style->textcol);
}
void CtrlPos::LeftDown(Point p, dword keyflags)
{
SetCapture();
moving = false;
pressed = (keyflags & K_MOUSELEFT);
if(GetCtrl())
{
Ctrl& c = *GetCtrl();
xpos = c.GetPos();
xp = p;
Size sz = GetSize();
Rect r = c.GetRect();
Ctrl::LogPos pos = xpos;
Rect _r(r); _r.Inflate(style->handsize+2);
if(GetAlignMode(sz, _r, p, pos, style->handsize))
{
pos = LogPosPopUp::ReAlign(c, pos);
c.SetPos(pos);
Action();
Refresh();
return;
}
else if((mode = RectCtrl::GetMode(r, p, keyflags, style->handsize)) != RectCtrl::NONE)
{
ci = RectCtrl::SetCursor(mode, keyflags, ci);
Refresh();
return;
}
}
CtrlFinder::LeftDown(p, keyflags);
Refresh();
}
void CtrlPos::MouseMove(Point p, dword keyflags)
{
moving = true;
pressed = (keyflags & K_MOUSELEFT);
//int m = RectCtrl::GetMode(r, p, keyflags, HANDSIZE);
//SetCursor(m, keyflags);
if(!GetCtrl()) return;
if(pressed && mode != RectCtrl::NONE)
{
Size sz = GetSize();
Rect r = LogPosPopUp::CtrlRect(xpos, sz);;
RectCtrl::CalcRect(r, p-xp, keyflags, mode, g);
r.Normalize();
Ctrl::LogPos pos = LogPosPopUp::MakeLogPos(xpos, r, sz);
GetCtrl()->SetPos(pos);
Action();
Refresh();
}
}
void CtrlPos::LeftUp(Point p, dword keyflags)
{
ReleaseCapture();
pressed = false;
moving = false;
//xpos.SetNull();
xp.SetNull();
mode = RectCtrl::NONE;
ci = RectCtrl::SetCursor(mode, keyflags, ci);
Refresh();
}
void CtrlPos::RightDown(Point p, dword keyflags)
{
//cancel
ReleaseCapture();
//pressed = false;
//moving = false;
////xpos.SetNull();
//xp.SetNull();
int m = mode;
mode = RectCtrl::NONE;
ci = RectCtrl::SetCursor(mode, keyflags, ci);
if(!GetCtrl()) return;
if(m != RectCtrl::NONE)
{
GetCtrl()->SetPos(xpos);
Action();
Refresh();
}
}
void CtrlPos::Updated()
{
//refresh the view of the currently selected ctrl
}
void CtrlPos::State(int reason)
{
if(reason != ENABLE) return;
if(!IsEnabled()) { c = NULL; Refresh(); }
}
void CtrlPos::Clear()
{
V::Clear();
Refresh();
}
CtrlPos::CtrlPos()
: pressed(false), moving(false), mode(RectCtrl::NONE), g(4,4)
{
BackPaint();
style = &RectCtrl::StyleDefault();
//xpos.SetNull();
xp.SetNull();
}

46
bazaar/CtrlPos/CtrlPos.h Normal file
View file

@ -0,0 +1,46 @@
#ifndef _CtrlPos_CtrlPos_h_
#define _CtrlPos_CtrlPos_h_
#include <CtrlLib/CtrlLib.h>
using namespace Upp;
#include <RectCtrl/RectCtrl.h>
#include <LogPosCtrl/LogPosCtrl.h>
#include <CtrlFinder/CtrlFinder.h>
#include <Gen/Gen.h>
class CtrlPos : public CtrlFinder
{
public:
typedef CtrlPos CLASSNAME;
typedef CtrlFinder V;
CtrlPos();
virtual void Clear();
virtual void Paint(Draw& w);
virtual void LeftDown(Point p, dword keyflags);
virtual void MouseMove(Point p, dword keyflags);
virtual void LeftUp(Point p, dword keyflags);
virtual void RightDown(Point p, dword keyflags);
virtual void State(int reason);
virtual void Updated();
virtual Rect GetVoidRect() const { return Ctrl::GetVoidRect(); }
void SetStyle(const RectCtrl::Style& s) { style = &s; Refresh(); }
static void DrawAlignHandle(Draw& w, const Size& sz, const Rect&r, const Ctrl::LogPos& pos, const Color& col);
static bool GetAlignMode(const Size& sz, const Rect& r, const Point& pp, Ctrl::LogPos& pos, int handsize);
protected:
const RectCtrl::Style* style;
Point g;
Point xp;
Ctrl::LogPos xpos;
int mode;
bool pressed;
bool moving;
Image ci;
};
#endif

View file

@ -0,0 +1,11 @@
uses
Core,
Gen,
RectCtrl,
CtrlFinder,
LogPosCtrl;
file
CtrlPos.h,
CtrlPos.cpp;

8
bazaar/CtrlPos/init Normal file
View file

@ -0,0 +1,8 @@
#ifndef _CtrlPos_icpp_init_stub
#define _CtrlPos_icpp_init_stub
#include "Core/init"
#include "Gen/init"
#include "RectCtrl/init"
#include "CtrlFinder/init"
#include "LogPosCtrl/init"
#endif

View file

@ -0,0 +1,32 @@
#ifndef _CtrlPosTest_CtrlPosTest_h
#define _CtrlPosTest_CtrlPosTest_h
#include <CtrlLib/CtrlLib.h>
using namespace Upp;
#define LAYOUTFILE <CtrlPosTest/CtrlPosTest.lay>
#include <CtrlCore/lay.h>
#include <CtrlPos/CtrlPos.h>
class CtrlPosTest : public WithCtrlPosTestLayout<TopWindow> {
public:
typedef CtrlPosTest CLASSNAME;
CtrlPosTest();
void VisitCB();
void ClearCB();
void EnableCB();
void DisableCB();
void ToInfo(const String& s);
void OnSelect(Ctrl& c, Point p, dword keyflags);
void OnMissed(Point p, dword keyflags);
CtrlPos hk;
FrameTop<WithControlLay<ParentCtrl> > ft;
};
#endif

View file

@ -0,0 +1,14 @@
LAYOUT(CtrlPosTestLayout, 412, 196)
ITEM(DropList, dv___0, LeftPosZ(336, 64).TopPosZ(48, 19))
ITEM(SliderCtrl, dv___1, LeftPosZ(336, 64).TopPosZ(84, 24))
ITEM(EditString, dv___2, LeftPosZ(336, 64).TopPosZ(12, 19))
ITEM(DocEdit, info, LeftPosZ(12, 292).TopPosZ(12, 148))
END_LAYOUT
LAYOUT(ControlLay, 264, 24)
ITEM(Button, visit, SetLabel(t_("Visit")).LeftPosZ(4, 56).VSizePosZ(4, 5))
ITEM(Button, clear, SetLabel(t_("Clear")).LeftPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, enable, SetLabel(t_("Enable")).RightPosZ(60, 56).VSizePosZ(4, 5))
ITEM(Button, disable, SetLabel(t_("Disable")).RightPosZ(4, 56).VSizePosZ(4, 5))
END_LAYOUT

View file

@ -0,0 +1,12 @@
uses
CtrlLib,
CtrlPos;
file
CtrlPosTest.h,
main.cpp,
CtrlPosTest.lay;
mainconfig
"" = "GUI MT";

5
bazaar/CtrlPosTest/init Normal file
View file

@ -0,0 +1,5 @@
#ifndef _CtrlPosTest_icpp_init_stub
#define _CtrlPosTest_icpp_init_stub
#include "CtrlLib/init"
#include "CtrlPos/init"
#endif

View file

@ -0,0 +1,61 @@
#include "CtrlPosTest.h"
void CtrlPosTest::ToInfo(const String& s)
{
info.Insert(info.GetLength(), s + "\n");
info.SetCursor(info.GetLength());
}
void CtrlPosTest::OnSelect(Ctrl& c, Point p, dword keyflags)
{
String inf = "Selected: ";
inf << String(typeid(c).name());
ToInfo(inf);
}
void CtrlPosTest::OnMissed(Point p, dword keyflags)
{
String inf = ("Missed!");
ToInfo(inf);
}
void CtrlPosTest::VisitCB()
{
hk.Visit(*this);
}
void CtrlPosTest::ClearCB()
{
hk.Clear();
}
void CtrlPosTest::EnableCB()
{
hk.Enable();
}
void CtrlPosTest::DisableCB()
{
hk.Disable();
}
CtrlPosTest::CtrlPosTest()
{
CtrlLayout(*this, "Window title");
CtrlLayout(ft);
ft.Height(40);
AddFrame(ft);
ft.visit <<= THISBACK(VisitCB);
ft.clear <<= THISBACK(ClearCB);
ft.enable <<= THISBACK(EnableCB);
ft.disable <<= THISBACK(DisableCB);
hk.WhenLeftDown = THISBACK(OnSelect);
hk.WhenMissed = THISBACK(OnMissed);
hk.Visit(*this);
}
GUI_APP_MAIN
{
CtrlPosTest().Run();
}

View file

@ -29,6 +29,8 @@ bool PropRefresh(Ctrl& o, const Value& v) { o.Refresh(); return true; }
bool PropSetLogPos(Ctrl& o, const Value& v) { if(!v.Is<Ctrl::LogPos>()) return false; o.SetPos(RawValue<Ctrl::LogPos>::Extract(v)); return true; }
bool PropGetLogPos(const Ctrl& o, Value& v) { v = RawToValue(o.GetPos()); return true; }
bool PropGetTypeInfo(const Ctrl& o, Value& v) { v = String(typeid(o).name()); return true; }
CTRL_PROPERTIES(Ctrl, RecurseDone)
PROPERTY("data", PropSetData, PropGetData)
PROPERTY("enable", PropEnable, PropIsEnabled)
@ -43,4 +45,5 @@ PROPERTY("initFocus", PropInitFocus, PropIsInitFocus)
PROPERTY("backpaint", PropBackPaint, PropIsBackPaint)
PROPERTY("transparent", PropTransparent, PropIsTransparent)
//PROPERTY_SET("refresh", PropRefresh)
PROPERTY_GET("type", PropGetTypeInfo)
END_CTRL_PROPERTIES

View file

@ -16,9 +16,6 @@ public:
typedef CtrlPropTest CLASSNAME;
CtrlPropTest();
//hook
void EditCB();
//misc
void Test();
void InitDummies();
@ -28,6 +25,7 @@ public:
void DoEdit(Ctrl& c);
bool CanEdit();
void OnEdit();
void OnCtrlRight(Ctrl& c, Point p, dword keyflags);
public:
@ -39,6 +37,8 @@ public:
PropList pl;
CtrlMover hk;
bool edit;
};
#endif

View file

@ -36,7 +36,6 @@ bool CtrlPropTest::CanEdit()
void CtrlPropTest::OnCtrlRight(Ctrl& c, Point p, dword keyflags)
{
// if(&c == &rc) return;
if(&c == &hk) return;
if(!CanEdit()) return;
if(keyflags & K_SHIFT)

View file

@ -1,31 +1,34 @@
#include "CtrlPropTest.h"
void CtrlPropTest::EditCB()
void CtrlPropTest::OnEdit()
{
if(hk.IsEnabled())
if(edit)
{
edit = false;
mbi->Check(edit);
hk.Disable();
mbi->Check(false);
}
else
{
edit = true;
mbi->Check(edit);
hk.Enable();
mbi->Check(true);
SetFocus(); //kill foucus from all others
SetFocus();
}
}
CtrlPropTest::CtrlPropTest()
{
CtrlLayout(*this, "Window title");
edit = false;
mbi = &mb.Add(!IsReadOnly(), t_("Edit"), CtrlImg::selection(),
THISBACK(EditCB));
THISBACK(OnEdit));
AddFrame(mb);
hk.WhenRightDown = THISBACK(OnCtrlRight);
hk.Disable();
Add(hk.SizePos());
hk.Visit(*this);
hk.Disable();
InitDummies();
}

View file

@ -19,50 +19,47 @@ Rect RectCtrl::HandleAt(const Point& p, int size)
Rect q(p,p); q.Inflate(size); return q;
}
void RectCtrl::Paint(Draw& w)
void RectCtrl::DrawHandle(Draw& w, const Rect& r, const Color& col, int size)
{
Size sz = GetSize();
w.DrawRect(HandleAt(r.CenterPoint(), size), col);
if(r.IsNullInstance()) return;
w.DrawRect(HandleAt(r.TopLeft(), size), col);
w.DrawRect(HandleAt(r.BottomRight(), size), col);
w.DrawRect(HandleAt(r.TopRight(), size), col);
w.DrawRect(HandleAt(r.BottomLeft(), size), col);
//rect
w.DrawRect(r, style->rectcol);
w.DrawRect(HandleAt(r.CenterLeft(), size), col);
w.DrawRect(HandleAt(r.CenterRight(), size), col);
w.DrawRect(HandleAt(r.TopCenter(), size), col);
w.DrawRect(HandleAt(r.BottomCenter(), size), col);
}
//handle frame
void RectCtrl::DrawHandleFrame(Draw& w, const Rect& _r, const Color& col, int size)
{
Rect r(_r);
--r.right;
--r.bottom;
Vector<Point> vp;
vp << r.TopLeft() << r.TopRight() << r.BottomRight() << r.BottomLeft() << r.TopLeft();
w.DrawPolyline(vp, style->framesize, style->framecol);
w.DrawPolyline(vp, size, col);
}
//handles
int size = style->handsize;
w.DrawRect(HandleAt(r.CenterPoint(), size), style->handcol);
w.DrawRect(HandleAt(r.TopLeft(), size), style->handcol);
w.DrawRect(HandleAt(r.BottomRight(), size), style->handcol);
w.DrawRect(HandleAt(r.TopRight(), size), style->handcol);
w.DrawRect(HandleAt(r.BottomLeft(), size), style->handcol);
w.DrawRect(HandleAt(r.CenterLeft(), size), style->handcol);
w.DrawRect(HandleAt(r.CenterRight(), size), style->handcol);
w.DrawRect(HandleAt(r.TopCenter(), size), style->handcol);
w.DrawRect(HandleAt(r.BottomCenter(), size), style->handcol);
//text
if(pressed && moving)
void RectCtrl::DrawRectInfo(Draw& w, const Point& p, const Rect&r, const Color& framecol, const Color& textcol)
{
String t = AsString(r);
Size tsz = GetTextSize(t, StdFont());
w.DrawRect(10, 10, tsz.cx, tsz.cy, style->framecol);
w.DrawText(10, 10, t, StdFont(), style->textcol);
}
w.DrawRect(p.x-2, p.y-2, tsz.cx+4, tsz.cy+4, framecol);
w.DrawText(p.x, p.y, t, StdFont(), textcol);
}
int RectCtrl::GetMode(const Point& p, dword keyflags)
int RectCtrl::GetMode(const Rect& r, const Point& p, dword keyflags, int handsize)
{
int size = style->handsize<<1;
int size = handsize+2;
Rect q = r; q.Inflate(size);
if(!q.Contains(p)) return NONE;
if(HandleAt(r.CenterPoint(), size).Contains(p)) return CENTER;
if(HandleAt(r.TopLeft(), size).Contains(p)) return LEFTTOP;
if(HandleAt(r.BottomRight(), size).Contains(p)) return RIGHTBOTTOM;
if(HandleAt(r.TopRight(), size).Contains(p)) return RIGHTTOP;
@ -73,22 +70,19 @@ int RectCtrl::GetMode(const Point& p, dword keyflags)
if(HandleAt(r.TopCenter(), size).Contains(p)) return TOP;
if(HandleAt(r.BottomCenter(), size).Contains(p)) return BOTTOM;
if(HandleAt(r.CenterPoint(), size).Contains(p)) return CENTER;
return MOVE;
}
void RectCtrl::CalcRect(const Point& dp, dword keyflags)
void RectCtrl::CalcRect(Rect& r, const Point& dp, dword keyflags, int mode, const Point& g)
{
if(mode == NONE) return;
r = xr;
Point p = dp;
int m = mode;
if(!(keyflags & K_ALT)) m |= GRID;
if(m & GRIDX) p.x = dp.x/g.x*g.x;
if(m & GRIDY) p.y = dp.y/g.y*g.y;
if(m & GRIDX) p.x = p.x/g.x*g.x;
if(m & GRIDY) p.y = p.y/g.y*g.y;
if(keyflags & K_CTRL)
{
@ -126,27 +120,39 @@ void RectCtrl::CalcRect(const Point& dp, dword keyflags)
if(m & _BOTTOM)r.bottom -= p.y;
}
void RectCtrl::SetCursor(unsigned m, dword keyflags)
Image RectCtrl::SetCursor(unsigned m, dword keyflags, const Image& old)
{
switch(m & (ALL | _ALL))
{
case LEFTTOP: c = OverrideCursor(Img::ltrb()); break;
case RIGHTBOTTOM: c = OverrideCursor(Img::ltrb()); break;
case RIGHTTOP: c = OverrideCursor(Img::rtlb()); break;
case LEFTBOTTOM: c = OverrideCursor(Img::rtlb()); break;
case LEFTTOP: return OverrideCursor(Img::ltrb());
case RIGHTBOTTOM: return OverrideCursor(Img::ltrb());
case RIGHTTOP: return OverrideCursor(Img::rtlb());
case LEFTBOTTOM: return OverrideCursor(Img::rtlb());
case LEFT: c = OverrideCursor(Img::lr()); break;
case BOTTOM: c = OverrideCursor(Img::tb()); break;
case RIGHT: c = OverrideCursor(Img::lr()); break;
case TOP: c = OverrideCursor(Img::tb()); break;
case LEFT: return OverrideCursor(Img::lr());
case BOTTOM: return OverrideCursor(Img::tb());
case RIGHT: return OverrideCursor(Img::lr());
case TOP: return OverrideCursor(Img::tb());
case ALL: c = OverrideCursor(Img::mv()); break;
case CENTER: c = OverrideCursor(Img::fr()); break;
case ALL: return OverrideCursor(Img::mv());
case CENTER: return OverrideCursor(Img::fr());
default: OverrideCursor(c); break;
default: OverrideCursor(old); return Null;
}
}
void RectCtrl::Paint(Draw& w)
{
Size sz = GetSize();
if(r.IsNullInstance()) return;
w.DrawRect(r, style->rectcol);
DrawHandleFrame(w, r, style->framecol, style->framesize);
DrawHandle(w, r, style->handcol, style->handsize);
if(pressed)// && moving)
DrawRectInfo(w, Point(10,10), r, style->framecol, style->textcol);
}
void RectCtrl::LeftDown(Point p, dword keyflags)
{
SetCapture();
@ -155,27 +161,26 @@ void RectCtrl::LeftDown(Point p, dword keyflags)
xr = r;
xp = p;
mode = GetMode(p, keyflags);
SetCursor(mode, keyflags);
mode = GetMode(r, p, keyflags, style->handsize);
c = SetCursor(mode, keyflags, c);
if(mode == NONE) WhenMissed(p, keyflags);
Refresh();
}
void RectCtrl::MouseMove(Point p, dword keyflags)
{
moving = true;
pressed = (keyflags & K_MOUSELEFT);
//int m = GetMode(p, keyflags);
//int m = GetMode(r, p, keyflags, style->handsize);
//SetCursor(m, keyflags);
if(pressed && mode != NONE)
{
CalcRect(p-xp, keyflags);
r = xr;
CalcRect(r, p-xp, keyflags, mode, g);
r.Normalize();
UpdateActionRefresh();
}
else Refresh();
}
void RectCtrl::LeftUp(Point p, dword keyflags)
@ -186,7 +191,7 @@ void RectCtrl::LeftUp(Point p, dword keyflags)
xr.SetNull();
xp.SetNull();
mode = NONE;
SetCursor(mode, keyflags);
c = SetCursor(mode, keyflags, c);
Refresh();
}
@ -194,12 +199,19 @@ void RectCtrl::RightDown(Point p, dword keyflags)
{
//cancel
ReleaseCapture();
//pressed = false;
//moving = false;
//xr.SetNull();
//xp.SetNull();
int m = mode;
mode = NONE;
SetCursor(mode, keyflags);
if(xr.IsNullInstance()) return;
c = SetCursor(mode, keyflags, c);
if(m != NONE)
{
r = xr;
UpdateActionRefresh();
}
}
void RectCtrl::Updated()
{
@ -207,12 +219,12 @@ void RectCtrl::Updated()
}
RectCtrl::RectCtrl()
: pressed(false), moving(false)
: pressed(false), moving(false), mode(NONE), g(4,4)
{
Transparent();
//BackPaint();
style = &StyleDefault();
r.SetNull();
g = Point(4,4);
xr.SetNull();
xp.SetNull();
}

View file

@ -32,7 +32,7 @@ public:
virtual void Updated();
virtual void SetData(const Value& v) { r = v; Refresh(); }
virtual void SetData(const Value& v) { r = v; UpdateRefresh(); }
virtual Value GetData() const { return r; }
static const Style& StyleDefault();
@ -40,17 +40,21 @@ public:
Callback2<Point, dword> WhenMissed;
protected:
//helpers
inline static Rect HandleAt(const Point& p, int size);
int GetMode(const Point& p, dword keyflags);
void CalcRect(const Point& dp, dword keyflags);
void SetCursor(unsigned m, dword keyflags);
static void DrawHandle(Draw& w, const Rect& r, const Color& col, int size);
static void DrawHandleFrame(Draw& w, const Rect& r, const Color& col, int size);
static void DrawRectInfo(Draw& w, const Point& p, const Rect&r, const Color& framecol, const Color& textcol);
static int GetMode(const Rect& r, const Point& p, dword keyflags, int handsize);
static void CalcRect(Rect& r, const Point& dp, dword keyflags, int mode, const Point& g);
static Image SetCursor(unsigned m, dword keyflags, const Image& old);
protected:
const Style* style;
Rect r;
Point g; //grid
public:
enum
{
NONE = 0x0,
@ -91,6 +95,7 @@ protected:
GRID = GRIDX | GRIDY,
};
protected:
//cache
Point xp;
Rect xr;

View file

@ -1,4 +1,5 @@
LAYOUT(RectCtrlTestLayout, 640, 480)
ITEM(DocEdit, dv___0, LeftPosZ(72, 168).TopPosZ(64, 136))
ITEM(RectCtrl, rc, HSizePosZ(0, 0).VSizePosZ(0, 0))
END_LAYOUT