Incorrect bit depth showing in output Tiff file generated using Ghostscript - ghostscript.net

I am using compression LZW and bit depth 1,8,12 & 24, but in the output file generated i am always getting bit depth 1.
If i am using bit depth 12 i should get 12 in output.
I am using compression mode -sDEVICE=tifflzw.
I also tried -sDEVICE=tiff12nc for 12bit,-sDEVICE=tiff24nc for 24bit,-sDEVICE=tiffgray for 8 bit and finally -sCompression=lzw as compression mode.
Now if i try for 8bit it is working, in output file i am getting 8 bit.
but if i use 12 bit , in output file it is 24 bit.
Ghostscript.NET version 1.1.8.0

Related

Setting JPG density (dpi) with no increase in file size

I use (under Windows) the following command
magick convert -units pixelsperinch file_in -density 600 file_out
to set the dpi (no resampling, as dpi basically is, as far as I understand, just a tag that specifies pixel size) of a JPG image. It works, but I don't understand why it increases file size by several kiloBytes (an image of mine originally of 1658 kB got to 1717 kB, which is a 59 kB increase), whereas I would expect an increase, if any, of just a few bytes.
Did I get something wrong? Is it possible to change by command line (tools other than ImageMagick are welcomed too) density/dpi of a JPG without increase in file size?
Thanks in advance for any clue.
You can change/set the density without re-encoding the file (and thereby possibly changing its size or quality) with the much smaller, lighter weight and easier-to-install exiftool which "just" a Perl script:
exiftool -jfif:Xresolution=300 -jfif:Yresolution=300 YourImage.jpg
Different people call different things the density/resolution, so if the above command doesn't do what you want/need/hope/expect, maybe try:
exiftool -XResolution=300 -YResolution=300 YourImage.jpg
Trying to reproduce your problem:
Gimp's interlaced/progressive JPEG is smaller than the non-interlaced version (also produced by Gimp)
The magick convert output JPEG is not interlaced, and is in fact a bit smaller than Gimp's own non-interlaced. That file is the same size whether it is produced from an interlaced or non-interlaced version.
So, I would think that you are converting an interlaced/progressive JPEG. Note that this also demonstrates that IM is re-encoding the file, and comparing the original and the re-encoded in Gimp shows significant differences.
In the JPEG format, the H/V definitions are encoded in 4 bytes in the header, patching that should be a SMOP in about any programming language.
Try using the online tool https://convert.town/image-dpi. On my JFIF jpg this only changed the DPI and did not resample the image. Other software suggestions can be found on this Super User question, but this was the only one that worked for me without changing anything else in the image.
However I only have a JFIF jpg and you appear to have an Adobe jpg from your other comments, so your mileage may vary.
I verified the DPI change and no resampling using the Windows hex editor HxD, just looking at the 4 bytes detailed in the Wikipedia article linked by xenoid. And once you know what bytes are changing, you can skip the website and use a hex editor directly to set the X and Y DPIs.
As far as If I understand, there are several flavors of JPEG files. The details needed to change DPI metadata of JFIF flavor are explained here. Based on that I wrote my own Python script which allows to change DPI setting of a JFIF flavor JPEG without reencoding:
import sys,os
filename = sys.argv[1]
x_density = int(sys.argv[2])
y_density = int(sys.argv[3])
echo = True
if len(sys.argv) > 4:
if sys.argv[4] == 'quiet':
echo = False
assert x_density > 0 and x_density < 65536
assert y_density > 0 and y_density < 65536
# JPEG markers
APP0 = bytes.fromhex('FFD8FFE0') # JFIF
APP1 = bytes.fromhex('FFD8FFE1') # EXIF
with open(filename, 'rb+') as f: # 'w+b'
chunk = f.read(4)
if chunk == APP0:
f.seek(2,1) # relative seek
chunk = f.read(5)
if chunk == bytes.fromhex('4A46494600'): # JFIF indentfier
f.seek(2,1) # relative seek
print('Setting density of ' + os.path.split(filename)[1] + ' to ' + str(x_density) + 'x' + str(y_density) + ' dpi.') if echo else None
f.write(bytes.fromhex('01'))
f.write(x_density.to_bytes(2,'big'))
f.write(y_density.to_bytes(2,'big'))
else:
print('File hasn''t got the JFIF indentifier, nothing was done.')
elif chunk == APP1:
f.close() # needed otherwise exiftool cannot operate on file
print('This is an EXIF-JPEG, using exiftool to set DPI...')
os.system('exiftool -P -overwrite_original -XResolution={} -YResolution={} "{}"'.format(x_density,y_density,filename))
else:
print('File is not JFIF nor EXIF, cannot set DPI, nothing was done.')
print('Done.') if echo else None
Usage:
python this_script.py some-image.jpg Xdpi Ydpi [quiet]
The script does not read the full image nor change the file length, it just modifies a few bytes directly on the JPEG file.
Moreover, no temporary/backup copy is made, because I wanted the script to work on hard-linked files, so the overall process is quite fast for JFIF JPEGs.
The script is able to identify EXIF JPEGs and use exiftool to change DPI. If you don't have exiftool installed in your computer remember to adjust the script accordingly. A reason to use this script even if you have exiftool installed is speed; in my test this script is much faster than exiftool.
JFIF and EXIF are the most common flavors of JPEG files, but I hope someone is able to improve this script or report a way to set DPI (without reencoding) also for Adobe JPEGs with APP14 marker, which are not so rare.

