Dalelorenzo's GDI Blog

Image To Text Conversion With React And Tesseract.js (OCR)

Data is the backbone of every software application because the main purpose of an application is to solve human problems. To solve human difficulties, it is necessary to have some information about them.

Such information is represented as data, especially through computation. On the web, data is chiefly collected in the form of texts, epitomes, videos, and many more. Sometimes, personas contain all-important verses that are means to managed to achieve a certain purpose. These images were mostly managed manually because there was no way to process them programmatically.

The inability to extract text from idols was a data processing limitation I knowledge first-hand at my last companionship. We needed to process scanned knack placards and we had to do it manually since we couldn’t extract text from images.

There was a department called “Operations” within the company that was responsible for manual confirming talent posters and ascribing users' notes. Although we had a website through which consumers connected with us, the processing of talent placards was be carried forward manually behind the scenes.

At the time, our website was built chiefly with PHP( Laravel) for the backend and JavaScript( jQuery and Vue) for the frontend. Our technological stack was good enough to work with Tesseract.js the issue was considered important by the management.

I was willing to solve the problem but it was not necessary to solve the problem gues from the business’ or the management’s point of view. After leaving the company, I decided to do some research and try to find possible solutions. Eventually, I detected OCR.

What Is OCR?

OCR stands for “Optical Character Recognition” or “Optical Character Reader”. It is used to extract texts from images.

The Evolution Of OCR can be traced to various abilities but Optophone, “Gismo”, CCD flatbed scanner, Newton MesssagePad and Tesseract are the major inventions that go person recognition to a different level of usefulness.

So, why abuse OCR? Well, Optical Character Recognition solves a great deal of questions, one of which triggered me to write this article. I realized the ability to extract texts from an portrait ensures a lot of possibilities such as 😛 TAGEND

RegulationEvery formation needs to regulate users' tasks for some reasons. The regulation might be used to protect users’ rights and secure them from menaces or scams.Extracting texts from an persona enables an organization to process textual informed about an persona for regulation, peculiarly when the personas are provided for by some of the users.For sample, Facebook-like regulation of the number of texts on portraits used to support ads can be achieved with OCR. Likewise, obstructing sensitive material on Twitter is also made possible by OCR. SearchabilitySearching is one of the most common undertakings, especially on the internet. Searching algorithms are mostly based on manipulating texts. With Optical Character Recognition, it is possible to recognize people on epitomes and use them to provide relevant image causes to users. In short, portraits and videos are now searchable with the aid of OCR. AccessibilityHaving textbooks on epitomes has always been a challenge for accessibility and it is the rule of thumb to have few textbooks on an epitome. With OCR, screen books can providing access to textbooks on portraits to provide some required know-how to its customers. Data Processing Automation The processing of data is mostly automated for magnitude. Having textbooks on idols is a limitation to data processing because the texts cannot be handled except manually. Optical Character Recognition( OCR) fixes it is feasible to remove verses on epitomes programmatically thereby, ensuring data processing automation peculiarly when it has to do with the processing of verses on idols. Digitization Of Printed MaterialsEverything is going digital and there are still a lot of documents to be digitized. Cheques, credentials, and other physical records been in a position to be digitized with the use of Optical Character Recognition.

Finding out all the uses above increased my interests, so I decided to go further by querying a few questions 😛 TAGEND “How can I use OCR on the web, especially in a React application? ”

That question headed me to Tesseract.js.

What Is Tesseract.js?

[ Tesseract.js is a JavaScript library that gathers the original Tesseract from C to JavaScript WebAssembly thereby making OCR accessible in the browser. Tesseract.js engine was initially written in ASM.js and it was later ported to WebAssembly but ASM.js still helps as a backup in some cases when WebAssembly is not subsidized.

As territory on the website of Tesseract.js, it subscribes more than 100 usages, automatic verse orientation and write detection, a simple interface for see clauses, words and character bounce boxes.

Tesseract is an visual character recognition machine for many operating system. It is free software, released under the Apache Licence. Hewlett-Packard developed Tesseract as proprietary software in the 1980 s. It was secreted as open source in 2005 and its development has been sponsored by Google since 2006.

The recent account, copy 4, of Tesseract was released in October 2018 and it contains a brand-new OCR engine that uses a neural network method based on Long Short-Term Memory( LSTM) and it is meant to produce more accurate results.

Understanding Tesseract APIs

To genuinely understand how Tesseract labors, we need to break down some of its APIs and their constituents. According to the Tesseract.js documentation, there are two ways to approach apply it. Below is the first approach an its break down 😛 TAGEND Tesseract.recognize( persona, language,

logger: m => console.log( m)

). catch( deviate =>

console.error( deviate ); ). then( ensue =>

console.log( develop ); )}

