Отключить расширение после двойного щелчка

Можно ли отключить расширение TreeNode после doubleclick?

Спасибо

Ответ 1

Нет простого способа достичь этого, насколько я знаю. Одна мысль заключалась бы в том, чтобы переменная bool была установлена ​​в true в событии DoubleClick и использовала свойство e.Cancel события BeforeExpand, чтобы предотвратить расширение node. Однако эти два события запускаются в обратном порядке, так что это не решение. У меня нет другого решения с моей головы; будет обновляться, если я придумаю один.

Обновление

Я немного поиграл с этим, и я нашел один способ, который работает достаточно хорошо. Как я уже упоминал, проблема заключается в том, что BeforeExpand происходит до DoubleClick, поэтому мы не можем установить какое-либо состояние в DoubleClick для использования в BeforeExpand.

Мы можем, однако, обнаружить (потенциальные) двойные щелчки по-другому: путем измерения времени между событиями MouseDown. Если в течение периода времени мы получим два события MouseDown, которые определяют двойной щелчок (как указано в SystemInformation.DoubleClickTime), он должен быть двойным нажмите, правильно? Событие MouseDown возникает до BeforeExpand. Итак, следующий код работает достаточно хорошо:

private bool _preventExpand = false;
private DateTime _lastMouseDown = DateTime.Now;

private void treeView1_BeforeExpand(object sender, TreeViewCancelEventArgs e)
{
    e.Cancel = _preventExpand;
    _preventExpand  = false;
}

private void treeView1_MouseDown(object sender, MouseEventArgs e)
{
    int delta = (int)DateTime.Now.Subtract(_lastMouseDown).TotalMilliseconds;            
    _preventExpand = (delta < SystemInformation.DoubleClickTime);
    _lastMouseDown = DateTime.Now;
}

Я говорю "довольно хорошо", потому что я чувствую, что он предотвращает расширение node в некоторых случаях, когда это не должно (например, если вы в течение двойного щелчка нажимаете сначала на текст node, а затем на плюс знак). Это можно было бы решить каким-то образом, или, возможно, вы с этим справитесь.

Ответ 2

private bool isDoubleClick = false;

private void treeView1_BeforeCollapse(object sender, TreeViewCancelEventArgs e)
{
    if (isDoubleClick && e.Action == TreeViewAction.Collapse)
        e.Cancel = true;
}

private void treeView1_BeforeExpand(object sender, TreeViewCancelEventArgs e)
{
    if (isDoubleClick && e.Action == TreeViewAction.Expand)
        e.Cancel = true;
}

private void treeView1_MouseDown(object sender, MouseEventArgs e)
{
    isDoubleClick = e.Clicks > 1;
}

Вы можете объявить приватное поле isDoubleClick и установить различные события TreeView, как указано выше. Это предотвратит развертывание/свертывание узла TreeView при двойном щелчке. Однако развернуть/свернуть будет работать с помощью значков + и -.

Ответ 3

Событие MouseDown произойдет до событий BeforeExpand/BeforeCollapse. Вы можете проверить свойство Clicks в MouseEventArg, чтобы различать двойной щелчок и один клик:

bool dblClick;

private void treeView_MouseDown(object sender, MouseEventArgs e)
{
  dblClick = e.Button == MouseButtons.Left && e.Clicks == 2;
}

private void treeView_BeforeExpand(object sender, TreeViewCancelEventArgs e)
{
  if (e.Action == TreeViewAction.Expand) e.Cancel = dblClick;
}

Ответ 4

Обрабатывает событие BeforeExpand и устанавливает свойство Отменить событие args object к true.

private void OnBeforeExpand(object sender, TreeViewCancelEventArgs e)
{
    e.Cancel = true;
}

TreeViewCancelEventArgs содержит также затронутый node и действие, вызвавшее событие, чтобы вы могли реализовать более сложную логику, чтобы включить или отключить поведение расширения, чем мой простой пример.

Ответ 5

Да. Вы можете сделать это.

Где-то сам по себе в коде напишите это:

bool CanExpand = true;

... и внутри обработчика с двойным щелчком напишите это:

CanExpand = false;

....... и внутри um.. событие BeforeExpand введите следующее:

if( CanExpand )
   Application.DoEvents();
else e.Cancel = true;

Надеюсь, это помогло.


Я просто испытал это, и он работает безупречно.:-) Ниже приведен весь код, который я использовал для его проверки. Итак, вы можете увидеть, как это работает:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace WindowsFormsApplication1
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        bool CanExpand = true;

        private void treeView1_DoubleClick(object sender, EventArgs e)
        {
            CanExpand = false;
        }

        private void treeView1_BeforeExpand(object sender, TreeViewCancelEventArgs e)
        {
            if (CanExpand)
                Application.DoEvents();
            else
                e.Cancel = true;
        }
    }
}

Ответ 6

Я знаю, что эта ветка довольно старая, но теперь такая же проблема и нашла альтернативное решение. Я не уверен, что treeView_blockInfo_NodeMouseDoubleClick был доступен в то время, когда этот поток был открыт, но мое решение состоит в том, чтобы прикрепить это событие и использовать этот фрагмент кода:

private void treeView_blockInfo_NodeMouseDoubleClick(object sender, TreeNodeMouseClickEventArgs e)
{
    if (!e.Node.IsExpanded)
    {
        e.Node.Expand();
    }
    else
    {
        e.Node.Collapse();
    }
}

Работает для меня (хотя я не тестировал это на глубину). Единственная проблема, о которой я могу думать, это то, что она может вызвать мерцание.

Ответ 7

Здесь простое решение:

int treeX;   // somewhere in class scope

// Add a MouseMove event handler
private void treeView1_MouseMove(object sender, MouseEventArgs e)
{
    treeX = e.X;
}

// Add a BeforeExpand event handler
private void treeView1_BeforeExpand(object sender, TreeViewCancelEventArgs e)
{
    if (treeX > e.Node.Bounds.Left) e.Cancel = true;
}

Ответ 8

Попробуйте изменить точку зрения. Вместо того, чтобы отключить расширение при двойном щелчке, вы можете разрешить расширение только тогда, когда пользователь нажимает кнопку [+].

Таким образом, вы можете использовать метод GetHitTestInfoAt и разрешить расширение, только если выбранным элементом является htOnButton. Следующий код работает для Delphi 6:

procedure Form1.TreeView1Expanding(Sender: TObject; Node: TTreeNode; var AllowExpansion: Boolean);
var
   p:Tpoint;
   ht:THitTests;
begin
p:=Mouse.CursorPos;
ht:=treeview1.GetHitTestInfoAt(treeview1.ScreenToClient(p).x,treeview1.screentoclient(p).y);
AllowExpansion:=(htOnButton in ht);
end;

Ответ 9

Простейший способ:

treeList.OptionsBehavior.AllowExpandOnDblClick = false;