How to make a textbox non-selectable using C#

前端 未结 11 1914
轮回少年
轮回少年 2021-02-19 11:09

I\'m using C#/.NET for a Windows Forms application. I have a text box. How can I make the text box unselectable?

I don\'t want to disable the complete textbox.

相关标签:
11条回答
  • 2021-02-19 11:45

    I had the same problem. I had a dialog up and needed multiline text to be displayed. I could not use a label as it has to be a textbox because of the multiline and text wrap.

    I first mad it readonly, but if the dialog is flashed by other windows, the text becomes selected which looks horrible. So I found the problem.

    In the form builder program (whatever it is called), there is a property for the TextBox called TabStop. I set that to false and the read-only textbox text never gets selected. Problem solved.

    0 讨论(0)
  • 2021-02-19 11:46

    The messages that cause text can be intercepted and blocked. I would have thought that EM_SETSEL would be all that is required. However, even when the mouse clicks and drags, there is no EM_SETEL message, but the text still selects. Possibly one of the messages has a pointer to a struct that contains the info.

    Note: I'm not sure if this prevents all ways to select text.

    public class TextBox2 : TextBox {
    
        private const int EM_SETSEL = 0x00B1;
        private const int WM_LBUTTONDBLCLK = 0x203;
        private const int WM_MOUSEMOVE = 0x200;
        private const int WM_KEYDOWN = 0x100;
        private const int VK_CONTROL = 0x11;
        private const int VK_SHIFT = 0x10;
    
        public TextBox2() {
            this.ShortcutsEnabled = false; // disabled right click menu
            this.Cursor = Cursors.Default;
    
        }
    
        protected override void OnGotFocus(EventArgs e) {
            base.OnGotFocus(e);
            HideCaret(this.Handle); // doesn't work from OnHandleCreated
        }
    
        [DllImport("user32.dll")]
        public static extern bool HideCaret(IntPtr hWnd);
    
        public override bool PreProcessMessage(ref Message msg) {
            // prevents the user from using the SHIFT or CTRL + arrow keys to select text
            if (msg.Msg == WM_KEYDOWN)
                return true;
    
            return base.PreProcessMessage(ref msg);
        }
    
        protected override void WndProc(ref Message m) {
            if (m.Msg == EM_SETSEL || m.Msg == WM_MOUSEMOVE || m.Msg == WM_LBUTTONDBLCLK)
                return;
    
            base.WndProc(ref m);
        }
    }
    
    0 讨论(0)
  • 2021-02-19 11:47

    IsHitTestVisible="False" prevents the textbox from displaying the bounding box when hovering or clicking with the mouse. That was enough in my case to take benefit of the textwrapping feature of the textbox while making it insensitive to user actions

    0 讨论(0)
  • 2021-02-19 11:52

    Try using CanFocus property.

    0 讨论(0)
  • 2021-02-19 11:53

    This has worked just fine to me:

    textBox.ReadOnly = true
    
    0 讨论(0)
  • 2021-02-19 11:54

    Old question, and I'm not completely happy with my hack of an answer to this problem, but if the original intention was to use the text box to display data without allowing it to be selected in any way, this is a method that has (so far) worked for me.

    First, the non-default properties of my text box:

    Multiline        = true
    ReadOnly         = true
    ScrollBars       = Both
    ShortcutsEnabled = false
    TabStop          = false
    WordWrap         = false
    

    Then mouse event handling. Both MouseMove and DoubleClick were mapped to trigger textBox1_MouseGeneral(), and I had additional actions happening in the Click event, thus the apparent duplication of the two event handlers.

        private void MouseEvent()
        {
            textBox1.SelectionLength = 0;
    
            focusControl.Focus(); // Move focus to another control
        }
    
        private void textBox1_Click(object sender, EventArgs e)
        {
            MouseEvent();
        }
    
        private void textBox1_MouseGeneral(object sender, EventArgs e)
        {
            MouseEvent();
        }
    

    You get a flash of a caret cursor, then textBox1 loses focus.

    0 讨论(0)
提交回复
热议问题