The recognize method takes portrait as its firstly argument, communication( which can be multiple) as its second argument and logger: m => console.log( me) as its last-place contention. The persona format supported by Tesseract are jpg, png, bmp and pbm which can only ensure the availability as factors( img, video or canvas ), folder objective (< input >), blob object, footpath or URL to an image and base6 4 encoded portrait.( Read now for more information about all of the persona formats Tesseract can handle .)

Language is given as a string such as eng. The+ signaling could be used to concatenate several languages as in eng+ chi_tra. The speech statement is used to determine the studied usage data to be used in processing of images.

Note: You’ll find all of the available expressions and their codes over here.

logger: m => console.log( m) is very useful to get information about the progress of an persona being processed. The logger asset takes a function that will be called multiple times as Tesseract process an persona. The constant to the logger function should be an object with workerId, jobId, status and progress as its assets:

workerId:' worker-2 00030 ’, jobId:' job-7 34747 ’, status:' spot text’, progress:' 0.9 ’

progress is a number between 0 and 1, and it is in percentage to show the progress of an epitome approval process.

Tesseract automatically generates the object as a parameter to the logger function but it can also be supplied manually. As a recognition process is taking place, the logger objective qualities are modernized each time the role is called. So, it can be used to show a alteration progress saloon, vary some one of the purposes of an lotion, or used to achieve any hoped outcome.

The result in the code above was a result of the likenes acknowledgment process. Each of the owneds of cause has the dimension bbox as the x/ y coordinates of their border box.

Here are the assets of the result object, their entails or calls:

textbook: "I am codingnninja from Nigeria..."

hocr: "

import createWorker from 'tesseract.js';

const craftsman= createWorker (

logger: m => console.log( m)


( async() =>

await worker.load ();

await worker.loadLanguage( 'eng' );

await worker.initialize( 'eng' );

const data: verse= await worker.recognize( 'https :// tesseract.projectnaptha.com/ img/ eng_bw.png' );

console.log( verse );

await worker.terminate (); )();

This approach is related to the first approaching but with different implementations.

createWorker( options) originates a web proletarian or node child process that creates a Tesseract worker. The laborer facilitates set up the Tesseract OCR engine. The onu() technique quantities the Tesseract core-scripts, loadLanguage() onus any language supplied to it as a fibre, initialize() forms sure Tesseract is fully ready for use and then the recognize technique is used to process the image accommodated. The complete() approach stops the worker and scavenges up everything.

Note: Please check Tesseract APIs documentation for more information.

Now, we have to build something to really see how effective Tesseract.js is.

What Are We Going To Build?

We are going to build a gift card PIN extractor because removing PIN from a offering card was the issue that led to this writing adventure in the first place.

We will build a simple application that removes the PIN from a scanned talent card. As I set out to build a simple gift card pin extractor, I will go you through some of the challenges I faced along the line, the solutions I required, and my conclusion based on my experience.

Go to source system -

Below is the image we are going to use for testing because it has some realistic qualities that are possible in the real world.

We will extract AQUX-QWMB6L-R 6JAU from the card. So, let’s get started.

Station Of React And Tesseract

There is a question to attend to before installing React and Tesseract.js and the issues to is, why exploiting React with Tesseract? Practically, we can use Tesseract with Vanilla JavaScript, any JavaScript libraries or frameworks such React, Vue and Angular.

Using React in this case is a personal preference. Initially, I wanted to use Vue but I decided to go with React because I am more familiar with React than Vue.

Now, let’s continue with the installations.

To install React with create-react-app, you have to run the system below 😛 TAGEND npx create-react-app image-to-text cd image-to-text yarn computed Tesseract.js


npm install tesseract.js

I decided to go with yarn to install Tesseract.js because I was unable to install Tesseract with npm but yarn got the job done without stress. You can use npm but I recommend positioning Tesseract with yarn judge from my experience.

Now, let’s start our development server by running the code below 😛 TAGEND yarn start


npm start

After running yarn start or npm start, your default browser should open a webpage that looks like below 😛 TAGEND

You could also navigate to localhost: 3000 in the browser equipped the page is not launched automatically.

After installing React and Tesseract.js, what next?

Setting Up An Upload Form

In this case, we are going to adjust the home page( App.js) we are only viewed in the browser to contain the form we need 😛 TAGEND

importation useState, useRef from 'react'; import Tesseract from 'tesseract.js'; import ' ./ App.css';

purpose App()

const[ imagePath, setImagePath]= useState( "" );

const[ verse, setText]= useState( "" );

const handleChange=( episode) =>

setImage( URL.createObjectURL( event.target.files[ 0 ]));


Actual image uploaded


Extracted text


); export default App

