How to calculate inverse of hard-light composite blend mode? - graphics

I have an 'old' RGBA canvas on the client and a newer version of the same image on the server. There are small visual differences between them.
I want to be able for the server to send to the client some 'diff' to be able to update it's image to match the new version, without having to send the whole image data again.
A two-frame transparent webm video would be ideal (ie. use webm to encode the differences), but hardware support for webm with transparency is abysmal, and browser support for extracting a specific frame from a video is also very poor.
Instead I am looking at using the hard light blend mode, which should allow me to send a single image to the client, and have any RGBA pixel converted to any other (with a margin of error of 1).
How should I generate the difference image though? Which combination of blend modes can generate diff if new = hardlight(old, diff)

Let Ch, Cw, Cd be the value you have, the value you want, and the diff value:
if (Cw > Ch)
Cd = 1 - (1-Cw)/2(1-Ch)
else if (Cw < Ch)
Cd = Cw/2Ch
else
Cd = 0.5

Related

How can I get the color of a pixel on screen with Node.js or C?

I am trying to get the color of a pixel on my screen using node.js. I want it to be returned in RGB format, e.g. (255, 0, 0). My current solution is to use screenshot-desktop to screenshot my entire screen in JPG format, decode it to get the raw pixel data, and get the color of a given pixel. However, this lags out my entire computer for 1-2 seconds as it is taking the screenshot. This is unusable as I would like to do this multiple times per second. So my question is: How can I get the color of a given pixel on the screen, without taking a full screenshot?
I am using Linux with X11. There is an X11 library for node.js, so I asssume I should use that to get the pixel color, I'm just not sure how. If you could show me how to do it in C then I can easily use node.js to do the same thing.
Thanks!
Oh my gosh I just figured it out after posting this. I was using robotjs for reading the mouse position and I totally forgot it can do screen stuff too! So, the solution would be to do
var robot = require('robotjs');
var color = robot.getPixelColor(x, y);
X11 solution using x11 node library ( I am the author ):
query windows tree with QueryTree starting at the root window
get every child geometry using GetGeometry request
if your point is not inside any child, use current window id and get 1x1 pixmap from the current image: GetImage(format, currentWindow, x, y, 1, 1, planeMask) ( 2 for format and 0xffffffff for plane mask should work ). Make sure you calculate relative x y position as you travers windows tree.
if child window covers your point query children for that window and repeat again. Note that QueryTree returns windows in bottom to top stacking order so make sure you pick last one covering your point
Once you have 1x1 pixmap from the topmost window under your point - the buffer should contain only color bytes for your image, RGB order and bit mask might depend on red_mask, green_mask, blue_mask from display.screen[0].depths[visual].
If you cache "topmost window" between requests and only start from root when no match anymore the above solution might be much more performant then the one using robotjs ( although much more low level and complicated ) Good luck!

Ghostscript : Crop Certain Area?

I am new to ghostscript.
I have a pdf which contains a card. i want to crop that card out.
Currently with the understanding of document i am only able to convert the pdf to image but have no luck in cropping.
Saw every other related question but there are not working for me.
This is code i used in batch file for converting the pdf to image:
"C:\Program Files\gs\gs9.50\bin\gswin64c.exe" -sDEVICE=png16m -r300 -o c:\users\jen\desktop\pdf.png -f "c:\users\jen\desktop\pdf.pdf
pause
now i don't know how to crop with it too ?
i want to crop at certain postition like: Left:28 Top:524 Width:492.3 Height:161
EDIT
I will be using this in firebase functions.
Example PDF file THE_PDF_TO_CROP. I want to cutout the blue area of pdf to image.
You need to set several parameters; Firstly you need to specify the width and height of the output bitmap. You can use either -dDEVICEHEIGHTPOINTS and -dDEVICEWIDTHPOINTS, or alternatively you can specify the output size in pixels using -g<x>x<y> where and are the number of pixels in the x and y directions. Obviously that will vary depending on the resolution. You can't (obviously) use fractional pixels.
If you use -dDEVICEWIDTHPOINTS and -dDEVICEHEIGHTPOINTS then you also need to set -dFIXEDMEDIA to tell the interpreter not to use the media size from the PDF file instead.
So that shoould create an output bitmap of the correct size. If you try rendering your file using just that, you will see that it renders just a portion of the page from the bottom left. So now you need to shift the content around so that the portion you want lies at the bottom left of the media. You can do that by using the PageOffset PostScript operator.
You haven't given any numbers, nor supplied an example file, so lets say (for the sake of example) that you want to render a 1 inch by 2 inch portion of the document. Lets further say that you the part you want rendered starts 2.5 inches from the left edge, and 1.5 inches from the bottom edge.
A suitable command line would be:
gs -sDEVICEWIDTHPOINTS=72 -dDEVICEHEIGHTPOINTS=144 -dFIXEDMEDIA -r300 -sDEVICE=png16m -o out.png -c "<</PageOffset [-180 -108]>> setpagedevice" -f input.pdf
Note that PDF (and PostScript) units are 1/72 inch so 72 = 1 inch, 144 = 2 inches. You need to shift the origin of the page down and left, which is why the values for PageOffset are negative.
If that doesn't work for you I'll need to see your PDF file and you'll need to tell me which version of Ghostscript you are using.

How to change a part of the color of the background, which is black, to white?

I have been working on PyTesseract OCR and converting PDF to JPEG inorder to OCR the image. A part of the image has a black background and white text, which Tesseract is unable to identify, whereas all other parts of my image are being read perfectly well. Is there a way to change a part of the image that has black background? I tried a few SO resources, but doesn't seem to help.
I am using Python 3, Open CV version 4 and PyTesseract
opencv has a bitwise not function wich correctly reverses the image
you can put a mask / freeze on the rest of the image (the part that is correct already) and use something like this:
imageWithMask = cv2.bitwise_not(imageWithMask)
alternatively you can also perform the operation on a copy of the image and only copy over parts / pixels / regions you need....

