1
votes

I did

private void richTextBox1_MouseDown(object sender, MouseEventArgs e)
 {
     if (e.Button == System.Windows.Forms.MouseButtons.Right)
     {
         MessageBox.Show("you got it!");
     }

 }

But what i want is:

  1. When doing a right click on a line in the richTextBox consider the line as item so the menu commands will take effect only for the specific line i did right click on. Like delete,paste,copy

  2. If i select paste it will paste the new text to the bottom(end) of the richTextBox. But if i click on copy or delete it will consider it to the specific line i did the right click on.

  3. To make paste for one line or for batch of lines and add them as lines in the bottom(end) of the richTextBox.

This is how i'm adding the text as lines today to the richTextBox. The lines are links. Each line in the richTextBox is a link. And what i want to paste to the richTextBox is only links not just text. So each link i paste to the richTextBox should be added like i'm doing it: The for loops is just for the constructor first time.

for (int i = 0; i < lines.Count; i++)
            {
                RichTextBoxExtensions.AppendText(richTextBox1, "Ready: ", Color.Red, 8.25f);
                richTextBox1.AppendText(lines[i] + (i < lines.Count - 1 ? Environment.NewLine : String.Empty));
            }

            richTextBox1.AppendText(Environment.NewLine);

            for (int i = 0; i < newList.Count; i++)
            {
                RichTextBoxExtensions.AppendText(richTextBox1, "Ready: ", Color.Red, 8.25f);
                richTextBox1.AppendText(newList[i] + (i < newList.Count - 1 ? Environment.NewLine : String.Empty));
            }

lines and newList are list

This was just an example how i'm adding the links to the richTextBox. So when i make paste of a link or link they should be added in this way like how i'm doing it.

This is how the richTextBox looks like now for example:

Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101330&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101330&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101345&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101345&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101400&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101400&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101415&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101415&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101430&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101430&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101445&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101445&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101500&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101500&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101515&ir=true

So if i'm doing now a paste of a link for example: http://microsoft.com Now the richTextBox content will look like:

Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101330&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101330&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101345&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101345&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101400&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101400&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101415&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101415&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101430&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101430&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101445&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101445&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101500&ir=true
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101500&ir=false
Ready: http://www.sat24.com/image2.ashx?region=is&time=201702101515&ir=true
Ready: http://www.microsoft.com

And if i paste multiple links then it will add the link to the bottom.

I think this is the fastest way to append text from clipboard:

string newText = Clipboard.GetText();
richTextBox1.SelectionStart = richTextBox1.TextLength;
richTextBox1.SelectionLength = 0;
richTextBox1.SelectedText = newText;

But i want it to be added to the end the bottom of the richTextBox and in the format i'm doing it with the Ready:

And in what event should i do it ? How do i add a context menu in code and using the paste menu ?

Update

I tried something like this now:

