/// <summary> /// struct to handle the caret (L, C) co-ordinates /// L = one-based line number of the line containing the caret /// C = one-based column number in the line containing the caret /// </summary> public struct CharPoint { private int l, c; public static readonly CharPoint Empty;
static CharPoint() { CharPoint.Empty = new CharPoint(); } public CharPoint(int l, int c) { this.l = l; this.c = c; } public override string ToString() { return(String.Format("{{L={0}, C={1}}}", this.l, this.c)); } } public class ExtTextBox: RichTextBox { [DllImport("user32")] private static extern IntPtr SendMessage(HandleRef hWnd, int msg, int wParam, int lParam); [DllImport("user32")] private static extern int GetCaretPos(ref Point lpPoint); private int EM_LINEINDEX = 0xbb; private int EM_LINEFROMCHAR = 0xc9; private int EM_GETSEL = 0xb0; private ListBox _fieldListBox; private bool insideDesc;
public ExtTextBox() { this.KeyDown+=new KeyEventHandler(ExtTextBox_KeyDown);
this.AcceptsTab=true;
} /// <summary> /// Gets the caret current (X, Y) position. /// </summary> /// <value> /// Point struct /// </value> public Point GetCaretXYPosition { get { Point pt = Point.Empty; // get a Point struct with the caret current (X, Y) position GetCaretPos(ref pt); // return the Point struct with the caret current (X, Y) position return pt; } }
/// <summary> /// Gets the caret current (L, C) position. /// </summary> /// <value> /// CharPoint struct /// </value> public CharPoint GetCaretLCPosition { get { CharPoint cpt = CharPoint.Empty; // save the handle reference for the ExtToolBox HandleRef hr = new HandleRef(this, base.Handle ); // Send the EM_LINEFROMCHAR message with the value of -1 in wParam. // The return value is the zero-based line number // of the line containing the caret. int l = (int)SendMessage(hr,EM_LINEFROMCHAR, -1, 0); // Send the EM_GETSEL message to the ToolBox control. // The low-order word of the return value is the character // position of the caret relative to the first character in the // ToolBox control, i.e. the absolute character index. int sel = (int)SendMessage(hr, EM_GETSEL,0, 0); // get the low-order word from sel int ai = sel & 0xffff; // Send the EM_LINEINDEX message with the value of -1 in wParam. // The return value is the number of characters // that precede the first character in the line containing the caret. int li = (int)SendMessage(hr,EM_LINEINDEX, -1, 0); // Subtract the li (line index) from the ai (absolute character index), // The result is the column number of the caret position // in the line containing the caret. int c = ai - li; cpt = new CharPoint(l+1,c+1); // Add 1 to the l and c since these are zero-based. // Return a CharPoint with the caret current (L,C) position return new CharPoint(l+1,c+1); } } public ListBox FieldListBox { get{ return _fieldListBox;} set { _fieldListBox=value; _fieldListBox.KeyPress+=new KeyPressEventHandler(_fieldListBox_KeyPress);
} } /// <summary> /// Show autofieldlist /// </summary> public void ShowFieldListBox() { Point p=this.GetCaretXYPosition; _fieldListBox.Top=p.Y+this.Top+3; _fieldListBox.Left=p.X+this.Left+10; _fieldListBox.Visible=true; _fieldListBox.Focus();
} public void HideFieldListBox() { _fieldListBox.Visible=false;
//在formA里面
using(FormB frm = new FormB())
{
//do something
}
//上面的代码是弹出B。然后这样似乎就可以了啊。
获取或设置一个值,该值指示用户能否使用 TAB 键将焦点放到该控件上。ControlStyles 枚举
ControlStyles.Selectable
如果为 true,则控件可以接收焦点。
如果你还需要动态定位的话就用自己扩展一个带获取当前光标位置的RichTextBox 作输入控件
我实现过一个类似VS的智能代码提示框,不过用的是ListBox
帮你顶
---------------------------------------------这个wangxt(海贝)怎么每个帖子上的回复都是"帮你顶"???
===
可能不能满足搂主的需求。不仅是得到焦点的问题,背景窗口标题也会处于非激活状态。
我没有解决过,不过有一类控件很类似,就是下拉列表。下拉列表是一个其实新窗口,但
选中它不会使背景窗体失去焦点。这个实现方式和搂主的问题很类似。可以去看看。
/// struct to handle the caret (L, C) co-ordinates
/// L = one-based line number of the line containing the caret
/// C = one-based column number in the line containing the caret
/// </summary>
public struct CharPoint
{
private int l, c; public static readonly CharPoint Empty;
static CharPoint()
{
CharPoint.Empty = new CharPoint();
} public CharPoint(int l, int c)
{
this.l = l;
this.c = c;
} public override string ToString()
{
return(String.Format("{{L={0}, C={1}}}", this.l, this.c));
} } public class ExtTextBox: RichTextBox
{
[DllImport("user32")] private static extern IntPtr SendMessage(HandleRef hWnd, int msg, int wParam, int lParam);
[DllImport("user32")] private static extern int GetCaretPos(ref Point lpPoint);
private int EM_LINEINDEX = 0xbb;
private int EM_LINEFROMCHAR = 0xc9;
private int EM_GETSEL = 0xb0; private ListBox _fieldListBox;
private bool insideDesc;
public ExtTextBox()
{
this.KeyDown+=new KeyEventHandler(ExtTextBox_KeyDown);
this.AcceptsTab=true;
}
/// <summary>
/// Gets the caret current (X, Y) position.
/// </summary>
/// <value>
/// Point struct
/// </value>
public Point GetCaretXYPosition
{
get
{
Point pt = Point.Empty;
// get a Point struct with the caret current (X, Y) position
GetCaretPos(ref pt);
// return the Point struct with the caret current (X, Y) position
return pt;
}
}
/// <summary>
/// Gets the caret current (L, C) position.
/// </summary>
/// <value>
/// CharPoint struct
/// </value>
public CharPoint GetCaretLCPosition
{
get
{
CharPoint cpt = CharPoint.Empty;
// save the handle reference for the ExtToolBox
HandleRef hr = new HandleRef(this, base.Handle );
// Send the EM_LINEFROMCHAR message with the value of -1 in wParam.
// The return value is the zero-based line number
// of the line containing the caret.
int l = (int)SendMessage(hr,EM_LINEFROMCHAR, -1, 0);
// Send the EM_GETSEL message to the ToolBox control.
// The low-order word of the return value is the character
// position of the caret relative to the first character in the
// ToolBox control, i.e. the absolute character index.
int sel = (int)SendMessage(hr, EM_GETSEL,0, 0);
// get the low-order word from sel
int ai = sel & 0xffff;
// Send the EM_LINEINDEX message with the value of -1 in wParam.
// The return value is the number of characters
// that precede the first character in the line containing the caret.
int li = (int)SendMessage(hr,EM_LINEINDEX, -1, 0);
// Subtract the li (line index) from the ai (absolute character index),
// The result is the column number of the caret position
// in the line containing the caret.
int c = ai - li;
cpt = new CharPoint(l+1,c+1);
// Add 1 to the l and c since these are zero-based.
// Return a CharPoint with the caret current (L,C) position
return new CharPoint(l+1,c+1);
}
} public ListBox FieldListBox
{
get{ return _fieldListBox;}
set
{
_fieldListBox=value;
_fieldListBox.KeyPress+=new KeyPressEventHandler(_fieldListBox_KeyPress);
}
} /// <summary>
/// Show autofieldlist
/// </summary>
public void ShowFieldListBox()
{
Point p=this.GetCaretXYPosition;
_fieldListBox.Top=p.Y+this.Top+3;
_fieldListBox.Left=p.X+this.Left+10;
_fieldListBox.Visible=true;
_fieldListBox.Focus();
} public void HideFieldListBox()
{
_fieldListBox.Visible=false;
} private void ExtTextBox_KeyDown(object sender, KeyEventArgs e)
{
if(e.KeyCode==Keys.OemQuotes)
{
this.insideDesc=!this.insideDesc; // prevent from showing the listbox
} if(e.KeyCode==Keys.OemPeriod)// && !insideDesc)
this.ShowFieldListBox();
else
HideFieldListBox();
} private void _fieldListBox_KeyPress(object sender, KeyPressEventArgs e)
{
if(_fieldListBox.SelectedIndex!=-1)
{
this.AppendText(_fieldListBox.SelectedItem.ToString()+";");
HideFieldListBox();
this.Focus();
}
}
}具体用法是:
先构造一个ListBox 的实例,填好list item 调用FieldListBox将实例赋值给这个ExtTextBox