欢迎光临
我们一直在努力

研究心得——->Seskin控件包中SeskinEdit汉字问题的解决办法-ASP教程,ASP应用

建站超值云服务器,限时71元/月

公司采用seskin控件包来开发。却发现seskinedit在使用汉字是有问题。主要是由汉字时光标定位不准。鼠标选字也选不准。

于是看了其代码。发现它在计算文本长度时采用的函数textlength有问题。

其实tcanvas提供了一个textlength方法,在去文本长度时汉字没有问题。

所以把这里替换下来就行了。

替换后的se_controls单元中的tsecustomedit的代码如下

tsecustomedit = class(tsecustomcontrol)

private

ftext: widestring;

flmouseselecting: boolean;

fcaretposition: integer;

fselstart: integer;

fsellength: integer;

ffirstvisiblechar: integer;

fpopupmenu: tsecustompopupmenu;

fautoselect: boolean;

fcharcase: teditcharcase;

fhideselection: boolean;

fmaxlength: integer;

freadonly: boolean;

fonchange: tnotifyevent;

fpasswordchar: widechar;

fpasswordkind: tpasswordkind;

ftextalignment: talignment;

factionstack: teditactionstack;

fpopupmenudropshadow: boolean;

fpopupmenushowanimationtime: integer;

fpopupmenublendvalue: integer;

fpopupmenushadowwidth: integer;

fpopupmenushowanimation: tseanimationrec;

fpopupmenublend: boolean;

fcontextmenuoptions: tsepopupmenuoptions;

procedure updatefirstvisiblechar;

procedure updatecareteposition;

procedure updatecarete;

procedure wmgetdlgcode(var msg: twmgetdlgcode); message wm_getdlgcode;

procedure wmcopy(var message: tmessage); message wm_copy;

procedure wmpaste(var message: tmessage); message wm_paste;

procedure wmcut(var message: tmessage); message wm_cut;

procedure wmundo(var message: tmessage); message wm_undo;

procedure wmcontexmenu(var message: tmessage); message wm_contextmenu;

procedure wmlbuttondblclk(var message: twmlbuttondblclk); message

wm_lbuttondblclk;

{ unicode }

procedure wmimestartcomposition(var message: tmessage); message

wm_ime_startcomposition;

procedure wmimecomposition(var msg: tmessage); message wm_ime_composition;

{ vcl messages }

procedure cmenabledchanged(var msg: tmessage); message cm_enabledchanged;

procedure cmfontchanged(var message: tmessage); message cm_fontchanged;

procedure cmtextchanged(var msg: tmessage); message cm_textchanged;

function getseltext: widestring;

function getvisibleseltext: widestring;

function getnextwordbeging(startposition: integer): integer;

function getprivwordbeging(startposition: integer): integer;

function getselstart: integer;

function getsellength: integer;

function gettext: widestring;

procedure settext(const value: widestring);

procedure setfont(value: tfont);

procedure setcaretposition(const value: integer);

procedure setsellength(const value: integer);

procedure setselstart(const value: integer);

procedure setautoselect(const value: boolean);

procedure setcharcase(const value: teditcharcase);

procedure sethideselection(const value: boolean);

procedure setmaxlength(const value: integer);

procedure setpasswordchar(const value: widechar);

procedure setcursor(const value: tcursor);

procedure settextalignment(const value: talignment);

procedure setpasswordkind(const value: tpasswordkind);

procedure setpopupmenublendvalue(const value: integer);

procedure setpopupmenudropshadow(const value: boolean);

procedure setpopupmenushadowwidth(const value: integer);

procedure setpopupmenushowanimation(const value: tseanimationrec);

procedure setpopupmenushowanimationtime(const value: integer);

procedure setpopupmenublend(const value: boolean);

procedure setcontextmenuoptions(const value: tsepopupmenuoptions);

protected

function geteditrect: trect; virtual;

function getpasswordcharwidth: integer; virtual;

function getcharx(a: integer): integer;

function getcoordinateposition(x: integer): integer;

function getselrect: trect; virtual;

function getalignmentflags: integer;

procedure paintbuffer; override;

procedure painttext; virtual;

procedure paintbackground(rect: trect; canvas: tcanvas); virtual;

procedure paintselectedtext; virtual;

procedure drawpasswordchar(symbolrect: trect; selected: boolean); virtual;

function validtext(newtext: widestring): boolean; virtual;

function canautosize(var newwidth, newheight: integer): boolean; override;

procedure borderchanged; override;

procedure hasfocus; override;

procedure killfocus; override;

procedure mousedown(button: tmousebutton; shift: tshiftstate; x, y:

integer);

override;

procedure mouseup(button: tmousebutton; shift: tshiftstate; x, y: integer);

override;

procedure mousemove(shift: tshiftstate; x, y: integer); override;

