4

I'm interested to create a vector point layer representing the centroid of some 500-1000 PDF files exported from QGIS to find PDFs geographically rather than using file explorer. I would like to automate this using PyQGIS.

I tested with the algorithm 'Tile Index' to manually extract the extents of 3 PDFs into a single GeoPackage through a batch process. Setting the output to the same .gpkg successfully appends each tile index into one GeoPackage. Writing the PyQGIS to take the centroid would then be straight forward. It is the first part which is convoluted. Below is the end result of my test.

example1

example2

I have a filing system where all 500-1000 PDFs are stored in client folders structured as below. The PDFs outlined green below are always stored in a folder named "!pdf's". An example of the file path is below.

example3

"V:/GIS - Files/1. Client Projects/A/Angus, A/ALN511253 - Lo/!pdf's/ALN511220-01.pdf"

I'd like to get the tile index of all 500-1000 PDFs in one swoop. Is it possible to target the "!pdf's" folder across all client folders using PyQGIS?

There are generic PDFs in the folder named 'Other' so I cannot search for all PDFs from the directory 'Client Projects'.

1
+50

In pure Python3, here the solution :

import os
import pathlib

my_path = "V:/GIS - Files/1. Client Projects/"
pdf_parent_folder = "!pdf's"
pdf_paths = []

for path, sub, files in os.walk(my_path):
    if pdf_parent_folder in sub:
        for path, sub, files in os.walk(os.path.join(path, pdf_parent_folder)):
            for name in files:
                if os.path.splitext(name)[1] == ".pdf":
                    pdf_paths.append(str(pathlib.PurePath(path, name)))
  • os.walk : get all files in the directory and subdirectories,
  • files : contains list of all files,
  • os.path.splitext : split the file name and the extension,
  • pdf_paths : Python list which contains all .pdf file complete path.

EDIT for explain how to use

Once you have copied the script above, you can use it as :

# copy the entire code above

for pdf_file_path in pdf_paths:
    python_pdf_object = method_that_open_and_read_the_pdf(pdf_file_path)
    # script here for do something with the python_pdf_object
    # ...
    # end of the script
  • Thank you for looking at this. Admittedly I'm a PyQGIS novice and following no python errors in the console, I'm a little lost how to progress it along! – James B Sep 9 at 13:06
  • My code stores all "!pdf's" pdf paths in the pdf_paths list, after my code, create a loop for each element of this list (= each pdf) for do what you want, here getting the tile index. – J. Monticolo Sep 9 at 13:11
  • Sorry if you feel you're holding my hand. I've successfully created the list in the python module but after reading about loops I'm non the wiser! The list is delimited by a comma but I do not know how to copy the list into the input for the tile index. – James B Sep 9 at 16:01
  • I've made an edit, it that more explicit for you ? – J. Monticolo Sep 10 at 7:28
  • I'm going to have to open another question as I have never used GDAL in pyqgis and really have no idea how to integrate them - I'll link it here when open. – James B Sep 10 at 8:50
1

Try pdfrw:

pdfrw is a Python library and utility that reads and writes PDF files

from pdfrw import PdfReader
from shapely.geometry import Polygon

pdffile = '/home/bera/Desktop/Layout 1.pdf'
pdf = PdfReader(pdffile)

box = pdf.pages[0].VP[0].Measure.GPTS #Dont know if this is standard "language" for all pdfs or just pdfs from QGIS
coords = [(float(lat),float(long)) for lat,long in zip(box[::2], box[1::2])]
poly = Polygon(coords)
poly.crs = {'init': 'epsg:4326', 'no_defs': True}
print(poly.centroid.y, poly.centroid.x)

Out:

17.887067033281365 59.31314913291589

Traverse the directories, output a csv with all points and add to QGIS.

enter image description here

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.