The part of the code above that it was necessary to our scrutiny at this point is the function handleChange.

const handleChange=( happening) =>

setImage( URL.createObjectURL( event.target.files[ 0 ]));

In the role, URL.createObjectURL takes a selected file through event.target.files[ 0] and forms a remark URL that can be used with HTML labels such as img, audio and video. We squandered setImagePath to add the URL to the state. Now, the URL can now be accessed with imagePath.


We set the image’s src attribute to imagePath to preview it in the browser before processing it.

Converting Selected Images To Texts

As we have grabbed the path to the image selected, we can pass the image’s path to Tesseract.js to extract verses from it.

import useState from 'react'; import Tesseract from 'tesseract.js'; import ' ./ App.css';

capacity App()

const[ imagePath, setImagePath]= useState( "" );

const[ verse, setText]= useState( "" );

const handleChange=( incident) =>

setImagePath( URL.createObjectURL( event.target.files[ 0 ]));

const handleClick=() =>


imagePath, 'eng',

logger: m => console.log( m)


. catch( deviate =>

console.error( deviate );


. then( develop =>

// Get Confidence score

give confidence= result.confidence

let verse= result.text

setText( textbook );



Actual imagePath uploaded


Extracted text


); export default App

We add the part “handleClick” to “App.js and it contains Tesseract.js API that makes the path to the selected epitome. Tesseract.js makes “imagePath”, “language”, “a specify object”.

The button below is added to the form to call “handClick” which initiations image-to-text conversion whenever the button is clicked.

When the processing is successful, we retrieve both “confidence” and “text” from the research results. Then, we supplement “text” to the state with “setText( text) ”.

By adding to


, we expose the removed text.

It has become clear that “text” is extracted from the epitome but what is confidence?

Confidence shows how accurate the transition is. The confidence elevation is between 1 to 100. 1 stands for the worst while 100 stands for the best in terms of accuracy. It can also be used to determine whether an extracted verse should be accepted as accurate or not.

Then the question is what ingredients can affect the confidence orchestrate or the accuracy of the entire conversion? It is largely affected by three major factors -- a better quality and sort of such documents squandered, the quality of the scan created from the above-mentioned documents and the processing cleverness of the Tesseract engine.

Now, let’s lent the system below to “App.css” to style the application a bit.


text-align: midst;. App-image

extent: 60 vmin;

pointer-events: nothing;. App-main

background-color: #282c34;

min-height: 100 vh;

parade: flex;

flex-direction: piece;

align-items: centre;

justify-content: hub;

font-size: calc( 7px+ 2vmin );

dye: grey;. text-box

background: #fff;

colour: #333;

border-radius: 5px;

text-align: centre;

Here is the result of my first evaluation 😛 TAGEND Sequel In Firefox

The confidence level of the result above is 64. It is worth noting that the endow card likenes is dark in color and it surely changes the result we get.

If you take a closer look at the epitome above, you will see the pin from the card is almost accurate in the removed text. It is not accurate because the gift poster is not really clear.

Oh, wait! What the hell is it was like in Chrome?

Outcome In Chrome

Ah! The sequel is even worse in Chrome. But why is the outcome in Chrome different from Mozilla Firefox? Different browsers treat portraits and their colouring sketches differently. That conveys, an idol can be yielded differently will vary depending on the browser. By supplying pre-rendered image.data to Tesseract, it is likely to produce a different outcome in different browsers because different image.data is supplied to Tesseract depending on the browser in use. Preprocessing an image, as we will see later in this article, will help achieve a consistent result.

We need to be more accurate so that we can be sure we are getting or yielding the correct information. So there is a requirement to take it a little further.

Let’s try more to see if we can achieve the aim in the end.

Testing For Accuracy

There are a lot of factors that affect an image-to-text conversion with Tesseract.js. Most of these factors revolve around the nature of the persona we want to process and the rest depends on how the Tesseract engine administers the conversion.

Internally, Tesseract preprocesses likeness before the actual OCR conversion but it doesn’t ever grant accurate reactions.

As a mixture, we can preprocess likeness to achieve accurate shifts. We can binarise, change, dilate, deskew or rescale an portrait to preprocess it for Tesseract.js.

Image pre-processing is a lot of work or an extensive arena on its own. Fortunately, P5. js has provided all the image preprocessing techniques we want to use. Instead of reinventing the pedal or utilizing the whole of the library merely because we want to use a minuscule part of it, I have replica the ones we need. All the likenes preprocessing proficiencies are included in preprocess.js.

What Is Binarization?

Binarization is the conversion of the pixels of an image to either pitch-black or lily-white. We just wanted to binarize the previous gift placard to check whether the accuracy will be better or not.

Previously, we obtained some textbooks from a offering card but the target PIN was not as accurate as we wanted. So there is a need to find another way to get an accurate result.

Now, we want to binarize the offering placard, i.e. we want to convert its pixels to black and white so that we can see whether a better statu of accuracy can be achieved or not.

The functions below will be used for binarization and it is included in a separate file announced preprocess.js.

gathering preprocessImage( canvas)

const ctx= canvas.getContext( '2d' );

const epitome= ctx.getImageData( 0,0, canvas.width, canvas.height );

thresholdFilter( image.data, 0.5 );

return image;

Export default preprocessImage

What does the code above time?

We introduce canvas to hold an persona data to apply some filters, to pre-process the image, before deliver it to Tesseract for conversion.

The first preprocessImage function is located in preprocess.js and organizes the canvas for help by getting its pixels. The role thresholdFilter binarizes the persona by converting its pixels to either pitch-black or grey.

Let’s call preprocessImage to see if the verse extracted from the previous talent card can be more accurate.

By the time we revise App.js, it is desirable to now was like the system this 😛 TAGEND

importation useState, useRef from 'react'; import preprocessImage from ' ./ preprocess'; import Tesseract from 'tesseract.js'; import ' ./ App.css';

run App()

const[ likenes, setImage]= useState( "" );

const[ textbook, setText]= useState( "" );

const canvasRef= useRef( null );

const imageRef= useRef( null );

const handleChange=( contest) =>

setImage( URL.createObjectURL( event.target.files[ 0 ]))

const handleClick=() =>

const canvas= canvasRef.current;

const ctx= canvas.getContext( '2d' );

ctx.drawImage( imageRef.current, 0, 0 );

ctx.putImageData( preprocessImage( canvas ), 0,0 );

const dataUrl= canvas.toDataURL( "image/ jpeg" );


dataUrl, 'eng',

logger: m => console.log( m)


. catch( err =>

console.error( stumble );


. then( reaction =>

// Get Confidence score

cause confidence= result.confidence

console.log( confidence)

// Get full output

let text= result.text

setText( textbook );



Actual image uploaded



Extracted text


); export default App

First, we have to import “preprocessImage” from “preprocess.js” with the system below 😛 TAGEND import preprocessImage from ' ./ preprocess';

Then, we contribute a canvas label to the form. We positioned the ref dimension of both the canvas and the img calls to canvasRef and imageRef respectively. The refs are used to access the canvas and the likenes from the App component. We get hold of both the canvas and the epitome with “useRef” as in 😛 TAGEND const canvasRef= useRef( null ); const imageRef= useRef( null );

In this part of the system, we incorporate the likenes to the canvas as we can only preprocess a canvas in JavaScript. We then convert it to a data URL with “jpeg” as its image format.

const canvas= canvasRef.current; const ctx= canvas.getContext( '2d' );

ctx.drawImage( imageRef.current, 0, 0 ); ctx.putImageData(preprocessImage(canvas),0,0); const dataUrl= canvas.toDataURL( "image/ jpeg" );

“dataUrl” is overstepped to Tesseract as the portrait to be processed.

Now, let’s check whether the textbook extracted will be more accurate.

Test# 2

The image above shows the result in Firefox. It is obvious that the dark part of the persona has been changed to white but preprocessing the image doesn’t lead to a more accurate result. It is even worse.

The first shift only has two flawed characters but this one has four flawed reputations. I even tried varying the threshold level but to no avail. We don’t get a better develop not because binarization is bad but because binarizing the portrait doesn’t fix the nature of the likenes in a way that is suitable for the Tesseract engine.

Let’s check what it also looks like in Chrome 😛 TAGEND

We get the same outcome.

After getting a worse answer by binarizing the epitome, there is a need to check other epitome preprocessing procedures to see whether we can solve the problem or not. So, we are going to try dilation, inversion, and blurring next.

Let’s only get the code for each of the techniques from P5. js as used by this article. We will lend the portrait processing techniques to preprocess.js and use them one by one. It is necessary to understand each of the epitome preprocessing procedures we want to use before using them, so we are going to discuss them first.

What Is Dilation?

Dilation is adding pixels to the boundaries of objects in an persona to make it wider, bigger, or most open. The “dilate” technique is used to preprocess our likeness to increase the brightness of the objects on the likeness. We need a function to dilate images abusing JavaScript, so the code snippet to dilate an portrait is added to preprocess.js.

What Is Blur?

Blurring is smoothing the dyes of an idol by reducing its sharpness. Sometimes, likeness have small-minded dots/ patches. To eliminate those spots, we can blur the portraits. The code snippet to blur an epitome is included in preprocess.js.

What Is Inversion?

Inversion is changing brightnes areas of an likenes to a night dye and dark areas to a sun dye. For example, if an persona has a black background and grey foreground, we can invert it so that its background will be white and its foreground will be black. We have been previously supplemented the code snippet to invert an idol to preprocess.js.

After adding dilate, invertColors and blurARGB to “preprocess.js”, we can now use them to preprocess epitomes. To use them, we need to update the initial “preprocessImage” function in preprocess.js 😛 TAGEND

preprocessImage (...) now looks like this 😛 TAGEND

function preprocessImage( canvas)

const stage= 0.4;

const radius= 1;

const ctx= canvas.getContext( '2d' );

const epitome= ctx.getImageData( 0,0, canvas.width, canvas.height );

blurARGB( image.data, canvas, radius );

dilate( image.data, canvas );

invertColors( image.data );

thresholdFilter( image.data, level );

return persona;

In preprocessImage above, we apply four preprocessing procedures to an idol: blurARGB() to remove the dots on the likenes, dilate() to increase the brightness of the epitome, invertColors() to switch the foreground and background hue of the epitome and thresholdFilter() to convert the epitome to black and white which is more suitable for Tesseract conversion.

The thresholdFilter() makes image.data and position as its constants. elevation is used to set how white-hot or black the idol should be. We specified the thresholdFilter level and blurRGB radius by trial and error as we are not sure how lily-white, dark or smooth the epitome should be for Tesseract to produce a great result.

Test# 3

Here is the new decision after applying four skills 😛 TAGEND

The image above represents the result we come in both Chrome and Firefox.

Oops! The aftermath is terrible.

Instead of using all four techniques, why don’t we just use two of them at a time?

Yeah! We can simply use invertColors and thresholdFilter techniques to alter the image to black and white, and permutation the foreground and the backdrop of the likenes. But how do we know what and what proficiencies to combine? We know what to combine based on the nature of the persona we want to preprocess.

For example, a digital epitome has to be converted to black and white, and an portrait with patches has to be blurred to remove the dots/ patches. What really matters is to understand what each of the techniques is used for.

To use invertColors and thresholdFilter, we need to comment out both blurARGB and dilate in preprocessImage 😛 TAGEND

office preprocessImage( canvas)

const ctx= canvas.getContext( '2d' );

const likenes= ctx.getImageData( 0,0, canvas.width, canvas.height );

// blurARGB( image.data, canvas, 1 );

// dilate( image.data, canvas );

invertColors( image.data );

thresholdFilter( image.data, 0.5 );

return image; Assessment# 4

Now, here is the new outcome 😛 TAGEND

The result is still worse than the one without any preprocessing. After adjusting each of the techniques for this particular image and some other epitomes, I have come to the conclusion that portraits with different nature require different preprocessing procedures.

In short, expending Tesseract.js without idol preprocessing induced the best outcome for the endow card above. All other experiments with image preprocessing provided less precise outcomes.


Initially, I wanted to extract the PIN from any Amazon gift card but I couldn’t achieve that because there is no point to match an incompatible PIN to get a consistent result. Although it is possible to process an idol to get an accurate PIN, yet such preprocessing will be inconsistent by the time another epitome with various quality is used.

The Best Outcome Produced

The image below showcases the best upshot produced by the experiments.

Assessment# 5

The verses on the epitome and the ones extracted are totally the same. The changeover has 100% accuracy. I tried to reproduce the result but I was only able to reproduce it when using portrait with similar nature.

Observance And Readings

Some likeness that are not preprocessed may grant different outcomes in different browsers. This claim is evident in the first research. The outcome in Firefox is different from the one in Chrome. However, preprocessing likeness assists achieve a consistent outcome in other research. Blacknes shade on a white-hot background tends to give feasible decisions. The likenes below is an example of an accurate make without any preprocessing. I likewise was able to get the same level of accuracy by preprocessing the image but it took me a good deal of adjustment which was unnecessary.

The transition is 100% accurate.

A textbook with a big font size tends to be more accurate.

Fonts with arched borders tend to confuse Tesseract. The best answer I got was achieved when I exploited Arial( typeface ). OCR is currently not good enough for automating image-to-text conversion, especially when more than 80% elevation of accuracy is compelled. Nonetheless, it can be used to realize the manual processing of texts on epitomes less stressful by extracting verses for manual correction. OCR is currently not good enough to pass useful information to screen readers for accessibility. Supplying inaccurate information to a screen reader can easily mislead or distract users. OCR is very promising as neural networks make it possible to learn and improve. Deep learning will clear OCR a game-changer in the near future. Work decisions with confidence. A confidence compose can be used to make decisions that can greatly impact our works. The confidence orchestrate can be used to determine whether to accept or spurn a outcome. From my own experience and experimentation, I realized that any confidence composition below 90 isn’t really useful. If I exclusively need to extract some rods from a textbook, I will expect a confidence orchestrate between 75 and 100, and anything below 75 will be rejected.

In case I am dealing here with textbooks without the need to extract any part of it, I will definitely admit a confidence tally between 90 to 100 but reject any compose below that. For instance, 90 and above accuracy will be expected if I want to digitize certificates such as cheques, a historic draft or whenever an precise reproduce is necessary. But a compose that is between 75 and 90 is acceptable when an accurate simulate is not important such as getting the PIN from a knack card. In short, a confidence score helps in making decisions that impact our applications.


Given the data processing limitation caused by texts on idols and the harms associated with it, Optical Character Recognition( OCR) is a beneficial technology to embracing. Although OCR has its disadvantages, it is very promising because of its use of neural networks.

Over time, OCR will overcome most of its limiteds with the help of deep understand, but before then, the approaches highlighted in this article can be utilized to deal with text extraction from images, at least, to reduce the adversity and damages associated with manual processing -- especially from a business point of view.

It is now your turn to try OCR to obtain verses from epitomes. Good luck!

Further Reading

P5. js Pre-Processing in OCR Improving the quality of the production Using JavaScript to Preprocess Images for OCR OCR in the browser with Tesseract.js A Quick History of Optical Character Recognition The Future of OCR is Deep Learning Timeline of Optical Character Recognition

Read more: smashingmagazine.com

Comments (0) Trackbacks (0)

No comments yet.

Leave a comment

No trackbacks yet.