Help
RSS
API
Feed
Maltego
Contact
Domain > arunmichaeldsouza.com
×
More information on this domain is in
AlienVault OTX
Is this malicious?
Yes
No
DNS Resolutions
Date
IP Address
2025-06-18
3.75.10.80
(
ClassC
)
2025-11-14
13.52.188.95
(
ClassC
)
Port 443
HTTP/1.1 200 OKAccept-Ranges: bytesAge: 8400Cache-Control: public,max-age0,must-revalidateCache-Status: Netlify Edge; hitContent-Length: 112442Content-Type: text/html; charsetUTF-8Date: Fri, 14 Nov 2025 19:03:23 GMTEtag: 8e6eaf6b8cf86ad12e6866d7aa21fc4b-sslNetlify-Vary: cookie__next_preview_data:presence|__prerender_bypass:presenceServer: NetlifyStrict-Transport-Security: max-age31536000X-Nf-Request-Id: 01KA1W0DQPHPYQ9Q9FFAVP2R63 !DOCTYPE html>html>head>meta namedescription contentRamblings on web development, JavaScript, open source and tech in general./>meta namekeywords contentblog, personal website, technology blog, personal blog/>meta propertyog:title contentArun Michael Dsouza/>meta propertyog:url contenthttps://arunmichaeldsouza.com/>meta propertyog:description contentRamblings on web development, JavaScript, open source and tech in general./>meta propertyog:image contenthttps://arunmichaeldsouza.com/img/arun-michael-dsouza.png/>meta itempropname contentArun Michael Dsouza/>meta itempropdescription contentRamblings on web development, JavaScript, open source and tech in general./>meta itempropimage contenthttps://arunmichaeldsouza.com/img/arun-michael-dsouza.png/>meta nametwitter:card contentsummary/>meta nametwitter:site content@amdsouza92/>meta nametwitter:title contentArun Michael Dsouza/>meta nametwitter:description contentRamblings on web development, JavaScript, open source and tech in general./>meta nametwitter:creator content@amdsouza92/>meta nametwitter:image:src contenthttps://arunmichaeldsouza.com/img/arun-michael-dsouza.png/>title>Arun Michael Dsouza/title>meta charSetutf-8/>meta http-equivContent-Type contenttext/html; charsetutf-8/>meta contentwidthdevice-width,initial-scale1 nameviewport/>link relshortcut icon href/img/favicon.png/>meta namenext-head-count content20/>link relstylesheet data-hrefhttps://fonts.googleapis.com/css?familySource+Sans+Pro:400,700/>script> (function(i, s, o, g, r, a, m) { iGoogleAnalyticsObject r; ir ir || function() { (ir.q ir.q || ).push(arguments) }, ir.l 1 * new Date(); a s.createElement(o), m s.getElementsByTagName(o)0; a.async 1; a.src g; m.parentNode.insertBefore(a, m) })(window, document, script, https://www.google-analytics.com/analytics.js, ga); ga(create, UA-103805032-1, auto); ga(send, pageview); /script>link relpreconnect hrefhttps://fonts.gstatic.com crossorigin />noscript data-n-css>/noscript>script defer nomodule src/_next/static/chunks/polyfills-5cd94c89d3acac5f.js>/script>script src/_next/static/chunks/webpack-fd82975a6094609f.js defer>/script>script src/_next/static/chunks/framework-5f4595e5518b5600.js defer>/script>script src/_next/static/chunks/main-a054bbf31fb90f6a.js defer>/script>script src/_next/static/chunks/pages/_app-7857ddb502a3bd24.js defer>/script>script src/_next/static/chunks/pages/index-d7e612956f41dff9.js defer>/script>script src/_next/static/YMDQPiVmplN7PEyWOgvCb/_buildManifest.js defer>/script>script src/_next/static/YMDQPiVmplN7PEyWOgvCb/_ssgManifest.js defer>/script>script src/_next/static/YMDQPiVmplN7PEyWOgvCb/_middlewareManifest.js defer>/script>style data-hrefhttps://fonts.googleapis.com/css?familySource+Sans+Pro:400,700>@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qOK7j.woff) format(woff)}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwlxdo.woff) format(woff)}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qNa7lujVj9_mf.woff2) format(woff2);unicode-range:U+0460-052F,U+1C80-1C88,U+20B4,U+2DE0-2DFF,U+A640-A69F,U+FE2E-FE2F}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qPK7lujVj9_mf.woff2) format(woff2);unicode-range:U+0301,U+0400-045F,U+0490-0491,U+04B0-04B1,U+2116}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qNK7lujVj9_mf.woff2) format(woff2);unicode-range:U+1F00-1FFF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qO67lujVj9_mf.woff2) format(woff2);unicode-range:U+0370-03FF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qN67lujVj9_mf.woff2) format(woff2);unicode-range:U+0102-0103,U+0110-0111,U+0128-0129,U+0168-0169,U+01A0-01A1,U+01AF-01B0,U+0300-0301,U+0303-0304,U+0308-0309,U+0323,U+0329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qNq7lujVj9_mf.woff2) format(woff2);unicode-range:U+0100-02AF,U+0304,U+0308,U+0329,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20CF,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:400;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xK3dSBYKcSV-LCoeQqfX1RYOo3qOK7lujVj9w.woff2) format(woff2);unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+2074,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwmhdu3cOWxy40.woff2) format(woff2);unicode-range:U+0460-052F,U+1C80-1C88,U+20B4,U+2DE0-2DFF,U+A640-A69F,U+FE2E-FE2F}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwkxdu3cOWxy40.woff2) format(woff2);unicode-range:U+0301,U+0400-045F,U+0490-0491,U+04B0-04B1,U+2116}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwmxdu3cOWxy40.woff2) format(woff2);unicode-range:U+1F00-1FFF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwlBdu3cOWxy40.woff2) format(woff2);unicode-range:U+0370-03FF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwmBdu3cOWxy40.woff2) format(woff2);unicode-range:U+0102-0103,U+0110-0111,U+0128-0129,U+0168-0169,U+01A0-01A1,U+01AF-01B0,U+0300-0301,U+0303-0304,U+0308-0309,U+0323,U+0329,U+1EA0-1EF9,U+20AB}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwmRdu3cOWxy40.woff2) format(woff2);unicode-range:U+0100-02AF,U+0304,U+0308,U+0329,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20CF,U+2113,U+2C60-2C7F,U+A720-A7FF}@font-face{font-family:Source Sans Pro;font-style:normal;font-weight:700;src:url(https://fonts.gstatic.com/s/sourcesanspro/v22/6xKydSBYKcSV-LCoeQqfX1RYOo3ig4vwlxdu3cOWxw.woff2) format(woff2);unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+2074,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD}/style>/head>body>div id__next data-reactroot>section classlayout>header>div classtext-center>nav>h1 classpage-primary-title>a href/>Arun Michael Dsouza/a>/h1>ul>li>a href/>Home/a>/li>li>a href/about>About/a>/li>li>a href/talks>Talks/a>/li>li>a href/open-source>Open Source/a>/li>/ul>/nav>/div>/header>div classcontent>style> html{line-height:1.15;-ms-text-size-adjust:100%;-webkit-text-size-adjust:100%}body{margin:0}article,aside,footer,header,nav,section{display:block}h1{font-size:2em;margin:.67em 0}figcaption,figure,main{display:block}figure{margin:1em 40px}hr{box-sizing:content-box;height:0;overflow:visible}pre{font-family:monospace,monospace;font-size:1em}a{background-color:transparent;-webkit-text-decoration-skip:objects}abbrtitle{border-bottom:none;text-decoration:underline;text-decoration:underline dotted}b,strong{font-weight:inherit;font-weight:bolder}code,kbd,samp{font-family:monospace,monospace;font-size:1em}dfn{font-style:italic}mark{background-color:#ff0;color:#000}small{font-size:80%}sub,sup{font-size:75%;line-height:0;position:relative;vertical-align:baseline}sub{bottom:-.25em}sup{top:-.5em}audio,video{display:inline-block}audio:not(controls){display:none;height:0}img{border-style:none}svg:not(:root){overflow:hidden}button,input,optgroup,select,textarea{font-family:sans-serif;font-size:100%;line-height:1.15;margin:0}button,input{overflow:visible}button,select{text-transform:none}typereset,typesubmit,button,html typebutton{-webkit-appearance:button}typebutton::-moz-focus-inner,typereset::-moz-focus-inner,typesubmit::-moz-focus-inner,button::-moz-focus-inner{border-style:none;padding:0}typebutton:-moz-focusring,typereset:-moz-focusring,typesubmit:-moz-focusring,button:-moz-focusring{outline:1px dotted ButtonText}fieldset{padding:.35em .75em .625em}legend{box-sizing:border-box;color:inherit;display:table;max-width:100%;padding:0;white-space:normal}progress{display:inline-block;vertical-align:baseline}textarea{overflow:auto}typecheckbox,typeradio{box-sizing:border-box;padding:0}typenumber::-webkit-inner-spin-button,typenumber::-webkit-outer-spin-button{height:auto}typesearch{-webkit-appearance:textfield;outline-offset:-2px}typesearch::-webkit-search-cancel-button,typesearch::-webkit-search-decoration{-webkit-appearance:none}::-webkit-file-upload-button{-webkit-appearance:button;font:inherit}details,menu{display:block}summary{display:list-item}canvas{display:inline-block}hidden,template{display:none}body,html{font-family:Source Sans Pro,sans-serif;font-size:16px}.text-center{text-align:center}.text-left{text-align:left}.separator{margin-top:40px}.lh{line-height:22px}.ul-reset{padding:0;margin:0;list-style:none}a{color:#4263eb;text-decoration:none}a:hover{cursor:pointer;text-decoration:underline}.icon-location{width:15px;height:15px}.img-resp{width:100%;height:auto}header{position:fixed;margin:0;width:100%;top:0;left:0;background-color:#fff;border-bottom:1px solid #4263eb;padding:15px 0;z-index:1000}header .page-primary-title{margin:0 0 10px}nav ul{margin:0;padding:0;list-style-type:none}nav ul li{display:inline-block;margin-right:5px}nav ul li:not(:last-child):after{content:/;color:#4263eb}nav ul li a{padding-right:5px;font-size:1.2em}nav ul li a:hover{text-decoration:underline}footer{padding:15px 0;border-top:1px solid #4263eb}footer nav ul li a{font-size:1em}.content-wrapper{width:60%;margin:150px auto 40px}@media screen and (max-width:768px){.content-wrapper{width:100%;padding:0 15px;box-sizing:border-box}}.page-primary-title{font-size:2em;margin-bottom:15px}.page-primary-title>a{display:inline-block;color:#1e1e1e;padding-bottom:5px;border-bottom:4px solid #4263eb}.page-primary-title>a:hover{text-decoration:none}@media screen and (max-width:768px){.page-primary-title>a{font-size:1em}}.sub-text{margin-bottom:40px;color:#585858}.sub-text span{color:#4b4b4b;font-weight:700}.pre-text{margin-bottom:10px;color:#585858;font-weight:400}.page-secondary-title{margin:0 0 40px;color:#1e1e1e;padding-bottom:10px;border-bottom:1px solid #4263eb}.page-secondary-title>a{color:#1e1e1e}.page-secondary-title>a:hover{text-decoration:none}.grid{padding-right:15px;padding-left:15px;margin-right:auto;margin-left:auto}.grid .row{margin-left:-15px;margin-right:-15px}.grid .row:after,.grid .row:before{content:;clear:both;display:table}.grid .row class*cm-col{position:relative;padding-left:15px;padding-right:15px}@media (min-width:768px){.grid .row .col-30{float:left;width:30%}}@media (min-width:768px){.grid .row .col-70{float:left;width:70%}}@media (min-width:768px){.grid .row .col-80{float:left;width:80%}}@media (min-width:768px){.grid .row .col-20{float:left;width:20%}}.list-item{margin-bottom:40px}.list-item .info{padding:0 0 0 10px}@media (max-width:768px){.list-item .info{padding:0}}.list-item .info .page-secondary-title{margin:0 0 20px}@media (max-width:768px){.list-item .info .page-secondary-title{margin:10px 0}}@media (max-width:768px){.list-item .info .pre-text{margin:0}}.content-wrapper{width:70%;margin-top:130px}@media screen and (max-width:768px){.content-wrapper{width:100%}}.tags-container a{display:block;font-size:1.25em;margin-bottom:10px}.tags-container svg{width:18px;vertical-align:middle}.list-item .info .page-secondary-title{width:95%} .list-item img { width: 100%; height: auto; } .grid .row .col-80 { width: 100%; } /style>p classdescription>Ramblings on web development, JavaScript, open source and tech in general./p>main>section classcontent-wrapper>div classgrid>div classrow>div classcol-80>h1 classpage-primary-title>a href/>All blog posts/a>/h1>div classsub-text lh>Ramblings on span>programming/span>, span>open source/span>, span>game development/span>,!-- --> span>construction toys /span>and span>tech /span>in general./div>div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/web-platform's-hidden-gems---shape-detection-api>img src/img/blogs/web-platform's-hidden-gems---shape-detection-api/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/web-platform's-hidden-gems---shape-detection-api>Web platform's hidden gems - Shape Detection API/a>/h2>div classpre-text>span>Mon Feb 04 2021/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/web-platform's-hidden-gems---battery-status-api>img src/img/blogs/web-platform's-hidden-gems---battery-status-api/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/web-platform's-hidden-gems---battery-status-api>Web platform's hidden gems - Battery Status API/a>/h2>div classpre-text>span>Thu Jan 28 2021/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/building-the-brxlz-liverpool-fc-anfield-stadium>img src/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/building-the-brxlz-liverpool-fc-anfield-stadium>Building the BRXLZ Liverpool FC Anfield Stadium/a>/h2>div classpre-text>span>Sat Nov 21 2020/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/web-platform's-hidden-gems---device-orientation-api>img src/img/blogs/web-platform's-hidden-gems---device-orientation-api/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/web-platform's-hidden-gems---device-orientation-api>Web platform's hidden gems - Device Orientation API/a>/h2>div classpre-text>span>Fri Sep 25 2020/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/web-platform's-hidden-gems---gamepad-api>img src/img/blogs/web-platform's-hidden-gems---gamepad-api/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/web-platform's-hidden-gems---gamepad-api>Web platform's hidden gems - Gamepad API/a>/h2>div classpre-text>span>Sun Jun 14 2020/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/web-platform's-hidden-gems-(series)>img src/img/blogs/web-platform's-hidden-gems-(series)/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/web-platform's-hidden-gems-(series)>Web platform's hidden gems (series)/a>/h2>div classpre-text>span>Tue Mar 24 2020/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/using-joypad.js-for-a-better-gaming-experience-on-the-web>img src/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/using-joypad.js-for-a-better-gaming-experience-on-the-web>Using joypad.js for a better gaming experience on the web/a>/h2>div classpre-text>span>Wed Dec 12 2019/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/loading-images-gracefully-with-react-image-appear>img src/img/blogs/loading-images-gracefully-with-react-image-appear/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/loading-images-gracefully-with-react-image-appear>Loading images gracefully with react-image-appear/a>/h2>div classpre-text>span>Fri Apr 26 2019/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/easy-json-logging-in-node-js-using-woodlot>img src/img/blogs/easy-json-logging-in-node-js-using-woodlot/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/easy-json-logging-in-node-js-using-woodlot>Easy JSON logging in Node JS using Woodlot/a>/h2>div classpre-text>span>Thu Apr 04 2019/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/aliasing-module-paths-in-node-js>img src/img/blogs/aliasing-module-paths-in-node-js/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/aliasing-module-paths-in-node-js>Aliasing module paths in Node JS/a>/h2>div classpre-text>span>Fri Jan 04 2019/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/updating-state-of-a-parentless-component-in-react>img src/img/blogs/updating-state-of-a-parentless-component-in-react/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/updating-state-of-a-parentless-component-in-react>Updating state of a parentless component in React/a>/h2>div classpre-text>span>Thu Dec 28 2017/span>/div>/div>/div>/div>/div>/div>div>div classgrid list-item>div classrow>div classcol-30>a href/blog/getting-started-with-react-16>img src/img/blogs/getting-started-with-react-16/1-small.png/>/a>/div>div classcol-70>div classinfo>h2 classpage-secondary-title>a href/blog/getting-started-with-react-16>Getting started with React 16/a>/h2>div classpre-text>span>Mon Nov 13 2017/span>/div>/div>/div>/div>/div>/div>/div>/div>/div>/div>/section>/main>/div>/section>footer>div classtext-center>nav>ul>li>a href/>Home/a>/li>li>a href/about>About/a>/li>li>a href/talks>Talks/a>/li>li>a href/open-source>Open Source/a>/li>/ul>/nav>/div>/footer>/div>script id__NEXT_DATA__ typeapplication/json>{props:{pageProps:{blogs:{frontmatter:{title:Web platforms hidden gems - Shape Detection API,url:web-platforms-hidden-gems---shape-detection-api,date:Mon Feb 04 2021,metaDescription:A few months back I started the Web platforms hidden gems blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web. Even though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer! In the previous blog post, I explained the Battery Status API, using which developers can fetch information about the systems battery charge levels and use it in web applications to make adjustments to resource usage. Feel free to read through it and try it out if youd like. This is the fourth blog post of the series and in this post, Ill be talking about the Shape Detection API.,metaKeywords:Face detection javascript, text detection javascript, barcode detection javascript, QR code detection javascript, shape detection API, facial tagging, facial recognition javascript, artificial intelligence, machine learning, opencv, web platform, web development,metaImage:https://arunmichaeldsouza.com/img/blogs/web-platforms-hidden-gems---shape-detection-api/1.png},markdownBody:\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/1.png)\n\nA few months back I started the **Web platforms hidden gems**(\u003chttps://arunmichaeldsouza.com/blog/web-platforms-hidden-gems-(series)\u003e) blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web.\n\nEven though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer!\n\nIn the previous blog post, I explained the Battery Status API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---battery-status-api), using which developers can fetch information about the systems battery charge levels and use it in web applications to make adjustments to resource usage. Feel free to read through it and try it out if youd like.🙂\n\nThis is the fourth blog post of the series and in this post, Ill be talking about the Shape Detection API(https://wicg.github.io/shape-detection-api/).\n\nJust a disclaimer though, this API is in very early stages and may undergo major changes in terms of implementation and usage.\n\n## Shape detection on the web\n\n\u003e The shape detection API enables developers to detect shapes (faces, text, bar codes etc.) from still images or live image feeds.\n\nDetecting shapes or patterns from images can be a computationally expensive task and may require different kinds of libraries or third party APIs. But the Shape Detection API makes it a readily available feature in the browser that web developers can use. Using the Shape Detection API web developers can detect faces, text, bar codes and even QR codes which can be used for user identification, URL redirection, facial tagging etc.\n\nThe Shape Detection API uses the underlying hardware for detection capabilities which provides accelerated operation.\n\n## Face detection API\n\nThe Face Detection API is a subset of the Shape Detection API which enables the detection of human faces in images. The **window.FaceDetector** interface can be used to create a new instance of the face detector. It provides a **detect()** method that receives the image as an argument and returns a promise, which when resolved, returns an array of detected faces. The image provided to the method may come from any type of image buffer source such as an image, video or canvas tag.\n\nThe **window.FaceDetector** interface supports the following options -\n\n- **maxDetectedFaces** \\- Hints the user agent to try and limit the number of detected faces in the scene.\n- **fastMode** - Hints the user agent to try and prioritize speed over accuracy.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/2.png)\n\nEach detected face consists of a **bounding box** that defines the exact location and extent of the face in the image, as well as **landmark locations** for facial features such as eyes, mouth and nose. The landmark locations contain an array of points defining the vertices of a simple polygon surrounding the feature.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/3.png)\n\nAs of now, the Face Detection API is available on Chrome and Opera behind the **Experimental Web Platform features** flag. You can enable it by going into **chrome://flags/#enable-experimental-web-platform-features** and selecting **Enabled**.\n\nI prepared a demo for the Face Detection API running on Chrome 88. Please feel free to check out the code below -\n\nhttps://gist.github.com/ArunMichaelDsouza/ffe8b8eedf5909732a22907283f86430(https://gist.github.com/ArunMichaelDsouza/ffe8b8eedf5909732a22907283f86430)\n\n## Barcode Detection API\n\nThe Barcode Detection API is another subset of the Shape Detection API which enables the detection of linear or 2D barcodes in images. The **window.BarcodeDetector** interface can be used to create a new instance of the barcode detector. It also provides a **detect()** method that receives the image as an argument and returns a promise, which when resolved, returns an array of the detected barcodes. The image provided to the method may come from any type of image buffer source such as an image, video or canvas tag.\n\nThe **window.BarcodeDetector** interface supports an optional bar code formats list setting. Using this list, developers can explicitly specify the bar code formats that are required to be supported by the application.\n\n\u003e Note: Limiting the search to a particular subset of supported formats is likely to provide better performance. To see a complete list of supported formats please see this link.(https://developer.mozilla.org/en-US/docs/Web/API/Barcode_Detection_API#supported_barcode_formats)\n\nIn order to see which formats are actually supported by the Barcode Detection API in your browser, you can use the **window.BarcodeDetector.getSupportedFormats()** method. This returns a promise which resolves to an array of supported formats.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/4.png)\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/5.png)\n\nEach detected barcode consists of a **bounding box** that defines the exact location and extent of the barcode feature in the image. It also contains the X, Y coordinates of the **corner points** of the feature, the **format** of the barcode and the **raw value**.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/6.png)\n\nBounding box and other data of the detected barcode\n\nAs of now, the Barcode Detection API is available by default starting in Chrome 83, Edge 83 and Opera 72.\n\nI prepared a demo for the Barcode Detection API running on Chrome 88. Please feel free to check out the code below -\n\nhttps://gist.github.com/ArunMichaelDsouza/b29459609fdd4247a096e9e052ad99dc(https://gist.github.com/ArunMichaelDsouza/b29459609fdd4247a096e9e052ad99dc)\n\n## Text Detection API\n\nThe Text Detection API is another subset of the Shape Detection API which enables the detection of text in images. The **window.TextDetector** interface can be used to create a new instance of the text detector. It also provides a **detect()** method that receives the image as an argument and returns a promise, which when resolved, returns the detected text as an array. The image provided to the method may come from any type of image buffer source such as an image, video or canvas tag.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/7.png)\n\nUsing the Text Detection API\n\nThe **bounding box** information and the X, Y coordinates of the **corner points** of the detected text are returned by the resolved promise. On some platforms, the recognized characters or the raw text value is also returned.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/8.png)\n\nBounding box and corner points of the detected text\n\nAs of now, the Text Detection API is available on Chrome and Opera behind the **Experimental Web Platform features** flag. You can enable it by going into **chrome://flags/#enable-experimental-web-platform-features** and selecting **Enabled**.\n\nI prepared a demo for the Text Detection API running on Chrome 88. Please feel free to check out the code below -\n\nhttps://gist.github.com/ArunMichaelDsouza/fc95a5fb574cb2295d2d092aa0c03fbf(https://gist.github.com/ArunMichaelDsouza/fc95a5fb574cb2295d2d092aa0c03fbf)\n\n\u003e Note: It is advisable to reuse the same detector instance for several detections as it may allocate and hold significant system resources.\n\nAll detectors work asynchronously and they do not block the main thread. They are also available to be used by web workers.\n\n## Browser support\n\nAs mentioned above, both the Face detection API and the Text Detection API are available on Chrome and Opera behind the **Experimental Web Platform features** flag. You can enable it by going into **chrome://flags/#enable-experimental-web-platform-features** and selecting **Enabled**.\n\nWhereas the Barcode Detection API is available by default starting in Chrome 83, Edge 83 and Opera 72.\n\n!(/img/blogs/web-platforms-hidden-gems---shape-detection-api/9.png)\n\nBarcode Detection API browser support\n\nI would like to point out again that this specification is in very early stages so it may undergo major changes in terms of implementation and usage. But that shouldnt stop you from experimenting with it. So go ahead and give it a try!\n\nYou might be interested in the previous blog post about the Battery Status API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---battery-status-api), using which developers can fetch information about the systems battery charge levels and use it in web applications to make adjustments to resource usage. Feel free to read through it and try it out as well if youd like.🙂\n\nIn the next blog post of the series, I would be covering the File System Access API(https://wicg.github.io/file-system-access/). So keep an eye out on this space for more info.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:web-platforms-hidden-gems---shape-detection-api},{frontmatter:{title:Web platforms hidden gems - Battery Status API,url:web-platforms-hidden-gems---battery-status-api,date:Thu Jan 28 2021,metaDescription:A few months back I started the Web platforms hidden gems blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web. Even though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer! In the previous blog post, I explained the Device Orientation API, using which developers can develop web applications with device orientation detection capabilities. This can be really useful for a variety of use cases like gaming - for controlling a character or an object and even for gesture recognition in web applications for enhanced accessibility. Feel free to read through it and try it out if youd like.This is the fourth blog post of the series and in this post, Ill be talking about the Battery Status API.,metaKeywords:battery, power, battery API, web platform, power management, resource, energy, web development,metaImage:https://arunmichaeldsouza.com/img/blogs/web-platforms-hidden-gems---battery-status-api/1.png},markdownBody:\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/1.png)\n\nA few months back I started the **Web platforms hidden gems**(\u003chttps://arunmichaeldsouza.com/blog/web-platforms-hidden-gems-(series)\u003e) blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web.\n\nEven though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer!\n\nIn the previous blog post, I explained the Device Orientation API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---device-orientation-api), using which developers can develop web applications with device orientation detection capabilities. This can be really useful for a variety of use cases like gaming - for controlling a character or an object and even for gesture recognition in web applications for enhanced accessibility. Feel free to read through it and try it out if youd like.🙂\n\nThis is the third blog post of the series and in this post, Ill be talking about the Battery Status API(https://www.w3.org/TR/battery-status/).\n\n\u003e Update: The Battery Status API has been deprecated and is no longer recommended for use. Some browsers might still support it, but the standard itself is in the process of being dropped.\n\n## Fetching the battery status\n\n\u003e The Battery Status API specification defines a means for web developers to programmatically determine the battery status of the hosting device.\n\nThis means that using this API, developers would be able to fetch information about the systems battery charge levels and use it in web applications to make adjustments to resource usage.\n\nThe Battery Status API exposes the **getBattery()** method on the navigator object that returns a promise which, when resolved, returns the information about the batterys state.\n\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/2.png)\n\nThe returned data shows whether the system is being charged or not, what is the charge level or the percentage of the battery left and also returns some useful event handlers that can be used to detect certain changes in the battery usage.\n\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/3.png)\n\n## Detecting change in charging level\n\nThe **levelchange** event type can be used to detect any changes in the charging level. This event is fired whenever the charging level either increases (while charging) or decreases (while discharging).\n\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/4.png)\n\nThe returned data shows the charging level which is a value between 0 and 1, multiply that by 100 and you have the battery percentage.\n\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/5.png)\n\n## Other event types\n\n**chargingchange** \\- This event is fired whenever a change in charging state takes place, that is when the charging unit is connected or disconnected.\n\n**chargingtimechange** - This event is fired whenever the battery charging time gets updated. The **chargingTime** attribute represents the time remaining in seconds until the systems battery is fully charged.\n\n**dischargingtimechange** - This event is fired whenever the battery discharging time gets updated. The **dischargingTime** attribute represents the time remaining in seconds until the systems battery is completely discharged and the system is about to be suspended.\n\n## Browser support\n\nAs mentioned above, the standard itself is in the process of being dropped due to privacy concerns. But its still worth checking out what potentially wouldve been a nice addition to the web platform.\n\n!(/img/blogs/web-platforms-hidden-gems---battery-status-api/6.png)\n\nYou might be interested in the previous blog post about the Device Orientation API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---device-orientation-api), using which developers can develop web applications with device orientation detection capabilities. Feel free to read through it and try it out as well if youd like.🙂\n\nIn the next blog post of the series, I would be covering the Shape Detection API(https://wicg.github.io/shape-detection-api/). So keep an eye out on this space for more info.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:web-platforms-hidden-gems---battery-status-api},{frontmatter:{title:Building the BRXLZ Liverpool FC Anfield Stadium,url:building-the-brxlz-liverpool-fc-anfield-stadium,date:Sat Nov 21 2020,metaDescription:Ive been a huge fan of construction toys since I was a kid, be it Lego, Duplo, Meccano, or Mechanix! I had them all and I never used to get tired of playing with them. I dont mean to brag but I used to build some of the most interesting towers, houses, games, mini-cities, puzzles, and mazes, that too without any manuals or guides. Just pure imagination and creativity. Ah! those were the days. Anyway, this isnt about me reminiscing about the fun times I had building those sets and playing with them. Rather Its about a new set that I got the chance to build (which is amazing by the way), and I want to share my experience here.,metaKeywords:brxlz, lego, construction toy, construction set, lego building, lego creator, liverpool, lfc, liverpoolfc, anfield, stadium, anfield lego,metaImage:https://arunmichaeldsouza.com/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/1.jpg},markdownBody:\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/1.jpg)\n\nIve been a huge fan of construction toys since I was a kid, be it Lego(https://en.wikipedia.org/wiki/Lego), Duplo(https://en.wikipedia.org/wiki/Lego_Duplo), Meccano(https://en.wikipedia.org/wiki/Meccano), or Mechanix(https://www.google.com/search?qmechanix+sets\u0026tbmisch\u0026ved2ahUKEwiS3LPc4MvsAhUJyxQKHUtJB_kQ2-cCegQIABAA\u0026oqmechanix+sets\u0026gs_lcpCgNpbWcQAzIECCMQJzoECAAQQzoCCAA6BggAEAgQHjoECAAQGDoGCAAQChAYUMJZWOteYKpqaABwAHgAgAE5iAH_AZIBATWYAQCgAQGqAQtnd3Mtd2l6LWltZ8ABAQ\u0026sclientimg\u0026eiIliTX5JDiZZTy5KdyA8\u0026bih701\u0026biw1440)! I had them all and I never used to get tired of playing with them.\n\nI dont mean to brag but I used to build some of the most interesting towers, houses, games, mini-cities, puzzles, and mazes, that too without any manuals or guides. Just pure imagination and creativity. Ah! those were the days.\n\nAnyway, this isnt about me reminiscing about the fun times I had building those sets and playing with them. Rather Its about a new set that I got the chance to build (which is amazing by the way), and I want to share my experience here.\n\nSo for my birthday this year, I got the BRXLZ Liverpool FC Anfield Stadium(https://uk.foco.com/products/liverpool-fc-anfield-brxlz-stadium) construction set as a present and since I am a huge Liverpool FC(https://www.liverpoolfc.com/) fan, I was totally blown away!\n\nThe overall quality of the set is top-notch and the level of detail is absolutely amazing! Believe me cause Ive seen the real thing. From the main stands roof to the Kop end even the brick patterns on the outside of Anfield road stand - its just perfect!\n\nThe set contains 4,650 pieces (also includes extra pieces just in case you lose a few here and there) and a 126-page manual that has all the step by step instructions.\n\nSince many of the pieces that come along are really small and can have different color shades, my suggestion would be to identify the pieces from the chart and sort them out based on shape and color. That way its easier to locate the pieces and use them in the steps.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/2.png)\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/3.png)\n\nOnce you have all the pieces sorted out, you can pick the ones required in a particular step and start placing them together.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/4.png)\n\n## Day 1\n\nSo I started off by setting up the foundation for the entire structure, this sets up the base for the stairs, the field, and all the stands.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/5.jpg)\n\n## Day 2\n\nThe stairs have started to shape up and fresh grass has been laid out on the field. The groundwork for the seating area has also started.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/6.JPG)\n\n## Day 3\n\nThe lower end of the seating area is complete and the exteriors of the stands are starting to shape up. At this point, I would suggest placing the pitch sticker on the field because there is more room available for easy movement.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/7.JPG)\n\n## Day 4\n\nThe upper end of the seating area is starting to shape up and the entrance/exit tunnels are now complete.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/8.JPG)\n\n## Day 5\n\nThe roof on the Kop end has been placed and the upper level seats are almost complete.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/9.jpg)\n\n## Day 6\n\nWith the seating area and the exteriors complete on all sides, its time to work on the roof structures. The roof on the Kop end has been extended and the base has been set up to place roofs on rest of the sides.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/10.JPG)\n\n## Day 7\n\nThe roofs are starting to shape up with the Anfield road stand roof complete.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/11.JPG)\n\n## Day 8\n\nThe roof on the Sir Kenny Dalglish stand is now complete. The main stands roof has been extended, on top of which the truss would be placed.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/12.JPG)\n\n## Day 9\n\nAnd its complete! Anfield stadium - home of Liverpool FC, the Premier League Champions!\n\nWith the roofs of the main stand and the Kop end in place. The truss and the extended roof have been put together to complete the massive main stand\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/13.JPG)\n\nHere is the complete set with all the stickers placed - the LFC crest on the outside of the main stand, the Kop end and the Anfield sticker on the front.\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/14.png)\n\nComplete BRXLZ Liverpool FC Anfield Stadium set\n\n!(/img/blogs/building-the-brxlz-liverpool-fc-anfield-stadium/15.png)\n\nBRXLZ Liverpool FC Anfield Stadium\n\nI would say its not complex to build the overall set if you sort the pieces out correctly from the very beginning. Like I said some pieces have different color shades which can be a bit tricky to identify.\n\nThe set has a lot of tiny pieces and for the entirety of it, you would be building all the structures end to end using a lot of different pieces and placing them together. And if you are an avid builder like me, you will definitely enjoy building it. I did for sure! And it would give you a real sense of accomplishment once you complete the set.\n\nIt took me 9 days, where I was spending around 3-4 hours per day building it, thats approximately 36 hours or 1.5 days in total. Not bad at all if you ask me!😄\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92).\n\nCheers!\n\nPS: Erica Louise(https://ericalouise.com/), If you are reading this - thank you again for the wonderful present!😄\n,slug:building-the-brxlz-liverpool-fc-anfield-stadium},{frontmatter:{title:Web platforms hidden gems - Device Orientation API,url:web-platforms-hidden-gems---device-orientation-api,date:Fri Sep 25 2020,metaDescription:A few months back I started the Web platforms hidden gems blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web. Even though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer! This is the third blog post of the series and in this post, Ill be talking about the Device Orientation API.,metaKeywords:orientation, gaming, orientation API, gesture recognition, game development, accessibility, device orientation, device motion, accelerometer, gyroscope, compass,metaImage:https://arunmichaeldsouza.com/img/blogs/web-platforms-hidden-gems---device-orientation-api/1.png},markdownBody:\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/1.png)\n\nA few months back I started the Web platforms hidden gems(\u003chttps://arunmichaeldsouza.com/blog/web-platforms-hidden-gems-(series)\u003e) blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web.\n\nEven though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer!\n\nIn the previous blog post, I explained the Gamepad API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---gamepad-api), using which developers can connect gamepads and similar input devices to the browser and use them in their gaming applications. Feel free to read through it and try it out if youd like. 🙂\n\nThis is the second blog post of the series and in this post, Ill be talking about the Device Orientation API(https://w3c.github.io/deviceorientation/spec-source-orientation.html).\n\nJust a disclaimer though, this API is in very early stages and may undergo major changes in terms of implementation and usage.\n\n## Detecting device orientation\n\n\u003e The Device Orientation specification provides several new DOM events for obtaining information about the physical orientation and movement of the hosting device.\n\nThe information returned by the events is provided by sources such as gyroscopes, compasses, and accelerometers. Using the data provided by these sources, we can determine information about the orientation as well as the motion of the device.\n\nThis can be really useful for a variety of use cases like gaming - for controlling a character or an object and even for gesture recognition in web applications for enhanced accessibility.\n\n\u003e Note : The events are only fired in a **secure browsing context** (https).\n\nThe **deviceorientation** event is emitted whenever a significant change in orientation occurs.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/2.png)\n\n## 3-dimensional coordinate system\n\nTo use the values returned by the events we need to understand the **3-dimensional coordinate system** used by device orientation -\n\n- The **X-axis** runs from the left side of the device to the right side of the device.\n- The **Y-axis** runs from the bottom of the device towards the top of the device.\n- The **Z-axis** runs from the screen of the device up to the sky.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/3.png)\n\nDevice orientation defines the following rotations along the 3 axes -\n\n- The rotation around the **Z-axis** is called **Alpha**.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/4.png)\n\n- The rotation around the **X-axis** is called **Beta**.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/5.png)\n\n- The rotation around the **Y-axis** is called **Gamma**.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/6.png)\n\nThe change in orientation returned by the event is expressed in terms of these values - **Alpha**, **Beta** and **Gamma**.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/7.png)\n\nUsing these values we can determine the change in rotation with respect to the 3 axes.\n\n## Simulating device orientation using chrome dev tools\n\nIn order to simulate the device orientation event and visualize the change in the values, we can make use of the chrome dev tools in-built device orientation sensor and simulate different types of device orientations such as portrait, landscape, and even custom ones.\n\nTo launch the simulator, simply open the dev tools window and press **Command+Shift+P** (Mac) or **Ctrl+Shift+P** (Windows or Linux) to open the command menu. Type \sensors\ and select show sensors. From the orientation list select one of the preset or you can select a custom one as well.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/8.gif)\n\nOn actual mobile devices, its rather different. Most mobile browsers dont allow access to sensor data due to security reasons. It can only be made available for use by the web page after the user has granted permission to access the data.\n\nFor requesting user permission to access the orientation data, the Permissions API(https://www.w3.org/TR/permissions/) can be used as follows -\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/9.png)\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/10.gif)\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/11.gif)\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/12.gif)\n\n## Detecting device motion\n\nSimilarly, theres the **devicemotion** event that can help us to determine how fast the device is accelerating.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/13.png)\n\nThe device motion event uses the same 3-dimensional coordinate system and provides acceleration values with respect to the 3 axes.\n\nThe event object returns the following information -\n\n- **accelerationIncludingGravity** and **acceleration** - Acceleration values for the 3 axes (**X**, **Y** and **Z**) with and without the effects of gravity.\n- **rotationRate** \\- Rotation values for the 3 axes represented as **alpha**, **beta** and **gamma**.\n- **interval** - Represents the time interval in milliseconds during which the data is obtained from the device.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/14.png)\n\nFor requesting user permission to access the motion data, we can again use the Permissions API as follows -\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/15.png)\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/16.gif)\n\n## Browser support\n\nAs of now, the API is a work in progress and is subject to change but the events themselves are supported by all modern browsers.\n\n!(/img/blogs/web-platforms-hidden-gems---device-orientation-api/17.png)\n\nI would like to point out again that this specification is in very early stages so it may undergo major changes in terms of implementation and usage. But that shouldnt stop you from experimenting with it. So go ahead and give it a try!\n\nYou might be interested in the previous blog post about the Gamepad API(https://arunmichaeldsouza.com/blog/web-platforms-hidden-gems---gamepad-api), using which developers can connect gamepads and similar input devices to the browser and use them in their gaming applications. Feel free to read through it and try it out as well if youd like. 🙂\n\nIn the next blog post of the series, I would be covering the Battery Status API(https://www.w3.org/TR/battery-status/). So keep an eye out on this space for more info.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:web-platforms-hidden-gems---device-orientation-api},{frontmatter:{title:Web platforms hidden gems - Gamepad API,url:web-platforms-hidden-gems---gamepad-api,date:Sun Jun 14 2020,metaDescription:A few weeks back I started the Web Platform’s hidden gems blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web. Even though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer! This is the first blog post of the series and in this post, Ill be talking about the Gamepad API.,metaKeywords:gamepad, gaming, joypad, gamepad api, game development, gamer, game design, unity 3d, unreal engine, javascript, playstation, xbox, ps4,metaImage:https://arunmichaeldsouza.com/img/blogs/web-platforms-hidden-gems---gamepad-api/1.png},markdownBody:\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/1.png)\n\nA few weeks back I started the Web platforms hidden gems(\u003chttps://arunmichaeldsouza.com/blog/web-platforms-hidden-gems-(series)\u003e) blog series. The idea behind the series is to cover the native API enhancements to the web platform and shed some light on how these APIs can be used to create some really interesting experiences on the web.\n\nEven though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Having said that, I feel that its important for developers to know about these specifications and understand the possibilities that the native web has to offer!\n\nThis is the first blog post of the series and in this post, Ill be talking about the Gamepad API(https://w3c.github.io/gamepad/).\n\nJust a disclaimer though, this API is in very early stages and may undergo major changes in terms of implementation and usage.\n\n## Connecting a gamepad to the browser\n\n\u003e The Gamepad specification defines a low-level interface that represents gamepad devices.\n\nThis means that using this API, developers would be able to connect gamepads and similar input devices to the browser and be able to use them in their gaming applications. There would be no need to design any complex mouse/keyboard based interfaces for game controls that can be tricky to operate and can take some time to get used to. Game developers would be able to provide more natural controls to their users like joystick driven character movements.\n\nThe **gamepadconnected** event is emitted whenever a new gamepad is connected to the page. If the gamepad is already connected when the page loads and gains focus then the event is emitted when a button is pressed or an axis is moved on the gamepad.\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/2.png)\n\nThe **window.navigator.getGamepads()** method returns an array of Gamepad objects, one for each gamepad connected to the device. The Gamepad API supports up to 4 simultaneous connections at the moment.\n\nIf you log out the 0th index (the first connected gamepad) you can see the gamepad info -\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/3.png)\n\nThe Gamepad interface stores information about the connected gamepad\n\nThe **gamepaddisconnected** event is emitted whenever a gamepad (which has previously received data from the page) has been disconnected.\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/4.png)\n\n## Tracking button press and axis movement\n\nCurrently, the gamepad API only supports these two events - **gamepadconnected** and **gamepaddisconnected**. There is no standardized way to detect gamepad button presses or axis movements. The Gamepad interface(https://developer.mozilla.org/en-US/docs/Web/API/Gamepad) does return useful information about the gamepad buttons, axes and their current states (button press and axis movement values) but there is no actual event that is dispatched when these actions are performed by the user.\n\nBut there is a way to continuously **poll** for button and axis value changes using **window.requestAnimationFrame()(https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame)** \\-\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/5.png)\n\nIn the context of a video game, a **game loop** is something that continuously checks for user input, updates the game state and renders the scene. **requestAnimationFrame()** seems to be fitting well for this as we can perform all these operations in its callback and it would remain in sync with the repaint tasks in every frame.\n\nIdeally thats how user input should be polled in a gaming application.\n\nId highly recommend checking this article - Anatomy of a video game(https://developer.mozilla.org/en-US/docs/Games/Anatomy) if you want to know more about how a typical game loop workflow can be implemented in JavaScript.\n\nThis does give us the user input states as expected but we still need a way to store and discard these values in an efficient way. Ideally in the form of an API that can be exposed and reused in any gaming application.\n\nThat is the very reason why I created **joypad.js(https://github.com/ArunMichaelDsouza/joypad.js)** \\- a JavaScript library that lets you connect and use various gaming controllers with browsers that support the Gamepad API. Its less than 5KB in size with zero dependencies and has support for button press, axis movement events and vibration play effect.\n\nSubscribing to events is as simple as specifying an event name and a callback that is fired whenever the specified event is triggered.\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/6.png)\n\nFor more details on how to use it or to know how it works under the hood (Spoiler alert: it uses the requestAnimationFrame() polling technique), please feel free to go to its Github page(https://github.com/ArunMichaelDsouza/joypad.js).\n\nNow coming back to the Gamepad API, the button/axis layout is as follows -\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/7.png)\n\nThis is the **Standard Gamepad** button layout which is supported by most controllers in which button locations are laid out in a left cluster of four buttons, a right cluster of four buttons, a center cluster of three buttons (some controllers have four) and a pair of front-facing buttons (shoulder buttons) on the left and right side of the gamepad.\n\nPlease note that since the Gamepad API is in very early stages, the standard gamepad button layout may differ from browser to browser. The image shown above describes the default button mappings as on **Chrome**.\n\n## Browser support\n\nAs of now the Gamepad specification is a work in progress and was published by the Web Applications Working Group(https://www.w3.org/2019/webapps/) as a working draft. The specification is intended to become a W3C recommendation.\n\nThe API itself is supported by all modern browsers(https://caniuse.com/#searchgamepad).\n\n!(/img/blogs/web-platforms-hidden-gems---gamepad-api/8.png)\n\nI would like to point out again that the Gamepad API is in very early stages so it may undergo major changes in terms of implementation and usage. But that shouldnt stop you from experimenting with it. So go ahead give it a try, add gamepad support to your existing games or maybe develop some new ones!\n\nIn the next blog post of the series, I would be covering the Device Orientation API(https://w3c.github.io/deviceorientation/spec-source-orientation.html). So keep an eye out on this space for more info.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:web-platforms-hidden-gems---gamepad-api},{frontmatter:{title:Web platforms hidden gems (series),url:web-platforms-hidden-gems-(series),date:Tue Mar 24 2020,metaDescription:The web has certainly grown a lot over the last half a decade and continues to grow at an enormous pace. The highlight of this explosive growth is the continuous addition of feature-rich APIs that enables developers to create much more interactive and efficient web applications. Enhancements such as GPU accelerated graphics/computation, lower-level APIs that provide better control and hardware access not only allow developers to cater to a wider spectrum of users but also to support various other platforms and use cases. This makes the web portable and extensible in the true sense. Even though these specifications are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like. Looking beyond the JavaScript framework landscape, there are a lot of nifty features that the web platform offers natively and its important for developers to know about these specifications and understand the possibilities that the native web has to offer!,metaKeywords:Web development, web api, web platform, native web, javascript api, javascript engine, javascript,metaImage:https://arunmichaeldsouza.com/img/blogs/web-platforms-hidden-gems-(series)/1.png},markdownBody:\n!(\u003c/img/blogs/web-platforms-hidden-gems-(series)/1.png\u003e)\n\nThe web has certainly grown a lot over the last half a decade and continues to grow at an enormous pace. The highlight of this explosive growth is the continuous addition of feature-rich APIs that enables developers to create much more interactive and efficient web applications.\n\nEnhancements such as GPU accelerated graphics/computation, lower-level APIs that provide better control and hardware access not only allow developers to cater to a wider spectrum of users but also to support various other platforms and use cases. This makes the web portable and extensible in the true sense.\n\nEven though these APIs are in very early stages at the moment, they seem to be really promising and tend to provide an idea on how web development in the coming years would look like.\n\nLooking beyond the JavaScript framework landscape, there are a lot of nifty features that the web platform offers natively and its important for developers to know about these specifications and understand the possibilities that the native web has to offer!\n\n!(\u003c/img/blogs/web-platforms-hidden-gems-(series)/2.png\u003e)\n\nThe browser has become more than just a renderer or a document viewer. Developers have been constantly pushing the boundaries of the web which has led to its common adoption as a software platform!\n\nAs an attempt to shed some light on these web platform APIs, I have decided to start the blog series - **Web platforms hidden gems**. The first blog post of the series would cover the Gamepad API(https://w3c.github.io/gamepad/) and would be published soon. So keep an eye out on this space for more info.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:web-platforms-hidden-gems-(series)},{frontmatter:{title:Using joypad.js for a better gaming experience on the web,url:using-joypad.js-for-a-better-gaming-experience-on-the-web,date:Wed Dec 12 2019,metaDescription:I still vividly remember playing games on my PC, the times when detailed polygon models werent a thing, open worlds were small and well, not that open (to be very honest) and online multiplayer gaming was still underway. For most games, controls mapped to a standard keyboard were fine to play with. But for games with more complex controls, it was just more viable to switch to a standard gamepad.,metaKeywords:gamepad, gaming, joypad, gamepad api, game development, gamer, game design, unity 3d, unreal engine, javascript, playstation, xbox, ps4,metaImage:https://arunmichaeldsouza.com/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/1.png},markdownBody:\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/1.png)\n\nI still vividly remember playing games on my PC, the times when detailed polygon models(https://en.wikipedia.org/wiki/Polygonal_modeling) werent a thing, open worlds were small and well, not that open (to be very honest) and online multiplayer gaming was still underway. For most games, controls mapped to a standard keyboard were fine to play with. But for games with more complex controls, it was just more viable to switch to a standard gamepad.\n\nDesktop games provide this flexibility to gamers majorly because they have native support for connecting external devices like gamepads and joysticks. But on the web its totally different, you just need a browser and either your mouse or keyboard becomes the controller.\n\nUsing a mouse to move around is fun, but it can turn out to be quite a daunting task for gamers that prefer more natural controls like a directional pad or a joystick for character movements.\n\nFor long there has been no native support in the browser for connecting gamepads or joysticks. Developers had to design mouse/keyboard based interfaces for game controls that can be tricky to operate and can take some time to get used to.\n\n## Press start to play 🎮\n\nTurns out a few years back the W3C introduced the Gamepad specification(https://w3c.github.io/gamepad/) which has been under constant development since then and has been implemented by various browser vendors (but is still subject to change). As stated in the spec -\n\n\u003e The Gamepad specification defines a low-level interface that represents gamepad devices.\n\nThis means that using this API, developers would be able to connect gamepads and similar input devices to the browser and be able to use them in their gaming applications. Sounds cool right? Its quite the contrary when you go about implementing it.\n\n## Enter boss stage ⚔️\n\nAs of now, only 2 events are supported by the gamepad API -\n\n**gamepadconnected** - indicates that a gamepad has been connected.\n\n**gamepaddisconnected** - indicates that a gamepad has been disconnected.\n\nThere is no standardized way to detect gamepad button presses or axis movements. The Gamepad interface(https://developer.mozilla.org/en-US/docs/Web/API/Gamepad) does return useful information about the gamepad buttons, axes and their current states (button press and axis movement values) but there is no actual event that is dispatched when these actions are performed by the user.\n\nThe **window.navigator.getGamepads()** method returns an array of Gamepad objects, one for each gamepad connected to the device. If you log out the 0th index (the first connected gamepad) you can see the gamepad info -\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/2.png)\n\nThe Gamepad interface stores information about the connected gamepad\n\nNotice that theres a mapping of all the buttons present on the gamepad. This mapping stores information about the button states.\n\nNow if you press any of the buttons and log the info out again, you would notice that the state doesnt change -\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/3.png)\n\nEven though it was pressed, the value remains **false**. That is because once after you release the button, the state of the button is reverted. So you cant really capture the button state (and as mentioned earlier there is no standard event for this) and the state is lost.\n\nWhat if we wrap this inside a **setInterval()** call -\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/4.png)\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/5.png)\n\nNow we are able to catch the button state as it updates, but is this the best way to do it?\n\n## Bonus round 🌟\n\nBefore answering that question, first lets try to understand why **setInterval()** is not the right candidate for this job.\n\nWe all know that in JavaScript everything runs on a single thread and the timer functions are no exception. To execute code using **setInterval()** we specify a callback that is executed every **x** milliseconds. The delays provided to these timer functions are some times not honored due to priority execution of resource-intensive tasks (if any in the task queue). This leads to inconsistent delay intervals.\n\nYou might have noticed a jank while using **setInterval()** to animate elements on the page. This is caused due to unnecessary and forceful reflows of the page elements even before the users screen is ready to process and render those updates. This is called Layout Thrashing(https://developers.google.com/web/fundamentals/performance/rendering/avoid-large-complex-layouts-and-layout-thrashing) and should be avoided at all costs!\n\nNow the next question is what could be the most efficient way to query the Gamepad objects if **setInterval()** is not the right solution?\n\n### requestAnimationFrame() to the rescue!\n\nAs stated on MDN -\n\n\u003e The **window.requestAnimationFrame()(https://developer.mozilla.org/en-US/docs/Web/API/window/requestAnimationFrame)** method tells the browser that you wish to perform an animation and requests that the browser calls a specified function to update an animation before the next repaint. The method takes a callback as an argument to be invoked before the repaint.\n\nThis basically means that the callback provided to **requestAnimationFrame()** is guaranteed to be executed at the start of the frame. The number of times the callback function is requested is around 60 times a second but will match the screens refresh rate.\n\nIn the context of a video game, a **game loop** is something that continuously checks for user input, updates the game state and renders the scene. **requestAnimationFrame()** seems to be fitting well for this as we can perform all these operations in its callback and it would remain in sync with the repaint tasks in every frame.\n\nIdeally thats how user input should be polled in a gaming application.\n\nId highly recommend checking this article - https://developer.mozilla.org/en-US/docs/Games/Anatomy(https://developer.mozilla.org/en-US/docs/Games/Anatomy) if you want to know more about how a typical game loop workflow can be implemented in JavaScript.\n\nNow coming back to the Gamepad API, querying the Gamepad objects and accessing the button/axis states can be done effectively using **requestAnimationFrame()** \\-\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/6.png)\n\nThis does give us the user input states as expected but we still need a way to store and discard these values in an efficient way. Ideally in the form of an API that can be exposed and reused in any gaming application.\n\n## Time to power up! 🍄\n\nId like to Introduce **joypad.js**(https://github.com/ArunMichaelDsouza/joypad.js) - a JavaScript library that lets you connect and use various gaming controllers with browsers that support the Gamepad API. Its less than 5KB in size with zero dependencies and has support for button press, axis movement events and vibration play effect.\n\nIts a utility library that I open-sourced a few months back under the MIT license(https://github.com/ArunMichaelDsouza/joypad.js#license). It exposes an event-based API(https://github.com/ArunMichaelDsouza/joypad.js#api) that can be used to subscribe to certain events that are detected and dispatched internally by the library.\n\nSubscribing to events is as simple as specifying an event name and a callback that is fired whenever the specified event is triggered.\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/7.png)\n\nThe following events are supported by the library -\n\n**connect** - Fired whenever a controller is connected.\n\n**disconnect** \\- Fired whenever a controller is disconnected.\n\n**button_press** - Fired whenever a controllers button is pressed.\n\n**axis_move** - Fired whenever a controllers axis (analog stick) is moved.\n\nTo know more about the joypad.js events please check out the detailed documentation here(https://github.com/ArunMichaelDsouza/joypad.js#events).\n\njoypad.js supports the standard gamepad button layout which is supported by most controllers in which button locations are laid out in a left cluster of four buttons, a right cluster of four buttons , a center cluster of three buttons (some controllers have four) and a pair of front-facing buttons (shoulder buttons) on the left and right side of the gamepad.\n\nPlease note that since the Gamepad API is in very early stages, the standard gamepad button layout may differ from browser to browser.\n\nThe following image describes the default button mappings as on **Chrome** -\n\n!(/img/blogs/using-joypad.js-for-a-better-gaming-experience-on-the-web/8.png)\n\nThe standard gamepad button layout can be overridden using the **customButtonMapping(https://github.com/ArunMichaelDsouza/joypad.js#custombuttonmapping-object)** setting and can be used for better cross-browser button mappings support.\n\nThe library also has support for adjusting the threshold for the axis (analog stick) movement which can be done using the **axisMovementThreshold(https://github.com/ArunMichaelDsouza/joypad.js#axismovementthreshold-number)** setting. To know more about all the settings please check the detailed documentation here(https://github.com/ArunMichaelDsouza/joypad.js#settings).\n\njoypad.js works on all modern browsers that support the Gamepad API. Please feel free to give it a try and provide your feedback. I would like to point out again that the Gamepad API is in very early stages so it may undergo major API changes. Ill try my best to keep the library up to date with the specification. Nonetheless, pull requests are welcomed for bug fixes and new features :)\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:using-joypad.js-for-a-better-gaming-experience-on-the-web},{frontmatter:{title:Loading images gracefully with react-image-appear,url:loading-images-gracefully-with-react-image-appear,date:Fri Apr 26 2019,metaDescription:Believe it or not, progressively loading images tend to degrade the overall user experience of a web application. And this can be more concerning for applications that rely heavily on high quality images. To fix this issue, a common technique is to display a placeholder image (for a short span) and replace it with the original image once it has loaded completely. In this blog post well be looking at a React JS based component called react-image-appear, which applies this very same technique and helps in loading images smoothly!,metaKeywords:javascript, react, reactjs, image loading, smooth loading, lazy loading, react-image-appear, javascript development, javascript frameworks,metaImage:https://arunmichaeldsouza.com/img/blogs/loading-images-gracefully-with-react-image-appear/1.png},markdownBody:\n!(/img/blogs/loading-images-gracefully-with-react-image-appear/1.png)\n\nBelieve it or not, progressively loading images tend to degrade the overall user experience of a web application. And this can be more concerning for applications that rely heavily on high quality images. To fix this issue, a common technique is to display a placeholder image (for a short span) and replace it with the original image once it has loaded completely.\n\nIn this blog post well be looking at a React JS based component called react-image-appear(https://github.com/ArunMichaelDsouza/react-image-appear), which applies this very same technique and helps in loading images smoothly!\n\n!(/img/blogs/loading-images-gracefully-with-react-image-appear/2.gif)\n\n## What is react-image-appear ?\n\nIt is a React JS component which makes images appear with transition as they load. It basically wraps an image within a placeholder element and adds a gif loader in between.\n\n## Usage\n\nFirstly the component needs to be installed using npm or yarn(https://github.com/ArunMichaelDsouza/react-image-appear#installation). Using it in your codebase is pretty straightforward, simply import the component and provide the required **src** prop with any of the available optional props.\n\n## Props\n\nApart from the required **src** prop there are various optional props that can be used to customise the image loading experience provided by react-image-appear. You can have custom loaders, placeholders, animations etc.\n\n!(/img/blogs/loading-images-gracefully-with-react-image-appear/3.gif)\n\n!(/img/blogs/loading-images-gracefully-with-react-image-appear/4.gif)\n\n!(/img/blogs/loading-images-gracefully-with-react-image-appear/5.gif)\n\nThis is the full props list -\n\n- **src** - The image source. This is a required prop.\n- **loader** \\- Adds a custom loader to the component. When not provided, applies a default one.\n- **loaderStyle** - Adds custom styling to the loader.\n- **loaderClass** - Adds CSS classes to the loader.\n- **placeholder** - Adds a placeholder background to the component.\n- **placeholderStyle** - Adds custom styling to the placeholder.\n- **placeholderClass** - Adds CSS classes to the placeholder.\n- **animation** - Add a CSS3 powered animation to the image as it appears. Default animation is **fadeIn**.\n- **animationDuration** \\- Specifies the animation duration for the image to appear. Default duration is **700ms**.\n- **easing** - Specifies the timing-function for the CSS3 powered animation. Default easing is **ease-in-out**.\n- **showLoader** - Specifies whether to show the loader or not. Default value is **true**.\n\nTo know more about the usage and examples for all the props, you can check out the complete documentation here(https://github.com/ArunMichaelDsouza/react-image-appear#props).\n\nThis project has also been ported to AngularJS 1.x - ng-image-appear(https://github.com/ArunMichaelDsouza/ng-image-appear).\n\nreact-image-appear is completely free to use and has been open sourced under the MIT license(https://github.com/ArunMichaelDsouza/react-image-appear#license). For its long term sustenance and growth I recently launched a Patreon page(https://www.patreon.com/arunmichaeldsouza)!\n\nIf you or your company use react-image-appear or any of my other projects, or like what Im doing, please consider backing me so I can continue maintaining and working on these projects and new ones. Your pledge could be as small as $1/month. Id really appreciate your support!\n\nThats it for now! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:loading-images-gracefully-with-react-image-appear},{frontmatter:{title:Easy JSON logging in Node JS using Woodlot,url:easy-json-logging-in-node-js-using-woodlot,date:Thu Apr 04 2019,metaDescription:There are a lot of options available when it comes to choosing a tool for data logging in your Node JS application. At times you would find yourself switching back and forth between different tools just to get that perfect logger configuration set up properly for your project. But of course, due to the instant availability of multiple open source JavaScript packages and tools (thanks to NPM) this doesnt only apply to loggers. It has spread across to almost every facet of JavaScript development now. But for the purpose of this blog post, lets just stick to Node JS data logging. A common need while developing applications is to have your data logs get aggregated in an output file, instead of just getting logged to the console or the standard output stream (stdout). This makes it easy to resolve bugs faster, gain insights from the data being logged and maybe analyse it at a later stage. For this very purpose we are required to use third-party data logging modules, and well be looking at one such open source module called Woodlot.,metaKeywords:woodlot, json logging, nodejs, nodejs logger, data logging, expressjs, restify, middleware logger,metaImage:https://arunmichaeldsouza.com/img/blogs/easy-json-logging-in-node-js-using-woodlot/1.png},markdownBody:\n!(/img/blogs/easy-json-logging-in-node-js-using-woodlot/1.png)\n\nThere are a lot of options available when it comes to choosing a tool for data logging in your Node JS application. At times you would find yourself switching back and forth between different tools just to get that perfect logger configuration set up properly for your project.\n\nBut of course, due to the instant availability of multiple open source JavaScript packages and tools (thanks to NPM(https://www.npmjs.com/)) this doesnt only apply to loggers. It has spread across to almost every facet of JavaScript development now. But for the purpose of this blog post, lets just stick to Node JS data logging.\n\nA common need while developing applications is to have your data logs get aggregated in an output file, instead of just getting logged to the console or the standard output stream (stdout). This makes it easy to resolve bugs faster, gain insights from the data being logged and maybe analyse it at a later stage.\n\nFor this very purpose we are required to use third-party data logging modules, and well be looking at one such open source module called Woodlot(http://adpushup.github.io/woodlot/).\n\n## What is Woodlot?\n\nWoodlot is an all-in-one JSON logging module for Node JS which was open sourced by AdPushup Inc(https://www.adpushup.com/). It supports -\n\n- HTTP middleware logging for Express JS(https://expressjs.com/), Restify(http://restify.com/) etc.\n- Custom logging with different logging levels.\n- Log output in JSON format with request body/query params, headers and cookies.\n- Apache common(http://httpd.apache.org/docs/current/logs.html#common) and combined(http://httpd.apache.org/docs/current/logs.html#combined) log formats as output.\n- Multiple file streams for log aggregation.\n- A simple to use events API.\n- Node JS version 0.10 and above.\n\nThe best part about using Woodlot is that you can use it to integrate middleware logging and custom logging both in your application, instead of installing separate modules.\n\nWoodlot logs JSON output by default which makes it easier to aggregate and understand the logged data.\n\n## Middleware Logging\n\nThe Woodlot **middlewareLogger** can be hooked into an existing Express JS middleware chain and can be used to log all HTTP requests.\n\nThis middleware logger configuration will generate log output in JSON format.\n\n!(/img/blogs/easy-json-logging-in-node-js-using-woodlot/2.png)\n\nThe Woodlot middleware logger supports whitelisting and strict checking for routes and user analytics (platform, country) logging as well. Apart from JSON format support, it also also has support for logging in Apaches access log formats.\n\nDocumentation on all of the different options that the middleware logger supports can be found here(https://github.com/adpushup/woodlot#as-an-expressjs-middleware).\n\n## Custom Logging\n\nThe Woodlot **customLogger** can be used to perform custom logging with different logging levels.\n\nThis custom logger configuration will generate log output in JSON format.\n\n!(/img/blogs/easy-json-logging-in-node-js-using-woodlot/3.png)\n\nThe Woodlot custom logger supports four different logging levels - info(https://github.com/adpushup/woodlot#info), debug(https://github.com/adpushup/woodlot#debug), warn(https://github.com/adpushup/woodlot#warn) and err(https://github.com/adpushup/woodlot#err). It supports data logging in standard text format as well.\n\nDocumentation on all of the different options that the custom logger supports can be found here(https://github.com/adpushup/woodlot#custom-logging).\n\n## Events\n\nWoodlot emits events at various operations that can be used to track critical data. This events API is what makes Woodlot truly extensible.\n\nThese events can be captured and can be sent to a third party service or to a database for aggregation and analysis.\n\n!(/img/blogs/easy-json-logging-in-node-js-using-woodlot/4.png)\n\nThere are various middleware logger and custom logger events that Woodlot emits. Documentation of the Woodlot events API can be found here(https://github.com/adpushup/woodlot#events).\n\nWoodlot is completely free to use and has been open sourced under the MIT license(https://github.com/adpushup/woodlot#license). For its long term sustenance and growth I recently launched a Patreon page(https://www.patreon.com/arunmichaeldsouza)!\n\nIf you or your company use Woodlot or any of my other projects, or like what Im doing, please consider backing me so I can continue maintaining and working on these projects and new ones. Your pledge could be as small as $1/month. Id really appreciate your support!\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:easy-json-logging-in-node-js-using-woodlot},{frontmatter:{title:Aliasing module paths in Node JS,url:aliasing-module-paths-in-node-js,date:Fri Jan 04 2019,metaDescription:Typing out long and error-prone paths to your Node JS modules can be a daunting task! Even with code-completion features like IntelliSense in place (which is supported by almost every IDE or text editor), this can become more challenging as your codebase grows. Just imagine changing the directory structure of your project and youre forced to change all occurrences of the modules currently being referenced multiple times throughout your project. Its a maintenance nightmare! Moreover, it looks damn ugly! Code should be easy to read and understand. And with the current module systems in Node JS or JavaScript in general, this can turn out to be a problem since these systems dont have native support for meaningful referencing. An alias to a module path clearly indicates the location and purpose of the module being used. Dots and slashes hardly tell anything!,metaKeywords:module aliasing, babel, webpack, javascript, nodejs, symlinks, vscode, javascript development, javascript frameworks,metaImage:https://arunmichaeldsouza.com/img/blogs/aliasing-module-paths-in-node-js/1.png},markdownBody:\n!(/img/blogs/aliasing-module-paths-in-node-js/1.png)\n\n## The \Relative path hell\ Problem\n\nTyping out long and error-prone paths to your Node JS modules can be a daunting task!\n\nEven with code-completion features like IntelliSense(https://en.wikipedia.org/wiki/Intelligent_code_completion) in place (which is supported by almost every IDE or text editor), this can become more challenging as your codebase grows.\n\nJust imagine changing the directory structure of your project and youre forced to change all occurrences of the modules currently being referenced multiple times throughout your project. Its a maintenance nightmare!\n\nMoreover, it looks damn ugly!\n\nCode should be easy to read and understand. And with the current module systems in Node JS or JavaScript in general, this can turn out to be a problem since these systems dont have native support for meaningful referencing.\n\n\u003e An alias to a module path clearly indicates the location and purpose of the module being used. Dots and slashes hardly tell anything!\n\n!(/img/blogs/aliasing-module-paths-in-node-js/2.png)\n\n## The Solution\n\nThere might be a possible solution to this \relative path hell\ problem -\n\n**Symlinks**\n\n\u003e A Symlink or a Symbolic Link(https://en.wikipedia.org/wiki/Symbolic_link) is simply a shortcut or a reference to another file. It is a file that points to another file.\n\nBasically, you can create symlinks to your modules and have your Node JS app refer to these modules using the created symlinks.\n\nSymlinks can be created using the **ln(https://www.computerhope.com/unix/uln.htm)** command available on Linux/UNIX/Mac. If youre not already on Windows 10 then youre probably not leveraging the linux bash shell that comes bundled with it (more info(https://www.howtogeek.com/249966/how-to-install-and-use-the-linux-bash-shell-on-windows-10/)), in that case, you can use the standard Windows **mlink**(https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/mklink) command.\n\nBut wait a minute, you dont actually have to manually create all these symlinks by yourselves. Instead, you can write a simple Node JS script which can automate the symlink creation process for you. The Node JS file system(https://nodejs.org/api/fs.html) module exposes the **fs.symlink(https://nodejs.org/api/fs.html#fs_fs_symlink_target_path_type_callback)** method which can be used for creating symlinks for directories or files.\n\n## Good News!\n\nTheres an existing NPM package which can do this job for you called **link-module-alias**(https://github.com/Rush/link-module-alias).\n\nSimply add the required module aliases into your projects **package.json** file and add a **postinstall** script, which will automatically initialise the symlink creation process for you.\n\n!(/img/blogs/aliasing-module-paths-in-node-js/3.png)\n\nAfter your configuration is complete, simply run -\n\n**npm install** \\- Installs your projects dependencies and automatically executes the postinstall script.\n\nor\n\n**npm run postinstall** - Only executes the postinstall script.\n\nOnce the postinstall script executes, it makes a call to link-module-alias which creates the required symlinks for your project. Your Node JS app will then be able to resolve all references to the defined aliases.\n\n!(/img/blogs/aliasing-module-paths-in-node-js/4.png)\n\nNow whenever you are requiring your modules, you can simply do this -\n\n!(/img/blogs/aliasing-module-paths-in-node-js/5.png)\n\nNo matter where you are in your project tree, all your aliased modules will resolve successfully.\n\n## The icing on the cake\n\nIf you happen to use VS Code(https://code.visualstudio.com/) then all of your aliased modules and directories will have their files appear in the VS Code autocompletion drop-down, which makes it super handy to use your aliased modules!\n\n!(/img/blogs/aliasing-module-paths-in-node-js/6.png)\n\nAnother plus point to be mentioned here is that this particular approach doesnt need any runtime hooks in your apps entry point, unlike other approaches to solve this problem which rely on runtime hooks. Runtime hooks add a level of unnecessary computation and complexity to your app. If by any chance a runtime hook fails, it might crash your entire app.\n\n## Update (2021): Subpath Imports\n\nSupport for subpath imports(https://nodejs.org/api/packages.html#subpath-imports) was added in Node JS v14.6.0, v12.19.0 which helps in the creation of import maps that only apply to import specifiers from within the package itself. Entries in the imports field must always start with **\\#** to ensure they are disambiguated from package specifiers.\n\n!(/img/blogs/aliasing-module-paths-in-node-js/7.png)\n\n## Other solutions\n\n1. **module-alias**\n\n If you have no issues with require hooks then you can consider this package - module-alias(https://github.com/ilearnio/module-alias). There are a few gotchas though that youll need to keep in mind while using this package. For example, this package **modifies the default require behavior!** And should be used with caution.\n\n2. **Yarn Workspaces** \n Yarn Workspaces(https://yarnpkg.com/lang/en/docs/workspaces/), in particular, cater to JavaScript projects which have multiple internal packages (also called workspaces) as dependencies. Each workspace has its own dependencies and can be linked to the global workspace for easy access.\n3. **Webpack Resolve** \n If youre bundling your modules with webpack, then you can use webpacks module resolution options(https://webpack.js.org/configuration/resolve/) to set aliases for your modules. This obviously makes sense on the client side where you are transpiling and bundling your JavaScript code with webpack.\n4. **babel-plugin-module-resolver** \n The babel module resolver plugin(https://github.com/tleunen/babel-plugin-module-resolver) can be used with the babel transpilation pipeline to resolve modules with custom aliases for directories or specific files.\n\nThat pretty much sums it up! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:aliasing-module-paths-in-node-js},{frontmatter:{title:Updating state of a parentless component in React,url:updating-state-of-a-parentless-component-in-react,date:Thu Dec 28 2017,metaDescription:State is the fundamental way to store and retrieve your React application’s data. It’s nothing but a JavaScript object, which React allows you to update via the setState() method.,metaKeywords:javascript, react, reactjs, javascript development, javascript frameworks,metaImage:http://arunmichaeldsouza.com/img/blogs/updating-state-of-a-parentless-component-in-react/1.png},markdownBody:\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/1.png)\n\nState is the fundamental way to store and retrieve your React applications data. Its nothing but a JavaScript object, which React allows you to update via the **setState()** method.\n\nUsing **setState()** is pretty straightforward, simply call the method and pass in the state variables that need to be updated, which in turn, re-renders the component tree.\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/2.png)\n\nSince **setState()** updates the state of a particular React component, it needs to be called within that components context.\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/3.png)\n\nIn the example above, **this** provides the context to the **setState()** call, which refers to the **InputBox** component.\n\n\u003e Note : **setState()** is actually asynchronous. More info here(https://reactjs.org/docs/react-component.html#setstate).\n\nAs mentioned earlier, **this** represents the component itself. If you log it out, youll see that it returns the **state** and **props** tied to the component.\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/4.png)\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/5.png)\n\nLogging out **this** returns the whole React component\n\nNow this means that updating the state of a React component can be as easy as this -\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/6.png)\n\nA suitable method to update the state of a **Parentless** component would be to pass a callback as a prop, to the **Child** component, which once fired, updates the state of the **Parent**.\n\nPretty handy! But this obviously makes sense when you have a relatively smaller component tree, and you would want to avoid returning callbacks from a deeply nested component, all the way up to the topmost parent.\n\nBut what if we want to update the state of the topmost parent, from a deeply nested component ?\n\nWell, we can keep a reference of the topmost parents component instance, and call **setState()** when we want to trigger the state change.\n\nLets see how -\n\n\u003e Note : **ReactDOM.render()** returns a reference to the component being mounted.\n\nAs you can see, we can simply create a **function** at the global level and call it from our **DeeplyNestedChild** and pass the value for the state variable to be changed in the **Parent** component. Once called, we can set the state of the **Parent** component using its reference returned by **ReactDOM.render()**.\n\nThis method can majorly help in cases, where we want to update the state of a **Parent** component in one component tree, from a **Child** component of some other component tree, considering if one of the component trees is getting dynamically generated using, say for example a **Portal(https://reactjs.org/docs/portals.html)**.\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/7.png)\n\nOnly want to trigger a re-render? You can do so using **forceUpdate()(https://reactjs.org/docs/react-component.html#forceupdate)** -\n\n!(/img/blogs/updating-state-of-a-parentless-component-in-react/8.png)\n\nThats it for now! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:updating-state-of-a-parentless-component-in-react},{frontmatter:{title:Getting started with React 16,url:getting-started-with-react-16,date:Mon Nov 13 2017,metaDescription:It’s been some time since Facebook released React 16. The new release has a lot of new features to facilitate the designing of robust components and enhancements to speed up the rendering pipeline.,metaKeywords:javascript, react16, react, es6, reactjs,metaImage:http://arunmichaeldsouza.com/img/blogs/getting-started-with-react-16/1.png},markdownBody:\n!(/img/blogs/getting-started-with-react-16/1.png)\n\nIts been some time since Facebook released React 16(https://reactjs.org/blog/2017/09/26/react-v16.0.html).\n\nThe new release has a lot of new features to facilitate the designing of robust components and enhancements to speed up the rendering pipeline.\n\nReact 16 is supposed to be completely backwards compatible with React 15. As stated in the official React 16 blog post(https://reactjs.org/blog/2017/09/26/react-v16.0.html#upgrading) -\n\n\u003e If your app runs in 15.6 without any warnings, it should work in 16.\n\nReact 16 also ships with the new MIT license(https://opensource.org/licenses/MIT). If you havent followed the news as to why the React team has switched to the new license, be sure to read this article(https://medium.freecodecamp.org/facebook-just-changed-the-license-on-react-heres-a-2-minute-explanation-why-5878478913b2).\n\nTalking about its stability, the React team has been serving the production build of React 16 to Facebook(https://www.facebook.com/) and Messenger(https://www.messenger.com/). Despite the new feature additions, it is 32% lesser in size as compared to the previous release.\n\nNow without wasting any more time, lets talk about the features of React 16.\n\n## Fragments and Strings\n\nReact 16 gives you the ability to return elements in an **array** from the render method.\n\n!(/img/blogs/getting-started-with-react-16/2.png)\n\nThat means, for the most part, you wont be required to perform mapping of array elements inside your render methods. Simply return the array and itll render just fine.\n\nThe only downside here is that it still expects a **key** value to be added to every array element in order to work.\n\nI feel its not that big of an issue, plus the React team has assured that the future release of React will most probably have this requirement removed.\n\nEven **strings** and **numbers** can be returned from the render method now.\n\n!(/img/blogs/getting-started-with-react-16/3.png)\n\nPrevious versions of React used to throw this error -\n\n!(/img/blogs/getting-started-with-react-16/4.png)\n\nStrings and numbers cannot be returned from the render method in React 15\n\nAs you can see, only valid React elements were allowed to be returned from the render method.\n\nWith React 16, the render method can return -\n\n\\- React elements \n\\- Strings and numbers \n\\- Portals \n\\- Null \n\\- Boolean expressions\n\n**Strings** and **numbers** are rendered as regular **text nodes** in the DOM, and as you wouldve guessed, **null** renders nothing.\n\n**UPDATE** : React 16.2 was released on November 28th, which has improved support for returning multiple children (aka Fragment) from a components render method. More info on the same can be found on the official blog post(https://reactjs.org/blog/2017/11/28/react-v16.2.0-fragment-support.html).\n\n## Error Boundaries\n\nError Boundaries help you to catch run time errors in your app and allow you to render a fallback UI.\n\nWhen an error occurred, previous versions of React used to leave your app in a broken state. In order to tackle this, React 16 provides a brand new lifecycle hook called **componentDidCatch**, which helps you to catch run time errors.\n\nError Boundaries capture errors **inside their subtree**, which means if an error occurs in any of the child components within that Error Boundary, then the componentDidCatch lifecycle method of that particular Error Boundary will fire.\n\n!(/img/blogs/getting-started-with-react-16/5.png)\n\ncomponentDidCatch returns two parameters - an **error** object which gives you the stack trace, and an **info** object, which gives the component stack data.\n\n### How Error Boundaries work\n\n!(/img/blogs/getting-started-with-react-16/6.gif)\n\nFew things to note here -\n\nErrors in **all lifecycle methods** can be caught by an Error Boundary, including the **constructor** method.\n\nAn Error Boundary cannot catch an error within itself.\n\nIf an Error Boundary fails for some reason, the error will propagate to the closest Error Boundary above it.\n\nHeres an example on how to create and use an Error Boundary -\n\nIn the above example, when an error is thrown in the **Child** component (line no 17), the componentDidCatch lifecycle method of the **Parent** component fires (line no 33). Based on that, we change the state and render a fallback UI in its place (line no 38).\n\n### What happens when an error occurs ?\n\nOnce an error occurs, **error stack trace** and **component stack data** are logged to the console, and the component tree is unmounted from the root. This prevents from showing corrupted data to the user.\n\n!(/img/blogs/getting-started-with-react-16/7.png)\n\n!(/img/blogs/getting-started-with-react-16/8.png)\n\nBut is there really a need to unmount the whole React component tree ? Well, the React team has debated this decision, and in their experience it is worse to leave corrupted UI in place than to completely remove it. Read more about it here(https://reactjs.org/blog/2017/07/26/error-handling-in-react-16.html#new-behavior-for-uncaught-errors).\n\n## Portals\n\nPortals let you render or teleport a child node into a different DOM node hierarchy.\n\n!(/img/blogs/getting-started-with-react-16/9.png)\n\nThe first argument passed to a portal is a **child** component, which is any renderable entity (what the render method supports) and a **DOM node**, to which the child is mounted.\n\nPortals can typically be used to render hovercards or modals, where the content is to be shown in a visually different and non-contained fashion, out of its parent.\n\n### How Portals work\n\n!(/img/blogs/getting-started-with-react-16/10.gif)\n\nHow Portals work\n\nThe above illustration shows the process of creating a portal in order to render a **Text** component from DOM hierarchy 1, into DOM hierarchy 2 via the **modal** node.\n\nThe **Modal** component creates a portal which mounts the Text component to a different DOM hierarchy.\n\nHeres the code for the above example -\n\n### Event Bubbling in Portals\n\nEvent Bubbling in Portals works the same way as it does for normal React components regardless of its position in the DOM tree.\n\nAn event fired from inside a portal will propagate to ancestors in the containing React tree, even if those elements are not ancestors in the DOM tree.\n\nIn this case, the button in the Modal component has no **onClick** handler, so once a user clicks on that button, the event propagates to its ancestor in the component tree, and the **onClick** handler of that component fires.\n\n## Custom DOM attributes\n\nWith React 16, you can pass custom attributes to your React components.\n\nIn the past, React used to ignore unknown DOM attributes. If you wrote JSX with an attribute that React doesnt recognize, React would just skip it. But React 16 allows them to be added to the component.\n\n!(/img/blogs/getting-started-with-react-16/11.png)\n\n!(/img/blogs/getting-started-with-react-16/12.png)\n\nNote that you should still use the canonical React naming for known attributes -\n\n!(/img/blogs/getting-started-with-react-16/13.png)\n\n### Attributes whitelist\n\nPrevious versions of React used to have an attributes whitelist, which contained a list of attributes that React can recognize and allow them to be added to components.\n\n!(/img/blogs/getting-started-with-react-16/14.png)\n\nReact 16 gets rid of this, so theres no more attribute matching with the whitelist resulting in smaller file sizes.\n\n!(/img/blogs/getting-started-with-react-16/15.png)\n\n!(/img/blogs/getting-started-with-react-16/16.png)\n\nCustom attributes are handy if you need to use a non-standard attribute, or if you need to integrate with a third-party library that relies on such attributes. Just like before, React 16 also lets you use **data-** and **aria-** attributes with your components.\n\n## New core architecture\n\nReact 16 has an entirely re-written architecture codenamed **Fiber**.\n\n### Async rendering\n\nThe new core algorithm is completely backwards compatible and is based on a **priority scheduling** system. Events are streamed based on priority and are scheduled to be rendered by the browser, and this method does not block the main thread.\n\nEvents such as **typing** are considered to be high priority events, where the user needs to get realtime feedback, others such as ajax are considered low priority events.\n\nThe scheduling system makes heavy use of the **requestIdleCallback** API.\n\nThis method queues a function to be called during a browsers idle periods. This enables developers to perform background and low priority work on the main event loop, without impacting latency-critical events such as animation and input response.\n\nIn browsers where this API is not supported, React provides a polyfill.\n\nIf you want to know more about how Fiber works, I would definitely recommend you to check out this talk(https://www.youtube.com/watch?vZCuYPiUIONs\u0026index5\u0026listPLb0IAmt7-GS3fZ46IGFirdqKTIxlws7e0) by Lin Clark, or read about the details in this blog post(https://code.facebook.com/posts/1716776591680069/react-16-a-look-inside-an-api-compatible-rewrite-of-our-frontend-ui-library/) by the React team.\n\n## Improved server-side rendering\n\nThe server-side renderer in React 16 has also been re-written. It is said to be **3x faster**.\n\nIt provides faster streaming of components down the wire, to the client.\n\nThe new packaging strategy (which is facilitated by the Rollup module bundler(https://rollupjs.org/)) gets rid of **process.env checks**, which are really slow.\n\nReact 16 supports streaming of components via the new **renderToNodeStream(https://reactjs.org/docs/react-dom-server.html#rendertonodestream)** API. Feel free to check out the documentation of **ReactDOMServer**(https://reactjs.org/docs/react-dom-server.html) for more details.\n\nOne of the core React team members, Sasha Aickin, wrote a great article(https://hackernoon.com/whats-new-with-server-side-rendering-in-react-16-9b0d78585d67) about React 16s SSR improvements.\n\nAs stated in the blog post -\n\n\u003e When comparing against React 15 with process.env compiled out, theres about a 2.4x improvement in Node 4, about a 3x performance improvement in Node 6, and a full 3.8x improvement in the new Node 8.4 release. And if you compare against React 15 without compilation, React 16 has a full order of magnitude gain in SSR in the latest version of Node!\n\n!(/img/blogs/getting-started-with-react-16/17.png)\n\n## Reduced file size\n\nDespite all the new feature additions, React 16 is actually **smaller** as compared to 15.6.1!\n\n!(/img/blogs/getting-started-with-react-16/18.png)\n\nThe size difference is partly attributable to a change in packaging. React now uses Rollup to create flat bundles for each of its different target formats, resulting in both size and runtime performance wins.\n\n## Installation\n\nYou can get started with React 16 right away, its available on NPM and Yarn.\n\n!(/img/blogs/getting-started-with-react-16/19.png)\n\nDetailed installation instructions can be found here(https://reactjs.org/docs/installation.html). Details on deprecations and breaking changes can be found here(https://reactjs.org/blog/2017/09/26/react-v16.0.html#upgrading).\n\nI also presented a talk on React 16 sometime back, you can check out the deck here(https://speakerdeck.com/arunmichaeldsouza/getting-started-with-react-16), which was retweeted(https://twitter.com/amdsouza92/status/919986205168513024) by Dan Abramov as well.\n\nThats it for now! If you have any questions or suggestions, dont forget to leave a comment down below. Also, feel free to say hi 👋 to me on Twitter(https://twitter.com/amdsouza92) and Github(https://github.com/ArunMichaelDsouza).\n\nCheers!\n,slug:getting-started-with-react-16},title:Arun Michael Dsouza,description:Ramblings on web development, JavaScript, open source and tech in general.},__N_SSG:true},page:/,query:{},buildId:YMDQPiVmplN7PEyWOgvCb,isFallback:false,gsp:true,scriptLoader:}/script>/body>/html>
View on OTX
|
View on ThreatMiner
Please enable JavaScript to view the
comments powered by Disqus.
Data with thanks to
AlienVault OTX
,
VirusTotal
,
Malwr
and
others
. [
Sitemap
]