Extracting Text from a PDF file with embedded font

I have a PDF file containing some tabular data.
http://dl.dropbox.com/u/44235928/sample_rotate-0.pdf
I have to extract the tabular data from it. I have tried following with no success :
Select the text and paste it to notepad/excel-sheet. (I am getting junk characters)
Used save as text from Acrobat Reader. It is also giving junk characters and not the actual text.
Tried ApachePDFBox command line utility to extract text from PDF. It is also giving junk characters instead of real texts.
Finally I am trying a OCR solution. I am converting the pdf file into .tif images using ImageMagick and getting those images processed by tesseract OCR.
The OCR solution is not very accurate though( about 80% words matched ).
I tried changing density and geometry of the image created from PDF to get better results from tesseract OCR.
convert -rotate 90 -geometry 10000 -depth 8 -density 800 sample.pdf img_800_10000.tif;
tesseract img_800_10000.tif img_800_10000.tif nobatch letters;
I am not sure for what kind of image( density, geometry, monochromatic, sharpen boundary etc) would be best suited for the OCR.
Please suggest what could be the best possible parameters(density,geometry,depth etc) for generating images from a PDF file, so that the tesseract accuracy will increase.
I am open to other( non-ocr ) solutions as well.
In this case I recommend to NOT use ImageMagick for the PDF -> TIFF conversion. Instead, use Ghostscript. Two reasons:
Using Ghostscript directly will give you more control over individual parameters of the conversion.
ImageMagick cannot do that particular conversion itself -- it will call Ghostscript as its 'delegate' anyway, but will not allow you to give all the same fine-grained control that your own Ghostscript command will give you.
Most of the text in the table of your sample PDF is extremely small (I guess, only 4 or 5 pt high). This makes it rather difficult to run a successful OCR unless you increase the resolution considerably.
Ghostscript uses -r72 by default for image format output (such as TIFF). Tesseract works best with r=300 or r=400 -- but only for a font size from 10-12 pt or higher. Therefor, to compensate for the small text size you should make Ghostscript using a resolution of at least 1200 DPI when it renders the PDF to the image.
Also, you'll have to rotate the image so the text displays in the normal reading direction (not bottom -> top).
This is the command which I would try first:
gs \
-o sample.tif \
-sDEVICE=tiffg4 \
-r1200 \
-dAutoRotatePages=/PageByPage \
sample_rotate-0.pdf
You may need to play with variations of the -r1200 parameter (higher or lower) for best results.
Since a comment asked "How to define the geometry of an image when using Ghostscript as we do in convert?", here is an answer:
It does not make sense to define geometry (that is image dimensions) and resolution for a raster image created by Ghostscript at the same time.
Once you convert a vector based page of a given dimension (such as PDF) into a raster image (such as the TIFF G4 format) giving a desired resolution (as done in the other answer), you already indirectly and implicitly also did set the dimension:
The original PDF dimension of your sample file sample_rotate-0.pdf is 1008x612 points.
At a resolution of 72 DPI (the default Ghostscript uses if not given directly, or -r72 in the Ghostscript command if given directly) the image dimensions will be 1008x612 pixels.
At a resolution of 720 DPI (-r720 in the Ghostscript command) the image dimensions will be 10080x6120 pixels.
At a resolution of 1440 DPI (-r1440 in the Ghostscript command of my other answer) the image dimensions will be 20160x12240 pixels.
At a resolution of 1200 DPI (-r1200 in the Ghostscript command) the image dimensions will be 16800x10200 pixels.
At resolution of 1000 DPI (-r1000 in the Ghostscript command) the image dimensions will be 14000x8500 pixels.
At a resolution of 120 DPI (-r120 in the Ghostscript command) the image dimensions will be 1680x1020 pixels.
At resolution of 100 DPI (-r100 in the Ghostscript command) the image dimensions will be 1400x850 pixels.
If you absolutely insist to specify the dimension/geometry for the output image on the Ghostscript commandline (rather than the resolution), you can do so by adding -gNNNNxMMMM -dPDFFitPage to the commandline.
There you can find decoded content of your file: https://docs.google.com/open?id=0B1YEM-11PerqSHpnb1RQcnJ4cFk
A absolutely sure the OCR is the best way to read pdf file, but you can try REGEX-ing the native content. It going to be be the hard and long way.

Do FrontBuffer have alpha value?

I was trying to save a .tga image using GetFrontBufferData method,but alpha value is lost.They are totally one.I could get right alpha value from RenderTarget or BackBuffer,but not rgb value is not correct.Even the scene present to show immediately,backbuffer still seems darker than frontbuffer.
Now I get 2 questions:
Q1:Do FrontBuffer have alpha value?
Q2:What is the difference between the data of back buffer and front buffer when you try to render transparent things?
When you render a transparent object, its alpha value is used to perform alpha blending. Once the blending is completed, new value is written to the back buffer. If you want to preserve the alpha value, the format of the back buffer should be D3DFMT_A8R8G8B8. You should also remember about clearing the alpha channel while calling IDirect3DDevice9::Clear(). Once the rendering is completed, the back buffer and the front buffer pointers are simply flipped (read more). Thus, both buffers have the same format (so if you created the back buffer with RGBA format, the front buffer would also be RGBA). By the way, you can get the back buffer and lock it instead of getting the front buffer.
By default, alpha blending performs the same operations on R, G, B and A channels, but you can specify a separate operation for the alpha channel only - see this.

Resources