2009-02-27 5 views
3

모바일 장치를 사용하여 사진을 찍어 웹 서비스를 사용하여 보내는 응용 프로그램을 개발하고 있습니다. 그러나 내가 4 장의 사진을 찍은 후에 나는 아래 코드에서 OutOfMemoryException을 얻고있다. 나는 GC.Collect()이라고 전화를 시도했다. 그러나 그것도 도움이되지 않았다. 어쩌면 여기 누군가가 나에게이 문제를 다루는 방법에 대한 조언을 줄 수있을 것이다.OutOfMemoryException 모바일 장치에서

public static Bitmap TakePicture() 
{ 
    var dialog = new CameraCaptureDialog 
    { 
     Resolution = new Size(1600, 1200), 
     StillQuality = CameraCaptureStillQuality.Default 
    }; 

    dialog.ShowDialog(); 

    // If the filename is empty the user took no picture 
    if (string.IsNullOrEmpty(dialog.FileName)) 
     return null; 

    // (!) The OutOfMemoryException is thrown here (!) 
    var bitmap = new Bitmap(dialog.FileName); 

    File.Delete(dialog.FileName); 

    return bitmap; 
} 

기능은 이벤트 처리기에 의해 호출됩니다 대신 메모리에 비트 맵으로 이미지를 저장하기 위해 당신이 선택하기 때문에 그래서

private void _pictureBox_Click(object sender, EventArgs e) 
{ 
    _takePictureLinkLabel.Visible = false; 

    var image = Camera.TakePicture(); 
    if (image == null) 
     return; 

    image = Camera.CutBitmap(image, 2.5); 
    _pictureBox.Image = image; 

    _image = Camera.ImageToByteArray(image); 
} 

답변

5

난 당신이 참조에 들고 생각한다. 부수적 인 이유는 ShowDialog을 사용할 때 대화 상자가 자동으로 처리되지 않으므로 대화 상자가 using이어야합니다 (그래도 아직 GC가 undisposed이지만 참조되지 않은 대화를 수집 할 것으로 기대합니다).

마찬가지로 이미지가 using 일 수는 있지만 다시 한 번 다음과 같이 설정해야합니다. 가치 시도,하지만 ...

public static Bitmap TakePicture() 
{ 
    string filename; 
    using(var dialog = new CameraCaptureDialog 
    { 
     Resolution = new Size(1600, 1200), 
     StillQuality = CameraCaptureStillQuality.Default 
    }) { 

     dialog.ShowDialog(); 
     filename = dialog.FileName; 
    }  
    // If the filename is empty the user took no picture 
    if (string.IsNullOrEmpty(filename)) 
     return null; 

    // (!) The OutOfMemoryException is thrown here (!) 
    var bitmap = new Bitmap(filename); 

    File.Delete(filename); 

    return bitmap; 
} 

private void _pictureBox_Click(object sender, EventArgs e) 
{ 
    _takePictureLinkLabel.Visible = false; 

    using(var image = Camera.TakePicture()) { 
     if (image == null) 
      return; 

     image = Camera.CutBitmap(image, 2.5); 
     _pictureBox.Image = image; 

     _image = Camera.ImageToByteArray(image); 
    } 
} 

나는 또한 일을 최대한 빨리 출시되는 것을 보장하기 위해 CutBitmap 등의 작은주의 것입니다.

+1

코드를 약간 수정하면 그림 상자 이미지를 설정하는 곳에서 먼저 기존 이미지를 모두 삭제할 수 있습니다. la if (_pictureBox.Image! = null) _pictureBox.Image.Dispose(). – ctacke

2

당신의 모바일 장치는 일반적으로 디스크 옵션 스왑 메모리를 가지고 있지 않습니다 디스크의 파일보다 빠르게 휴대 전화의 메모리를 소비합니다. 귀하의 "새로운 Bitmap()"라인은 많은 양의 메모리를 할당하므로 예외가 발생할 가능성이 매우 높습니다. 또 다른 경쟁자는 많은 양의 메모리를 할당 할 Camera.ImageToByteArray입니다. 이것은 아마도 당신이 컴퓨터에 익숙한 것만 큼 크지 않을 것이지만, 귀하의 휴대 전화는 거대합니다.

사용하기 전, 즉 웹 서비스로 보낼 때까지 디스크에 그림을 유지하십시오. 그들을 표시하기 위해 내장 된 컨트롤을 사용하면 아마도 메모리 효율이 가장 좋을 것이며 일반적으로 이미지 파일을 가리킬 수 있습니다.

건배

+0

"보통"없다. CE에는 디스크로 교체 할 수있는 조항이 없으므로 장치가 필요하지 않습니다. – ctacke

관련 문제