Q&A

  • StringGrid에서 행을 선택적으로 읽어오려면..
Grid의 Cell를 각 행단위로 선택적으로 원하는 행만 읽어오고 싶은데

어떻게 해야하는지 궁금하군요...





1  COMMENTS
  • Profile
    구창민 1999.08.31 02:00
    문해영 께서 말씀하시기를...

    > Grid의 Cell를 각 행단위로 선택적으로 원하는 행만 읽어오고 싶은데

    > 어떻게 해야하는지 궁금하군요...

    >

    >



    문해영님 안녕하세요?

    아래내용을 참조하시면 해결가능할거 같네요.

    영대님 팁에서 펐답니다.

    < StringGrid 의 선택영역만 클립보드로 복사하기 >

    // <사용방법> 아래 코딩을 하신후에 StringGrid의 Options의 goRangeSelect 를 True로

    // 설정하신 다음에 컴파일 하세요

    // 실행후 StringGrid의 특정영역을 마우스나 키보드로 영역을 선택하신후

    // Button1 을 클릭하시면 StringGrid의 선택영역의 내용이 클립보드로

    // 복사된후 다시 Memo 에 붙여넣기가 됩니다



    unit Unit1;



    interface



    uses

    Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,

    StdCtrls, Buttons, Grids, clipbrd;



    type

    TForm1 = class(TForm)

    StringGrid1: TStringGrid;

    Memo1: TMemo;

    Button1: TButton;

    procedure FormActivate(Sender: TObject);

    procedure Button1Click(Sender: TObject);

    private

    { Private declarations }

    public

    { Public declarations }

    end;



    var

    Form1: TForm1;



    implementation

    {$R *.DFM}



    procedure CopyStreamToClipboard(S: TStream; fmt: Word);

    var

    hMem: THandle;

    pMem: Pointer;

    begin

    {stream의 위치를 맨 앞으로 이동시킨다}

    S.Position := 0;



    {stream의 크기만큼 전역 힙(heap)에 메모리 블록을 할당한후 원도우 핸들을 얻는다}

    hMem := GlobalAlloc(GHND or GMEM_DDESHARE, S.Size);

    if hMem <> 0 then

    begin

    {전역 힙의 할당된 메모리 블록을 고정(lock)시킨다}

    pMem := GlobalLock(hMem);

    if pMem <> nil then

    begin

    {할당받은 메모리 블럭에 stream의 내용을 복사한다}

    S.Read(pMem^, S.Size);

    {위의 S.Read()에 의해 증가된 포인터를 다시 맨 앞으로 이동시킨다}

    S.Position := 0;

    {전역 힙에서 메모리 블록의 잠금 해제}

    GlobalUnlock(hMem);



    {클립보드를 열러서 주어진 포맷(여기서는 CF_TEXT)과 원도우 핸들로 지정된

    데이타를 클립보드에 준다}

    Clipboard.Open;

    try

    Clipboard.SetAsHandle(fmt, hMem);

    finally

    Clipboard.Close;

    end;

    end

    else

    begin

    {메모리 lock의 실패로 memory block 예외를 발생시킨다}

    GlobalFree(hMem);

    OutOfMemoryError;

    end;

    end

    else

    begin

    {메모리 할당의 실패로 memory block 예외를 발생시킨다}

    OutOfMemoryError;

    end;

    end;



    procedure CopySelectedGridToClipboard(theGrid: TStringGrid);

    var

    m: TMemoryStream;

    i, j: Integer;

    S: String;

    begin

    m := TMemoryStream.Create;

    try

    with theGrid do

    for i := theGrid.Selection.Top to theGrid.Selection.Bottom do

    for j := theGrid.Selection.Left to theGrid.Selection.Right do

    begin

    S := Cells[j, i];

    // 맨 마지막 선택된 Column이면 CR/LF 를 추가하여 행구분

    if j = theGrid.Selection.Right then

    AppendStr(S, #13#10)

    else

    AppendStr(S, #9); // 각 Column을 Tab 문자로 구분

    m.WriteBuffer(S[1], Length(S));

    end;

    S[1] := #0; // 문자열 stream의 끝 표시

    m.WriteBuffer(S[1], 1);

    CopyStreamToClipboard(m, CF_TEXT); // stream의 내용을 클립보드로 복사

    finally

    m.Free;

    end;

    end;



    procedure TForm1.FormActivate(Sender: TObject);

    var

    i, j: Integer;

    begin

    // Column의 title을 만든다

    for i := 1 to StringGrid1.ColCount - 1 do

    StringGrid1.Cells[i, 0] := Char(Ord('A')+i-1);



    // Row의 title을 만든다

    for i := 1 to StringGrid1.RowCount - 1 do

    StringGrid1.Cells[0, i] := IntToStr(i);;



    // 임의의 자료를 만들어서 각 cell에 입력합니다

    for i := 1 to StringGrid1.ColCount - 1 do

    for j := 1 to StringGrid1.RowCount - 1 do

    StringGrid1.Cells[i, j] := Format('%.0n', [i * j * 10000.0]);

    end;



    procedure TForm1.Button1Click(Sender: TObject);

    begin

    // StringGrid의 선택된 영역을 클립보드로 북사

    CopySelectedGridToClipboard(StringGrid1);



    // 클립보드의 내용을 메모로 붙여넣기(테스트용)

    Memo1.Clear;

    Memo1.PasteFromClipboard;

    end;



    end.