|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
#include "selectiontool.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "rasterselectiontool.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "vectorselectiontool.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "tcurveutil.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "tenv.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "drawutil.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "tools/toolhandle.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "tools/cursors.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "toonz/stage2.h"
|
|
Toshihiro Shimizu |
890ddd |
#include "toonz/tobjecthandle.h"
|
|
Toshihiro Shimizu |
890ddd |
|
|
shun_iwasawa |
d51821 |
#include <qkeyevent></qkeyevent>
|
|
shun_iwasawa |
d51821 |
|
|
Toshihiro Shimizu |
890ddd |
using namespace ToolUtils;
|
|
Toshihiro Shimizu |
890ddd |
using namespace DragSelectionTool;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
TEnv::StringVar SelectionType("SelectionType", "Rectangular");
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::DragTool *createNewMoveSelectionTool(SelectionTool *st) {
|
|
Shinya Kitaoka |
120a6e |
VectorSelectionTool *vst = dynamic_cast<vectorselectiontool *="">(st);</vectorselectiontool>
|
|
Shinya Kitaoka |
120a6e |
RasterSelectionTool *rst = dynamic_cast<rasterselectiontool *="">(st);</rasterselectiontool>
|
|
Shinya Kitaoka |
120a6e |
if (vst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::VectorMoveSelectionTool(vst);
|
|
Shinya Kitaoka |
120a6e |
else if (rst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::RasterMoveSelectionTool(rst);
|
|
Shinya Kitaoka |
120a6e |
return 0;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::DragTool *createNewRotationTool(SelectionTool *st) {
|
|
Shinya Kitaoka |
120a6e |
VectorSelectionTool *vst = dynamic_cast<vectorselectiontool *="">(st);</vectorselectiontool>
|
|
Shinya Kitaoka |
120a6e |
RasterSelectionTool *rst = dynamic_cast<rasterselectiontool *="">(st);</rasterselectiontool>
|
|
Shinya Kitaoka |
120a6e |
if (vst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::VectorRotationTool(vst);
|
|
Shinya Kitaoka |
120a6e |
else if (rst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::RasterRotationTool(rst);
|
|
Shinya Kitaoka |
120a6e |
return 0;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::DragTool *createNewFreeDeformTool(SelectionTool *st) {
|
|
Shinya Kitaoka |
120a6e |
VectorSelectionTool *vst = dynamic_cast<vectorselectiontool *="">(st);</vectorselectiontool>
|
|
Shinya Kitaoka |
120a6e |
RasterSelectionTool *rst = dynamic_cast<rasterselectiontool *="">(st);</rasterselectiontool>
|
|
Shinya Kitaoka |
120a6e |
if (vst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::VectorFreeDeformTool(vst);
|
|
Shinya Kitaoka |
120a6e |
else if (rst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::RasterFreeDeformTool(rst);
|
|
Shinya Kitaoka |
120a6e |
return 0;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::DragTool *createNewScaleTool(SelectionTool *st, int type) {
|
|
Shinya Kitaoka |
120a6e |
VectorSelectionTool *vst = dynamic_cast<vectorselectiontool *="">(st);</vectorselectiontool>
|
|
Shinya Kitaoka |
120a6e |
RasterSelectionTool *rst = dynamic_cast<rasterselectiontool *="">(st);</rasterselectiontool>
|
|
Shinya Kitaoka |
120a6e |
if (vst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::VectorScaleTool(vst, type);
|
|
Shinya Kitaoka |
120a6e |
else if (rst)
|
|
Shinya Kitaoka |
120a6e |
return new DragSelectionTool::RasterScaleTool(rst, type);
|
|
Shinya Kitaoka |
120a6e |
return 0;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Shinya Kitaoka |
120a6e |
namespace {
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
// Return index of point with min x or y
|
|
Shinya Kitaoka |
120a6e |
int tminPoint(std::vector<tpointd> points, bool isX) {</tpointd>
|
|
Shinya Kitaoka |
120a6e |
int i;
|
|
Shinya Kitaoka |
120a6e |
int index = 0;
|
|
Shinya Kitaoka |
120a6e |
TPointD p = points[0];
|
|
Shinya Kitaoka |
120a6e |
for (i = 1; i < (int)points.size(); i++) {
|
|
Shinya Kitaoka |
120a6e |
TPointD nextP = points[i];
|
|
Shinya Kitaoka |
120a6e |
if (isX && p.x < nextP.x || !isX && p.y < nextP.y) continue;
|
|
Shinya Kitaoka |
120a6e |
index = i;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
return index;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int tminPoint(TPointD p0, TPointD p1, bool isX) {
|
|
Shinya Kitaoka |
120a6e |
std::vector<tpointd> v;</tpointd>
|
|
Shinya Kitaoka |
120a6e |
v.push_back(p0);
|
|
Shinya Kitaoka |
120a6e |
v.push_back(p1);
|
|
Shinya Kitaoka |
120a6e |
return tminPoint(v, isX);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Shinya Kitaoka |
120a6e |
} // namespace
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// FourPoints
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
FourPoints DragSelectionTool::FourPoints::orderedPoints() const {
|
|
Shinya Kitaoka |
120a6e |
FourPoints newPoints;
|
|
Shinya Kitaoka |
120a6e |
int i;
|
|
Shinya Kitaoka |
120a6e |
std::vector<tpointd> allPoints;</tpointd>
|
|
Shinya Kitaoka |
120a6e |
allPoints.push_back(m_p00);
|
|
Shinya Kitaoka |
120a6e |
allPoints.push_back(m_p01);
|
|
Shinya Kitaoka |
120a6e |
allPoints.push_back(m_p10);
|
|
Shinya Kitaoka |
120a6e |
allPoints.push_back(m_p11);
|
|
Shinya Kitaoka |
120a6e |
int minXindex1 = tminPoint(allPoints, true);
|
|
Shinya Kitaoka |
120a6e |
std::vector<tpointd> points;</tpointd>
|
|
Shinya Kitaoka |
120a6e |
for (i = 0; i < 4; i++)
|
|
Shinya Kitaoka |
120a6e |
if (i != minXindex1) points.push_back(allPoints[i]);
|
|
Shinya Kitaoka |
120a6e |
int minXindex2 = tminPoint(points, true);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int index = tminPoint(allPoints[minXindex1], points[minXindex2], false);
|
|
Shinya Kitaoka |
120a6e |
TPointD newPoint1 = allPoints[minXindex1];
|
|
Shinya Kitaoka |
120a6e |
TPointD newPoint2 = points[minXindex2];
|
|
Shinya Kitaoka |
120a6e |
if (index == 1) tswap(newPoint1, newPoint2);
|
|
Shinya Kitaoka |
120a6e |
newPoints.setP00(newPoint1);
|
|
Shinya Kitaoka |
120a6e |
newPoints.setP01(newPoint2);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
std::vector<tpointd> points2;</tpointd>
|
|
Shinya Kitaoka |
120a6e |
for (i = 0; i < 3; i++)
|
|
Shinya Kitaoka |
120a6e |
if (i != minXindex2) points2.push_back(points[i]);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
index = tminPoint(points2, false);
|
|
Shinya Kitaoka |
120a6e |
newPoints.setP10(points2[index]);
|
|
Shinya Kitaoka |
120a6e |
newPoints.setP11(points2[(index == 0) ? 1 : 0]);
|
|
Shinya Kitaoka |
120a6e |
return newPoints;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::FourPoints::getPoint(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index == 0)
|
|
Shinya Kitaoka |
120a6e |
return m_p00;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 1)
|
|
Shinya Kitaoka |
120a6e |
return m_p10;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 2)
|
|
Shinya Kitaoka |
120a6e |
return m_p11;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 3)
|
|
Shinya Kitaoka |
120a6e |
return m_p01;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 4)
|
|
Shinya Kitaoka |
120a6e |
return (m_p00 + m_p10) * 0.5;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 5)
|
|
Shinya Kitaoka |
120a6e |
return (m_p10 + m_p11) * 0.5;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 6)
|
|
Shinya Kitaoka |
120a6e |
return (m_p11 + m_p01) * 0.5;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 7)
|
|
Shinya Kitaoka |
120a6e |
return (m_p01 + m_p00) * 0.5;
|
|
Shinya Kitaoka |
120a6e |
return TPointD();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::FourPoints::setPoint(int index, const TPointD &p) {
|
|
Shinya Kitaoka |
120a6e |
if (index == 0)
|
|
Shinya Kitaoka |
120a6e |
m_p00 = p;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 1)
|
|
Shinya Kitaoka |
120a6e |
m_p10 = p;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 2)
|
|
Shinya Kitaoka |
120a6e |
m_p11 = p;
|
|
Shinya Kitaoka |
120a6e |
else if (index == 3)
|
|
Shinya Kitaoka |
120a6e |
m_p01 = p;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
FourPoints DragSelectionTool::FourPoints::enlarge(double d) {
|
|
Shinya Kitaoka |
120a6e |
TPointD v = normalize(getP10() - getP00());
|
|
Shinya Kitaoka |
120a6e |
TPointD p00 = getP00() - d * v;
|
|
Shinya Kitaoka |
120a6e |
TPointD p10 = getP10() + d * v;
|
|
Shinya Kitaoka |
120a6e |
v = normalize(getP11() - getP10());
|
|
Shinya Kitaoka |
120a6e |
p10 = p10 - d * v;
|
|
Shinya Kitaoka |
120a6e |
TPointD p11 = getP11() + d * v;
|
|
Shinya Kitaoka |
120a6e |
v = normalize(getP01() - getP11());
|
|
Shinya Kitaoka |
120a6e |
p11 = p11 - d * v;
|
|
Shinya Kitaoka |
120a6e |
TPointD p01 = getP01() + d * v;
|
|
Shinya Kitaoka |
120a6e |
v = normalize(getP00() - getP01());
|
|
Shinya Kitaoka |
120a6e |
p01 = p01 - d * v;
|
|
Shinya Kitaoka |
120a6e |
p00 = p00 + d * v;
|
|
Shinya Kitaoka |
120a6e |
return FourPoints(p00, p01, p10, p11);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
bool DragSelectionTool::FourPoints::isEmpty() {
|
|
Shinya Kitaoka |
120a6e |
return ((getP00().x == getP01().x && getP01().x == getP10().x &&
|
|
Shinya Kitaoka |
120a6e |
getP10().x == getP11().x) ||
|
|
Shinya Kitaoka |
120a6e |
(getP00().y == getP01().y && getP01().y == getP10().y &&
|
|
Shinya Kitaoka |
120a6e |
getP10().y == getP11().y));
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::FourPoints::empty() {
|
|
Shinya Kitaoka |
120a6e |
m_p00 = TPointD();
|
|
Shinya Kitaoka |
120a6e |
m_p01 = TPointD();
|
|
Shinya Kitaoka |
120a6e |
m_p10 = TPointD();
|
|
Shinya Kitaoka |
120a6e |
m_p11 = TPointD();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
bool DragSelectionTool::FourPoints::contains(TPointD p) {
|
|
Shinya Kitaoka |
120a6e |
double maxDistance =
|
|
Shinya Kitaoka |
120a6e |
std::max(tdistance2(getP00(), getP11()), tdistance2(getP10(), getP01()));
|
|
Shinya Kitaoka |
120a6e |
TPointD outP = p + maxDistance * TPointD(1, 1);
|
|
Shinya Kitaoka |
120a6e |
TSegment segment(outP, p);
|
|
Shinya Kitaoka |
120a6e |
std::vector<doublepair> d;</doublepair>
|
|
Shinya Kitaoka |
120a6e |
int inters = intersect(TSegment(getP00(), getP10()), segment, d);
|
|
Shinya Kitaoka |
120a6e |
inters += intersect(TSegment(getP10(), getP11()), segment, d);
|
|
Shinya Kitaoka |
120a6e |
inters += intersect(TSegment(getP11(), getP01()), segment, d);
|
|
Shinya Kitaoka |
120a6e |
inters += intersect(TSegment(getP01(), getP00()), segment, d);
|
|
Shinya Kitaoka |
120a6e |
return inters % 2 == 1;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
TRectD DragSelectionTool::FourPoints::getBox() const {
|
|
Shinya Kitaoka |
120a6e |
double x0 = std::min({getP00().x, getP10().x, getP01().x, getP11().x});
|
|
Shinya Kitaoka |
120a6e |
double y0 = std::min({getP00().y, getP10().y, getP01().y, getP11().y});
|
|
Shinya Kitaoka |
120a6e |
double x1 = std::max({getP00().x, getP10().x, getP01().x, getP11().x});
|
|
Shinya Kitaoka |
120a6e |
double y1 = std::max({getP00().y, getP10().y, getP01().y, getP11().y});
|
|
Shinya Kitaoka |
120a6e |
return TRectD(TPointD(x0, y0), TPointD(x1, y1));
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
FourPoints &DragSelectionTool::FourPoints::operator=(const TRectD &r) {
|
|
Shinya Kitaoka |
120a6e |
setP00(r.getP00());
|
|
Shinya Kitaoka |
120a6e |
setP01(r.getP01());
|
|
Shinya Kitaoka |
120a6e |
setP10(r.getP10());
|
|
Shinya Kitaoka |
120a6e |
setP11(r.getP11());
|
|
Shinya Kitaoka |
120a6e |
return *this;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
bool DragSelectionTool::FourPoints::operator==(const FourPoints &p) const {
|
|
Shinya Kitaoka |
120a6e |
return getP00() == p.getP00() && getP01() == p.getP01() &&
|
|
Shinya Kitaoka |
120a6e |
getP10() == p.getP10() && getP11() == p.getP11();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
FourPoints DragSelectionTool::FourPoints::operator*(const TAffine &aff) const {
|
|
Shinya Kitaoka |
120a6e |
FourPoints p;
|
|
Shinya Kitaoka |
120a6e |
p.setP00(aff * getP00());
|
|
Shinya Kitaoka |
120a6e |
p.setP10(aff * getP10());
|
|
Shinya Kitaoka |
120a6e |
p.setP11(aff * getP11());
|
|
Shinya Kitaoka |
120a6e |
p.setP01(aff * getP01());
|
|
Shinya Kitaoka |
120a6e |
return p;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::drawFourPoints(const FourPoints &rect,
|
|
Shinya Kitaoka |
120a6e |
const TPixel32 &color,
|
|
Shinya Kitaoka |
120a6e |
unsigned short stipple,
|
|
Shinya Kitaoka |
120a6e |
bool doContrast) {
|
|
Shinya Kitaoka |
120a6e |
GLint src, dst;
|
|
Shinya Kitaoka |
120a6e |
bool isEnabled;
|
|
Shinya Kitaoka |
120a6e |
tglColor(color);
|
|
Shinya Kitaoka |
120a6e |
if (doContrast) {
|
|
Shinya Kitaoka |
120a6e |
if (color == TPixel32::Black) tglColor(TPixel32(90, 90, 90));
|
|
Shinya Kitaoka |
120a6e |
isEnabled = glIsEnabled(GL_BLEND);
|
|
Shinya Kitaoka |
120a6e |
glGetIntegerv(GL_BLEND_SRC, &src);
|
|
Shinya Kitaoka |
120a6e |
glGetIntegerv(GL_BLEND_DST, &dst);
|
|
Shinya Kitaoka |
120a6e |
glEnable(GL_BLEND);
|
|
Shinya Kitaoka |
120a6e |
glBlendFunc(GL_ONE_MINUS_DST_COLOR, GL_ONE_MINUS_SRC_ALPHA);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
if (stipple != 0xffff) {
|
|
Shinya Kitaoka |
120a6e |
glLineStipple(1, stipple);
|
|
Shinya Kitaoka |
120a6e |
glEnable(GL_LINE_STIPPLE);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
glBegin(GL_LINE_STRIP);
|
|
Shinya Kitaoka |
120a6e |
tglVertex(rect.getP00());
|
|
Shinya Kitaoka |
120a6e |
tglVertex(rect.getP01());
|
|
Shinya Kitaoka |
120a6e |
tglVertex(rect.getP11());
|
|
Shinya Kitaoka |
120a6e |
tglVertex(rect.getP10());
|
|
Shinya Kitaoka |
120a6e |
tglVertex(rect.getP00());
|
|
Shinya Kitaoka |
120a6e |
glEnd();
|
|
Shinya Kitaoka |
120a6e |
glDisable(GL_LINE_STIPPLE);
|
|
Shinya Kitaoka |
120a6e |
if (doContrast) {
|
|
Shinya Kitaoka |
120a6e |
if (!isEnabled) glDisable(GL_BLEND);
|
|
Shinya Kitaoka |
120a6e |
glBlendFunc(src, dst);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Shinya Kitaoka |
120a6e |
namespace {
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// UndoMoveCenter
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
d1f6c4 |
class UndoMoveCenter final : public TUndo {
|
|
Shinya Kitaoka |
120a6e |
SelectionTool *m_tool;
|
|
Shinya Kitaoka |
120a6e |
TAffine m_aff;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
public:
|
|
Shinya Kitaoka |
120a6e |
UndoMoveCenter(SelectionTool *tool, const TAffine &aff)
|
|
Shinya Kitaoka |
120a6e |
: m_tool(tool), m_aff(aff) {}
|
|
Shinya Kitaoka |
120a6e |
~UndoMoveCenter() {}
|
|
Shinya Kitaoka |
473e70 |
void undo() const override {
|
|
Shinya Kitaoka |
120a6e |
m_tool->setCenter(m_aff.inv() * m_tool->getCenter());
|
|
Shinya Kitaoka |
120a6e |
m_tool->invalidate();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
void redo() const override {
|
|
Shinya Kitaoka |
120a6e |
m_tool->setCenter(m_aff * m_tool->getCenter());
|
|
Shinya Kitaoka |
120a6e |
m_tool->invalidate();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
int getSize() const override { return sizeof(*this) + sizeof(*m_tool); }
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
473e70 |
QString getHistoryString() override { return QObject::tr("Move Center"); }
|
|
Toshihiro Shimizu |
890ddd |
};
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// MoveCenterTool
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
d1f6c4 |
class MoveCenterTool final : public DragTool {
|
|
Shinya Kitaoka |
120a6e |
TPointD m_startPos;
|
|
Shinya Kitaoka |
120a6e |
TAffine m_transform;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
public:
|
|
Shinya Kitaoka |
120a6e |
MoveCenterTool(SelectionTool *tool)
|
|
Shinya Kitaoka |
120a6e |
: DragTool(tool), m_startPos(), m_transform() {}
|
|
Shinya Kitaoka |
120a6e |
void translateCenter(TAffine aff) {
|
|
Shinya Kitaoka |
120a6e |
getTool()->setCenter(aff * getTool()->getCenter());
|
|
Shinya Kitaoka |
120a6e |
m_transform *= aff;
|
|
Shinya Kitaoka |
120a6e |
getTool()->invalidate();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
void leftButtonDown(const TPointD &pos, const TMouseEvent &e) override {
|
|
Shinya Kitaoka |
120a6e |
m_startPos = pos;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
void leftButtonDrag(const TPointD &pos, const TMouseEvent &e) override {
|
|
Shinya Kitaoka |
120a6e |
TPointD delta = pos - m_startPos;
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = getTool()->getBBox();
|
|
Shinya Kitaoka |
120a6e |
TPointD bboxCenter = 0.5 * (bbox.getP11() + bbox.getP00());
|
|
Shinya Kitaoka |
120a6e |
double maxDistance2 =
|
|
Shinya Kitaoka |
120a6e |
32 * getTool()->getPixelSize() * getTool()->getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
TAffine aff = m_transform.inv() * TTranslation(delta);
|
|
Shinya Kitaoka |
120a6e |
TPointD newCenter = aff * getTool()->getCenter();
|
|
Shinya Kitaoka |
120a6e |
if (tdistance2(newCenter, bboxCenter) < maxDistance2)
|
|
Shinya Kitaoka |
120a6e |
translateCenter(TTranslation(bboxCenter - getTool()->getCenter()));
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
translateCenter(aff);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
void leftButtonUp(const TPointD &pos, const TMouseEvent &e) override {
|
|
Shinya Kitaoka |
120a6e |
UndoMoveCenter *undo = new UndoMoveCenter(getTool(), m_transform);
|
|
Shinya Kitaoka |
120a6e |
TUndoManager::manager()->add(undo);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
473e70 |
void draw() override {}
|
|
Toshihiro Shimizu |
890ddd |
};
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Shinya Kitaoka |
120a6e |
} // namespace
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// DeformTool
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
DragSelectionTool::DeformTool::DeformTool(SelectionTool *tool)
|
|
Shinya Kitaoka |
120a6e |
: DragTool(tool)
|
|
Shinya Kitaoka |
120a6e |
, m_curPos()
|
|
Shinya Kitaoka |
120a6e |
, m_isDragging(false)
|
|
Shinya Kitaoka |
120a6e |
, m_startScaleValue(tool->m_deformValues.m_scaleValue) {}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
MCCCS |
a0ce32 |
int DragSelectionTool::DeformTool::getSymmetricPointIndex(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index == 0 || index == 4 || index == 1 || index == 5) return index + 2;
|
|
Shinya Kitaoka |
120a6e |
return index - 2;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int DragSelectionTool::DeformTool::getBeforePointIndex(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) return (index == 0) ? 7 : index + 3;
|
|
Shinya Kitaoka |
120a6e |
return index - 4;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int DragSelectionTool::DeformTool::getNextPointIndex(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) return index + 4;
|
|
Shinya Kitaoka |
120a6e |
return (index == 7) ? 0 : index - 3;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int DragSelectionTool::DeformTool::getBeforeVertexIndex(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) return (index == 0) ? 3 : index - 1;
|
|
Shinya Kitaoka |
120a6e |
return index - 4;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int DragSelectionTool::DeformTool::getNextVertexIndex(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) return (index == 3) ? 0 : index + 1;
|
|
Shinya Kitaoka |
120a6e |
return (index == 7) ? 0 : index - 3;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::DeformTool::leftButtonDown(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
m_isDragging = true;
|
|
Shinya Kitaoka |
120a6e |
m_curPos = pos;
|
|
Shinya Kitaoka |
120a6e |
setStartPos(pos);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::DeformTool::leftButtonUp(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
addTransformUndo();
|
|
Shinya Kitaoka |
120a6e |
m_isDragging = false;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// Rotation
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
DragSelectionTool::Rotation::Rotation(DeformTool *deformTool)
|
|
Shinya Kitaoka |
120a6e |
: m_curAng(), m_dstAng(), m_deformTool(deformTool) {}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::Rotation::getStartCenter() const {
|
|
Shinya Kitaoka |
120a6e |
return m_deformTool->getTool()->getCenter();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::Rotation::leftButtonDrag(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
SelectionTool *tool = m_deformTool->getTool();
|
|
Shinya Kitaoka |
120a6e |
TPointD center = tool->getCenter();
|
|
Shinya Kitaoka |
120a6e |
TPointD curPos = m_deformTool->getCurPos();
|
|
Shinya Kitaoka |
120a6e |
TPointD delta = pos - curPos;
|
|
Shinya Kitaoka |
120a6e |
TPointD a = pos - center;
|
|
Shinya Kitaoka |
120a6e |
TPointD b = (pos - delta) - center;
|
|
Shinya Kitaoka |
120a6e |
double a2 = norm2(a);
|
|
Shinya Kitaoka |
120a6e |
double b2 = norm2(b);
|
|
Shinya Kitaoka |
120a6e |
const double epsilon = 1e-8;
|
|
Shinya Kitaoka |
120a6e |
double dang = 0;
|
|
Shinya Kitaoka |
120a6e |
double scale = 1;
|
|
Shinya Kitaoka |
120a6e |
if (a2 <= epsilon || b2 <= epsilon) return;
|
|
Shinya Kitaoka |
120a6e |
dang = asin(cross(a, b) / sqrt(a2 * b2)) * -M_180_PI;
|
|
Shinya Kitaoka |
120a6e |
if (e.isShiftPressed()) {
|
|
Shinya Kitaoka |
120a6e |
m_dstAng += dang;
|
|
Shinya Kitaoka |
120a6e |
double ang = tfloor((int)(m_dstAng + 22.5), 45);
|
|
Shinya Kitaoka |
120a6e |
dang = ang - m_curAng;
|
|
Shinya Kitaoka |
120a6e |
m_curAng = ang;
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
m_dstAng += dang;
|
|
Shinya Kitaoka |
120a6e |
dang = m_dstAng - m_curAng;
|
|
Shinya Kitaoka |
120a6e |
m_curAng = m_dstAng;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
tool->m_deformValues.m_rotationAngle =
|
|
Shinya Kitaoka |
120a6e |
tool->m_deformValues.m_rotationAngle + dang;
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->transform(TRotation(center, dang), dang);
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->setCurPos(pos);
|
|
Shinya Kitaoka |
120a6e |
TTool::getApplication()->getCurrentTool()->notifyToolChanged();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::Rotation::draw() {
|
|
Shinya Kitaoka |
120a6e |
tglDrawSegment(m_deformTool->getCurPos(),
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->getTool()->getCenter());
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// FreeDeform
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
DragSelectionTool::FreeDeform::FreeDeform(DeformTool *deformTool)
|
|
Shinya Kitaoka |
120a6e |
: m_deformTool(deformTool) {}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::FreeDeform::leftButtonDrag(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
SelectionTool *tool = m_deformTool->getTool();
|
|
Shinya Kitaoka |
120a6e |
TPointD delta = pos - m_deformTool->getCurPos();
|
|
Shinya Kitaoka |
120a6e |
TPointD center = tool->getCenter();
|
|
Shinya Kitaoka |
120a6e |
int index = tool->getSelectedPoint();
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = tool->getBBox();
|
|
Shinya Kitaoka |
120a6e |
FourPoints newBbox = bbox;
|
|
Shinya Kitaoka |
120a6e |
if (index < 4)
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(index, bbox.getPoint(index) + delta);
|
|
Shinya Kitaoka |
120a6e |
else {
|
|
Shinya Kitaoka |
120a6e |
int beforeIndex = m_deformTool->getBeforeVertexIndex(index);
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(beforeIndex, bbox.getPoint(beforeIndex) + delta);
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(index, bbox.getPoint(index) + delta);
|
|
Shinya Kitaoka |
120a6e |
int nextIndex = m_deformTool->getNextVertexIndex(index);
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(nextIndex, bbox.getPoint(nextIndex) + delta);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
tool->setBBox(bbox);
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->setCurPos(pos);
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->applyTransform(bbox);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// MoveSelection
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
DragSelectionTool::MoveSelection::MoveSelection(DeformTool *deformTool)
|
|
Shinya Kitaoka |
120a6e |
: m_deformTool(deformTool), m_lastDelta(), m_firstPos() {}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::MoveSelection::leftButtonDown(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->setCurPos(pos);
|
|
Shinya Kitaoka |
120a6e |
m_firstPos = pos;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::MoveSelection::leftButtonDrag(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
TAffine aff;
|
|
Shinya Kitaoka |
120a6e |
TPointD curPos = m_deformTool->getCurPos();
|
|
Shinya Kitaoka |
120a6e |
TPointD delta = pos - curPos;
|
|
Shinya Kitaoka |
120a6e |
if (e.isShiftPressed()) {
|
|
Shinya Kitaoka |
120a6e |
if (m_lastDelta == TPointD()) {
|
|
Shinya Kitaoka |
120a6e |
TPointD totalDelta = curPos - m_firstPos;
|
|
Shinya Kitaoka |
120a6e |
aff = TTranslation(totalDelta).inv();
|
|
Shinya Kitaoka |
120a6e |
} else
|
|
Shinya Kitaoka |
120a6e |
aff = TTranslation(m_lastDelta).inv();
|
|
Shinya Kitaoka |
120a6e |
if (fabs((curPos - m_firstPos).x) > fabs((curPos - m_firstPos).y))
|
|
Shinya Kitaoka |
120a6e |
m_lastDelta = TPointD((curPos - m_firstPos).x, 0);
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
m_lastDelta = TPointD(0, (curPos - m_firstPos).y);
|
|
Shinya Kitaoka |
120a6e |
aff *= TTranslation(m_lastDelta);
|
|
Shinya Kitaoka |
120a6e |
} else
|
|
Shinya Kitaoka |
120a6e |
aff = TTranslation(delta);
|
|
Shinya Kitaoka |
120a6e |
double factor = 1.0 / Stage::inch;
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->getTool()->m_deformValues.m_moveValue =
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->getTool()->m_deformValues.m_moveValue + factor * delta;
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->transform(aff);
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->setCurPos(pos);
|
|
Shinya Kitaoka |
120a6e |
TTool::getApplication()->getCurrentTool()->notifyToolChanged();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// Scale
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
DragSelectionTool::Scale::Scale(DeformTool *deformTool, int type)
|
|
Shinya Kitaoka |
120a6e |
: m_deformTool(deformTool)
|
|
Shinya Kitaoka |
120a6e |
, m_startCenter(deformTool->getTool()->getCenter())
|
|
Shinya Kitaoka |
120a6e |
, m_type(type)
|
|
Shinya Kitaoka |
120a6e |
, m_isShiftPressed(false)
|
|
Shinya Kitaoka |
120a6e |
, m_isAltPressed(false)
|
|
Shinya Kitaoka |
120a6e |
, m_scaleInCenter(true) {
|
|
Shinya Kitaoka |
120a6e |
int i;
|
|
Shinya Kitaoka |
120a6e |
for (i = 0; i < (int)m_deformTool->getTool()->getBBoxsCount(); i++)
|
|
Shinya Kitaoka |
120a6e |
m_startBboxs.push_back(m_deformTool->getTool()->getBBox(i));
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::Scale::getIntersectionPoint(const TPointD &point0,
|
|
Shinya Kitaoka |
120a6e |
const TPointD &point1,
|
|
Shinya Kitaoka |
120a6e |
const TPointD &point2,
|
|
Shinya Kitaoka |
120a6e |
const TPointD &point3,
|
|
Shinya Kitaoka |
120a6e |
const TPointD &p) const {
|
|
Shinya Kitaoka |
120a6e |
// Parametri della retta passante per point0, point1
|
|
Shinya Kitaoka |
120a6e |
double d1x = point0.x - point1.x;
|
|
Shinya Kitaoka |
120a6e |
double m1 = d1x == 0 ? 0 : (point0.y - point1.y) / d1x;
|
|
Shinya Kitaoka |
120a6e |
double q1 = point1.y - m1 * point1.x;
|
|
Shinya Kitaoka |
120a6e |
// Parametri della retta passante per p parallela alla retta passante per
|
|
Shinya Kitaoka |
120a6e |
// point1, point2
|
|
Shinya Kitaoka |
120a6e |
double d2x = point2.x - point3.x;
|
|
Shinya Kitaoka |
120a6e |
double m2 = d2x == 0 ? 0 : (point2.y - point3.y) / d2x;
|
|
Shinya Kitaoka |
120a6e |
double q2 = p.y - m2 * p.x;
|
|
Shinya Kitaoka |
120a6e |
// Calcolo l'intersezione tra le due rette
|
|
Shinya Kitaoka |
120a6e |
double x, y, m, q;
|
|
Shinya Kitaoka |
120a6e |
if (d1x == 0) {
|
|
Shinya Kitaoka |
120a6e |
x = point0.x;
|
|
Shinya Kitaoka |
120a6e |
m = m2;
|
|
Shinya Kitaoka |
120a6e |
q = q2;
|
|
Shinya Kitaoka |
120a6e |
} else if (d2x == 0) {
|
|
Shinya Kitaoka |
120a6e |
x = p.x;
|
|
Shinya Kitaoka |
120a6e |
m = m1;
|
|
Shinya Kitaoka |
120a6e |
q = q1;
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
assert(m1 != m2);
|
|
Shinya Kitaoka |
120a6e |
x = (q1 - q2) / (m2 - m1);
|
|
Shinya Kitaoka |
120a6e |
m = m1;
|
|
Shinya Kitaoka |
120a6e |
q = q1;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
y = m * x + q;
|
|
Shinya Kitaoka |
120a6e |
return TPointD(x, y);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::FourPoints DragSelectionTool::Scale::bboxScale(
|
|
Shinya Kitaoka |
120a6e |
int index, const FourPoints &oldBbox, const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = oldBbox;
|
|
Shinya Kitaoka |
120a6e |
TPointD p = oldBbox.getPoint(index);
|
|
Shinya Kitaoka |
120a6e |
int nextIndex = m_deformTool->getNextVertexIndex(index);
|
|
Shinya Kitaoka |
120a6e |
TPointD nextP = oldBbox.getPoint(nextIndex);
|
|
Shinya Kitaoka |
120a6e |
int nextIndex2 = m_deformTool->getNextVertexIndex(nextIndex);
|
|
Shinya Kitaoka |
120a6e |
TPointD next2P = oldBbox.getPoint(nextIndex2);
|
|
Shinya Kitaoka |
120a6e |
TPointD newP = getIntersectionPoint(next2P, nextP, nextP, p, pos);
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(nextIndex, newP);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
int beforeIndex = m_deformTool->getBeforeVertexIndex(index);
|
|
Shinya Kitaoka |
120a6e |
TPointD beforeP = oldBbox.getPoint(beforeIndex);
|
|
Shinya Kitaoka |
120a6e |
int before2Index = m_deformTool->getBeforeVertexIndex(beforeIndex);
|
|
Shinya Kitaoka |
120a6e |
TPointD before2P = oldBbox.getPoint(before2Index);
|
|
Shinya Kitaoka |
120a6e |
newP = getIntersectionPoint(before2P, beforeP, beforeP, p, pos);
|
|
Shinya Kitaoka |
120a6e |
bbox.setPoint(beforeIndex, newP);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) bbox.setPoint(index, pos);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
return bbox;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::Scale::computeScaleValue(int movedIndex,
|
|
Shinya Kitaoka |
120a6e |
const FourPoints newBbox) {
|
|
Shinya Kitaoka |
120a6e |
TPointD p = m_startBboxs[0].getPoint(movedIndex);
|
|
Shinya Kitaoka |
120a6e |
if (movedIndex < 4) {
|
|
Shinya Kitaoka |
120a6e |
int beforeIndex = m_deformTool->getBeforePointIndex(movedIndex);
|
|
Shinya Kitaoka |
120a6e |
int nextIndex = m_deformTool->getNextPointIndex(movedIndex);
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = bboxScale(nextIndex, newBbox, p);
|
|
Shinya Kitaoka |
120a6e |
TPointD scale1 = computeScaleValue(beforeIndex, bbox);
|
|
Shinya Kitaoka |
120a6e |
bbox = bboxScale(beforeIndex, newBbox, p);
|
|
Shinya Kitaoka |
120a6e |
TPointD scale2 = computeScaleValue(nextIndex, bbox);
|
|
Shinya Kitaoka |
120a6e |
if (movedIndex % 2 == 0)
|
|
Shinya Kitaoka |
120a6e |
return TPointD(scale1.x, scale2.y);
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
return TPointD(scale2.x, scale1.y);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
MCCCS |
a0ce32 |
int symmetricIndex = m_deformTool->getSymmetricPointIndex(movedIndex);
|
|
MCCCS |
a0ce32 |
TPointD s = m_startBboxs[0].getPoint(symmetricIndex);
|
|
Shinya Kitaoka |
120a6e |
TPointD center = m_scaleInCenter ? m_startCenter : s;
|
|
Shinya Kitaoka |
120a6e |
TPointD nearP =
|
|
Shinya Kitaoka |
120a6e |
m_startBboxs[0].getPoint(m_deformTool->getBeforePointIndex(movedIndex));
|
|
Shinya Kitaoka |
120a6e |
TPointD pc = getIntersectionPoint(nearP, p, p, s, center);
|
|
Shinya Kitaoka |
120a6e |
TPointD newp = newBbox.getPoint(movedIndex);
|
|
MCCCS |
a0ce32 |
TPointD news = newBbox.getPoint(symmetricIndex);
|
|
Shinya Kitaoka |
120a6e |
TPointD newNearP =
|
|
Shinya Kitaoka |
120a6e |
newBbox.getPoint(m_deformTool->getBeforePointIndex(movedIndex));
|
|
Shinya Kitaoka |
120a6e |
TPointD newpc = getIntersectionPoint(newNearP, newp, newp, news, center);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
double newD = tdistance2(newpc, center);
|
|
Shinya Kitaoka |
120a6e |
double oldD = tdistance2(pc, center);
|
|
Shinya Kitaoka |
120a6e |
double f = sqrt(newD / oldD) - 1;
|
|
Shinya Kitaoka |
120a6e |
TPointD startScaleValue = m_deformTool->getStartScaleValue();
|
|
Shinya Kitaoka |
120a6e |
if (movedIndex % 2 == 1) {
|
|
Shinya Kitaoka |
120a6e |
double sign = (pc.x < center.x && newpc.x < center.x) ||
|
|
Shinya Kitaoka |
120a6e |
(pc.x > center.x && newpc.x > center.x)
|
|
Shinya Kitaoka |
120a6e |
? 1
|
|
Shinya Kitaoka |
120a6e |
: -1;
|
|
Shinya Kitaoka |
120a6e |
double x =
|
|
Shinya Kitaoka |
120a6e |
startScaleValue.x == 0 ? f : startScaleValue.x + startScaleValue.x * f;
|
|
Shinya Kitaoka |
120a6e |
return TPointD(sign * x, startScaleValue.y);
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
double sign = (pc.y < center.y && newpc.y < center.y) ||
|
|
Shinya Kitaoka |
120a6e |
(pc.y > center.y && newpc.y > center.y)
|
|
Shinya Kitaoka |
120a6e |
? 1
|
|
Shinya Kitaoka |
120a6e |
: -1;
|
|
Shinya Kitaoka |
120a6e |
double y =
|
|
Shinya Kitaoka |
120a6e |
startScaleValue.y == 0 ? f : startScaleValue.y + startScaleValue.y * f;
|
|
Shinya Kitaoka |
120a6e |
return TPointD(startScaleValue.x, sign * y);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::Scale::getScaledPoint(int index,
|
|
Shinya Kitaoka |
120a6e |
const FourPoints &oldBbox,
|
|
Shinya Kitaoka |
120a6e |
const TPointD scaleValue,
|
|
Shinya Kitaoka |
120a6e |
const TPointD center) {
|
|
Shinya Kitaoka |
120a6e |
TPointD p = oldBbox.getPoint(index);
|
|
MCCCS |
a0ce32 |
int symmetricIndex = m_deformTool->getSymmetricPointIndex(index);
|
|
MCCCS |
a0ce32 |
TPointD s = oldBbox.getPoint(symmetricIndex);
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) {
|
|
Shinya Kitaoka |
120a6e |
int beforeIndex = m_deformTool->getBeforePointIndex(index);
|
|
Shinya Kitaoka |
120a6e |
int nextIndex = m_deformTool->getNextPointIndex(index);
|
|
Shinya Kitaoka |
120a6e |
TPointD newbp = getScaledPoint(beforeIndex, oldBbox, scaleValue, center);
|
|
Shinya Kitaoka |
120a6e |
TPointD newnp = getScaledPoint(nextIndex, oldBbox, scaleValue, center);
|
|
Shinya Kitaoka |
120a6e |
TPointD bp = oldBbox.getPoint(m_deformTool->getBeforePointIndex(index));
|
|
Shinya Kitaoka |
120a6e |
TPointD np = oldBbox.getPoint(m_deformTool->getNextPointIndex(index));
|
|
Shinya Kitaoka |
120a6e |
TPointD in = getIntersectionPoint(np, p, bp, p, newbp);
|
|
Shinya Kitaoka |
120a6e |
return getIntersectionPoint(newbp, in, np, p, newnp);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
TPointD nearP = oldBbox.getPoint(m_deformTool->getBeforePointIndex(index));
|
|
Shinya Kitaoka |
120a6e |
TPointD nearS =
|
|
MCCCS |
a0ce32 |
oldBbox.getPoint(m_deformTool->getBeforePointIndex(symmetricIndex));
|
|
Shinya Kitaoka |
120a6e |
TPointD pc = getIntersectionPoint(nearP, p, p, s, center);
|
|
Shinya Kitaoka |
120a6e |
TPointD sc = getIntersectionPoint(nearS, s, p, s, center);
|
|
Shinya Kitaoka |
120a6e |
if (center == pc) return pc;
|
|
Shinya Kitaoka |
120a6e |
TPointD v = normalize(center - pc);
|
|
Shinya Kitaoka |
120a6e |
double currentD = tdistance(sc, pc);
|
|
Shinya Kitaoka |
120a6e |
double startD = (index % 2 == 1)
|
|
Shinya Kitaoka |
120a6e |
? currentD / m_deformTool->getStartScaleValue().x
|
|
Shinya Kitaoka |
120a6e |
: currentD / m_deformTool->getStartScaleValue().y;
|
|
Shinya Kitaoka |
120a6e |
double factor = (index % 2 == 1) ? scaleValue.x : scaleValue.y;
|
|
Shinya Kitaoka |
120a6e |
double d = (currentD - startD * factor) * tdistance(center, pc) / currentD;
|
|
Shinya Kitaoka |
120a6e |
return TPointD(pc.x + d * v.x, pc.y + d * v.y);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TPointD DragSelectionTool::Scale::getNewCenter(int index, const FourPoints bbox,
|
|
Shinya Kitaoka |
120a6e |
const TPointD scaleValue) {
|
|
Shinya Kitaoka |
120a6e |
int xIndex, yIndex;
|
|
Shinya Kitaoka |
120a6e |
if (index < 4) {
|
|
Shinya Kitaoka |
120a6e |
xIndex = m_deformTool->getBeforePointIndex(index);
|
|
Shinya Kitaoka |
120a6e |
yIndex = m_deformTool->getNextPointIndex(index);
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
xIndex =
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->getNextPointIndex(m_deformTool->getNextPointIndex(index));
|
|
Shinya Kitaoka |
120a6e |
yIndex = index;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (index % 2 == 1) tswap(xIndex, yIndex);
|
|
Shinya Kitaoka |
120a6e |
FourPoints xBbox = bboxScale(xIndex, bbox, m_startCenter);
|
|
Shinya Kitaoka |
120a6e |
TPointD xCenter = getScaledPoint(
|
|
Shinya Kitaoka |
120a6e |
xIndex, xBbox, scaleValue,
|
|
MCCCS |
a0ce32 |
xBbox.getPoint(m_deformTool->getSymmetricPointIndex(xIndex)));
|
|
Shinya Kitaoka |
120a6e |
FourPoints yBbox = bboxScale(yIndex, bbox, m_startCenter);
|
|
Shinya Kitaoka |
120a6e |
TPointD yCenter = getScaledPoint(
|
|
Shinya Kitaoka |
120a6e |
yIndex, yBbox, scaleValue,
|
|
MCCCS |
a0ce32 |
yBbox.getPoint(m_deformTool->getSymmetricPointIndex(yIndex)));
|
|
Shinya Kitaoka |
120a6e |
TPointD in = getIntersectionPoint(bbox.getP00(), bbox.getP10(), bbox.getP10(),
|
|
Shinya Kitaoka |
120a6e |
bbox.getP11(), xCenter);
|
|
Shinya Kitaoka |
120a6e |
return getIntersectionPoint(in, xCenter, bbox.getP00(), bbox.getP10(),
|
|
Shinya Kitaoka |
120a6e |
yCenter);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
FourPoints DragSelectionTool::Scale::bboxScaleInCenter(
|
|
Shinya Kitaoka |
120a6e |
int index, const FourPoints &oldBbox, const TPointD newPos,
|
|
Shinya Kitaoka |
120a6e |
TPointD &scaleValue, const TPointD center, bool recomputeScaleValue) {
|
|
Shinya Kitaoka |
120a6e |
TPointD oldp = oldBbox.getPoint(index);
|
|
Shinya Kitaoka |
120a6e |
if (areAlmostEqual(oldp.x, newPos.x, 1e-2) &&
|
|
Shinya Kitaoka |
120a6e |
areAlmostEqual(oldp.y, newPos.y, 1e-2))
|
|
Shinya Kitaoka |
120a6e |
return oldBbox;
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = bboxScale(index, oldBbox, newPos);
|
|
Shinya Kitaoka |
120a6e |
if (recomputeScaleValue) scaleValue = computeScaleValue(index, bbox);
|
|
Shinya Kitaoka |
120a6e |
if (!m_scaleInCenter) return bbox;
|
|
MCCCS |
a0ce32 |
int symmetricIndex = m_deformTool->getSymmetricPointIndex(index);
|
|
Shinya Kitaoka |
120a6e |
// Gestisco il caso particolare in cui uno dei fattori di scalatura e' -100% e
|
|
Shinya Kitaoka |
120a6e |
// center e' al centro della bbox
|
|
MCCCS |
a0ce32 |
if (bbox.getPoint(index) == oldBbox.getPoint(symmetricIndex)) {
|
|
MCCCS |
a0ce32 |
bbox.setPoint(symmetricIndex, oldBbox.getPoint(index));
|
|
MCCCS |
a0ce32 |
bbox.setPoint(m_deformTool->getNextPointIndex(symmetricIndex),
|
|
Shinya Kitaoka |
120a6e |
oldBbox.getPoint(m_deformTool->getBeforePointIndex(index)));
|
|
MCCCS |
a0ce32 |
bbox.setPoint(m_deformTool->getBeforePointIndex(symmetricIndex),
|
|
Shinya Kitaoka |
120a6e |
oldBbox.getPoint(m_deformTool->getNextPointIndex(index)));
|
|
Shinya Kitaoka |
120a6e |
} else
|
|
Shinya Kitaoka |
120a6e |
bbox =
|
|
MCCCS |
a0ce32 |
bboxScale(symmetricIndex, bbox,
|
|
MCCCS |
a0ce32 |
getScaledPoint(symmetricIndex, oldBbox, scaleValue, center));
|
|
Shinya Kitaoka |
120a6e |
return bbox;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::Scale::leftButtonDown(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
m_isShiftPressed = e.isShiftPressed();
|
|
Shinya Kitaoka |
120a6e |
m_isAltPressed = e.isAltPressed();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void DragSelectionTool::Scale::leftButtonDrag(const TPointD &pos,
|
|
Shinya Kitaoka |
120a6e |
const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
SelectionTool *tool = m_deformTool->getTool();
|
|
Shinya Kitaoka |
120a6e |
bool isBboxReset = false;
|
|
Shinya Kitaoka |
120a6e |
if (m_isShiftPressed != e.isShiftPressed() ||
|
|
Shinya Kitaoka |
120a6e |
m_isAltPressed != e.isAltPressed()) {
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->applyTransform(m_startBboxs[0]);
|
|
Shinya Kitaoka |
120a6e |
tool->setBBox(m_startBboxs[0]);
|
|
Shinya Kitaoka |
120a6e |
tool->setCenter(m_startCenter);
|
|
Shinya Kitaoka |
120a6e |
isBboxReset = true;
|
|
Shinya Kitaoka |
120a6e |
m_isShiftPressed = e.isShiftPressed();
|
|
Shinya Kitaoka |
120a6e |
m_isAltPressed = e.isAltPressed();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
TPointD newPos = pos;
|
|
Shinya Kitaoka |
120a6e |
int selectedIndex = tool->getSelectedPoint();
|
|
Shinya Kitaoka |
120a6e |
if (m_isShiftPressed && m_type == GLOBAL) {
|
|
Shinya Kitaoka |
120a6e |
TPointD point = tool->getBBox().getPoint(selectedIndex);
|
|
Shinya Kitaoka |
120a6e |
TPointD delta;
|
|
Shinya Kitaoka |
120a6e |
if (!isBboxReset)
|
|
Shinya Kitaoka |
120a6e |
delta = pos - m_deformTool->getCurPos();
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
delta = pos - m_deformTool->getStartPos();
|
|
MCCCS |
a0ce32 |
int symmetricIndex = m_deformTool->getSymmetricPointIndex(selectedIndex);
|
|
MCCCS |
a0ce32 |
TPointD symmetricPoint = tool->getBBox().getPoint(symmetricIndex);
|
|
MCCCS |
a0ce32 |
TPointD v = normalize(point - symmetricPoint);
|
|
Shinya Kitaoka |
120a6e |
delta = v * (v * delta);
|
|
Shinya Kitaoka |
120a6e |
newPos = point + delta;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
m_scaleInCenter = m_isAltPressed;
|
|
Shinya Kitaoka |
120a6e |
m_deformTool->setCurPos(pos);
|
|
Shinya Kitaoka |
120a6e |
TPointD scaleValue = m_deformTool->transform(selectedIndex, newPos);
|
|
Shinya Kitaoka |
120a6e |
tool->m_deformValues.m_scaleValue = scaleValue;
|
|
Shinya Kitaoka |
120a6e |
TTool::getApplication()->getCurrentTool()->notifyToolChanged();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//=============================================================================
|
|
Toshihiro Shimizu |
890ddd |
// SelectionTool
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
SelectionTool::SelectionTool(int targetType)
|
|
Shinya Kitaoka |
120a6e |
: TTool("T_Selection")
|
|
Shinya Kitaoka |
120a6e |
, m_firstTime(true)
|
|
Shinya Kitaoka |
120a6e |
, m_dragTool(0)
|
|
Shinya Kitaoka |
120a6e |
, m_what(Outside)
|
|
Shinya Kitaoka |
120a6e |
, m_leftButtonMousePressed(false)
|
|
Shinya Kitaoka |
120a6e |
, m_shiftPressed(false)
|
|
Shinya Kitaoka |
120a6e |
, m_selecting(false)
|
|
Shinya Kitaoka |
120a6e |
, m_mousePosition(TPointD())
|
|
Shinya Kitaoka |
120a6e |
, m_stroke(0)
|
|
Shinya Kitaoka |
120a6e |
, m_justSelected(false)
|
|
Shinya Kitaoka |
120a6e |
, m_strokeSelectionType("Type:")
|
|
Shinya Kitaoka |
120a6e |
, m_deformValues()
|
|
Shinya Kitaoka |
120a6e |
, m_cursorId(ToolCursor::CURSOR_ARROW) {
|
|
Shinya Kitaoka |
120a6e |
bind(targetType);
|
|
Shinya Kitaoka |
120a6e |
m_prop.bind(m_strokeSelectionType);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.addValue(RECT_SELECTION);
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.addValue(FREEHAND_SELECTION);
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.addValue(POLYLINE_SELECTION);
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.setId("Type");
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
SelectionTool::~SelectionTool() {
|
|
Shinya Kitaoka |
120a6e |
delete m_dragTool;
|
|
Shinya Kitaoka |
120a6e |
if (m_stroke) {
|
|
Shinya Kitaoka |
120a6e |
delete m_stroke;
|
|
Shinya Kitaoka |
120a6e |
m_stroke = 0;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (!m_freeDeformers.empty()) clearPointerContainer(m_freeDeformers);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::clearDeformers() { clearPointerContainer(m_freeDeformers); }
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
TPointD SelectionTool::getCenter(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (m_centers.empty()) return TPointD();
|
|
Shinya Kitaoka |
120a6e |
assert((int)m_centers.size() > index);
|
|
Shinya Kitaoka |
120a6e |
return m_centers[index];
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::setCenter(const TPointD ¢er, int index) {
|
|
Shinya Kitaoka |
120a6e |
if (m_centers.empty()) return;
|
|
Shinya Kitaoka |
120a6e |
assert((int)m_centers.size() > index);
|
|
Shinya Kitaoka |
120a6e |
m_centers[index] = center;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int SelectionTool::getBBoxsCount() const { return m_bboxs.size(); }
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
DragSelectionTool::FourPoints SelectionTool::getBBox(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (m_bboxs.empty()) return DragSelectionTool::FourPoints();
|
|
Shinya Kitaoka |
120a6e |
assert((int)m_bboxs.size() > index);
|
|
Shinya Kitaoka |
120a6e |
return m_bboxs[index];
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::setBBox(const DragSelectionTool::FourPoints &points,
|
|
Shinya Kitaoka |
120a6e |
int index) {
|
|
Shinya Kitaoka |
120a6e |
if (m_bboxs.empty()) return;
|
|
Shinya Kitaoka |
120a6e |
assert((int)m_bboxs.size() > index);
|
|
Shinya Kitaoka |
120a6e |
m_bboxs[index] = points;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
FreeDeformer *SelectionTool::getFreeDeformer(int index) const {
|
|
Shinya Kitaoka |
120a6e |
if (m_freeDeformers.empty()) return 0;
|
|
Shinya Kitaoka |
120a6e |
return m_freeDeformers[index];
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::updateTranslation() {
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.setQStringName(tr("Type:"));
|
|
shun-iwasawa |
df7bb0 |
m_strokeSelectionType.setItemUIName(RECT_SELECTION, tr("Rectangular"));
|
|
shun-iwasawa |
df7bb0 |
m_strokeSelectionType.setItemUIName(FREEHAND_SELECTION, tr("Freehand"));
|
|
shun-iwasawa |
df7bb0 |
m_strokeSelectionType.setItemUIName(POLYLINE_SELECTION, tr("Polyline"));
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::updateAction(TPointD pos, const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
TImageP image = getImage(false);
|
|
Shinya Kitaoka |
120a6e |
TToonzImageP ti = image;
|
|
Shinya Kitaoka |
120a6e |
TRasterImageP ri = image;
|
|
Shinya Kitaoka |
120a6e |
TVectorImageP vi = image;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
m_what = Outside;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::StrokeSelectCursor;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (!ti && !vi && !ri) return;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
bool shift = e.isShiftPressed();
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (shift && !m_leftButtonMousePressed && isModifiableSelectionType()) {
|
|
Shinya Kitaoka |
120a6e |
m_what = ADD_SELECTION;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::SplineEditorCursorAdd;
|
|
Shinya Kitaoka |
120a6e |
} else if (m_leftButtonMousePressed)
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
FourPoints bbox = getBBox();
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
double pixelSize = getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
if (!bbox.isEmpty()) {
|
|
Shinya Kitaoka |
120a6e |
double maxDist = 8 * pixelSize;
|
|
Shinya Kitaoka |
120a6e |
double maxDist2 = maxDist * maxDist;
|
|
Shinya Kitaoka |
120a6e |
double p = (12 * pixelSize) - 3 * pixelSize;
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = NONE;
|
|
Shinya Kitaoka |
120a6e |
if (tdistance2(bbox.getP00(), pos) < maxDist2 + p)
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P00;
|
|
Shinya Kitaoka |
120a6e |
else if (tdistance2(bbox.getP11(), pos) < maxDist2 + p)
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P11;
|
|
Shinya Kitaoka |
120a6e |
else if (tdistance2(bbox.getP01(), pos) < maxDist2 + p)
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P01;
|
|
Shinya Kitaoka |
120a6e |
else if (tdistance2(bbox.getP10(), pos) < maxDist2 + p)
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P10;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (tdistance2(bbox.getBottomLeft() + TPointD(-p, -p), pos) < maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
m_what = ROTATION;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::RotBottomLeft;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
} else if (tdistance2(bbox.getBottomRight() + TPointD(p, -p), pos) <
|
|
Shinya Kitaoka |
120a6e |
maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
m_what = ROTATION;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::RotBottomRight;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
} else if (tdistance2(bbox.getTopRight() + TPointD(p, p), pos) < maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
m_what = ROTATION;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::RotCursor;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
} else if (tdistance2(bbox.getTopLeft() + TPointD(-p, p), pos) < maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
m_what = ROTATION;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::RotTopLeft;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
maxDist = 5 * pixelSize;
|
|
Shinya Kitaoka |
120a6e |
maxDist2 = maxDist * maxDist;
|
|
Shinya Kitaoka |
120a6e |
if (tdistance2(bbox.getP00(), pos) < maxDist2 ||
|
|
Shinya Kitaoka |
120a6e |
tdistance2(bbox.getP11(), pos) < maxDist2 ||
|
|
Shinya Kitaoka |
120a6e |
tdistance2(bbox.getP01(), pos) < maxDist2 ||
|
|
Shinya Kitaoka |
120a6e |
tdistance2(bbox.getP10(), pos) < maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
if (!e.isCtrlPressed() || isLevelType() || isSelectedFramesType()) {
|
|
Shinya Kitaoka |
120a6e |
m_what = SCALE;
|
|
Shinya Kitaoka |
120a6e |
if (tdistance2(bbox.getTopRight(), pos) < maxDist2 ||
|
|
Shinya Kitaoka |
120a6e |
tdistance2(bbox.getBottomLeft(), pos) < maxDist2)
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::ScaleCursor;
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::ScaleInvCursor;
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::DistortCursor;
|
|
Shinya Kitaoka |
120a6e |
m_what = DEFORM;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (isCloseToSegment(pos, TSegment(bbox.getPoint(0), bbox.getPoint(3)),
|
|
Shinya Kitaoka |
120a6e |
maxDist))
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P0M;
|
|
Shinya Kitaoka |
120a6e |
else if (isCloseToSegment(pos, TSegment(bbox.getPoint(1), bbox.getPoint(2)),
|
|
Shinya Kitaoka |
120a6e |
maxDist))
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = P1M;
|
|
Shinya Kitaoka |
120a6e |
else if (isCloseToSegment(pos, TSegment(bbox.getPoint(3), bbox.getPoint(2)),
|
|
Shinya Kitaoka |
120a6e |
maxDist))
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = PM1;
|
|
Shinya Kitaoka |
120a6e |
else if (isCloseToSegment(pos, TSegment(bbox.getPoint(0), bbox.getPoint(1)),
|
|
Shinya Kitaoka |
120a6e |
maxDist))
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = PM0;
|
|
Shinya Kitaoka |
120a6e |
if (m_selectedPoint == P0M || m_selectedPoint == P1M) {
|
|
Shinya Kitaoka |
120a6e |
if (!e.isCtrlPressed() || isLevelType() || isSelectedFramesType()) {
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::ScaleHCursor;
|
|
Shinya Kitaoka |
120a6e |
m_what = SCALE_X;
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::DistortCursor;
|
|
Shinya Kitaoka |
120a6e |
m_what = DEFORM;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (m_selectedPoint == PM1 || m_selectedPoint == PM0) {
|
|
Shinya Kitaoka |
120a6e |
if (!e.isCtrlPressed() || isLevelType() || isSelectedFramesType()) {
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::ScaleVCursor;
|
|
Shinya Kitaoka |
120a6e |
m_what = SCALE_Y;
|
|
Shinya Kitaoka |
120a6e |
} else {
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::DistortCursor;
|
|
Shinya Kitaoka |
120a6e |
m_what = DEFORM;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (!isLevelType() && !isSelectedFramesType() &&
|
|
Shinya Kitaoka |
120a6e |
tdistance2(getCenter(), pos) < maxDist2) {
|
|
Shinya Kitaoka |
120a6e |
m_what = MOVE_CENTER;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
TPointD hpos = bbox.getP10() - TPointD(14 * pixelSize, 15 * pixelSize);
|
|
Shinya Kitaoka |
120a6e |
TRectD rect(hpos - TPointD(14 * pixelSize, 5 * pixelSize),
|
|
Shinya Kitaoka |
120a6e |
hpos + TPointD(14 * pixelSize, 5 * pixelSize));
|
|
Shinya Kitaoka |
120a6e |
if (!m_deformValues.m_isSelectionModified && rect.contains(pos) && vi &&
|
|
Shinya Kitaoka |
120a6e |
!TTool::getApplication()->getCurrentObject()->isSpline()) {
|
|
Shinya Kitaoka |
120a6e |
m_what = GLOBAL_THICKNESS;
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::PumpCursor;
|
|
Shinya Kitaoka |
120a6e |
return;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
m_selectedPoint = NONE;
|
|
Shinya Kitaoka |
120a6e |
if ((isLevelType() || isSelectedFramesType()) && !isSameStyleType()) {
|
|
Shinya Kitaoka |
120a6e |
m_what = Inside;
|
|
Shinya Kitaoka |
120a6e |
ToolCursor::LevelSelectCursor;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (shift) return;
|
|
Shinya Kitaoka |
120a6e |
if (!vi && bbox.contains(pos)) {
|
|
Shinya Kitaoka |
120a6e |
m_what = Inside;
|
|
Shinya Kitaoka |
120a6e |
if (isLevelType() || isSelectedFramesType())
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::LevelSelectCursor;
|
|
Shinya Kitaoka |
120a6e |
else
|
|
Shinya Kitaoka |
120a6e |
m_cursorId = ToolCursor::MoveCursor;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::leftButtonDown(const TPointD &pos, const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
TImageP image = getImage(false);
|
|
Shinya Kitaoka |
120a6e |
if (!image) return;
|
|
Shinya Kitaoka |
120a6e |
if (m_polyline.size() == 0) {
|
|
Shinya Kitaoka |
120a6e |
modifySelectionOnClick(image, pos, e);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (m_what == ROTATION) m_dragTool = createNewRotationTool(this);
|
|
Shinya Kitaoka |
120a6e |
if (!e.isShiftPressed() && m_what == Inside)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = createNewMoveSelectionTool(this);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == MOVE_CENTER)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = new MoveCenterTool(this);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == SCALE)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = createNewScaleTool(this, 0);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == SCALE_X)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = createNewScaleTool(this, 1);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == SCALE_Y)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = createNewScaleTool(this, 2);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == DEFORM)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = createNewFreeDeformTool(this);
|
|
Shinya Kitaoka |
120a6e |
else if (m_what == GLOBAL_THICKNESS)
|
|
Shinya Kitaoka |
120a6e |
m_dragTool = new VectorChangeThicknessTool((VectorSelectionTool *)this);
|
|
Shinya Kitaoka |
120a6e |
if (m_dragTool) m_dragTool->leftButtonDown(pos, e);
|
|
Shinya Kitaoka |
120a6e |
} else
|
|
Shinya Kitaoka |
120a6e |
m_selecting = true;
|
|
Shinya Kitaoka |
120a6e |
if (m_selecting) {
|
|
Shinya Kitaoka |
120a6e |
if (m_stroke) {
|
|
Shinya Kitaoka |
120a6e |
delete m_stroke;
|
|
Shinya Kitaoka |
120a6e |
m_stroke = 0;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (m_strokeSelectionType.getValue() == FREEHAND_SELECTION)
|
|
Shinya Kitaoka |
120a6e |
startFreehand(pos);
|
|
Shinya Kitaoka |
120a6e |
if (m_strokeSelectionType.getValue() == POLYLINE_SELECTION)
|
|
Shinya Kitaoka |
120a6e |
addPointPolyline(pos);
|
|
Shinya Kitaoka |
120a6e |
else if (m_polyline.size() != 0)
|
|
Shinya Kitaoka |
120a6e |
m_polyline.clear();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
m_firstPos = m_curPos = pos;
|
|
Shinya Kitaoka |
120a6e |
m_leftButtonMousePressed = true;
|
|
Shinya Kitaoka |
120a6e |
m_shiftPressed = e.isShiftPressed();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::mouseMove(const TPointD &pos, const TMouseEvent &e) {
|
|
Shinya Kitaoka |
120a6e |
updateAction(pos, e);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (m_strokeSelectionType.getValue() == POLYLINE_SELECTION) {
|
|
Shinya Kitaoka |
120a6e |
m_mousePosition = pos;
|
|
Shinya Kitaoka |
120a6e |
invalidate();
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
shun-iwasawa |
7f1e30 |
bool SelectionTool::keyDown(QKeyEvent *event) {
|
|
Shinya Kitaoka |
120a6e |
if (isSelectionEmpty()) return false;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TPointD delta;
|
|
shun-iwasawa |
7f1e30 |
|
|
shun-iwasawa |
7f1e30 |
switch (event->key()) {
|
|
shun-iwasawa |
7f1e30 |
case Qt::Key_Up:
|
|
Shinya Kitaoka |
120a6e |
delta.y = 1;
|
|
shun-iwasawa |
7f1e30 |
break;
|
|
shun-iwasawa |
7f1e30 |
case Qt::Key_Down:
|
|
Shinya Kitaoka |
120a6e |
delta.y = -1;
|
|
shun-iwasawa |
7f1e30 |
break;
|
|
shun-iwasawa |
7f1e30 |
case Qt::Key_Left:
|
|
Shinya Kitaoka |
120a6e |
delta.x = -1;
|
|
shun-iwasawa |
7f1e30 |
break;
|
|
shun-iwasawa |
7f1e30 |
case Qt::Key_Right:
|
|
Shinya Kitaoka |
120a6e |
delta.x = 1;
|
|
shun-iwasawa |
7f1e30 |
break;
|
|
shun-iwasawa |
7f1e30 |
default:
|
|
Shinya Kitaoka |
120a6e |
return false;
|
|
shun-iwasawa |
7f1e30 |
break;
|
|
shun-iwasawa |
7f1e30 |
}
|
|
shun-iwasawa |
7f1e30 |
|
|
shun-iwasawa |
7f1e30 |
if (event->modifiers() & Qt::ShiftModifier) {
|
|
shun-iwasawa |
7f1e30 |
delta.x *= 10.0;
|
|
shun-iwasawa |
7f1e30 |
delta.y *= 10.0;
|
|
shun-iwasawa |
7f1e30 |
} else if (event->modifiers() & Qt::ControlModifier) {
|
|
shun-iwasawa |
7f1e30 |
delta.x *= 0.1;
|
|
shun-iwasawa |
7f1e30 |
delta.y *= 0.1;
|
|
shun-iwasawa |
7f1e30 |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TImageP image = getImage(true);
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
TToonzImageP ti = (TToonzImageP)image;
|
|
Shinya Kitaoka |
120a6e |
TRasterImageP ri = (TRasterImageP)image;
|
|
Shinya Kitaoka |
120a6e |
TVectorImageP vi = (TVectorImageP)image;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
if (!ti && !vi && !ri) return false;
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
DragTool *dragTool = createNewMoveSelectionTool(this);
|
|
Shinya Kitaoka |
120a6e |
TAffine aff = TTranslation(delta);
|
|
Shinya Kitaoka |
120a6e |
dragTool->transform(aff);
|
|
Shinya Kitaoka |
120a6e |
double factor = 1.0 / Stage::inch;
|
|
Shinya Kitaoka |
120a6e |
m_deformValues.m_moveValue += factor * delta;
|
|
Shinya Kitaoka |
120a6e |
dragTool->addTransformUndo();
|
|
Shinya Kitaoka |
120a6e |
TTool::getApplication()->getCurrentTool()->notifyToolChanged();
|
|
Shinya Kitaoka |
120a6e |
delete dragTool;
|
|
Shinya Kitaoka |
120a6e |
dragTool = 0;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
invalidate();
|
|
Shinya Kitaoka |
120a6e |
return true;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
int SelectionTool::getCursorId() const {
|
|
Shinya Kitaoka |
120a6e |
TImageP image = getImage(false);
|
|
Shinya Kitaoka |
120a6e |
TToonzImageP ti = (TToonzImageP)image;
|
|
Shinya Kitaoka |
120a6e |
TRasterImageP ri = (TRasterImageP)image;
|
|
Shinya Kitaoka |
120a6e |
TVectorImageP vi = (TVectorImageP)image;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
if (!ti && !vi && !ri) return ToolCursor::StrokeSelectCursor;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
return m_cursorId;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::drawPolylineSelection() {
|
|
Shinya Kitaoka |
120a6e |
if (m_polyline.empty()) return;
|
|
Shinya Kitaoka |
120a6e |
TPixel color = ToonzCheck::instance()->getChecks() & ToonzCheck::eBlackBg
|
|
Shinya Kitaoka |
120a6e |
? TPixel32::White
|
|
Shinya Kitaoka |
120a6e |
: TPixel32::Black;
|
|
Shinya Kitaoka |
120a6e |
tglColor(color);
|
|
Shinya Kitaoka |
120a6e |
tglDrawCircle(m_polyline[0], 2);
|
|
Shinya Kitaoka |
120a6e |
glBegin(GL_LINE_STRIP);
|
|
Shinya Kitaoka |
120a6e |
for (UINT i = 0; i < m_polyline.size(); i++) tglVertex(m_polyline[i]);
|
|
Shinya Kitaoka |
120a6e |
tglVertex(m_mousePosition);
|
|
Shinya Kitaoka |
120a6e |
glEnd();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
shun-iwasawa |
c189d1 |
void SelectionTool::drawFreehandSelection() {
|
|
shun-iwasawa |
c189d1 |
if (m_track.isEmpty()) return;
|
|
shun-iwasawa |
c189d1 |
TPixel color = ToonzCheck::instance()->getChecks() & ToonzCheck::eBlackBg
|
|
shun-iwasawa |
c189d1 |
? TPixel32::White
|
|
shun-iwasawa |
c189d1 |
: TPixel32::Black;
|
|
shun-iwasawa |
c189d1 |
tglColor(color);
|
|
shun-iwasawa |
c189d1 |
m_track.drawAllFragments();
|
|
shun-iwasawa |
c189d1 |
}
|
|
shun-iwasawa |
c189d1 |
|
|
shun-iwasawa |
c189d1 |
//-----------------------------------------------------------------------------
|
|
shun-iwasawa |
c189d1 |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::drawRectSelection(const TImage *image) {
|
|
Shinya Kitaoka |
120a6e |
const TVectorImage *vi = dynamic_cast<const *="" tvectorimage="">(image);</const>
|
|
Shinya Kitaoka |
120a6e |
unsigned short stipple = 0x3F33;
|
|
Shinya Kitaoka |
120a6e |
FourPoints selectingRect = m_selectingRect;
|
|
Shinya Kitaoka |
120a6e |
if (vi && m_curPos.x >= m_firstPos.x) stipple = 0xFF00;
|
|
Shinya Kitaoka |
120a6e |
drawFourPoints(selectingRect, TPixel32::Black, stipple, true);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::drawCommandHandle(const TImage *image) {
|
|
Shinya Kitaoka |
120a6e |
const TVectorImage *vi = dynamic_cast<const *="" tvectorimage="">(image);</const>
|
|
Shinya Kitaoka |
120a6e |
TPixel32 frameColor(127, 127, 127);
|
|
Shinya Kitaoka |
120a6e |
FourPoints rect = getBBox();
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
drawFourPoints(rect, frameColor, 0xffff, true);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
tglColor(frameColor);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
if (m_dragTool) m_dragTool->draw();
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
double pixelSize = getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
if (!isLevelType() && !isSelectedFramesType())
|
|
Shinya Kitaoka |
120a6e |
tglDrawCircle(getCenter(), pixelSize * 4);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
drawSquare(rect.getP00(), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(rect.getP01(), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(rect.getP10(), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(rect.getP11(), pixelSize * 4, frameColor);
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
if (vi && !m_deformValues.m_isSelectionModified) {
|
|
Shinya Kitaoka |
120a6e |
TPointD thickCommandPos =
|
|
Shinya Kitaoka |
120a6e |
rect.getP10() - TPointD(14 * pixelSize, 15 * pixelSize);
|
|
Shinya Kitaoka |
120a6e |
drawRectWhitArrow(thickCommandPos, pixelSize);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
drawSquare(0.5 * (rect.getP10() + rect.getP11()), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(0.5 * (rect.getP01() + rect.getP11()), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(0.5 * (rect.getP10() + rect.getP00()), pixelSize * 4, frameColor);
|
|
Shinya Kitaoka |
120a6e |
drawSquare(0.5 * (rect.getP01() + rect.getP00()), pixelSize * 4, frameColor);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::onActivate() {
|
|
Shinya Kitaoka |
120a6e |
if (m_firstTime) {
|
|
Shinya Kitaoka |
120a6e |
m_strokeSelectionType.setValue(::to_wstring(SelectionType.getValue()));
|
|
Shinya Kitaoka |
120a6e |
m_firstTime = false;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
if (isLevelType() || isSelectedFramesType()) return;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
doOnActivate();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::onDeactivate() {
|
|
Shinya Kitaoka |
120a6e |
if (isLevelType() || isSelectedFramesType()) return;
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
doOnDeactivate();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::onSelectionChanged() {
|
|
Shinya Kitaoka |
120a6e |
computeBBox();
|
|
Shinya Kitaoka |
120a6e |
invalidate();
|
|
Shinya Kitaoka |
120a6e |
m_polyline.clear();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
bool SelectionTool::onPropertyChanged(std::string propertyName) {
|
|
Shinya Kitaoka |
120a6e |
if (propertyName == m_strokeSelectionType.getName()) {
|
|
Shinya Kitaoka |
120a6e |
SelectionType = ::to_string(m_strokeSelectionType.getValue());
|
|
Shinya Kitaoka |
120a6e |
return true;
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
return false;
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
//! Viene aggiunto \b pos a \b m_track e disegnato il primo pezzetto del lazzo.
|
|
Shinya Kitaoka |
120a6e |
//! Viene inizializzato \b m_firstPos
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::startFreehand(const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
m_track.clear();
|
|
Shinya Kitaoka |
120a6e |
m_firstPos = pos;
|
|
Shinya Kitaoka |
120a6e |
double pixelSize = getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
m_track.add(TThickPoint(pos, 0), pixelSize * pixelSize);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
//! Viene aggiunto \b pos a \b m_track e disegnato un altro pezzetto del lazzo.
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::freehandDrag(const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
double pixelSize = getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
m_track.add(TThickPoint(pos, 0), pixelSize * pixelSize);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
//! Viene chiuso il lazzo (si aggiunge l'ultimo punto ad m_track) e viene creato
|
|
Shinya Kitaoka |
120a6e |
//! lo stroke rappresentante il lazzo.
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::closeFreehand(const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
if (m_track.isEmpty()) return;
|
|
Shinya Kitaoka |
120a6e |
double pixelSize = getPixelSize();
|
|
Shinya Kitaoka |
120a6e |
m_track.add(TThickPoint(m_firstPos, 0), pixelSize * pixelSize);
|
|
Shinya Kitaoka |
120a6e |
m_track.filterPoints();
|
|
Shinya Kitaoka |
120a6e |
double error = (30.0 / 11) * pixelSize;
|
|
Shinya Kitaoka |
120a6e |
m_stroke = m_track.makeStroke(error);
|
|
Shinya Kitaoka |
120a6e |
m_stroke->setStyle(1);
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
Toshihiro Shimizu |
890ddd |
|
|
Toshihiro Shimizu |
890ddd |
//-----------------------------------------------------------------------------
|
|
Toshihiro Shimizu |
890ddd |
|
|
Shinya Kitaoka |
120a6e |
//! Viene aggiunto un punto al vettore m_polyline.
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::addPointPolyline(const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
m_firstPos = pos;
|
|
Shinya Kitaoka |
120a6e |
m_mousePosition = pos;
|
|
Shinya Kitaoka |
120a6e |
m_polyline.push_back(pos);
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//-----------------------------------------------------------------------------
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
//! Agginge l'ultimo pos a \b m_polyline e chiude la spezzata (aggiunge \b
|
|
Shinya Kitaoka |
120a6e |
//! m_polyline.front() alla fine del vettore).
|
|
Shinya Kitaoka |
120a6e |
void SelectionTool::closePolyline(const TPointD &pos) {
|
|
Shinya Kitaoka |
120a6e |
if (m_polyline.size() <= 1) return;
|
|
Shinya Kitaoka |
120a6e |
if (m_polyline.back() != pos) m_polyline.push_back(pos);
|
|
Shinya Kitaoka |
120a6e |
if (m_polyline.back() != m_polyline.front())
|
|
Shinya Kitaoka |
120a6e |
m_polyline.push_back(m_polyline.front());
|
|
Shinya Kitaoka |
120a6e |
|
|
Shinya Kitaoka |
120a6e |
std::vector<tthickpoint> strokePoints;</tthickpoint>
|
|
Shinya Kitaoka |
120a6e |
for (UINT i = 0; i < m_polyline.size() - 1; i++) {
|
|
Shinya Kitaoka |
120a6e |
strokePoints.push_back(TThickPoint(m_polyline[i], 0));
|
|
Shinya Kitaoka |
120a6e |
strokePoints.push_back(
|
|
Shinya Kitaoka |
120a6e |
TThickPoint(0.5 * (m_polyline[i] + m_polyline[i + 1]), 0));
|
|
Shinya Kitaoka |
120a6e |
}
|
|
Shinya Kitaoka |
120a6e |
strokePoints.push_back(TThickPoint(m_polyline.back(), 0));
|
|
Shinya Kitaoka |
120a6e |
m_polyline.clear();
|
|
Shinya Kitaoka |
120a6e |
m_stroke = new TStroke(strokePoints);
|
|
Shinya Kitaoka |
120a6e |
assert(m_stroke->getPoint(0) == m_stroke->getPoint(1));
|
|
Shinya Kitaoka |
120a6e |
invalidate();
|
|
Toshihiro Shimizu |
890ddd |
}
|
|
shun_iwasawa |
d51821 |
|
|
shun_iwasawa |
d51821 |
//-----------------------------------------------------------------------------
|
|
shun_iwasawa |
d51821 |
|
|
shun_iwasawa |
d51821 |
// returns true if the pressed key is recognized and processed in the tool
|
|
shun_iwasawa |
d51821 |
// instead of triggering the shortcut command.
|
|
shun_iwasawa |
d51821 |
bool SelectionTool::isEventAcceptable(QEvent *e) {
|
|
shun_iwasawa |
d51821 |
if (!isEnabled()) return false;
|
|
shun_iwasawa |
d51821 |
if (isSelectionEmpty()) return false;
|
|
shun_iwasawa |
d51821 |
// arrow keys will be used for moving the selected region
|
|
shun_iwasawa |
d51821 |
QKeyEvent *keyEvent = static_cast<qkeyevent *="">(e);</qkeyevent>
|
|
shun_iwasawa |
d51821 |
int key = keyEvent->key();
|
|
shun_iwasawa |
d51821 |
return (key == Qt::Key_Up || key == Qt::Key_Down || key == Qt::Key_Left ||
|
|
shun_iwasawa |
d51821 |
key == Qt::Key_Right);
|
|
shun_iwasawa |
d51821 |
}
|