procedure keydown(var key: word; shift: tshiftstate); override;

procedure keypress(var key: char); override;

procedure selectword;

procedure change; dynamic;

function createpopupmenu(aowner: tcomponent): tsecustompopupmenu; virtual;

function createpopupmenuitem(aowner: tcomponent): tsecustomitem; virtual;

procedure buildpopupmenu;

procedure updatepopupmenuitems; virtual;

procedure doundo(sender: tobject);

procedure docut(sender: tobject);

procedure docopy(sender: tobject);

procedure dopaste(sender: tobject);

procedure dodelete(sender: tobject);

procedure doselectall(sender: tobject);

property caretposition: integer read fcaretposition write setcaretposition;

property popupmenu: tsecustompopupmenu read fpopupmenu;

public

constructor create(aowner: tcomponent); override;

destructor destroy; override;

procedure loaded; override;

procedure showcaret; virtual;

procedure hidecaret; virtual;

procedure copytoclipboard;

procedure pastefromclipboard;

procedure cuttoclipboard;

procedure clearselection;

procedure selectall;

procedure clear;

procedure undo;

procedure insertchar(ch: widechar);

procedure inserttext(atext: widestring);

procedure insertafter(position: integer; s: widestring; selected: boolean);

procedure deletefrom(position, length: integer; movecaret: boolean);

property selstart: integer read getselstart write setselstart;

property sellength: integer read getsellength write setsellength;

property seltext: widestring read getseltext;

published

property anchors;

property autoselect: boolean read fautoselect write setautoselect default

true;

property autosize;

property blending;

property bevelsides;

property bevelinner;

property bevelouter;

property bevelkind;

property bevelwidth;

property borderwidth;

property charcase: teditcharcase read fcharcase write setcharcase default

ecnormal;

property constraints;

property color;

property cursor write setcursor;

property dragcursor;

property dragkind;

property dragmode;

property enabled;

property imemode;

property imename;

property font write setfont;

property hideselection: boolean read fhideselection write sethideselection

default true;

property maxlength: integer read fmaxlength write setmaxlength default 0;

property performance;

property parentfont;

property parentshowhint;

property passwordkind: tpasswordkind read fpasswordkind write

setpasswordkind;

property passwordwidechar: widechar read fpasswordchar write setpasswordchar

