25#include <tqradiobutton.h>
26#include <tqbuttongroup.h>
32#include <karbon_part.h>
33#include <karbon_view.h>
34#include <render/vpainter.h>
35#include <render/vpainterfactory.h>
36#include <core/vselection.h>
37#include "vselecttool.h"
38#include <commands/vtransformcmd.h>
39#include <visitors/vselectiondesc.h>
40#include <visitors/vselectobjects.h>
41#include <widgets/vcanvas.h>
43VSelectOptionsWidget::VSelectOptionsWidget(
KarbonPart *part )
44 : KDialogBase( 0L,
"", true, i18n(
"Selection" ), Ok | Cancel ), m_part( part )
46 TQButtonGroup *group =
new TQButtonGroup( 1, TQt::Horizontal, i18n(
"Selection Mode" ),
this );
48 new TQRadioButton( i18n(
"Select in current layer" ), group );
49 new TQRadioButton( i18n(
"Select in visible layers" ), group );
50 new TQRadioButton( i18n(
"Select in selected layers" ), group );
52 group->setRadioButtonExclusive(
true );
55 connect( group, TQ_SIGNAL( clicked(
int ) ),
this, TQ_SLOT( modeChange(
int ) ) );
57 group->setInsideMargin( 4 );
58 group->setInsideSpacing( 2 );
60 setMainWidget( group );
61 setFixedSize( baseSize() );
64void VSelectOptionsWidget::modeChange(
int mode )
69VSelectTool::VSelectTool( KarbonView *view )
70 :
VTool( view,
"tool_select" ), m_state( normal )
74 m_objects.setAutoDelete(
true );
75 m_optionsWidget =
new VSelectOptionsWidget( view->part() );
77 connect( view, TQ_SIGNAL( selectionChange() ),
this, TQ_SLOT( updateStatusBar() ) );
80VSelectTool::~VSelectTool()
82 delete m_optionsWidget;
86VSelectTool::activate()
89 view()->setCursor( TQCursor( TQt::arrowCursor ) );
90 view()->part()->document().selection()->showHandle();
91 view()->part()->document().selection()->setSelectObjects();
93 view()->part()->document().selection()->selectNodes();
94 view()->repaintAll( view()->part()->document().selection()->boundingBox() );
99VSelectTool::statusText()
101 return i18n(
"Select" );
104TQString VSelectTool::contextHelp()
106 TQString s = i18n(
"<qt><b>Selection tool:</b><br>" );
107 s += i18n(
"<i>Select in current layer:</i><br>The selection is made in the layer selected in the layers docker.<br><br>" );
108 s += i18n(
"<i>Select in visible layers:</i><br>The selection is made in the visible layers (eye in the layers docker).<br><br>" );
109 s += i18n(
"<i>Select in selected layers:</i><br>The selection is made in the checked layers in the layers docker.<br><br>" );
110 s += i18n(
"<i>Position using arrow keys</i><br>The selection can be positioned up, down, left and right using the corresponding arrow keys." );
117 VPainter *painter = view()->painterFactory()->editpainter();
119 painter->setRasterOp( TQt::NotROP );
121 KoRect rect = view()->part()->document().selection()->boundingBox();
123 if( m_state != normal )
125 VObjectListIterator itr = m_objects;
126 for( ; itr.current(); ++itr )
128 itr.current()->draw( painter, &itr.current()->boundingBox() );
131 else if( m_state == normal )
133 painter->setPen( TQt::DotLine );
135 painter->moveTo( KoPoint( first().x(), first().y() ) );
136 painter->lineTo( KoPoint( m_current.x(), first().y() ) );
137 painter->lineTo( KoPoint( m_current.x(), m_current.y() ) );
138 painter->lineTo( KoPoint( first().x(), m_current.y() ) );
139 painter->lineTo( KoPoint( first().x(), first().y() ) );
140 painter->strokePath();
147VSelectTool::setCursor()
const
149 if( m_state != normal || !view() )
return;
150 switch( view()->part()->document().selection()->handleNode( last() ) )
154 view()->setCursor( TQCursor( TQt::SizeFDiagCursor ) );
158 view()->setCursor( TQCursor( TQt::SizeBDiagCursor ) );
162 view()->setCursor( TQCursor( TQt::SizeHorCursor ) );
166 view()->setCursor( TQCursor( TQt::SizeVerCursor ) );
169 view()->setCursor( TQCursor( TQt::arrowCursor ) );
174VSelectTool::mouseButtonPress()
181 m_activeNode = view()->part()->document().selection()->handleNode( first() );
182 KoRect rect = view()->part()->document().selection()->boundingBox();
184 if( m_activeNode != node_none )
186 else if( rect.contains( m_current ) && m_state == normal )
192 view()->part()->document().selection()->setState(
VObject::edit );
193 view()->repaintAll( rect );
200VSelectTool::rightMouseButtonPress()
210 view()->part()->document().selection()->setState(
VObject::edit );
211 view()->repaintAll( view()->part()->document().selection()->boundingBox() );
218VSelectTool::mouseDrag()
228VSelectTool::rightMouseButtonRelease()
236 VObjectList newSelection;
238 if( selector.visit( view()->part()->document() ) )
239 view()->part()->document().selection()->take( *newSelection.last() );
241 view()->part()->repaintAllViews( view()->part()->document().selection()->boundingBox() );
242 view()->selectionChanged();
246 else if( view()->part()->document().selection()->objects().count() > 0 )
248 view()->showSelectionPopupMenu( TQCursor::pos() );
253VSelectTool::mouseButtonRelease()
261 VObjectList newSelection;
262 VObjectList oldSelection = view()->part()->document().selection()->objects();
265 if( ! ctrlPressed() )
266 view()->part()->document().selection()->clear();
270 if( selector.visit( view()->part()->document() ) )
274 VObjectListIterator it( newSelection );
275 for( ; it.current(); ++it )
277 if( oldSelection.contains( it.current() ) )
278 lastMatched = it.current();
284 if( lastMatched && lastMatched != newSelection.first() )
287 view()->part()->document().selection()->append( newSelection.last() );
293 if( ! ctrlPressed() )
294 view()->part()->document().selection()->clear();
297 VObjectList newSelection;
299 if( selector.visit( view()->part()->document() ) )
300 view()->part()->document().selection()->append( newSelection.last() );
303 view()->part()->repaintAllViews( view()->part()->document().selection()->boundingBox() );
304 view()->selectionChanged();
310VSelectTool::mouseDragRelease()
312 if( m_state == normal )
315 KoPoint fp = first();
317 if( ! ctrlPressed() )
318 view()->part()->document().selection()->clear();
320 KoRect selRect = KoRect( fp.x(), fp.y(), lp.x() - fp.x(), lp.y() - fp.y() ).normalize();
322 view()->part()->document().selection()->append( selRect );
324 view()->part()->document().selection()->take( selRect );
325 view()->part()->repaintAllViews( selRect );
327 else if( m_state == moving )
332 view()->part()->addCommand(
334 &view()->part()->document(),
335 abs(
int( m_distx ) ) >= abs(
int( m_disty ) ) ? tqRound( m_distx ) : 0,
336 abs( int( m_distx ) ) <= abs( int( m_disty ) ) ? tqRound( m_disty ) : 0, altPressed() ),
339 view()->part()->addCommand(
340 new VTranslateCmd( &view()->part()->document(), tqRound( m_distx ), tqRound( m_disty ), altPressed() ),
343 else if( m_state == scaling )
346 view()->part()->addCommand(
347 new VScaleCmd( &view()->part()->document(), m_sp, m_s1, m_s2, altPressed() ),
352 view()->selectionChanged();
358VSelectTool::arrowKeyReleased( TQt::Key key )
364 case TQt::Key_Up: dy = 10;
break;
365 case TQt::Key_Down: dy = -10;
break;
366 case TQt::Key_Right: dx = 10;
break;
367 case TQt::Key_Left: dx = -10;
break;
371 view()->part()->addCommand(
373 &view()->part()->document(),
376 view()->selectionChanged();
381VSelectTool::keyReleased( TQt::Key key )
391 uint handleSize = selection->handleSize();
393 selection->setHandleSize( ++handleSize );
394 else if( handleSize > 1 )
395 selection->setHandleSize( --handleSize );
398 default:
return false;
408VSelectTool::updateStatusBar()
const
413 if( ! view()->part() )
416 int objcount = view()->part()->document().selection()->objects().count();
419 KoRect rect = view()->part()->document().selection()->boundingBox();
421 double x = KoUnit::toUserValue( rect.x(), view()->part()->unit() );
422 double y = KoUnit::toUserValue( rect.y(), view()->part()->unit() );
423 double r = KoUnit::toUserValue( rect.right(), view()->part()->unit() );
424 double b = KoUnit::toUserValue( rect.bottom(), view()->part()->unit() );
427 TQString selectMessage = i18n(
"[(left,bottom), (right,top)] (actual unit)",
"Selection [(%1, %2), (%3, %4)] (%5)").arg( x, 0,
'f', 1 ).arg( y, 0,
'f', 1 ).arg( r, 0,
'f', 1 ).arg( b, 0,
'f', 1 ).arg( view()->part()->unitName() );
430 selectionDesc.
visit( *view()->part()->document().selection() );
431 selectMessage += TQString(
"(%1)" ).arg( selectionDesc.description() );
433 view()->statusMessage()->setText( selectMessage );
436 view()->statusMessage()->setText( i18n(
"No selection" ) );
440VSelectTool::mouseDragCtrlPressed()
446VSelectTool::mouseDragCtrlReleased()
452VSelectTool::mouseDragShiftPressed()
462VSelectTool::mouseDragShiftReleased()
479 view()->repaintAll( view()->part()->document().selection()->boundingBox() );
486 if( m_state == normal )
493 KoPoint _first = view()->canvasWidget()->snapToGrid( first() );
494 KoPoint _last = view()->canvasWidget()->snapToGrid( last() );
495 KoRect rect = view()->part()->document().selection()->boundingBox();
497 if( m_state == moving )
499 KoPoint p( rect.x() + last().x() - first().x(), rect.bottom() + last().y() - first().y() );
500 p = view()->canvasWidget()->snapToGrid( p );
501 m_distx = p.x() - rect.x();
502 m_disty = p.y() - rect.bottom();
504 cmd =
new VTranslateCmd( 0L, abs(
int( m_distx ) ) >= abs(
int( m_disty ) ) ? m_distx : 0,
505 abs( int( m_distx ) ) <= abs( int( m_disty ) ) ? m_disty : 0 );
507 cmd =
new VTranslateCmd( 0L, m_distx, m_disty );
511 if( m_activeNode == node_lb )
513 m_sp = KoPoint( rect.right(), rect.bottom() );
514 m_s1 = ( rect.right() - _last.x() ) /
double( rect.width() );
515 m_s2 = ( rect.bottom() - _last.y() ) /
double( rect.height() );
517 else if( m_activeNode == node_mb )
519 m_sp = KoPoint( ( ( rect.right() + rect.left() ) / 2 ), rect.bottom() );
521 m_s2 = ( rect.bottom() - _last.y() ) /
double( rect.height() );
523 else if( m_activeNode == node_rb )
525 m_sp = KoPoint( rect.x(), rect.bottom() );
526 m_s1 = ( _last.x() - rect.x() ) /
double( rect.width() );
527 m_s2 = ( rect.bottom() - _last.y() ) /
double( rect.height() );
529 else if( m_activeNode == node_rm)
531 m_sp = KoPoint( rect.x(), ( rect.bottom() + rect.top() ) / 2 );
532 m_s1 = ( _last.x() - rect.x() ) /
double( rect.width() );
535 else if( m_activeNode == node_rt )
537 m_sp = KoPoint( rect.x(), rect.y() );
538 m_s1 = ( _last.x() - rect.x() ) /
double( rect.width() );
539 m_s2 = ( _last.y() - rect.y() ) /
double( rect.height() );
541 else if( m_activeNode == node_mt )
543 m_sp = KoPoint( ( ( rect.right() + rect.left() ) / 2 ), rect.y() );
545 m_s2 = ( _last.y() - rect.y() ) /
double( rect.height() );
547 else if( m_activeNode == node_lt )
549 m_sp = KoPoint( rect.right(), rect.y() );
550 m_s1 = ( rect.right() - _last.x() ) /
double( rect.width() );
551 m_s2 = ( _last.y() - rect.y() ) /
double( rect.height() );
553 else if( m_activeNode == node_lm )
555 m_sp = KoPoint( rect.right(), ( rect.bottom() + rect.top() ) / 2 );
556 m_s1 = ( rect.right() - _last.x() ) /
double( rect.width() );
561 m_s1 = m_s2 = kMax( m_s1, m_s2 );
562 cmd =
new VScaleCmd( 0L, m_sp, m_s1, m_s2 );
570 for( ; itr.current() ; ++itr )
574 copy = itr.current()->
clone();
579 m_objects.append( copy );
588VSelectTool::showDialog()
const
590 return m_optionsWidget->exec() == TQDialog::Accepted;
594VSelectTool::refreshUnit()
600VSelectTool::setup( TDEActionCollection *collection )
602 m_action =
static_cast<TDERadioAction *
>(collection -> action( name() ) );
606 m_action =
new TDERadioAction( i18n(
"Select Tool" ),
"14_select", TQt::SHIFT+TQt::Key_H,
this, TQ_SLOT( activate() ), collection, name() );
607 m_action->setToolTip( i18n(
"Select" ) );
608 m_action->setExclusiveGroup(
"select" );
613#include "vselecttool.moc"
Keeps track of visual per document properties.
VSelection * selection() const
Returns a pointer to the selection.
VSelectionMode
The different selection modes.
VSelectionMode selectionMode()
Returns the selection mode.
The base class for all karbon objects.
virtual VObject * clone() const =0
Create an exact copy of this object.
virtual void setState(const VState state)
Sets the state to a specified new state.
@ selected
visible, active and can be manipulated by tools
@ deleted
deleted, nearly dead
@ edit
visible, active and is currently manipulated by a tool
VDocument * document() const
Return document the object belongs to.
This visitor visits a selection and selects objects that are contained in a paramater selection recta...
This visitors visits structures and tries to capture relevant object type info as text.
VSelection manages a set of selected vobjects.
const VObjectList & objects() const
Read only access to the selected objects.
void append()
Adds all objects to the selection.
virtual const KoRect & boundingBox() const
Calculates the tightest bounding box around the object.
virtual bool visit(VObject &object)
General visit method.