mcsprodart. I’ll look forward to a response from Shane or another forum member.
I was just curious how you know that the shouldAntialias and imageInterpolation properties are having no effect?
mcsprodart. I’ll look forward to a response from Shane or another forum member.
I was just curious how you know that the shouldAntialias and imageInterpolation properties are having no effect?
@peavine 's script looks OK, although I haven’t tried it. The problem with yours was that you you were setting the properties of the imagerep after the drawInRect:::
– they need to be set before you draw.
Shane
I tested moving the line on a pdf created for test and the line antialias has no effect. If you change the interpolation, it has an effect. If uncomment the setSize line, which I’m assuming would set the page size to the same as the original which is needed otherwise it makes the page size huge at 72 dpi instead of 300 dpi. Any advice is appreciated to help resolve. Also can you help me understand the switch from theImageRep to newImageRep and theContext and why it is needed and what the following lines do?
current application’s NSGraphicsContext’s saveGraphicsState()
and
current application’s NSGraphicsContext’s restoreGraphicsState()
Here’s a screenshot showing aliasing.
Here is what it should look like
Here is the code:
use framework "AppKit"
use framework "Foundation"
use framework "PDFKit"
use scripting additions
set firstPage to 1
set lastPage to 1 -- use 0 for last page of PDF
set theResolution to 300
set thePDF to POSIX path of (choose file of type {"com.adobe.pdf"})
pdfToPng(thePDF, firstPage, lastPage, theResolution)
on pdfToPng(thePDF, firstPage, lastPage, theResolution) -- borrows significantly from scripts by Shane Stanley
set thePDF to current application's |NSURL|'s fileURLWithPath:thePDF
set theDocument to (current application's PDFDocument's alloc()'s initWithURL:thePDF)
set pdfPageCount to theDocument's pageCount()
if lastPage > pdfPageCount then error "A page number exceeds the total number of pages in the PDF"
if lastPage = 0 then set lastPage to pdfPageCount
set pdfFolder to thePDF's URLByDeletingLastPathComponent
set pdfFileName to (thePDF's URLByDeletingPathExtension())'s lastPathComponent()
repeat with i from firstPage to lastPage
set aPage to (theDocument's pageAtIndex:(i - 1))
set pageSize to (aPage's boundsForBox:(current application's kPDFDisplayBoxMediaBox))
set pageWidth to current application's NSWidth(pageSize)
set pageHeight to current application's NSHeight(pageSize)
set pixelWidth to (pageWidth * theResolution / 72) div 1
set pixelHeight to (pageHeight * theResolution / 72) div 1
set theImageRep to (current application's NSPDFImageRep's imageRepWithData:(aPage's dataRepresentation()))
set newImageRep to (current application's NSBitmapImageRep's alloc()'s initWithBitmapDataPlanes:(missing value) pixelsWide:pixelWidth pixelsHigh:pixelHeight bitsPerSample:8 samplesPerPixel:4 hasAlpha:yes isPlanar:false colorSpaceName:(current application's NSDeviceRGBColorSpace) bytesPerRow:0 bitsPerPixel:32)
current application's NSGraphicsContext's saveGraphicsState()
set theContext to (current application's NSGraphicsContext's graphicsContextWithBitmapImageRep:newImageRep)
(current application's NSGraphicsContext's setCurrentContext:theContext)
(theContext's setShouldAntialias:false) -- change to suit
(theContext's setImageInterpolation:(current application's NSImageInterpolationHigh)) -- change to suit
(theImageRep's drawInRect:{origin:{x:0, y:0}, |size|:{width:pixelWidth, height:pixelHeight}} fromRect:(current application's NSZeroRect) operation:(current application's NSCompositeSourceOver) fraction:1.0 respectFlipped:false hints:(missing value))
current application's NSGraphicsContext's restoreGraphicsState()
--(current application's newImageRep's setSize:{pageWidth, pageHeight}) -- if desired
set theData to (newImageRep's representationUsingType:(current application's NSBitmapImageFileTypePNG) |properties|:(missing value))
set thePNG to ((pdfFolder's URLByAppendingPathComponent:pdfFileName)'s URLByAppendingPathExtension:"png")
(theData's writeToURL:thePNG atomically:true)
end repeat
end pdfToPng
Heres the pdf for testing
test.pdf (51.7 KB)
Try NSImageInterpolationNone
. I’m not entirely convinced that what you’re seeing is antialiasing.
The first is the imageRep created directly from the PDF, so an NSPDFImageRep
, and you have to draw from that into a new NSBitmapImageRep
if you want a bitmap.
Think of it as being a bit like text item delimiters. You’re temporarily taking over the drawing engine, so you store its state, change it and use it, then restore it to how you found it.
Here’s a screenshot showing aliasing
That’s actually the anti-aliased image.
Also, would this be relevant?
NSImageInterpolationNone no longer works in Big Sur
Turns out setImageInterpolation: gets ignored now, but CGContextSetInterpolationQuality() still works. My guess is that Apple changed the NS-level behavior because interpolation is so fast nowadays that it’s no longer really a performance optimization, which seems to be how they were thinking of it. But the CG-level behavior gives you what you ask for.
That sounds like the issue you’re seeing. I can’t see any obvious solution – you can’t use CGContextSetInterpolationQuality()
from ASObjC.
Sorry for the delayed response. Your explanation was perfect @Shane_Stanley comparing text item delimiters. I removed the line setImageInterpolation with no change. I see no difference in changing the line setShouldAntialias from false to true. Should the reference be ‘theContext’s’? I’m wondering if that’s the issue and if should be something else.
(theContext’s setShouldAntialias:false) – change to suit
@Mockman I am running Sonoma and changing the line setImageInterpolation definitely does not change anything. even from Low to High. Again, is it the reference to ‘theContext’s’?
It looks like the issue is an Apple bug, and there’s not really anything you can do about that.
Just confirming…the use of reference to variable ‘theContext’s’ is correct in those two lines and in the correct order of steps before I give up. Can you confirm?
I think it means that the command no longer does much of anything… which you’re experiencing.
It’s the other command that still does something —CGContextSetInterpolationQuality
but per Shane, isn’t available to use this way.
They look right to me.