https://rubysash.com/programming/wordpress/optipng-vs-pngcrush-vs-gimp-to-reduce-png-size/ Ruby Sash Consulting AppSec, NetSec, DevOps, Social Engineering, Cloud, Forensics, Programming, SysAdmin Notes * Programming + Perl + Python + Visual Basic + WordPress * Firewalls + Check Point + UFW * Operating Systems + Linux + Windows * Pen Test + OWASP + Scanning & Enumeration + Security Tools * VmWare * Cloud + GCP + AWS + Azure * SIEM/MSSP * DLP * About + Contact + IT Security SIC Codes + Privacy Policy + Sitemap shrink Linux Wordpress 'optiPNG' vs 'PNGcrush' vs 'Gimp' to Reduce PNG Size October 13, 2020October 13, 2020 Dave 0 Comments automation, bash Which is better? NEITHER! optipng and pngcrush are dated tools, but they are free, and surprisingly still work. Here are some comparisons on compression levels on a PNG file vs the same file as JPG format. Page load speed is important as a ranking factor in search engines. It makes sense therefore, to optimize your page for speed. While a CDN is probably the better solution, it doesn't hurt to ALSO optimize your png files. I was using cygwin and noticed a few tools related to optimizing png files, and how reducing png size: * optipng * pngcrush I'm used to using other tools such as gimp and ifranview to reduce png size before but thought these tools were worth investigating at least. TLDR (Not suprisingly) jpg was a better format for web work but I liked optipng better if I had to choose between pngcrush and optipng. Both beat out gimp, unless I used indexed colors, which only work on specific types of images. Gimp > Export > rename as .jpg, save! Lossy vs Lossless JPG is "lossy" meaning, it compresses the data in a way where some of the original data is gone and can never be retrieved. PNG is "lossless" meaning, you can save (nearly) all of the original data. Transparency No such thing as a transparent background in jpgs, but PNGs can preserve this layer. OptiPNG Results Opti PNG shows me "as-it-happens" as it tries different filters and optimization methods. I liked this. I also like the display of optipng example command Shell [$ optipng -o7 -keep ] 1 $ optipng -o7 -keep pngtest.png optipng example output Shell [** Processing: pngte] 1 ** Processing: pngtest.png 2 500x515 pixels, 4x8 bits/pixel, RGB+alpha 3 Reducing image to 3x8 bits/pixel, RGB 4 Input IDAT size = 306918 bytes 5 Input file size = 307419 bytes 6 7 Trying: 8 zc = 9 zm = 9 zs = 0 f = 1 IDAT size = 287339 9 zc = 9 zm = 9 zs = 0 f = 2 IDAT size = 283790 10 zc = 9 zm = 9 zs = 0 f = 3 IDAT size = 276206 11 zc = 9 zm = 9 zs = 0 f = 4 IDAT size = 274093 12 zc = 9 zm = 9 zs = 0 f = 5 IDAT size = 273103 13 14 Selecting parameters: 15 zc = 9 zm = 9 zs = 0 f = 5 IDAT size = 273103 16 17 Output IDAT size = 273103 bytes (33815 bytes decrease) 18 Output file size = 273160 bytes (34259 bytes = 11.14% decrease) PNGcrush results PNG crush doesn't give me as much info but it does tell me CPU time, which is nice. pngcrush example Shell [$ pngcrush -brute pn] 1 $ pngcrush -brute pngtest.original.png pngcrush output Shell [ Recompressing IDAT] Recompressing IDAT chunks in pngtest.original.png to pngout.png 1 Total length of data found in critical chunks = 2 307419 3 Best pngcrush method = 118 (ws 15 fm 5 zl 9 zs 0) = 4 273160 CPU time decode 1.205000, encode 4.921000, other 0.246000, total 6.718000 sec Smallest PNG Size Results? original png info Shell [$ file pngtest.origi] 1 $ file pngtest.original.png file output Shell [pngtest.original.png] 1 pngtest.original.png: PNG image data, 500 x 515, 8-bit/color RGBA, non-interlaced It is entirely possible that there are different results based on file size, image type, image complexity etc. I didn't test thoroughly and just picked an image instead. Original PNG (301k) Original File Indexed PNG (61k) Indexed Optimized PNG (267k) optimized PNG JPG (71k) To be fair though, jpg is lossy, and others are not (with the obvious exception of indexed). jpg Batch Processing This wouldn't even be worth talking about without a way to automate it right? Who wants to manually process 3,142 png files? original files Shell [$ ls -alFh ] 1 $ ls -alFh list files in directory Shell [-rwxrwx---+ 1 david ] -rwxrwx---+ 1 david None 92K Sep 7 10:14 1-barrel-sandponics.png* 1 -rwxrwx---+ 1 david None 196K Sep 7 10:15 1-barrel-sandponics2.png 2 * 3 -rwxrwx---+ 1 david None 116K Sep 7 10:16 1-barrel-sandponics-back 4 .png* -rwxrwx---+ 1 david None 101K Sep 7 10:15 1-barrel-sandponics- bottom.png* For Loop in Shell Process all png files using optipng and keep backups. The for loop in the shell uses the f variable to replace the file names on each loop: bash for loop command Shell [$ for f in *.png; do] 1 $ for f in *.png; do optipng -keep -o7 $f;done for loop results Shell [** Processing: 1-bar] 1 ** Processing: 1-barrel-sandponics.png 2 321x573 pixels, 4x8 bits/pixel, RGB+alpha 3 Reducing image to 3x8 bits/pixel, RGB 4 Input IDAT size = 93262 bytes 5 Input file size = 93381 bytes 6 7 Trying: 8 zc = 9 zm = 9 zs = 0 f = 0 IDAT size = 78323 9 zc = 9 zm = 8 zs = 0 f = 0 IDAT size = 78238 10 zc = 9 zm = 9 zs = 0 f = 4 IDAT size = 75392 11 zc = 9 zm = 9 zs = 0 f = 5 IDAT size = 74314 12 13 Selecting parameters: 14 zc = 9 zm = 9 zs = 0 f = 5 IDAT size = 74314 15 16 Output IDAT size = 74314 bytes (18948 bytes decrease) 17 Output file size = 74421 bytes (18960 bytes = 20.30% decrease) 18 19 ** Processing: 1-barrel-sandponics2.png 20 363x747 pixels, 4x8 bits/pixel, RGB+alpha 21 Reducing image to 3x8 bits/pixel, RGB 22 Input IDAT size = 200112 bytes 23 Input file size = 200255 bytes 24 25 Trying: 26 zc = 9 zm = 9 zs = 0 f = 0 IDAT size = 172896 27 zc = 9 zm = 8 zs = 0 f = 0 IDAT size = 171951 28 zc = 9 zm = 9 zs = 0 f = 4 IDAT size = 170537 29 zc = 9 zm = 8 zs = 0 f = 4 IDAT size = 170046 30 zc = 9 zm = 8 zs = 0 f = 5 IDAT size = 169767 31 32 Selecting parameters: 33 zc = 9 zm = 8 zs = 0 f = 5 IDAT size = 169767 34 35 Output IDAT size = 169767 bytes (30345 bytes decrease) 36 Output file size = 169874 bytes (30381 bytes = 15.17% decrease) 37 38 ** Processing: 1-barrel-sandponics-back.png 39 353x545 pixels, 4x8 bits/pixel, RGB+alpha 40 Reducing image to 3x8 bits/pixel, RGB 41 Input IDAT size = 117985 bytes 42 Input file size = 118104 bytes 43 44 Trying: 45 zc = 9 zm = 9 zs = 0 f = 0 IDAT size = 104402 46 zc = 9 zm = 8 zs = 0 f = 0 IDAT size = 104205 47 48 Selecting parameters: 49 zc = 9 zm = 8 zs = 0 f = 0 IDAT size = 104205 50 51 Output IDAT size = 104205 bytes (13780 bytes decrease) 52 Output file size = 104312 bytes (13792 bytes = 11.68% decrease) 53 54 ** Processing: 1-barrel-sandponics-bottom.png 55 393x409 pixels, 4x8 bits/pixel, RGB+alpha 56 Reducing image to 3x8 bits/pixel, RGB 57 Input IDAT size = 102431 bytes 58 Input file size = 102550 bytes 59 60 Trying: 61 zc = 9 zm = 9 zs = 0 f = 0 IDAT size = 89245 62 63 Selecting parameters: 64 zc = 9 zm = 9 zs = 0 f = 0 IDAT size = 89245 65 66 Output IDAT size = 89245 bytes (13186 bytes decrease) 67 Output file size = 89352 bytes (13198 bytes = 12.87% decrease) After the loop does it's thing, you have results of the original copied to a .bak file and the new file available for you: original + new files Shell [-rw-rw-r--+ 1 david ] -rw-rw-r--+ 1 david None 73K Oct 13 18:11 1-barrel-sandponics.png -rwxrwx---+ 1 david None 92K Sep 7 10:14 1-barrel-sandponics.png .bak* 1 -rw-rw-r--+ 1 david None 166K Oct 13 18:11 1-barrel-sandponics2.png 2 -rwxrwx---+ 1 david None 196K Sep 7 10:15 1-barrel-sandponics2.png 3 .bak* 4 -rw-rw-r--+ 1 david None 102K Oct 13 18:12 1-barrel-sandponics-back 5 .png 6 -rwxrwx---+ 1 david None 116K Sep 7 10:16 1-barrel-sandponics-back 7 .png.bak* 8 -rw-rw-r--+ 1 david None 88K Oct 13 18:12 1-barrel-sandponics- bottom.png -rwxrwx---+ 1 david None 101K Sep 7 10:15 1-barrel-sandponics- bottom.png.bak* * - cygwin ssh-agent and ssh-add Automated Passwords * Setup rsyslog Client Forwarder on Raspberry Pi - Leave a Reply Cancel reply Your email address will not be published. Required fields are marked * [ ] [ ] [ ] [ ] [ ] [ ] [ ] Comment * [ ] Name * [ ] Email * [ ] Website [ ] [Post Comment] [ ] [ ] [ ] [ ] [ ] [ ] [ ] D[ ] This site uses Akismet to reduce spam. Learn how your comment data is processed. Sitting All Day? Fix Hip Flexors Free Book of DIY Games Free Games Book Tags Apache automation bash Check Point coding crontab CSS CSV data mining devnull DNS encoding encryption Featured Image firewall forensics games git hexdump http linux load balancer lwp mechanize pentest Perl programming proxy python scheduling scrape screen scripting shell SIC ssh svg sysadmin thunderbird tools troubleshooting ufw utf-8 windows Wordpress Recent Posts * Use SSH Keys with Git * Check Open Ports with Powershell * Setup rsyslog Client Forwarder on Raspberry Pi * 'optiPNG' vs 'PNGcrush' vs 'Gimp' to Reduce PNG Size * cygwin ssh-agent and ssh-add Automated Passwords * Basic Git Tutorial Crash Course * Setup DVWA to Practice Application Security Pentesting * How to Setup LAMP Stack Ubuntu 18.04 LTS * How to Set Up Free Amazon VPS (EC2) * Basic tkinter usage for Python 3 [ ] For I am not ashamed of the gospel, for it is the power of God for salvation to everyone who believes. - Romans 1:16 Do you see a man skillful in his work? He will stand before kings; he will not stand before obscure men. - Proverbs 22:29 Whatever you do, work heartily, as for the Lord and not for men.. - Colossians 3:23 One who is faithful in a very little is also faithful in much, and one who is dishonest in a very little is also dishonest in much. - Luke 16:10 Copyright (c) 2019 Ruby Sash Consulting.