Faster way of getting number of key frames than "show_frames" in ffprobe?

I'm making a little in-house utility using ffmpg and ffprobe. Works fine and does what is needed: give a count of the number of key frames in a video file plus some other details.
Alas, with the large video files this will be used on it can take many seconds for show_frames to return – and I then have to parse the JSON dump of frame data and keep a running count of the total key frames.
Is there a faster way? Perhaps it is listed in the "stream" or "format" data dumps and I am not recognizing what it is being called? I've been through the ffmpg and ffprobe docs and didn't find anything else.
For MP4 and MOV files, you can get this info by reading the contents of the STSS box
You can use a tool like MP4parser, which will generate a log file with an entry like this:
/moov/trak/mdia/minf/stbl/stss # 0x1d7218e
Box size: 0x74 version: 0x0 flags: 0x0
entry_count: 0x19
sample_number:
0x1 0x86 0x180 0x27a ....
That entry count (in Hex) is the number you want.
Alternatively, atomicparsley will also tell you of the location of the STSS within the file and you can then read it directly.

Where is the endianness of the frame buffer device accounted for?

I'm working on a board with an at91 sama5d3 based device. In order to test the framebuffer, I redirected a raw data file to /dev/fb0. The file was generated using gimp and exported as a raw data file in the 'normal RGB' format. So as a serialised byte stream the data format in the file is RGBRGB (where each colour is 8 bits).
When copied to the framebuffer, the Red and the Blues were swapped as the LCD controller operates in little endian format when configured for 24 bpp mode.
This got me wondering, at what point is the endianness of the framebuffer taken into account? I'm planning on using directfb and had a look at some of the docs but didn't see anything directly alluding to the endianness of the pixel data.
I'm not familiar with how the kernel framebuffer works and so am missing a few pieces of the puzzle.

Performimg image processing and save image with same compression factor using matlab

I can read an Image's metadata and find the image quality with the following command in linux, which I think is from ImageMagick:
identify -verbose image.jpg
The output of this command is the following:
...
Iterations: 0
Compression: JPEG
**Quality: 96**
...
The important thing to me is to find which compression factor was used to generate the JPEG file. So, I have questions regarding these metadata:
1- Is the image quality the same as the JPEG compression factor used? if no, how can I find which compression factor was used to compress an JPEG image?
2- Can I do this with matlab?
In Matlab, you can get the value of the quality factor of an image file with imfinfo (see the example).
Edit: However, the Quality is given in the Comment field, which can be filled differently depending on the software(s) that processed / generated your image. A more reliable method for you would be to use your unix command. In Matlab, you can type:
[~,res] = unix('identify -verbose image.jpg');
and res will contain the output from the command line (the exact same than what you obtain with your unix shell). You can then display it or parse it, as you like.
Then, it is also possible to save an image array to a JPG file at a given quality after some processing, with the function imwrite. The command will look like:
imwrite(A,'myFile.jpg', 'Quality', 96);
You can also specify the CodingMethod and the CodingProcess.
So yes, it is possible !

Detecting .png alpha channel in Windows/D3D

I'm loading a texture from .png using D3DXCreateTextureFromFile(). How can my program know if the image file contains an alpha channel?
This isn't too hard to do by simply examining the file.
A PNG file consists of:
A file header
One or more 'chunks'
The file header is always 8 bytes and should be skipped over.
Each chunk begins with 4 bytes indicating its length, and 4 bytes indicating its type. The first chunk should always be 13 bytes and have the type IHDR. This contains the information about the image.
The tenth byte in the header contains the exact information you're looking for. It will be equal to 6 if the PNG file is RGBA.
More information can be found here.
Call IDirect3DTexture9::GetSurfaceLevel and then call IDirect3DSurface9::GetDesc. The D3DSURFACE_DESC.Format member will tell you.

Resources