0
votes

In my application I have used a QLPreviewController to display some pdf files. Everything works fine, but there is an unwanted space in the top of content of QLPreviewController and couldn't find a way to remove it.

This is how I wrote it. (Please note that I am new to Xamarin.iOS and QLPreviewController)

public partial class ReportsViewController : UIViewController
{
    public override void ViewDidLoad()
    {
        base.ViewDidLoad();

        //Customize navigation bar for QLPreviewController
        if(UIDevice.CurrentDevice.CheckSystemVersion(11, 0)) // There is a bug with barTintColor on QLPreviewController for iOS 11 if you are showing it via presentViewController: animated:
        {
            var color = UIColor.FromRGB(red: 23, green: 61, blue: 86).CGColor;
            var rect = new CGRect(x: 0.0, y: 0.0, width: 1.0, height: 1.0);
            var alpha = color.Alpha;
            var opaque = alpha == 1;
            UIGraphics.BeginImageContextWithOptions(rect.Size, opaque, 0);
            var context = UIGraphics.GetCurrentContext();
            context.SetFillColor(color);
            context.FillRect(rect);
            var image = UIGraphics.GetImageFromCurrentImageContext();
            UIGraphics.EndImageContext();

            UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).SetBackgroundImage(image, UIBarMetrics.Default);

        }
        else // If iOS version is below 11.0
        {
            UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).BarTintColor = UIColor.FromRGBA(red: 255, green: 0, blue: 0, alpha: 1.0f);
        }

        UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).BarStyle = UIBarStyle.Black;
        UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).TintColor = UIColor.White;

        var reportSavedPath = "path to pdf file";
        var reportName = "Report name";
        var previewController = new QLPreviewController();
        var url = new NSUrl(reportSavedPath, true);
        var _dataSource = new PreviewControllerSource(this, url, reportName);
        previewController.DataSource = _dataSource;
        PresentViewController(previewController, true, completionHandler: null);
    }
}

public partial class ReportsViewController : UIViewController
{
    class PreviewControllerSource : QLPreviewControllerDataSource
    {
        ReportsViewController _parentClass = null;
        NSUrl _url = null;
        string _title = null;

        public PreviewControllerSource(ReportsViewController parentClass, NSUrl url, string title)
        {
            _parentClass = parentClass;
            _url = url;
            _title = title;
        }

        public override nint PreviewItemCount(QLPreviewController controller)
        {
            return 1;
        }

        public override IQLPreviewItem GetPreviewItem(QLPreviewController controller, nint index)
        {
            return new PreviewItem { title = _title, url = _url };
        }
    }
    public class PreviewItem : QLPreviewItem
    {
        public string title { get; set; }
        public NSUrl url { get; set; }
        public override string ItemTitle { get { return title; } }
        public override NSUrl ItemUrl { get { return url; } }
    }
}

This is how it looks like when the pdf is loaded

enter image description here

Can someone please help me to get this unwanted space removed?

1
Could you try a different PDF File of a different dimension and see if the unwanted space is the same amount? Also, which iOS version are you running into that error?Saamer
@Saamer I already tried with different different pdfs. But the space remains for all of them. Im using iOS 12.2GMHSJ
var rect = new CGRect(x: 0.0, y: 0.0, width: 1.0, height: 1.0); What would happen if you reduced these values to 0.1 ?Saamer
@Saamer It didn't work :(GMHSJ

1 Answers

0
votes

Have no idea about why you have to Customize navigation bar for QLPreviewController in your code. I removed it and it works perfect.

I would give you two ways to get rid of the unwanted sapce:

1.remove the code:

//UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).SetBackgroundImage(image, UIBarMetrics.Default);

2.if you really need the code to Customize navigation bar, add this line of code before PresentViewController:

//Add this line before PresentViewController
UINavigationBar.AppearanceWhenContainedIn(typeof(QLPreviewController)).SetBackgroundImage(null, UIBarMetrics.Default);

PresentViewController(previewController, true, completionHandler: null);

Update:

Spent the whole afternoon and only find a solution not so perfect. First, I would like to say that the navigationBar of your viewController and the navigationBar of QLPreviewController are two different bars.

To set the navigationbar color, you can simply set it in AppDelegate, this will affect the whole navigationBar color in your project.:

 public override bool FinishedLaunching(UIApplication application, NSDictionary launchOptions)
    {
        // Override point for customization after application launch.
        // If not required for your application you can safely delete this method

        UINavigationBar.Appearance.BarTintColor = UIColor.FromRGBA(red: 255, green: 0, blue: 0, alpha: 1.0f);
        UINavigationBar.Appearance.BarStyle = UIBarStyle.BlackOpaque;
        UINavigationBar.Appearance.TintColor = UIColor.White;


        return true;
    }

To change the navigationbarColor of QLPreviewControl, you can use the code in test function:

public partial class ViewController : UIViewController
{

    QLPreviewController previewController;

    public ViewController(IntPtr handle) : base(handle)
    {
    }

    public override void ViewDidLoad()
    {
        base.ViewDidLoad();

        this.AutomaticallyAdjustsScrollViewInsets = false;
        this.ExtendedLayoutIncludesOpaqueBars = false;
        this.EdgesForExtendedLayout = UIRectEdge.None;

        string path = NSBundle.MainBundle.PathForResource("myPdf.pdf","");
        var reportName = "Report name";
        previewController = new QLPreviewController();
        var url = new NSUrl(path, true);
        var _dataSource = new PreviewControllerSource(this, url, reportName);
        previewController.DataSource = _dataSource;

        this.NavigationController.PresentViewController(previewController, true, test);

    }

    public void test() {

            var firstChild = previewController.ChildViewControllers[0];

            if (firstChild is UINavigationController)
            {
                var naviVc = firstChild as UINavigationController;
                naviVc.NavigationBar.BarTintColor = UIColor.Red ;
            }
        }
}

The only thing that is not so perfect is that the test function will call until the presenting completed, so you would see the default color of navigationBar a while and then it will change to the color you want.

If you use a push action instead of modal, you can call test function inside the WillShowViewController(UINavigationController navigationController, [Transient] UIViewController viewController, bool animated):

public class naviDeleagte : UINavigationControllerDelegate {

    public override void WillShowViewController(UINavigationController navigationController, [Transient] UIViewController viewController, bool animated)
    {
        //call test here if you use a push instead of modal
    }
}

I uploaded my sample here and you can check it:navigationBar-color-xamarin.forms