private void richTextBox1_MouseDown(object sender, MouseEventArgs e)
        {
            if (e.Button == System.Windows.Forms.MouseButtons.Right)
            {
                var startIndex = richTextBox1.Text.IndexOf("Ready:") + "Ready:".Length;
                var length = richTextBox1.Text.IndexOf("Ready:", startIndex) - startIndex;

                int index = richTextBox1.SelectionStart;
                int line = richTextBox1.GetLineFromCharIndex(index);

                var code = richTextBox1.Text.Substring(startIndex + index, length - line - 1);

                label1.Text = code;
      }

I tried to add the two lines:

int index = richTextBox1.SelectionStart;
int line = richTextBox1.GetLineFromCharIndex(index);

This two lines i'm trying to get the mouse cursour position when i click on a line. So it will parse the line text the mouse is on like item in a listView.

But the substring i not correct.

If i'm doing it this way:

private void richTextBox1_MouseDown(object sender, MouseEventArgs e)
        {
            if (e.Button == System.Windows.Forms.MouseButtons.Right)
            {
                var startIndex = richTextBox1.Text.IndexOf("Ready:") + "Ready:".Length;
                var length = richTextBox1.Text.IndexOf("Ready:", startIndex) - startIndex;

                var code = richTextBox1.Text.Substring(startIndex, length - 1);

                label1.Text = code;
            }
        }

It will give me in label1 always the first line link. And not the line where the mouse cursour position is clicked on. If i click on line 7 then i want to see in label1 the whole text of line 7. If i clicked on line 65 then in label1 to see the whole text of line 65.

Same idea as in listView if i click on item.

1
Try using GetCharFromPosition supplying the mouse location followed by GetLineFromCharIndex from that position.LarsTech

1 Answers

1
votes

Your question is pretty straight forward, but its followed by a lot of unrelated stuff. I just went ahead and tried to answer the opening question which asks how to add a context menu to a richtextbox.

    private void txtbx_text1_MouseUp(object sender, MouseEventArgs e)
    {
        if (e.Button != MouseButtons.Right)
        {
            return;
        }
        ContextMenu cm = new ContextMenu();//make a context menu instance
        MenuItem item = new MenuItem();//make a menuitem instance
        item.Text = "remove all";//give the item a header
        item.Click += DoNothing;//give the item a click event handler
        cm.MenuItems.Add(item);//add the item to the context menu
        item = new MenuItem();//recycle the menu item
        item.Text = "load from file";//give the item a header
        item.Click += DoNothing;//give the item a click event handler
        cm.MenuItems.Add(item);//add the item to the context menu
        item = new MenuItem();//recycle item into a new menuitem
        item.Text = "save list";//give the item a header
        item.Click += DoNothing;//give the item a click event handler
        cm.MenuItems.Add(item);//add the item to the context menu
        ((RichTextBox)sender).ContextMenu = cm;//add the context menu to the sender
        cm.Show(txtbx_text1, e.Location);//show the context menu
    }


    private void DoNothing(object sender, EventArgs e)
    {
        //doing nothing
        return;
    }

Been toying with your other requirements and the following could get you going. It needs some love, but the premise is there and works:

    private void txtbx_text1_MouseUp(object sender, MouseEventArgs e)
    {
        if (e.Button != MouseButtons.Right)
        {
            return;
        }
        ContextMenu cm = new ContextMenu();//make a context menu instance
        MenuItem item = new MenuItem();//make a menuitem instance
        item.Text = "remove line";//give the item a header
        item.Click += (sendingelement, eventargs) => RemoveLine(item, e);//give the item a click event handler
        cm.MenuItems.Add(item);//add the item to the context menu
        ((RichTextBox)sender).ContextMenu = cm;//add the context menu to the sender
        cm.Show(txtbx_text1, e.Location);//show the context menu
    }

    private void RemoveLine(object sender, MouseEventArgs e)
    {
        if (txtbx_text1.Text.Length == 0)
        {
            return;
        }
        int charNextToCursor = txtbx_text1.GetCharIndexFromPosition(e.Location);
        int lineNumFromChar = txtbx_text1.GetLineFromCharIndex(charNextToCursor);
        int firstCharOfLine = txtbx_text1.GetFirstCharIndexFromLine(lineNumFromChar);
        int lineLength = txtbx_text1.Lines[lineNumFromChar].Length;
        string firstchar = txtbx_text1.Text.Substring(firstCharOfLine, 1);
        //txtbx_text1.Text = txtbx_text1.Text.Remove(firstCharOfLine, lineLength);
        if (lineNumFromChar == 0)
        {
            if (txtbx_text1.Lines.Length > 1)
            {
                txtbx_text1.Text = txtbx_text1.Text.Remove(firstCharOfLine, lineLength + 1);
            }
            else
            {
                txtbx_text1.Text = txtbx_text1.Text.Remove(firstCharOfLine, lineLength);
            }

        }
        else
        {
            txtbx_text1.Text = txtbx_text1.Text.Remove(firstCharOfLine - 1, lineLength + 1);
        }

        ((MenuItem)sender).Parent.Dispose();

        return;
    }