Solved

AutoScroll when drag node in treeview

Posted on 1998-08-20
13
377 Views
Last Modified: 2010-04-04
In a treeview component, when i try to move a node to
another node's position by draging, I found the treeview's
view area can not scrolling automaticly.

How to make any solution for the problem?

Thanks.

Ye Chen
0
Comment
Question by:yc
  • 9
  • 3
13 Comments
 
LVL 10

Expert Comment

by:viktornet
ID: 1337319
Here is something that will work...

var
  Down : Boolean;
  PT : TPoint;
procedure TForm1.TreeView1MouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Down := True;
end;

procedure TForm1.TreeView1MouseUp(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
  Down := False;
end;

procedure TForm1.TreeView1MouseMove(Sender: TObject; Shift: TShiftState; X,
  Y: Integer);
var
  pt : TPoint;
begin
  if Down then
  begin
    GetCursorPos(PT);
    if pt.y >= TreeView1.Height - 3 then
      if not(treeview1.Selected.Index >= treeview1.items.count - 4)then
        TreeView1.Selected :=TreeView1.Selected.GetNext;
  end;
end;

Talk to you later..

Regards,
Viktor Ivanov
0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337320
Here is a better version.... =)
---------------------------------------
var
     Down : Boolean;
     PT : TPoint;

procedure TForm1.TreeView1MouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
    Down := True;
end;

procedure TForm1.TreeView1MouseUp(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
   Down := False;
end;

procedure TForm1.TreeView1MouseMove(Sender: TObject; Shift: TShiftState; X,
  Y: Integer);
var
     pt : TPoint;
   begin
     if Down then
     begin
       GetCursorPos(PT);
       pt := ScreenToClient(pt);
       if pt.y >= TreeView1.Height + 40 then
       begin
         if not(treeview1.Selected.Index >= treeview1.items.count - 4)then
           SendMessage(treeview1.handle, WM_VSCROLL, 1, 0);
       end
       else if pt.y <= TreeView1.Top + 5then
       begin
         if not(treeview1.Selected.Index <= 4)then
           SendMessage(treeview1.handle, WM_VSCROLL, -1, 0);
       end;
     end;
end;
----------------------

I hope this helps!

Regards,
Viktor Ivanov
0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337321
Here is a better version.... =)
---------------------------------------
var
     Down : Boolean;
     PT : TPoint;

procedure TForm1.TreeView1MouseDown(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
    Down := True;
end;

procedure TForm1.TreeView1MouseUp(Sender: TObject; Button: TMouseButton;
  Shift: TShiftState; X, Y: Integer);
begin
   Down := False;
end;

procedure TForm1.TreeView1MouseMove(Sender: TObject; Shift: TShiftState; X,
  Y: Integer);
var
     pt : TPoint;
   begin
     if Down then
     begin
       GetCursorPos(PT);
       pt := ScreenToClient(pt);
       if pt.y >= TreeView1.Height + 40 then
       begin
         if not(treeview1.Selected.Index >= treeview1.items.count - 4)then
           SendMessage(treeview1.handle, WM_VSCROLL, 1, 0);
       end
       else if pt.y <= TreeView1.Top + 5then
       begin
         if not(treeview1.Selected.Index <= 4)then
           SendMessage(treeview1.handle, WM_VSCROLL, -1, 0);
       end;
     end;
end;
----------------------

I hope this helps!

Regards,
Viktor Ivanov
0
 

Author Comment

by:yc
ID: 1337322
Hi, viktornet

Thanks for your answer.

But when in drag-drop mode, i want not to change the current selected treenode, i think through autoscrolling the tree to find
the droptarget i need to drop to. So, use mouseup, mousedown, mousemove is not a very well idea i think.

How do you think about this?

Regards
Ye Chen

0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337323
Let me try it and I'll tell you. OK?

//Vik
0
 
LVL 10

Accepted Solution

by:
viktornet earned 100 total points
ID: 1337324
Ok, here is the new one that works...I just tried it...
-----------------------------
var          pt : TPoint;
procedure TForm1.TreeView1DragOver(Sender, Source: TObject; X, Y: Integer;
  State: TDragState; var Accept: Boolean);
begin
  Accept := Sender is TTreeView;
  GetCursorPos(PT);
            pt := ScreenToClient(pt);
            if pt.y >= TreeView1.Height + 40 then//Just fix this
            begin
              if not(treeview1.Selected.Index >= treeview1.items.count - 4)then
                SendMessage(treeview1.handle, WM_VSCROLL, 1, 0);
            end
            else if pt.y <= TreeView1.Top + 20 then//and also fix this
            begin
              if not(treeview1.Selected.Index <= 4)then
                SendMessage(treeview1.handle, WM_VSCROLL, -1, 0);
            end;
end;

procedure TForm1.TreeView1DragDrop(Sender, Source: TObject; X, Y: Integer);
var
  s : tpoint;
begin
  s := point(x,y);
  treeview1.Items.Insert(Treeview1.GetNodeAt(s.x,s.y + 10),'COOL');;
  treeview1.items.delete(treeview1.selected);
end;
--------------------------
Hope this helps =)

