我需要一个文本编辑器控件来在我的应用程序中进行列编辑。
像notepad++一样alt+鼠标拖动
来选择文本 block ,或者拉下一个长垂直光标并按某个键在光标上方的每一行插入一个字符。
我尝试了 ScintillaNET,但它 not suppor the column-modet对于插入,只能删除选定的文本 block
我需要以下效果(notepad++),但是ScintillaNET得到了:
最佳答案
我找到了解决的方法。仍在使用 ScintillaNET。
但是编码不够美观:)
class SelWrap
{
public int Begin { get; set; }
public int Length { get; set; }
}
//...
editor.KeyDown += (s, e) =>
{
// filter alt we will hold down alt to make vertical selection
if (e.Alt) return;
var tb = editor;
if (tb.Selections.Count < 2) return; // no in column mode
e.SuppressKeyPress = true; //block input, handle by below code
//refered from post #5825820
var input = Utility.GetCharFromKey(e.KeyCode).ToString();
if (input == "\0")
{
//SystemSounds.Beep.Play();
return;
}
var array = tb.Selections
.OrderBy(p => p.Start)
.Select(p => new SelWrap{Begin=p.Start, Length=p.End - p.Start })
.ToArray();
//do process every caret(or selection)
for (var i = 0; i < array.Length; i++)
{
var item = array[i];
if (item.Length > 0)
{
//if has selected text, just clean
tb.DeleteRange(item.Begin, item.Length);
for (var j = i + 1; j < array.Length; j++)
{
array[j].Begin -= item.Length;
}
}
if (input == "\b") //backspace
{
if (item.Length != 0) continue;
//delete a char before caret
tb.DeleteRange(item.Begin - 1, 1);
for (var j = i; j < array.Length; j++)
{
array[j].Begin--;
}
}
else //just insert that
{
tb.InsertText(item.Begin, input);
for (var j = i; j < array.Length; j++)
{
array[j].Begin++;
}
}
}
//restore caret status to keep column mode
tb.ClearSelections();
tb.SetSelection(array[0].Begin, array[0].Begin);
for (var i = 1; i < array.Length; i++)
{
var item = array[i];
tb.AddSelection(item.Begin, item.Begin);
}
};
//...
关于winforms - 如何实现ScintillaNET列编辑模式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35954882/