1.TNMSmtp组件在什么地方(我找不到FastNet)
2.怎么用FindDialog查找memo中的字符
3.怎么用ReplaceDialog替换memo中的字符

解决方案 »

  1.   

    1:D6中 组件板的第16页
    2:查找对话框的Options属性的取值及含义
    ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
    取值  含义
    ───────────────────────────────────────
    frDown    如果是真值,对话框中出现Down按钮,查找方向向下。如果是假b,Up按钮将被选中,查找方向向上,frDown 值可在设计或运行时设置。
    frDisableUpDown  如果是真值,Up和Down按钮将变灰,用户不能进行选取;如果是假值,用户可以选择其中之一。
    frFindNext   如果是真值,应用程序查找在FindNext属性中的字符串。
    frMatchCase  如果是真值,匹配检查框被选中。设计、运行时均可设置。
    frWholeWord  如果是真值,整字匹配检查框被选中,设计、运行时均可设置。
    ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
    在OnFind事件中可使用Options属性来决定以何种方式查找。Find方法响应查找对话框的OnFind事件。
    procedure TEditform.Find(Sender: TObject);
    begin
    with Sender as TFindDialog do
    if not SearchMemo(Memo1, FindText, Options) then
    ShowMessage('Cannot find "' + FindText + '".');
    end;
    其中SearchMemo函数是Search单元中定义的,SearchMemo可在
    TEdit,TMemo,以及其它TCustomEdit派生类中查找指定的字符串。查找从控件的脱字号(^)开始, 查找方式由Options决定。如果向后查找从控件的StlStart处开始,如果向前查找则从控件的SelEnd处查找。如果在控件中找到相匹配的字符串,则字符串被选中,函数返回真值。如无匹配的字符串,函数返回假值。
    特别注意的是TEdit,TMemo中有一个HideSeletion属性,它决定当焦点从该控制转移至其它控制时,被选中的字符是否保持被选中的状态。如果是真值,则只有获得焦点才能保持被选中状态。查找时,焦点在查找对话框上,因此要想了解查找情况,必须将HideSeletion设成假值。控制的缺省值为真值。
    SearchMemo代码如下:
    unit Search;
    interface
    uses WinProcs, SysUtils, StdCtrls, Dialogs;
    const
    WordDelimiters: set of Char = [#0..#255] -
    ['a'..'z','A'..'Z','1'..'9','0'];
    function SearchMemo(Memo: TCustomEdit;
    const SearchString: String;
    Options: TFindOptions): Boolean;
    function SearchBuf(Buf: PChar; BufLen: Integer;
    SelStart, SelLength: Integer;
    SearchString: String;
    Options: TFindOptions): PChar;
    implementation
    function SearchMemo(Memo: TCustomEdit;
    const SearchString: String;
    Options: TFindOptions): Boolean;
    var
    Buffer, P: PChar;
    Size: Word;
    begin
    Result := False;
    if (Length(SearchString) = 0) then Exit;
    Size := Memo.GetTextLen;
    if (Size = 0) then Exit;
    Buffer := StrAlloc(Size + 1);
    try
    Memo.GetTextBuf(Buffer, Size + 1);
    P := SearchBuf(Buffer, Size, Memo.SelStart,
    Memo.SelLength,SearchString, Options);
    if P <> nil then
    begin
    Memo.SelStart := P - Buffer;
    Memo.SelLength := Length(SearchString);
    Result := True;
    end;
    finally
    StrDispose(Buffer);
    end;
    end;
    function SearchBuf(Buf: PChar; BufLen: Integer;
    SelStart, SelLength: Integer;
    SearchString: String;
    Options: TFindOptions): PChar;varSearchCount, I: Integer;
    C: Char;
    Direction: Shortint;
    CharMap: array [Char] of Char;
    function FindNextWordStart(var BufPtr: PChar): Boolean;
    begin { (True XOR N) is equivalent to(not N) }
    Result := False; { (False XOR N) is equivalentto (N) }
    { When Direction is forward (1), skip nondelimiters, then skip delimiters. }
    { When Direction is backward (-1), skip delims, then
    skip non delims }
    while (SearchCount > 0) and((Direction = 1) xor (BufPtr^ in
    WordDelimiters)) do
    begin
    Inc(BufPtr, Direction);
    Dec(SearchCount);
    end;
    while (SearchCount > 0) and
    ((Direction = -1) xor (BufPtr^ in
    WordDelimiters)) do
    begin
    Inc(BufPtr, Direction);
    Dec(SearchCount);
    end;
    Result := SearchCount > 0;
    if Direction = -1 then
    begin { back up one char, to leave ptr on first non
    delim }
    Dec(BufPtr, Direction);
    Inc(SearchCount);
    end;
    end;
    begin
    Result := nil;
    if BufLen <= 0 then Exit;
    if frDown in Options then
    begin
    Direction := 1;
    Inc(SelStart, SelLength); { start search past end of
    selection }
    SearchCount := BufLen - SelStart - Length(SearchString);
    if SearchCount < 0 then Exit;
    if Longint(SelStart) + SearchCount > BufLen then Exit;
    end
    else
    begin
    Direction := -1;
    Dec(SelStart, Length(SearchString));
    SearchCount := SelStart;
    end;
    if (SelStart < 0) or (SelStart > BufLen) then Exit;
    Result := @Buf[SelStart];
    { Using a Char map array is faster than calling
    AnsiUpper on every character }
    for C := Low(CharMap) to High(CharMap) do
    CharMap[C] := C;
    if not (frMatchCase in Options) then
    begin
    AnsiUpperBuff(PChar(@CharMap), sizeof(CharMap));
    AnsiUpperBuff(@SearchString[1],
    Length(SearchString));
    end;
    while SearchCount > 0 do
    begin
    if frWholeWord in Options then
    if not FindNextWordStart(Result) then Break;
    I := 0;
    while (CharMap[Result[I]] = SearchString[I+1]) do
    begin
    Inc(I);
    if I >= Length(SearchString) then
    begin
    if (not (frWholeWord in Options)) or
    (SearchCount = 0) or
    (Result[I] in WordDelimiters) then
    Exit;
    Break;
    end;
    end;
    Inc(Result, Direction);
    Dec(SearchCount);
    end;
    Result := nil;
    end;
    end.
      

  2.   

    3:
    与查找对话框一样,替换对话框亦有OnFind 事件。用户输入查找字符串并按FindNext按钮时,发生OnFind 事件。用户选择Replace 或ReplacAll 时, 对话框发生OnRelpace事件,要替换的字符串存入ReplaceText属性中,要编写相应的代码以支持替换功能。
    表4.3 替换对话框的Options属性的取值及含义
    ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 
    取值     含义
    ────────────────────────────────────────
    frRelpace     如果是真值, 应用程序将ReplaceText 属性中的字符串
    FindText属性中的字符串。
    frReplacAll    如果是真值,应用程序将ReplaceText属性中的字符串替换,查找到的所有FindText属性中的字符串。
    ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
    例程中TEditForm.Replace方法响应OnReplace事件,Replace方法首先判断控制中被选中字符串是否与替换字符串相等,如果不等则进行替换。而后根据Options中的方式循环进行查找替换。直至无匹配字符串为止。其代码如下:
    procedure TEditForm.Replace(Sender: TObject);
    var
    Found: Boolean;
    begin
    with ReplaceDialog1 do
    begin
    if AnsiCompareText(Memo1.SelText, FindText) = 0 then
    Memo1.SelText := ReplaceText;
    Found := SearchMemo(Memo1, FindText, Options);
    while Found and (frReplaceAll in Options) do
    begin
    Memo1.SelText := ReplaceText;
    Found := SearchMemo(Memo1, FindText, Options);
    end;
    if (not Found) and (frReplace in Options) then
    ShowMessage('Cannot find "' + FindText + '".');
    end;
    end;