default widechar(#0);

property contextmenuoptions: tsepopupmenuoptions read fcontextmenuoptions

write setcontextmenuoptions;

property readonly: boolean read freadonly write freadonly default false;

property showhint;

property taborder;

property tabstop default true;

property text: widestring read gettext write settext;

property textalignment: talignment read ftextalignment write settextalignment

default taleftjustify;

property visible;

property onchange: tnotifyevent read fonchange write fonchange;

property onclick;

property ondblclick;

property ondragdrop;

property ondragover;

property onenddock;

property onenddrag;

property onenter;

property onexit;

property onkeydown;

property onkeypress;

property onkeyup;

property onmousedown;

property onmousemove;

property onmouseup;

property onstartdock;

property onstartdrag;

end;

{ tsecustomedit ===============================================================}

constructor tsecustomedit.create(aowner: tcomponent);

begin

inherited;

factionstack := teditactionstack.create(self);

fcontextmenuoptions := tsepopupmenuoptions.create;

performance := kspdoublebuffer;

bevelkind := kbksingle;

bevelwidth := 1;

borderwidth := 3;

tabstop := true;

width := 121;

height := 21;

color := clwindow;

ftextalignment := taleftjustify;

fautoselect := true;

autosize := true;

fcharcase := ecnormal;

fhideselection := true;

fmaxlength := 0;

freadonly := false;

fpasswordchar := widechar(#0);

flmouseselecting := false;

fcaretposition := 0;

fselstart := 0;

fsellength := 0;

ffirstvisiblechar := 1;

controlstyle := controlstyle + [cscapturemouse];

fpopupmenublend := false;

fpopupmenublendvalue := 150;

fpopupmenudropshadow := false;

fpopupmenushadowwidth := 4;

fpopupmenushowanimationtime := 300;

cursor := cursor;

end;

destructor tsecustomedit.destroy;

begin

if fpopupmenu <> nil then

fpopupmenu.free;

fcontextmenuoptions.free;

factionstack.free;

inherited;

end;

procedure tsecustomedit.loaded;

begin

inherited;

adjustsize;

end;

procedure tsecustomedit.hasfocus;

begin

inherited;

updatecarete;

caretposition := 0;

if autoselect then

selectall;

end;

procedure tsecustomedit.killfocus;

begin

inherited;

destroycaret;

invalidate;

end;

function tsecustomedit.getcharx(a: integer): integer;

var

wholetextwidth : integer;

editrectwidth : integer;

begin

result := geteditrect.left;

if passwordkind <> pknone then

wholetextwidth := length(text) * getpasswordcharwidth

else

{wholetextwidth := textwidth(canvas, copy(text, 1, length(text)),

dt_noprefix); }

wholetextwidth := canvas.textwidth(copy(text, 1, length(text)));

if a > 0 then

begin

canvas.font.assign(controlfont);

if passwordkind <> pknone then

begin

if a <= length(text) then

result := result + (a – ffirstvisiblechar + 1) * getpasswordcharwidth

else

result := result + (length(text) – ffirstvisiblechar + 1) *

getpasswordcharwidth;

end

else

begin

if a <= length(text) then

result := result + canvas.textwidth(copy(text, ffirstvisiblechar, a –

ffirstvisiblechar + 1))

//result := result + textwidth(canvas, copy(text, ffirstvisiblechar, a – ffirstvisiblechar + 1), dt_noprefix)

else

result := result + canvas.textwidth(copy(text, ffirstvisiblechar,

length(text) – ffirstvisiblechar + 1));

//result := result + textwidth(canvas, copy(text, ffirstvisiblechar, length(text) – ffirstvisiblechar + 1), dt_noprefix);

end;

end;

editrectwidth := geteditrect.right – geteditrect.left;

if wholetextwidth < editrectwidth then

case textalignment of

tarightjustify: result := result + (editrectwidth – wholetextwidth);

tacenter: result := result + ((editrectwidth – wholetextwidth) div 2);

end;

end;

function tsecustomedit.getcoordinateposition(x: integer): integer;

var

curx : double;

tmpx,

wholetextwidth,

editrectwidth : integer;

begin

result := ffirstvisiblechar – 1;

if length(text) = 0 then

exit;

if passwordkind <> pknone then

wholetextwidth := length(text) * getpasswordcharwidth

else

wholetextwidth := canvas.textwidth(copy(text, 1, length(text)));

//wholetextwidth :=textwidth(canvas, copy(text, 1, length(text)), dt_noprefix);

editrectwidth := geteditrect.right – geteditrect.left;

tmpx := x;

if wholetextwidth < editrectwidth then

case textalignment of

tarightjustify: tmpx := x – (editrectwidth – wholetextwidth);

tacenter: tmpx := x – ((editrectwidth – wholetextwidth) div 2);

end;

if passwordkind <> pknone then

begin

result := result + (tmpx – geteditrect.left) div getpasswordcharwidth;

if result < 0 then

result := 0

else

if result > length(text) then

result := length(text);

end

else

begin

canvas.font.assign(controlfont);

{curx := geteditrect.left + textwidth(canvas, text[ffirstvisiblechar],

dt_noprefix) / 2; }

curx := geteditrect.left + canvas.textwidth(text[ffirstvisiblechar]) / 2;

while (curx < tmpx) and (result + 1 <= length(text)) and (curx <

geteditrect.right) do

begin

//curx := curx + textwidth(canvas, text[result + 1], dt_noprefix) / 2;

curx := curx + canvas.textwidth(text[result + 1]) / 2;

if result + 1 + 1 <= length(text) then

//curx := curx + textwidth(canvas, text[result + 1 + 1], dt_noprefix) / 2;

curx := curx + canvas.textwidth(text[result + 1 + 1]) / 2;

result := result + 1;

end;

end;

end;

function tsecustomedit.geteditrect: trect;

begin

with result do

begin

result := getborderrect;

canvas.font.assign(controlfont);

result.bottom := result.top + canvas.textheight(pq);

end;

end;

function tsecustomedit.getalignmentflags: integer;

begin

case ftextalignment of

tacenter: result := dt_center;

tarightjustify: result := dt_right;

else

result := dt_left;

end;

end;

procedure tsecustomedit.keydown(var key: word; shift: tshiftstate);

var

tmps : widestring;

oldcaretposition : integer;

begin

inherited keydown(key, shift);

oldcaretposition := caretposition;

case key of

vk_end: caretposition := length(text);

vk_home: caretposition := 0;

vk_left:

if ssctrl in shift then

caretposition := getprivwordbeging(caretposition)

else

caretposition := caretposition – 1;

vk_right:

if ssctrl in shift then

caretposition := getnextwordbeging(caretposition)

else

caretposition := caretposition + 1;

vk_delete, 8: {delete or backspace key was pressed}

if not readonly then

begin

if sellength <> 0 then

begin

if shift = [ssshift] then

cuttoclipboard

else

clearselection;

end

else

begin

tmps := text;

if tmps <> then

if key = vk_delete then

begin

factionstack.fragmentdeleted(caretposition + 1, tmps[caretposition

+ 1]);

delete(tmps, caretposition + 1, 1);

end

else

begin {backspace key was pressed}

if caretposition > 0 then

factionstack.fragmentdeleted(caretposition,

tmps[caretposition]);

delete(tmps, caretposition, 1);

caretposition := caretposition – 1;

end;

text := tmps;

end;

end;

vk_insert:

if shift = [ssctrl] then

copytoclipboard

else

if shift = [ssshift] then

pastefromclipboard;

ord(c),

ord(c):

if shift = [ssctrl] then

copytoclipboard;

ord(v),

ord(v):

if shift = [ssctrl] then

pastefromclipboard;

ord(x),

ord(x):

if shift = [ssctrl] then

cuttoclipboard;

ord(z), ord(z):

if shift = [ssctrl] then

undo;

end;

if key in [vk_end, vk_home, vk_left, vk_right] then

begin

if ssshift in shift then

begin

if sellength = 0 then

fselstart := oldcaretposition;

fselstart := caretposition;

fsellength := fsellength – (caretposition – oldcaretposition);

end

else

fsellength := 0;

invalidate;

end;

updatecareteposition;

end;

procedure tsecustomedit.keypress(var key: char);

begin

inherited keypress(key);

if (ord(key) >= 32) and not readonly then

insertchar(chartowidechar(key));

end;

procedure tsecustomedit.mousedown(button: tmousebutton; shift: tshiftstate;

x, y: integer);

begin

inherited;

if button = mbleft then

flmouseselecting := true;

setfocus;

if button = mbleft then

begin

caretposition := getcoordinateposition(x);

sellength := 0;

end;

end;

procedure tsecustomedit.paintbuffer;

var

r : trect;

begin

r := geteditrect;

r.bottom := fheight – r.top;

paintbackground(r, canvas);

if (self is tsecustomcombobox) and (tsecustomcombobox(self).combostyle =

kcsdropdownlist) then

exit;

if focused or not hideselection then

fillrect(canvas, getselrect, clhighlight);

painttext;

if focused or not hideselection then

paintselectedtext;

end;

procedure tsecustomedit.paintbackground(rect: trect; canvas: tcanvas);

begin

fillrect(canvas, rect, color);

end;

procedure tsecustomedit.painttext;

var

tmprect : trect;

curchar : integer;

lpwcharwidth : integer;

begin

tmprect := geteditrect;

if passwordkind <> pknone then

begin

lpwcharwidth := getpasswordcharwidth;

for curchar := 0 to length(text) – ffirstvisiblechar + 1 – 1 do

drawpasswordchar(rect(curchar * lpwcharwidth + getcharx(0),

tmprect.top,

(curchar + 1) * lpwcharwidth + getcharx(0),

tmprect.bottom), false);

end

else

begin

canvas.font.assign(controlfont);

drawtext(canvas, copy(text, ffirstvisiblechar, length(text) –

ffirstvisiblechar + 1),

tmprect, getalignmentflags or dt_noprefix);

end;

end;

procedure tsecustomedit.updatefirstvisiblechar;

var

leditrect : trect;

begin

if ffirstvisiblechar >= (fcaretposition + 1) then

begin

ffirstvisiblechar := fcaretposition;

if ffirstvisiblechar < 1 then

ffirstvisiblechar := 1;

end

else

begin

leditrect := geteditrect;

if passwordkind <> pknone then

while ((fcaretposition – ffirstvisiblechar + 1) * getpasswordcharwidth >

leditrect.right – leditrect.left)

and (ffirstvisiblechar < length(text)) do

inc(ffirstvisiblechar)

else

begin

canvas.font.assign(controlfont);

{while (textwidth(canvas, copy(text, ffirstvisiblechar, fcaretposition –

ffirstvisiblechar + 1), dt_noprefix) > leditrect.right – leditrect.left)

and (ffirstvisiblechar < length(text)) do

inc(ffirstvisiblechar); }

while (canvas.textwidth(copy(text, ffirstvisiblechar, fcaretposition –

ffirstvisiblechar + 1)) > leditrect.right – leditrect.left)

and (ffirstvisiblechar < length(text)) do

inc(ffirstvisiblechar);

end;

end;

invalidate;

end;

procedure tsecustomedit.mousemove(shift: tshiftstate; x, y: integer);

var

oldcaretposition : integer;

tmpnewposition : integer;

begin

inherited;

if flmouseselecting then

begin

tmpnewposition := getcoordinateposition(x);

oldcaretposition := caretposition;

if (x > geteditrect.right) then

caretposition := tmpnewposition + 1

else

caretposition := tmpnewposition;

if sellength = 0 then

fselstart := oldcaretposition;

fselstart := caretposition;

fsellength := fsellength – (caretposition – oldcaretposition);

end;

end;

procedure tsecustomedit.mouseup(button: tmousebutton; shift: tshiftstate;

x, y: integer);

begin

inherited;

flmouseselecting := false;

end;

procedure tsecustomedit.copytoclipboard;

var

data : thandle;

dataptr : pointer;

size : cardinal;

s : widestring;

begin

if passwordkind = pknone then

if length(seltext) > 0 then

begin

s := seltext;

if not iswinnt then

begin

clipboard.astext := s;

end

else

begin

size := length(s);

data := globalalloc(gmem_moveable + gmem_ddeshare, 2 * size + 2);

try

dataptr := globallock(data);

try

move(pwidechar(s)^, dataptr^, 2 * size + 2);

clipboard.setashandle(cf_unicodetext, data);

finally

globalunlock(data);

end;

except

globalfree(data);

raise;

end;

end;

end;

end;

procedure tsecustomedit.pastefromclipboard;

var

data : thandle;

insertion : widestring;

begin

if readonly then

exit;

if clipboard.hasformat(cf_unicodetext) then

begin

data := clipboard.getashandle(cf_unicodetext);

try

if data <> 0 then

insertion := pwidechar(globallock(data));

finally

if data <> 0 then

globalunlock(data);

end;

end

else

insertion := clipboard.astext;

inserttext(insertion);

end;

procedure tsecustomedit.paintselectedtext;

var

tmprect : trect;

curchar : integer;

lpwcharwidth : integer;

begin

tmprect := getselrect;

if passwordkind <> pknone then

begin

lpwcharwidth := getpasswordcharwidth;

for curchar := 0 to length(getvisibleseltext) – 1 do

drawpasswordchar(rect(curchar * lpwcharwidth + tmprect.left,

tmprect.top,

(curchar + 1) * lpwcharwidth + tmprect.left,

tmprect.bottom),

true);

end

else

begin

canvas.font.assign(controlfont);

canvas.font.color := clhighlighttext;

drawtext(canvas, getvisibleseltext, tmprect, getalignmentflags or

dt_noprefix)

end;

end;

function tsecustomedit.getvisibleseltext: widestring;

begin

if selstart + 1 >= ffirstvisiblechar then

result := seltext

else

result := copy(seltext, ffirstvisiblechar – selstart, length(seltext) –

(ffirstvisiblechar – selstart) + 1);

end;

procedure tsecustomedit.buildpopupmenu;

var

tmpitem : tsecustomitem;

begin

fpopupmenu := createpopupmenu(self);

if fpopupmenu = nil then

exit;

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditundo;

onclick := doundo;

end;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

tmpitem.caption := -;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditcut;

onclick := docut;

end;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditcopy;

onclick := docopy;

end;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditpaste;

onclick := dopaste;

end;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditdelete;

onclick := dodelete;

end;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

tmpitem.caption := -;

fpopupmenu.items.add(tmpitem);

tmpitem := createpopupmenuitem(fpopupmenu);

with tmpitem do

begin

caption := seditselectall;

onclick := doselectall;

end;

fpopupmenu.items.add(tmpitem);

end;

function tsecustomedit.createpopupmenu(aowner: tcomponent): tsecustompopupmenu;

begin

result := tsecustompopupmenu.create(aowner);

end;

function tsecustomedit.createpopupmenuitem(aowner: tcomponent): tsecustomitem;

begin

result := tsecustomitem.create(self);

end;

procedure tsecustomedit.docut(sender: tobject);

begin

cuttoclipboard;

end;

procedure tsecustomedit.docopy(sender: tobject);

begin

copytoclipboard;

end;

procedure tsecustomedit.dodelete(sender: tobject);

begin

clearselection;

end;

procedure tsecustomedit.dopaste(sender: tobject);

begin

pastefromclipboard;

end;

procedure tsecustomedit.updatepopupmenuitems;

function setitemenabled(event: tnotifyevent; aenabled: boolean):

tsecustomitem;

var

item : tsecustomitem;

begin

item := fpopupmenu.items.finditem(integer(@event), fkhandle);

if item <> nil then

item.enabled := aenabled;

result := item;

end;

var

seltextempty : boolean;

begin

if fpopupmenu = nil then

buildpopupmenu;

seltextempty := seltext <> ;

setitemenabled(doundo, factionstack.atleast(1) and not readonly);

setitemenabled(docut, seltextempty and (not (passwordkind <> pknone)) and not

readonly);

setitemenabled(docopy, seltextempty and not (passwordkind <> pknone));

setitemenabled(dopaste, (clipboard.astext <> ) and not readonly);

setitemenabled(dodelete, seltextempty and not readonly);

setitemenabled(doselectall, seltext <> text);

{ set properties }

fpopupmenu.popupmenuoptions := fcontextmenuoptions;

end;

function tsecustomedit.getnextwordbeging(startposition: integer): integer;

var

spacefound,

wordfound : boolean;

begin

result := startposition;

spacefound := false;

wordfound := false;

while (result + 2 <= length(text)) and

((not ((text[result + 1] <> widespace) and spacefound))

or not wordfound) do

begin

if text[result + 1] = widespace then

spacefound := true;

if text[result + 1] <> widespace then

begin

wordfound := true;

spacefound := false;

end;

result := result + 1;

end;

if not spacefound then

result := result + 1;

end;

function tsecustomedit.getprivwordbeging(startposition: integer): integer;

var

wordfound : boolean;

begin

result := startposition;

wordfound := false;

while (result > 0) and

((text[result] <> widespace) or not wordfound) do

begin

if text[result] <> widespace then

wordfound := true;

result := result – 1;

end;

end;

procedure tsecustomedit.clearselection;

var

tmps : widestring;

begin

if readonly then

exit;

tmps := text;

factionstack.fragmentdeleted(selstart + 1,

copy(tmps, selstart + 1, sellength));

delete(tmps, selstart + 1, sellength);

text := tmps;

caretposition := selstart;

sellength := 0;

end;

procedure tsecustomedit.cuttoclipboard;

begin

if passwordkind = pknone then

copytoclipboard;

clearselection;

end;

procedure tsecustomedit.selectall;

begin

setcaretposition(length(text));

selstart := 0;

sellength := length(text);

invalidate;

end;

procedure tsecustomedit.doselectall(sender: tobject);

begin

selectall;

end;

procedure tsecustomedit.drawpasswordchar(symbolrect: trect; selected: boolean);

var

r : trect;

rgn : hrgn;

begin

{ !!! dont forget include clipping rountines

char symbol image must not extend out of editrect}

rgn := createrectrgn(symbolrect.left, symbolrect.top, symbolrect.right,

symbolrect.bottom);

try

selectcliprgn(canvas.handle, rgn);

canvas.font.assign(controlfont);

if selected then

canvas.font.color := clhighlighttext;

r := symbolrect;

inflaterect(r, -2, -3);

case fpasswordkind of

pkchar: drawtext(canvas, fpasswordchar, symbolrect, dt_left or

dt_noprefix);

pkrect: fillrect(canvas, r, canvas.font.color);

pkroundrect: fillroundrect(canvas, r, 2, canvas.font.color);

pkcircle:

begin

r := rect(0, 0, rectwidth(r), rectwidth(r));

rectcenter(r, symbolrect);

fillroundrect(canvas, r, rectwidth(r) div 2 + 1, canvas.font.color);

end;

pktriangle:

begin

r := rect(0, 0, rectwidth(r), rectwidth(r));

if not odd(rectwidth(r)) then

r.right := r.right + 1;

rectcenter(r, symbolrect);

canvas.brush.color := canvas.font.color;

canvas.polygon([

point(r.left + rectwidth(r) div 2 + 1, r.top),

point(r.right, r.bottom),

point(r.left, r.bottom)

]);

end;

end;

finally

selectcliprgn(canvas.handle, 0);

deleteobject(rgn);

end;

end;

function tsecustomedit.canautosize(var newwidth, newheight: integer): boolean;

begin

result := true;

canvas.font.assign(controlfont);

newheight := textheight(canvas, pq) + geteditrect.top * 2;

end;

procedure tsecustomedit.selectword;

begin

selstart := getprivwordbeging(caretposition);

;

sellength := getnextwordbeging(selstart) – selstart;

caretposition := selstart + sellength;

end;

procedure tsecustomedit.updatecarete;

begin

canvas.font.assign(controlfont);

createcaret(handle, 0, 0, canvas.textheight(pq));

caretposition := fcaretposition;

showcaret;

end;

procedure tsecustomedit.hidecaret;

begin

windows.hidecaret(handle);

end;

procedure tsecustomedit.showcaret;

begin

windows.showcaret(handle);

end;

function tsecustomedit.getpasswordcharwidth: integer;

begin

canvas.font.assign(controlfont);

case fpasswordkind of

pkchar: result := canvas.textwidth(fpasswordchar);

pkrect, pkroundrect, pkcircle, pktriangle: result := canvas.textwidth( w);

else

result := 10;

end;

if result = 0 then

result := 1;

end;

procedure tsecustomedit.change;

begin

inherited changed;

if enabled and handleallocated then

setcaretposition(caretposition);

if assigned(fonchange) then

fonchange(self);

end;

procedure tsecustomedit.wmimestartcomposition(var message: tmessage);

var

imc : himc;

logfont : tlogfont;

cf : tcompositionform;

begin

inherited;

imc := immgetcontext(handle);

if imc <> 0 then

begin

if assigned(font) then

begin

getobject(font.handle, sizeof(tlogfont), @logfont);

immsetcompositionfont(imc, @logfont);

end;

cf.dwstyle := cfs_rect;

cf.rcarea := geteditrect;

cf.ptcurrentpos := point(getcharx(fcaretposition), cf.rcarea.top);

immsetcompositionwindow(imc, @cf);

immreleasecontext(handle, imc);

end;

end;

procedure tsecustomedit.wmimecomposition(var msg: tmessage);

var

imc : himc;

buff : widestring;

i : integer;

begin

if msg.lparam and gcs_resultstr <> 0 then

begin

imc := immgetcontext(handle);

if imc <> 0 then

begin

try

{ get the result string }

setlength(buff, immgetcompositionstringw(imc, gcs_resultstr, nil, 0) div

sizeof(widechar));

immgetcompositionstringw(imc, gcs_resultstr, pwidechar(buff),

length(buff) * sizeof(widechar));

finally

immreleasecontext(handle, imc);

end;

{ insert char messages for each char in string }

for i := 1 to length(buff) do

insertchar(buff[i]);

msg.result := 0;

exit;

end;

end;

inherited;

end;

procedure tsecustomedit.wmgetdlgcode(var msg: twmgetdlgcode);

begin

inherited;

msg.result := dlgc_wantarrows or dlgc_wantchars;

end;

procedure tsecustomedit.wmcut(var message: tmessage);

begin

cuttoclipboard;

end;

procedure tsecustomedit.wmcopy(var message: tmessage);

begin

copytoclipboard;

end;

procedure tsecustomedit.wmpaste(var message: tmessage);

begin

pastefromclipboard;

end;

procedure tsecustomedit.wmcontexmenu(var message: tmessage);

var

lform : tcustomform;

begin

inherited;

if csdesigning in componentstate then

exit;

updatepopupmenuitems;

lform := getparentform(self);

if lform <> nil then

lform.sendcancelmode(nil);

fpopupmenu.popupcomponent := self;

with message do

fpopupmenu.popup(lparamlo, lparamhi);

end;

procedure tsecustomedit.wmlbuttondblclk(var message: twmlbuttondblclk);

begin

inherited;

flmouseselecting := false;

selectword;

end;

procedure tsecustomedit.cmfontchanged(var message: tmessage);

begin

inherited;

controlfont.assign(font);

adjustsize;

updatecarete;

end;

procedure tsecustomedit.setfont(value: tfont);

begin

inherited font := value;

controlfont.assign(value);

adjustsize;

end;

function tsecustomedit.gettext: widestring;

begin

result := ftext;

end;

procedure tsecustomedit.settext(const value: widestring);

var

tmps : widestring;

loldtext : widestring;

begin

if not validtext(value) then

exit;

tmps := value;

loldtext := text;

if (value <> ) and (charcase <> ecnormal) then

case charcase of

ecuppercase: ftext := ansiuppercase(tmps);

eclowercase: ftext := ansilowercase(tmps);

end

else

ftext := tmps;

invalidate;

if text <> loldtext then

change;

end;

procedure tsecustomedit.setcaretposition(const value: integer);

begin

if value < 0 then

fcaretposition := 0

else

if value > length(text) then

fcaretposition := length(text)

else

fcaretposition := value;

updatefirstvisiblechar;

if sellength <= 0 then

fselstart := value;

if focused then

setcaretpos(getcharx(fcaretposition), geteditrect.top);

end;

procedure tsecustomedit.setpasswordchar(const value: widechar);

begin

if fpasswordchar <> value then

begin

if value <> widechar(#0) then

fpasswordkind := pkchar;

fpasswordchar := value;

invalidate;

caretposition := caretposition; //update caret position

end;

end;

procedure tsecustomedit.setsellength(const value: integer);

begin

if fsellength <> value then

begin

fsellength := value;

invalidate;

end;

end;

procedure tsecustomedit.setselstart(const value: integer);

begin

if fselstart <> value then

begin

sellength := 0;

fselstart := value;

caretposition := fselstart;

invalidate;

end;

end;

procedure tsecustomedit.setautoselect(const value: boolean);

begin

if fautoselect <> value then

fautoselect := value;

end;

function tsecustomedit.getselstart: integer;

begin

if fsellength > 0 then

result := fselstart

else

if fsellength < 0 then

result := fselstart + fsellength

else

result := caretposition;

end;

function tsecustomedit.getselrect: trect;

begin

result := geteditrect;

result.left := getcharx(selstart);

result.right := getcharx(selstart + sellength);

intersectrect(result, result, geteditrect);

end;

function tsecustomedit.getsellength: integer;

begin

result := abs(fsellength);

end;

function tsecustomedit.getseltext: widestring;

begin

result := copy(text, selstart + 1, sellength);

end;

procedure tsecustomedit.setcharcase(const value: teditcharcase);

var

tmps : widestring;

begin

if fcharcase <> value then

begin

fcharcase := value;

if text <> then

begin

tmps := text;

case value of

ecuppercase: text := ansiuppercase(tmps);

eclowercase: text := ansilowercase(tmps);

end;

end;

end;

end;

procedure tsecustomedit.sethideselection(const value: boolean);

begin

if fhideselection <> value then

begin

fhideselection := value;

invalidate;

end;

end;

procedure tsecustomedit.setmaxlength(const value: integer);

begin

if fmaxlength <> value then

begin

fmaxlength := value;

end;

end;

procedure tsecustomedit.setcursor(const value: tcursor);

begin

if value = crdefault then

inherited cursor := cribeam

else

inherited cursor := value;

end;

function tsecustomedit.validtext(newtext: widestring): boolean;

begin

result := true;

end;

procedure tsecustomedit.settextalignment(const value: talignment);

begin

if ftextalignment <> value then

begin

ftextalignment := value;

invalidate;

end;

end;

procedure tsecustomedit.updatecareteposition;

begin

setcaretposition(caretposition);

end;

procedure tsecustomedit.inserttext(atext: widestring);

var

tmps : widestring;

begin

if readonly then

exit;

tmps := text;

factionstack.fragmentdeleted(selstart + 1, copy(tmps, selstart + 1,

sellength));

delete(tmps, selstart + 1, sellength);

factionstack.fragmentinserted(selstart + 1, length(atext), sellength <> 0);

insert(atext, tmps, selstart + 1);

if (maxlength <= 0) or (length(tmps) <= maxlength) then

begin

text := tmps;

caretposition := selstart + length(atext);

end;

sellength := 0;

end;

procedure tsecustomedit.insertchar(ch: widechar);

begin

if readonly then

exit;

inserttext(ch);

end;

procedure tsecustomedit.insertafter(position: integer; s: widestring;

selected: boolean);

var

tmps : widestring;

insertion : widestring;

begin

tmps := text;

insertion := s;

if maxlength > 0 then

insertion := copy(insertion, 1, maxlength – length(tmps));

insert(insertion, tmps, position + 1);

text := tmps;

if selected then

begin

selstart := position;

sellength := length(insertion);

caretposition := selstart + sellength;

end;

end;

procedure tsecustomedit.deletefrom(position, length: integer; movecaret:

boolean);

var

tmps : widestring;

begin

tmps := text;

delete(tmps, position, length);

text := tmps;

if movecaret then

begin

sellength := 0;

selstart := position – 1;

end;

end;

procedure tsecustomedit.doundo(sender: tobject);

begin

undo;

end;

procedure tsecustomedit.wmundo(var message: tmessage);

begin

undo;

end;

procedure tsecustomedit.undo;

begin

factionstack.rollbackaction;

end;

procedure tsecustomedit.setpasswordkind(const value: tpasswordkind);

begin

if fpasswordkind <> value then

begin

fpasswordkind := value;

invalidate;

end;

end;

procedure tsecustomedit.setpopupmenublendvalue(const value: integer);

begin

fpopupmenublendvalue := value;

end;

procedure tsecustomedit.setpopupmenudropshadow(const value: boolean);

begin

fpopupmenudropshadow := value;

end;

procedure tsecustomedit.setpopupmenushadowwidth(const value: integer);

begin

fpopupmenushadowwidth := value;

end;

procedure tsecustomedit.setpopupmenushowanimation(

const value: tseanimationrec);

begin

fpopupmenushowanimation := value;

end;

procedure tsecustomedit.setpopupmenushowanimationtime(

const value: integer);

begin

fpopupmenushowanimationtime := value;

end;

procedure tsecustomedit.cmtextchanged(var msg: tmessage);

begin

inherited;

ftext := inherited text;

sellength := 0;

invalidate;

end;

procedure tsecustomedit.setpopupmenublend(const value: boolean);

begin

fpopupmenublend := value;

end;

procedure tsecustomedit.clear;

begin

text := ;

end;

procedure tsecustomedit.borderchanged;

begin

inherited;

adjustsize;

end;

procedure tsecustomedit.setcontextmenuoptions(const value: tsepopupmenuoptions);

begin

fcontextmenuoptions.assign(value);

end;

procedure tsecustomedit.cmenabledchanged(var msg: tmessage);

begin

if handleallocated and not (csdesigning in componentstate) then

enablewindow(handle, enabled);

invalidate;

end;

总共用了我一个半小时的时间去追踪,真tmd。为什么双字节冲突这么明显的bug开发人员都不去解决?

赞(0)
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com 特别注意:本站所有转载文章言论不代表本站观点! 本站所提供的图片等素材,版权归原作者所有,如需使用,请与原作者联系。未经允许不得转载:IDC资讯中心 » 研究心得——->Seskin控件包中SeskinEdit汉字问题的解决办法-ASP教程,ASP应用
分享到: 更多 (0)

相关推荐

  • 暂无文章