MonoTouch: утечка памяти при рисовании PDF в пользовательском графическом контексте - PullRequest
2 голосов
/ 06 декабря 2011

У меня есть приложение, которое в основном представляет собой читатель PDF.Я загружаю PDF из Интернета и создаю эскизы для этого PDF.Однако, кажется, что когда я генерирую эти миниатюры, выделяется лот памяти (проверяется с помощью инструментов), иногда части этого собираются GC, но в конце концов мое приложение сдается.У меня было до 38 Мб памяти при создании миниатюр для одного PDF (100х100 больших пальцев, ~ 60 страниц).

Я создаю один эскиз за раз, сохраняю его и затем повторяю процесс, поэтому в разделеПри любых обстоятельствах в памяти должен быть только один эскиз (по крайней мере, при их создании).Мой код для создания миниатюр выглядит следующим образом:

public UIImage GetPageThumbnail(int pageNumber, SizeF size)
{
    //If using retina display, make sure to scale-up the thumbnail as well.
    size.Width = size.Width * UIScreen.MainScreen.Scale;
    size.Height = size.Height * UIScreen.MainScreen.Scale;

    UIGraphics.BeginImageContext(size);
    CGContext tempContext = UIGraphics.GetCurrentContext();
    CGPDFPage page = Document.GetPage(pageNumber);

    RectangleF drawArea = new RectangleF(new PointF(0f, 0f), size);
    CGAffineTransform transform = page.GetDrawingTransform( CGPDFBox.Crop, drawArea, 180, true); //fit PDF to context
    transform.xx = -transform.xx;   // }
    transform.x0 = 0;               // }flip horizontally

    //Console.WriteLine("XX: " + transform.xx + ", YX:" + transform.yx + ", XY:" + transform.xy + ", YY:" + transform.yy + ", X0:" + transform.x0 + ", Y0:" + transform.y0);

    tempContext.ConcatCTM(transform);

    tempContext.DrawPDFPage (page);
    UIImage returnImage = UIGraphics.GetImageFromCurrentImageContext();
    UIGraphics.EndImageContext();
    return returnImage;
}

Я пытался явно избавиться от контекста и страницы PDF, но это не дало эффекта (на самом деле это выглядело хуже, но примите это с щепоткой соли).

Я видел несколько постов об утечке памяти с помощью MonoTouch и PDF (в основном в этом посте ), но это довольно старо.Я использую новейший MonoTouch (5.0.2).

1 Ответ

4 голосов
/ 08 декабря 2011

Не уверен, где проблема в вашем коде, но вот мой код для создания больших страниц PDF-страниц.Работает без нареканий.Может быть, это поможет вам.Я думаю, что ваша проблема может быть в том, что вы делаете с возвращенным изображением, когда вы надеваете.

public static UIImageView GetLowResPagePreview (CGPDFPage oPdfPage, RectangleF oTargetRect)
        {
            RectangleF oOriginalPdfPageRect = oPdfPage.GetBoxRect (CGPDFBox.Media);
            RectangleF oPdfPageRect = PdfViewerHelpers.RotateRectangle( oPdfPage.GetBoxRect (CGPDFBox.Media), oPdfPage.RotationAngle);

            // Create a low res image representation of the PDF page to display before the TiledPDFView
            // renders its content.
            int iWidth = Convert.ToInt32 ( oPdfPageRect.Size.Width );
            int iHeight = Convert.ToInt32 ( oPdfPageRect.Size.Height );
            CGColorSpace oColorSpace = CGColorSpace.CreateDeviceRGB();
            CGBitmapContext oContext = new CGBitmapContext(null, iWidth, iHeight, 8, iWidth * 4, oColorSpace, CGImageAlphaInfo.PremultipliedLast);

            // First fill the background with white.
            oContext.SetFillColor (1.0f, 1.0f, 1.0f, 1.0f);
            oContext.FillRect (oOriginalPdfPageRect);
            // Scale the context so that the PDF page is rendered 
            // at the correct size for the zoom level.
            oContext.ConcatCTM ( oPdfPage.GetDrawingTransform ( CGPDFBox.Media, oPdfPageRect, 0, true ) );
            oContext.DrawPDFPage (oPdfPage);
            CGImage oImage = oContext.ToImage();
            UIImage oBackgroundImage = UIImage.FromImage( oImage );
            oContext.Dispose();
            oImage.Dispose ();
            oColorSpace.Dispose ();

            UIImageView oBackgroundImageView = new UIImageView (oBackgroundImage);
            oBackgroundImageView.Frame = new RectangleF (new PointF (0, 0), oPdfPageRect.Size);
            oBackgroundImageView.ContentMode = UIViewContentMode.ScaleToFill;
            oBackgroundImageView.UserInteractionEnabled = false;
            oBackgroundImageView.AutoresizingMask = UIViewAutoresizing.None;
            return oBackgroundImageView;
        }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...