Невозможно изменить selectedNode в TreeView во время AfterLabelEdit - PullRequest
2 голосов
/ 22 сентября 2011

У меня проблема с выбранным узлом в виде дерева.

Вот два сценария. (# 2 вызывает мою проблему)

1 - Если я выберу «уровень» узла, нажмите F2, измените метку и нажмите Enter. SelectedNode внутри AfterLabelEdit изменится. SelectedNode изменится с «Level1» на «Root».

2 - Если я выберу «уровень» узла, нажмите F2, измените метку, но щелкните где-нибудь в древовидной структуре, выбранный узел никогда не изменится.

Является ли событие событием, которое вызывает проблему?

Я создал небольшой тестовый проект, чтобы показать проблему.

public partial class Form1 : Form
{
    public Form1()
    {
        InitializeComponent();
        this.Load += new EventHandler(Form1_Load);
        this.treeView1.KeyDown += new KeyEventHandler(Form1_KeyDown);
        this.treeView1.AfterLabelEdit += new NodeLabelEditEventHandler(treeView1_AfterLabelEdit);
    }

void treeView1_AfterLabelEdit(object sender, NodeLabelEditEventArgs e)
{
    Console.WriteLine(this.treeView1.SelectedNode);
    this.treeView1.SelectedNode = this.treeView1.SelectedNode.Parent;
    Console.WriteLine(this.treeView1.SelectedNode);
    TreeNode test = this.treeView1.SelectedNode;
}

void Form1_KeyDown(object sender, KeyEventArgs e)
{
    if (this.treeView1.SelectedNode != null)
    {
        if (e.KeyData == Keys.F2)
        {
            this.treeView1.SelectedNode.BeginEdit();
        }
    }

    base.OnKeyDown(e);
}

void Form1_Load(object sender, EventArgs e)
{
    this.treeView1.Nodes.Add(new TreeNode("root"));
    this.treeView1.Nodes[0].Nodes.Add(new TreeNode("level1"));

    this.treeView1.Nodes[0].Nodes[0].Nodes.Add(new TreeNode("level2"));
    this.treeView1.SelectedNode = this.treeView1.Nodes[0];
    this.treeView1.SelectedNode.ExpandAll();
    this.treeView1.SelectedNode = this.treeView1.Nodes[0].Nodes[0];
}

}

Ответы [ 2 ]

3 голосов
/ 22 сентября 2011

Это проблема порядка событий, щелчок мыши срабатывает после AfterLabelEdit, поэтому он выигрывает. Типичный трюк BeginInvoke не работает, вам понадобится таймер для выбора узла:

    void treeView1_AfterLabelEdit(object sender, NodeLabelEditEventArgs e) {
        TreeNode nextnode = this.treeView1.SelectedNode.Parent;
        var timer = new Timer() { Enabled = true, Interval = 50 };
        timer.Tick += delegate {
            this.treeView1.SelectedNode = nextnode;
            timer.Dispose();
        };
    }

Это работает, довольно некрасиво. Это происходит только тогда, когда пользователь щелкает конкретный узел, возможно, вам не следует отменять выбор. Престижность за репро код между прочим.

1 голос
/ 22 сентября 2011

Что-то вроде хака, но это выберет корневой узел, когда пользователь щелкнет где-то еще в древовидной структуре, за исключением узла level2:

private bool SelectParent = false;
void treeView1_AfterLabelEdit(object sender, NodeLabelEditEventArgs e)
{
    this.treeView1.SelectedNode = e.Node.Parent;
    SelectParent = true;
}

    private void treeView1_MouseDown(object sender, MouseEventArgs e)
    {
        if (SelectParent)
        {
            this.treeView1.SelectedNode = this.treeView1.SelectedNode.Parent;
            SelectParent = false;
        }

    }

поместите это в свой конструктор form1:

    this.treeView1.MouseDown += new System.Windows.Forms.MouseEventHandler(this.treeView1_MouseDown);
...