2009-11-20 7 views
1

양식에 슬라이드 쇼로 표시되는 이미지를 순환하는 Windows Form이 있습니다. 이 작업을 수행하는 방식은 Panel에있는 폼의 크기를 제어하고 메모리에있는 Image 개체를 그리는 이벤트 처리기를 추가하는 것입니다. 새로운 이미지로드 _image에 의해 참조되는 페인트 이벤트 핸들러가 몇 번의 반복 후에 실행을 중지합니다.

void panel_Paint(object sender, PaintEventArgs e) 
{ 
    if (_bShowImage) 
    { 
    Point leftCorner = new Point((this.Bounds.Width/2) - (_image.Width/2), (this.Bounds.Height/2) - (_image.Height/2)); 

    e.Graphics.DrawImage(_image, leftCorner); 

    _bShowImage = false; 
    } 
} 

, 나는 다시 그리기 패널을 강요 해요 :

_bShowImage = true; 
_panel.Refresh(); 

을 직후, 이미지 배치와 글로벌 변수에서 역 참조 :

_image.Dispose(); 
_image = null; 

잠시 동안, 예를 들어 5 회 반복되는 것을 보았습니다. 그런 다음 panel_Paint() 핸들러가 호출되지 않습니다. 디스플레이에 2-3 개의 JPG를 사용하고 있는데 처음 x 시간 동안 잘 보였으므로 손상되지 않았 음을 알았습니다. 나는 잘 실행되는 패널의 Refresh() 메소드 주위에 디버그 라인을 넣었다. 그것은 마치 핸들러에 대한 호출이 삭제 된 것과 같습니다. 누구든지 전에이 문제가 발생 했습니까?

+0

PictureBox를 사용하지 않는 이유가 있습니까? 조금씩 다시 칠해야 할 때마다 이런 식으로 전체 이미지를 그리는 데 오버 헤드가 발생합니다 ... 직접 작업 할 경우 다시 그려야 할 영역에주의를 기울이는 것이 좋습니다. PaintEventArgs에서 가져옵니다. –

답변

0

사진을 그림 상자에 넣고 그런 방식으로 반복하면 매번 전체 창에서 다시 칠하지 않아도됩니다. 단지 생각

...

토니

+0

처음에는 PictureBox를 사용했지만 같은 문제가 발생하여 직접 처리하기로 결정했습니다. – Michali

1

이 지금 완전히 거꾸로입니다. 당신은 지금과 같은 페인트 이벤트 핸들러를 사용합니다. 그것은 괜찮아요 (나는 그것이 그림 상자보다 낫다고 말하고 싶습니다.) 그런 다음 _bShowImage와 _image.Dispose를 삭제해야합니다. 대신 새 이미지로 전원을 켜기 전에 _image를 처리해야합니다. 그러나 그 전까지는.

또는 페인트 한 직후에 absolutley가 _image를 처리해야하는 경우 Panel.CreateGraphics를 사용하여 Graphichs 개체를 가져와 즉시 _image를 그려 이벤트를 삭제할 수 있습니다.

그대로 - 혼란 스러울뿐입니다. 또한 : .Invalidate()는 거의 항상 원하는 것입니다. -Refresh(). VB6 시대 이래로 많은 사람들의 마음을 사로 잡은 것입니다.

+0

지금 Paint 이벤트 처리를 한쪽에 넣고 그 제안을 찾아갔습니다. 이제 실제 예외가 발생하면서 어딘가에 도착할 것입니다. System.Runtime.InteropServices.ExternalException : GDI +에서 일반 오류가 발생했습니다. System.Drawing.Graphics.DrawImage에서 System.Drawing.Graphics.DrawImage에서 System.Drawing.Graphics.CheckErrorStatus (INT32 상태) (이미지 화상 INT32의 X, Y의 INT32) (이미지의 이미지 포인트 포인트) 에서 나는 그것이 메모리 누출일지도 모른다고 생각했다. 그러나 나는 이미지를 처분했다. 또한 Graphics 객체는 전역 객체이므로 마지막에 한 번만 처리합니다. – Michali

+1

이것은 역방향으로 들립니다. 전역으로 유지하고 폐기하고 즉시 null로 설정하여 사용하려고하면 최소한 null 참조 예외가 발생합니다. 아니면 로컬로 만들 수 있습니다. 주변에 "글로벌"처분 참조가 있으면 아무 것도 좋지 않습니다. 거의 항상 .Dispose()를 잊어 버릴 수 있습니다.그러나 아직 사용중인 것을 폐기하지 마십시오. 적어도 지금 추적중인 버그에 대해서는 .Dispose()를 삭제하십시오. –

관련 문제