Regards,
Viktor Ivanov
0
Enabling OSINT in Activity Based Intelligence

Activity based intelligence (ABI) requires access to all available sources of data. Recorded Future allows analysts to observe structured data on the open, deep, and dark web.

 
LVL 10

Expert Comment

by:viktornet
ID: 1337325
You may use this in dragdrop...

procedure TForm1.TreeView1DragDrop(Sender, Source: TObject; X, Y: Integer);
var
  Noder : TTreeNode;
begin
  Noder := TreeView1.Selected;
  treeview1.Items.Insert(treeview1.GetNodeAt(x,y),Noder.Text);
  treeview1.items.delete(Noder);
end;

/vvik
0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337326
You actually asked about scrolling not how to insert them so I think I answered your question......

//Viktor
0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337327
Well, what do you think??? Does it work now???

Regards,
Viktor Ivanov
0
 

Author Comment

by:yc
ID: 1337328
Hi, Viktor Ivanov

Now, My Code is the following, and it works very well.
Please take attentions to the different with your coding. :)

procedure TForm1.TreeView1DragOver(Sender, Source: TObject; X, Y: Integer;
  State: TDragState; var Accept: Boolean);
begin
  Accept := Sender is TTreeView;

            if Y >= TreeView1.Height - 40 then
                SendMessage(treeview1.handle, WM_VSCROLL, SB_LINEDOWN, 0)
            else if Y <= 40 then
                SendMessage(treeview1.handle, WM_VSCROLL, SB_LINEUP, 0);
end;


But, there are two questions:

1. In Micrisoft Win95's Explorer, when you draging a file or directionary on the bottom
 and stop moving, Explorer 's tree scrollup automaticly until to the last.
I found if when i stop moving on then tree bottom, the treeview also stop scrollup automaticly.
It seems Explorer use a timer behind. How can i do as Explorer?

2. When dragover a node,  How to expand or collaps it after a little time automaticly ?


Regards

Ye Chen
0
 
LVL 3

Expert Comment

by:rickpet
ID: 1337329
Yes...I'm sure MS uses a timer to kick off scrolls...once you leave the explorer...

Instead of SendMessage, have you tried Perform?  This is faster as it goes straight to the control and doesn't have to go through the message handling system...

Rick
0
 

Author Comment

by:yc
ID: 1337330
Hi viktornet,

Would you give me some code using perform?

Thanks.

Ye Chen
0
 
LVL 10

Expert Comment

by:viktornet
ID: 1337331
Here is some code.....

In OnMouseMove() of a Button for example....
begin
  if ssLeft in Shift then
  begin
    ReleaseCapture;
    Button1.Perform(WM_SYSCOMMAND, $F012, 0);
//Button1.Perform(WM_SYSCOMMAND, $F012, 0); is same as
//SendMessage(Button1.Handle, WM_SYSCOMMAND, $F012, 0);
  end;
end;

BTW, I'd like to know if you are going to accept my answer or reject it . o O???

ThanQ~
0

Featured Post

How your wiki can always stay up-to-date

Quip doubles as a “living” wiki and a project management tool that evolves with your organization. As you finish projects in Quip, the work remains, easily accessible to all team members, new and old.
- Increase transparency
- Onboard new hires faster
- Access from mobile/offline

Join & Write a Comment

Introduction The parallel port is a very commonly known port, it was widely used to connect a printer to the PC, if you look at the back of your computer, for those who don't have newer computers, there will be a port with 25 pins and a small print…
Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
When you create an app prototype with Adobe XD, you can insert system screens -- sharing or Control Center, for example -- with just a few clicks. This video shows you how. You can take the full course on Experts Exchange at http://bit.ly/XDcourse.
This video demonstrates how to create an example email signature rule for a department in a company using CodeTwo Exchange Rules. The signature will be inserted beneath users' latest emails in conversations and will be displayed in users' Sent Items…

746 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

14 Experts available now in Live!

Get 1:1 Help Now