<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: 🇨🇵️ Nathan Graule</title>
    <description>The latest articles on DEV Community by 🇨🇵️ Nathan Graule (@solarliner).</description>
    <link>https://dev.to/solarliner</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F96048%2F154937b5-6ae4-4ed5-ad99-3cc366b13c62.jpg</url>
      <title>DEV Community: 🇨🇵️ Nathan Graule</title>
      <link>https://dev.to/solarliner</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/solarliner"/>
    <language>en</language>
    <item>
      <title>A colorful journey</title>
      <dc:creator>🇨🇵️ Nathan Graule</dc:creator>
      <pubDate>Fri, 22 May 2020 13:22:10 +0000</pubDate>
      <link>https://dev.to/solarliner/a-colorful-journey-28pf</link>
      <guid>https://dev.to/solarliner/a-colorful-journey-28pf</guid>
      <description>&lt;p&gt;Aahhh, computer color. Red, green and blue phosphors illuminated by an electron guided by a carefully-controlled&lt;br&gt;
 magnetic field, quick enough so that the human eye doesn't see the previous image dim down before the next is sent through... Wait this ins't the 80s anymore you say?&lt;/p&gt;

&lt;h1&gt;
  
  
  What is color, anyway?
&lt;/h1&gt;

&lt;p&gt;Our eyes work in a fascinating way. Nature has devised a way to count how many photons enter it (though not literally, reality is &lt;a href="https://en.wikipedia.org/wiki/Wave%E2%80%93particle_duality"&gt;much more nuanced&lt;/a&gt;). Whats more is that they don't count all photons the same way - we have different receptors for different frequencies of light - 4 of them in fact: Rods which react to pretty much any light ray in the visible spectrum, and Long , Medium and Short cones which react respectively to short, medium and long frequencies of light.&lt;/p&gt;

&lt;p&gt;No, that's not confusing because when talking about light, we often use the term "wavelength" instead of frequency; and since the wavelength of a light ray is inversely proportional to its frequency, Short cones are sensitive to short wavelengths, and so on.&lt;/p&gt;

&lt;p&gt;These cones each contribute a part of what we see as "color", while the rods in our eye sense more of a general brightness. The Short cone sense what we perceive as blue, the Medium cone if for greens, and the Long cone is all about the red color.&lt;/p&gt;

&lt;h1&gt;
  
  
  Formalizing color: XYZ
&lt;/h1&gt;

&lt;p&gt;Back before any of this computery stuff had been thought of, in 1931, the &lt;a href="https://en.wikipedia.org/wiki/International_Commission_on_Illumination"&gt;Commission Internationale de l'Éclairage&lt;/a&gt; (International Commission for Illumination, abbreviated as CIE) ran a survey on vision and ended up on a method to map out spectral data (the intensity of light rays at a given wavelength, formally named &lt;a href="https://en.wikipedia.org/wiki/Spectral_power_distribution"&gt;Spectral Power Distribution&lt;/a&gt; or SPD) into how much each of our cones respond; and thus, the &lt;strong&gt;CIE XYZ&lt;/strong&gt; color space was born.&lt;/p&gt;

&lt;p&gt;The XYZ color space maps out spectral data by using &lt;strong&gt;color matching functions&lt;/strong&gt; which represent the sensitivity of each color component to the spectrum of light. We can then calculate how much of the X, Y and Z components a particular SPD gives, and get a good estimation of the excitation level of each cone. This is useful in, for example, representing &lt;a href="https://en.wikipedia.org/wiki/Black-body_radiation"&gt;Black-body radiation&lt;/a&gt; on a computer monitor.&lt;/p&gt;

&lt;p&gt;In more formal math terms, this means we integrate a product of our SPD and each of the color-matching functions over the entire spectrum to get an intensity of each channel. We can form a 3-dimensional vector with the resulting values, which we can then work on, and formalize the notion of color as a vector in a vector space with the "traditional" addition and products - encoding mathematically the notion of the additivity of color.&lt;/p&gt;

&lt;h1&gt;
  
  
  The idea of chromaticity and working with xyY
&lt;/h1&gt;

&lt;p&gt;In the XYZ color space, because our Medium cones (green colors) is much more sensitive and covers a greater range of the visible light, the Y component works really well in approximating brightness (though, not quite, see LAB later). Therefore we can generate another color space that separates "colorfulness" and "brightness" - the result is still 3 components (forming a 3D vector still), but it has the added benefit that since brightness is kind of arbitrary, we can focus on the more interesting property of light: its colorfulness, or formally, its &lt;strong&gt;chromaticity&lt;/strong&gt; (because we like big words!).&lt;/p&gt;

&lt;p&gt;In other words, we can only work with XZ values by scaling the XYZ color so that the Y component is exactly 1.0, and we end up with a xyY space, which we usually only plot the x and y values into a 2D graph, as they are much easier to work with. What we end up with, is the famous (maybe?) "horseshoe" diagram, or &lt;strong&gt;gamut diagram&lt;/strong&gt;:&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--V7Uxba0q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://upload.wikimedia.org/wikipedia/commons/thumb/b/ba/PlanckianLocus.png/533px-PlanckianLocus.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--V7Uxba0q--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://upload.wikimedia.org/wikipedia/commons/thumb/b/ba/PlanckianLocus.png/533px-PlanckianLocus.png" alt="Spectral and Plankian locus"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The outer edge of the diagram, making out the horse-shoe shape, is the &lt;strong&gt;spectral locus&lt;/strong&gt;, sometimes also called the monochromatic locus. They're basically the chromaticity values lasers of each wavelength would take. Inside, each chromaticity value corresponds to a color the human eye can see - outside this edge are colors we can't see, or at least not fully. If the chromaticity value is negative in either direction, the color is called "imaginary" - it can't be made in real life (it'd have a negative SPD, and negative intensities don't strictly exist).&lt;/p&gt;

&lt;p&gt;The line in the middle with colors in the Kelvin scale is the Plankian locus - its the chromaticities of objects emitting black-body radiation - like our star, the Sun. The Sun emits a warm 5800 K which if you look it up on the gamut diagram, translates to a slightly yellow white. The Sun isn't white!&lt;/p&gt;

&lt;p&gt;Note: the xy chromaticities have a third component, z, defined such that x + y + z = 1. This is a point that has some&lt;br&gt;
 value&lt;br&gt;
 in the&lt;br&gt;
 next section.&lt;/p&gt;

&lt;h1&gt;
  
  
  Making out color from primaries: RGB colors
&lt;/h1&gt;

&lt;p&gt;It turns out, you can make all the colors in the above diagram by taking 3 chromaticities that aren't aligned - this corresponds to taking 3 colors such that the third can't be made by mixing the other two. So if you've ever had an argument in whether green or yellow is a primary color; well the answer is both and neither, &lt;em&gt;at the same time&lt;/em&gt;. This because you can take 3 xy points such that they for a triangle, and call that a color space - wether it's red-green-blue or red-yellow-blue or orange-turquoise-purple, they're all valid primaries, and therefore all valid color spaces.&lt;/p&gt;

&lt;p&gt;There's an added complexity, though. Because the xy plane only defines color, we have lost the definition of black and white. If there is sort of a white color appearing in the above gamut, it's because it's the point where the x and y values are equal - but this &lt;strong&gt;does not&lt;/strong&gt; define what "white" is.&lt;/p&gt;

&lt;p&gt;Instead, this is left to us to define what we will consider as white, and out of the many definitions of white these 3 are the most used:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Illuminant E&lt;/strong&gt;: E stands for Equal-energy and is the point where the x, y, and z chromaticity components are all equal at 1/3 - this is maybe the most natural white point given the gamut diagram, however it gives a warmer tint to the color space as the equal-energy point feels itself as having a blue tint.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Illuminant D65&lt;/strong&gt;: D stands for Daylight, and 65 is for taking a blackbody radiating at 6500 K as the white point. This is also the color of the overcast sky.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Illuminant D50&lt;/strong&gt;: A warmer Daylight white point taken as the blackbody radiation of 5000 K.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;There are other categories and other illuminants, but these are the most used ones.&lt;/p&gt;

&lt;p&gt;Choosing these 4 values (the red, green, blue and white points) is important as they define the amount of colors the color space can reproduce. Indeed, only colors &lt;em&gt;inside&lt;/em&gt; the "gamut triangle" formed by the primaries can be encoded and reproduced.&lt;/p&gt;

&lt;h2&gt;
  
  
  An example: &lt;a href="https://en.wikipedia.org/wiki/SRGB"&gt;sRGB&lt;/a&gt;
&lt;/h2&gt;

&lt;p&gt;sRGB is the standard color space devised by HP and Microsoft in 1996 and went on to be, as the name suggest, the standard color space of monitors, images and printers.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--4tFfqArO--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://upload.wikimedia.org/wikipedia/commons/thumb/6/60/Cie_Chart_with_sRGB_gamut_by_spigget.png/430px-Cie_Chart_with_sRGB_gamut_by_spigget.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--4tFfqArO--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://upload.wikimedia.org/wikipedia/commons/thumb/6/60/Cie_Chart_with_sRGB_gamut_by_spigget.png/430px-Cie_Chart_with_sRGB_gamut_by_spigget.png" alt="sRGB color gamut diagram"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Out of the all the colors you can make, sRGB can only encode a small amount of them, which doesn't make it a very good color space. However at the time, CRT monitors were the best technology there was, and these were the colors they could reproduce.&lt;/p&gt;

&lt;h1&gt;
  
  
  The catch: RGB colors are not linear
&lt;/h1&gt;

&lt;p&gt;The human eye is, unfortunately, far from perfect. Not only do you only see "correctly" for only 2° around the center of your vision, that your peripheral vision is only in black-and-white, but you don't perceive colors &lt;em&gt;linearly&lt;/em&gt;. Indeed, if you have one light-bulb turned on, and you turn a second one on, suddenly everything is twice as bright. But if you turn on a 3rd one, the whole room is only a third brighter. However, to a camera sensor, or spectrometer, you still added one light-bulb every time.&lt;/p&gt;

&lt;p&gt;We perceive light &lt;strong&gt;logarithmically&lt;/strong&gt;, that is we are more sensitive to changes in low-light conditions than to the same changes in well-lit situations. This means, darker areas of an image would have more "brightness definition" than lighter areas. And with only 8 bits per channel to spare, this would quickly lead to artifacts in dark patches of images. Therefore, sRGB transforms the linear RGB values by &lt;strong&gt;gama-correcting&lt;/strong&gt; them.&lt;/p&gt;

&lt;p&gt;This is all fine until you want to manipulate images - as is the case with anything from adding a watermark to pictures to creating photo montages to editing blockbuster VFX on top of camera footage. Because by applying this gamma correction to our RGB values, the principle that "color is additive" is broken.&lt;/p&gt;

&lt;p&gt;However, for a long time (and even in Photoshop at least up until recently), image manipulation programs have taken the naive approach to work on gamma-corrected color directly, leading to unnatural results when applying filters (such as blurring an image) or layering (the "Add" blending mode really isn't additive, and the "Screen" blending mode is a pale attempt at making a "visually decent" additive blending mode while still working with gamma-corrected values). Ideally, if you juxtapose a red and a green square, and blur the resulting image, ideally you should see a slight yellow tone emerge (the red color "transitions" linearly from the red square to the green square in the xy plane, therefore passing by yellow hues). Instead, when working on gamma-corrected values the naive way, the blending yields darker values. See &lt;a href="https://ninedegreesbelow.com/photography/linear-gamma-blur-normal-blend.html"&gt;this page&lt;/a&gt; for examples and a more in depth look.&lt;/p&gt;

&lt;p&gt;More formally, gamma correction isn't a linear map, and therefore the XYZ or RGB vector space will lose the properties of additions and multiplication defined in those input spaces. Simply put, the resulting vector space is &lt;em&gt;not&lt;/em&gt; linear, and therefore linear addition/multiplication operations will &lt;em&gt;not&lt;/em&gt; work as expected.&lt;/p&gt;

&lt;h1&gt;
  
  
  Conclusion: In practice
&lt;/h1&gt;

&lt;p&gt;If you worry about me researching about computer color just to write a blog post about it, don't worry - this is the compilation of the few weeks I've spent gathering around data to write a Rust crate working with raw color; and I&lt;br&gt;
 needed this crate for a project that I didn't really finish, but was about rendering black holes, and needed to generate colors from black body radiation, straight from spectral data, computed from Plankian equations. Fun!&lt;/p&gt;

&lt;p&gt;All in all, computer color is a mess; and there's no sign of anything that can be done here. Given all the variables&lt;br&gt;
 that exist in capture, storage and display technology, getting to represent colors as accurately as they happen in&lt;br&gt;
  reality is something closer to black magic wizardry than engineering. This is why working with colors is so hard&lt;br&gt;
  , and why working as a digital artist involves complicated pipelines.&lt;/p&gt;

&lt;p&gt;And this also means that nobody, especially myself, should do what I did: implement it all from scratch.&lt;/p&gt;

&lt;h1&gt;
  
  
  Appendix
&lt;/h1&gt;

&lt;p&gt;&lt;em&gt;&lt;a href="https://unsplash.com/photos/UBhpOIHnazM"&gt;Cover photo&lt;/a&gt; by Ajeet Mestry on Unsplash&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;&lt;a href="https://commons.wikimedia.org/wiki/File:PlanckianLocus.png"&gt;Gamut diagram&lt;/a&gt; from Wikipedia&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;&lt;a href="https://commons.wikimedia.org/wiki/File:Cie_Chart_with_sRGB_gamut_by_spigget.png"&gt;sRGB gamut diagram&lt;/a&gt; from Wikipedia&lt;/em&gt;&lt;/p&gt;

</description>
      <category>computerscience</category>
      <category>color</category>
      <category>rgb</category>
    </item>
    <item>
      <title>A beginner's tutorial to Preact - Part 4: First steps with Preact</title>
      <dc:creator>🇨🇵️ Nathan Graule</dc:creator>
      <pubDate>Sun, 11 Aug 2019 12:37:49 +0000</pubDate>
      <link>https://dev.to/solarliner/a-beginner-s-tutorial-to-preact-part-4-first-steps-with-preact-4omj</link>
      <guid>https://dev.to/solarliner/a-beginner-s-tutorial-to-preact-part-4-first-steps-with-preact-4omj</guid>
      <description>&lt;p&gt;Now that we have reviewed everything we need to know prior to launching ourselves with Preact.&lt;/p&gt;

&lt;h1&gt;
  
  
  What is Preact?
&lt;/h1&gt;

&lt;p&gt;Preact is a 3kb library which allows developers to write applications using the same patterns we saw earlier. Preact provides its own implementation of the &lt;code&gt;h&lt;/code&gt; function which outputs Virtual DOM (the "pure JavaScript representation of DOM nodes" we have talked about earlier), and uses an efficient rendering algorithm to try and make as few changes to the web page as possible. It also boasts many more features that we will look at later.&lt;/p&gt;

&lt;h1&gt;
  
  
  The canonical "Hello World" application
&lt;/h1&gt;

&lt;h2&gt;
  
  
  Dependencies
&lt;/h2&gt;

&lt;p&gt;Let's start by creating a project. I'm going to use CodeSandbox (as I have already for the examples) as it allows me to embed the project into the post directly for you to run and tweak. So, either start a new "Vanilla (+ TS)" project, or start a new npm project (&lt;code&gt;npm init&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;The second thing to do, of course, is to install Preact. We're going to use version 10, which at the time of writing is still in Release Candidate, but is a complete rewrite of Preact itself, and writing a tutorial with a well known expire date isn't all that useful. Use &lt;code&gt;preact@next&lt;/code&gt; if in beta, or just &lt;code&gt;preact&lt;/code&gt; if you're reading this after version 10 was released as stable.&lt;/p&gt;

&lt;p&gt;Next, if you're not using CodeSandbox, install Parcel as a development dependency: &lt;code&gt;npm i --save-dev parcel&lt;/code&gt;, and optionally TypeScript (&lt;code&gt;npm i --save-dev typescript&lt;/code&gt;). This is to replicate the CodeSandbox environment&lt;/p&gt;

&lt;h2&gt;
  
  
  The index.html file
&lt;/h2&gt;

&lt;p&gt;Next, we're going to need to create a basic index file for the browser to load - it will point to the script, and have an identified div element for us to render the application in.&lt;/p&gt;

&lt;p&gt;CodeSandbox already provides that by default, although we'll need to change the script extension from &lt;code&gt;js&lt;/code&gt; to &lt;code&gt;jsx&lt;/code&gt; (or &lt;code&gt;ts&lt;/code&gt; to &lt;code&gt;tsx&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;Here's the contents of &lt;code&gt;index.html&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight html"&gt;&lt;code&gt;&lt;span class="nt"&gt;&amp;lt;html&amp;gt;&lt;/span&gt;
  &lt;span class="nt"&gt;&amp;lt;head&amp;gt;&lt;/span&gt;
    &lt;span class="nt"&gt;&amp;lt;title&amp;gt;&lt;/span&gt;Parcel Sandbox&lt;span class="nt"&gt;&amp;lt;/title&amp;gt;&lt;/span&gt;
    &lt;span class="nt"&gt;&amp;lt;meta&lt;/span&gt; &lt;span class="na"&gt;charset=&lt;/span&gt;&lt;span class="s"&gt;"UTF-8"&lt;/span&gt; &lt;span class="nt"&gt;/&amp;gt;&lt;/span&gt;
  &lt;span class="nt"&gt;&amp;lt;/head&amp;gt;&lt;/span&gt;

  &lt;span class="nt"&gt;&amp;lt;body&amp;gt;&lt;/span&gt;
    &lt;span class="nt"&gt;&amp;lt;div&lt;/span&gt; &lt;span class="na"&gt;id=&lt;/span&gt;&lt;span class="s"&gt;"app"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/div&amp;gt;&lt;/span&gt;

    &lt;span class="nt"&gt;&amp;lt;script &lt;/span&gt;&lt;span class="na"&gt;src=&lt;/span&gt;&lt;span class="s"&gt;"src/index.tsx"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/script&amp;gt;&lt;/span&gt;
  &lt;span class="nt"&gt;&amp;lt;/body&amp;gt;&lt;/span&gt;
&lt;span class="nt"&gt;&amp;lt;/html&amp;gt;&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h2&gt;
  
  
  The JavaScript entry-point of the application
&lt;/h2&gt;

&lt;p&gt;Next, we need to create the file referenced in the script element - CodeSandbox users can rename the existing file in &lt;code&gt;src&lt;/code&gt;, while local users can just create it at &lt;code&gt;src/index.jsx&lt;/code&gt; or &lt;code&gt;src/index.tsx&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Eitherway, if any, remove all contents, and let's start with our necessary imports:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight tsx"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;h&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;render&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;preact&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Here, we import Preact's implementation of the &lt;code&gt;h&lt;/code&gt; function, and also a &lt;code&gt;render&lt;/code&gt; function - we'll use that later.&lt;/p&gt;

&lt;h3&gt;
  
  
  Our first component
&lt;/h3&gt;

&lt;p&gt;Next, we need to write something for Preact to render. For this we need to write a &lt;strong&gt;component&lt;/strong&gt;. We'll talk more about components in the next part, but in short, components are the reusable pieces of code that ca be passed props, and have state - they are the reusable elements that are at the base of reusability in modern JavaScript framework applications.&lt;/p&gt;

&lt;p&gt;Components come in two variants - function-based, or class-based. More and more projects use function-based components, especially now that Hooks are getting more popular (more on that later). We'll use a function-based component, and name it &lt;code&gt;Application&lt;/code&gt;. Let's add it in our &lt;code&gt;index&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight tsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;Application&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Hello world!&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;That's it. This function accepts no props (as they are given through the arguments), and simply return a paragraph element (actually, it's Virtual DOM equivalent).&lt;/p&gt;

&lt;p&gt;We need to use that new component somewhere, and that's why we also have imported the &lt;code&gt;render&lt;/code&gt; function.&lt;/p&gt;

&lt;h3&gt;
  
  
  Rendering our component
&lt;/h3&gt;

&lt;p&gt;Since Preact deals with Virtual DOM through its &lt;code&gt;h&lt;/code&gt; function, we need a way for that Virtual DOM to become, well, real. This is what the &lt;code&gt;render&lt;/code&gt; function does - it inputs a Virtual DOM node, and a DOM element to insert the generated DOM into. We already have a div tag in our &lt;code&gt;index.html&lt;/code&gt; made for the purpose of hosting our application - so let's use that. Then, we need a Virtual DOM node to pass into the render, and that Virtual DOM will come from our component. Remember that Preact's &lt;code&gt;h&lt;/code&gt; function &lt;em&gt;returns&lt;/em&gt; Virtual DOM, but what you may not know (but probably have guessed), is that the function can also take components instead of tag name as first parameter. This is how we reuse components in Preact. And, where we can use &lt;code&gt;h&lt;/code&gt;, we can also write JSX - therefore that's how we'll pass the Application component to the render function.&lt;/p&gt;

&lt;p&gt;Anyhow, let's get some generated DOM into our web page. We'll get a reference to the &lt;code&gt;&amp;lt;div id="app"&amp;gt;&lt;/code&gt; element in the DOM, and pass it to the &lt;code&gt;render&lt;/code&gt; function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight tsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;root&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;getElementById&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;app&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;render&lt;/span&gt;&lt;span class="p"&gt;(&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Application&lt;/span&gt;&lt;span class="p"&gt;/&amp;gt;,&lt;/span&gt; &lt;span class="nx"&gt;root&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Our component displays "Hello World!" onto the web page! 🔥&lt;/p&gt;

&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/2w5s9"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;h3&gt;
  
  
  Nesting components
&lt;/h3&gt;

&lt;p&gt;Let's create &lt;em&gt;more components&lt;/em&gt;, shall we?&lt;/p&gt;

&lt;p&gt;Components are good for several things - but at their most basic, they allow to create reusable elements; for example, a button component we'll write next.&lt;/p&gt;

&lt;p&gt;Leaving the implementation to next part, let's use this hypothetical Button component into our application. We want this component to be customizable to a certain degree, which can be done through propertiess. We can pass any value through those props, which includes functions (as &lt;a href="https://www.oreilly.com/library/view/javascript-the-definitive/9781449393854/ch08s04.html"&gt;functions are values&lt;/a&gt;). This will be useful in keeping our Button component generic and therefore reusable - we will expose a "onClick" prop which expects a callback function which will get called when the user clicks on the component.&lt;/p&gt;

&lt;p&gt;Let's use this specification for the accepted properties (often abbreviated as props) of this Button component:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kr"&gt;interface&lt;/span&gt; &lt;span class="nx"&gt;ButtonProps&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="cm"&gt;/** Any CSS color string, from names to hex codes to HSL, HSV or RGB(A) functions */&lt;/span&gt;
  &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="cm"&gt;/** Changes the button elevation by altering the shadow property of the button */&lt;/span&gt;
  &lt;span class="nl"&gt;elevated&lt;/span&gt;&lt;span class="p"&gt;?:&lt;/span&gt; &lt;span class="nx"&gt;boolean&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="cm"&gt;/** Callback function which gets called when the user clicks on the button */&lt;/span&gt;
  &lt;span class="nl"&gt;onClick&lt;/span&gt;&lt;span class="p"&gt;?:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;ev&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;MouseEvent&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;void&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;&lt;em&gt;Note: This is valid TypeScript which I use in the source code to define the component properties, see the CodeSandbox examples&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;With this, we can create an application with two buttons to showcase how they can each be customized separatedly. In the following code, each button gets assigned a random color; the first button has a callback which shows an alert box on click while the second doesn't have any callback; also only the first button is elevated (as it is by default), the second button has its elevation turned off.&lt;/p&gt;

&lt;p&gt;Below is the code with its accompanying CodeSandbox example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;Application&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;color1&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;colors&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;round&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;random&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;colors&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;&lt;span class="p"&gt;)];&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;color2&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;colors&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;round&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;Math&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;random&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="nx"&gt;colors&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt;&lt;span class="p"&gt;)];&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;p&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="nx"&gt;Hello&lt;/span&gt; &lt;span class="nx"&gt;world&lt;/span&gt;&lt;span class="o"&gt;!&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/p&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="nx"&gt;color&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;color1&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;alert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;First button was clicked!&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="nx"&gt;Learn&lt;/span&gt; &lt;span class="nx"&gt;more&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="nx"&gt;color&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;color2&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;elevated&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="nx"&gt;Another&lt;/span&gt; &lt;span class="nx"&gt;button&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/cr5eo"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;h1&gt;
  
  
  In the next part
&lt;/h1&gt;

&lt;p&gt;We will look at how to implement this Button component (though you can peek into the CodeSandbox source code by yourself if you want to figure it out). We'll cover the two ways to write components, as well as several useful techniques.&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>typescript</category>
      <category>preact</category>
      <category>jsx</category>
    </item>
    <item>
      <title>A beginners' tutorial to Preact - Part 3: JSX</title>
      <dc:creator>🇨🇵️ Nathan Graule</dc:creator>
      <pubDate>Sun, 11 Aug 2019 12:37:27 +0000</pubDate>
      <link>https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-3-jsx-1k68</link>
      <guid>https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-3-jsx-1k68</guid>
      <description>&lt;p&gt;We saw on the previous part how to make it much easier to create content from JavaScript, however we are still left with a rather tedious way to express our DOM nodes. Let's see how we can make this a bit better.&lt;/p&gt;

&lt;h1&gt;
  
  
  JSX, or as it should be called, XML-in-JS
&lt;/h1&gt;

&lt;p&gt;The current &lt;code&gt;h&lt;/code&gt; function has lot lot going for it. It creates a tree of DOM elements on the fly, in a way that's concise and not so different visually than the tree it generates.&lt;/p&gt;

&lt;p&gt;However, all that "function-calling" will quickly become an eyesore and a keyboard-sore - navigating complex elements quickly becomes mentally straining. What if I told you we can bring the HTML back into the JavaScript?&lt;/p&gt;

&lt;p&gt;This is exactly what JSX is. It allows developers to write the &lt;code&gt;h&lt;/code&gt; function calls in an HTML-esque (or rather, XML-esque) way. Not only is there less to write, but JSX code emphasizes data and structure more clearly than the mess of function calls any regularly-sized piece of code would be.&lt;/p&gt;

&lt;p&gt;What does it look like? Let's revisit our project from the last part:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight tsx"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;root&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"app"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;header&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;My custom-generated web page&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h2&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;How neat is that?&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h2&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;header&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;class&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"container"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt; &lt;span class="na"&gt;class&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"content"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;That's pretty neat.&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="c1"&gt;// Prepending here because scripts should ideally be at the end of the body&lt;/span&gt;
&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;body&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;prepend&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;root&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;We can clearly see how this "simple syntax sugar" trick immediately improved the readability of our function.&lt;/p&gt;

&lt;p&gt;If you try that using our custom-defined &lt;code&gt;h&lt;/code&gt; function (more on that later), however, you'll see the following error:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight plaintext"&gt;&lt;code&gt;TypeError: Can't convert null to object
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This is because when a tag doesn't have any attribute in JSX, instead of passing an empty object as argument, the transformed JS uses &lt;code&gt;null&lt;/code&gt; instead. We need to account for that and check for null before applying attributes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight tsx"&gt;&lt;code&gt;&lt;span class="cm"&gt;/**
 * Creates an element and returns it
 * @param tag Tag name, like the HTML tag
 * @param attrs Object of attributes to add to the node
 * @param children Children nodes to append into the created element
 */&lt;/span&gt;
&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nx"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;object&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;HTMLElement&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)[]&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="c1"&gt;// **ADDED**: Append given attributes (if defined)&lt;/span&gt;
  &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;attrs&lt;/span&gt; &lt;span class="o"&gt;!==&lt;/span&gt; &lt;span class="kc"&gt;null&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;key&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;setAttribute&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;]);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="c1"&gt;// Insert children&lt;/span&gt;
  &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// Text is special in the DOM, we must treat it accordingly&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;typeof&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;string&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;createTextNode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h1&gt;
  
  
  Using JSX in your project
&lt;/h1&gt;

&lt;p&gt;The problem with JSX, is that you can't use it directly. If you do, your JavaScript engine of choice will complain - because JSX isn't part of the JavaScript language - it's a trick placed on top of JavaScript to help with writing nested &lt;code&gt;h&lt;/code&gt; functions. This is where Babel comes in.&lt;/p&gt;

&lt;p&gt;Babel has plugins to turn your JSX into h function calls, which in turns makes the JavaScript valid again. A proper introduction to Babel isn't in the scope here, and if you don't know about Babel, you should definitely check it out as it has become part of the everyday tooling of the JavaScript developer.&lt;/p&gt;

&lt;p&gt;Another solution to enable using JSX is with TypeScript. The TS transpiler has support for JSX, and you can convert it using it. Again, configuring TypeScript is outside the scope, and the documentation for the project is awesome, so do check it out if you need it.&lt;/p&gt;

&lt;h1&gt;
  
  
  In the next part
&lt;/h1&gt;

&lt;p&gt;We're going to step outside of the boring but necessary theory and create our first project, using what we learned on top of Preact!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>typescript</category>
      <category>jsx</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>A beginners' tutorial to Preact - Part 2: The DOM, and Hyperscript</title>
      <dc:creator>🇨🇵️ Nathan Graule</dc:creator>
      <pubDate>Mon, 10 Jun 2019 15:56:45 +0000</pubDate>
      <link>https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-2-dom-hyperscript-and-jsx-48op</link>
      <guid>https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-2-dom-hyperscript-and-jsx-48op</guid>
      <description>&lt;h1&gt;
  
  
  How to birth &lt;del&gt;HTML&lt;/del&gt; DOM from JavaScript
&lt;/h1&gt;

&lt;p&gt;Before we dive into writing "HTML", let's clarify something.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Document Object Model
&lt;/h2&gt;

&lt;p&gt;The DOM is, in effect, what the browser translates the HTML to when loading the web page into memory. The DOM contains all information about the current document. It's a tree, branching out from a root element (as represented by the &lt;code&gt;&amp;lt;html&amp;gt;&lt;/code&gt; tag in HTML). HTML is the written representation of the DOM, and JavaScript manipulate the DOM instead of the HTML, because it is faster to modify the content tree than write HTML for the browser to parse again.&lt;/p&gt;

&lt;h2&gt;
  
  
  Creating DOM nodes from JavaScript
&lt;/h2&gt;

&lt;p&gt;Ideally, we want a fast way to type the DOM that we want to insert as part of the reusable elements that will be the foundation of our applications. In a nutshell, a DOM node must be created, setup and appended to the page as a child of another node for it to appear in the browser window. A vanilla JavaScript solution would look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;div&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;classList&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;foo&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createTextNode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;I am the visible part of the node iceberg&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;body&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will create the following DOM (as represented in HTML):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight html"&gt;&lt;code&gt;&lt;span class="nt"&gt;&amp;lt;div&lt;/span&gt; &lt;span class="na"&gt;class=&lt;/span&gt;&lt;span class="s"&gt;"foo"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&lt;/span&gt;I am the visible part of the node iceberg&lt;span class="nt"&gt;&amp;lt;/div&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And a second version with a paragraph element nested inside the div:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;divEl&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;div&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;classList&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;foo&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;parEl&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;p&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;parEl&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;classList&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;content&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="nx"&gt;parEl&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createTextNode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;I am the visible part of the node iceberg&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;

&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;body&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;will render the following DOM:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight html"&gt;&lt;code&gt;&lt;span class="nt"&gt;&amp;lt;div&lt;/span&gt; &lt;span class="na"&gt;class=&lt;/span&gt;&lt;span class="s"&gt;"foo"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;p&lt;/span&gt; &lt;span class="na"&gt;class=&lt;/span&gt;&lt;span class="s"&gt;"content"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&lt;/span&gt;I am the visible part of the node iceberg&lt;span class="nt"&gt;&amp;lt;/p&amp;gt;&amp;lt;/div&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Seeing as this is the quintessential pattern for inserting content into the page (or, more generally, "DOM manipulation"), we can clearly do better.&lt;/p&gt;

&lt;p&gt;Let's define a function that will create the element with the given tag and class list, and return it.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Note: The types come from TypeScript, which I'll use in this series. Stip the types away (after the colon) to make it into regular JavaScript.&lt;/em&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="cm"&gt;/**
 * Creates an element and returns it
 * @param tag Tag name, like the HTML tag
 * @param classes List of CSS classes to apply
 */&lt;/span&gt;
&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;classes&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;[])&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="k"&gt;for &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;classes&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;""&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;continue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;classList&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;klass&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Okay, but that's not helpful. We still need to manually insert them into the page. We can do this two ways: either add a parent node as argument to the function, or a list of children to add to the element being created.&lt;/p&gt;

&lt;p&gt;The first solution means we will need to first define the parent node in order to pass it to children, to avoid duplication and to ensure the children all have the same parents. This introduces boilerplate.&lt;/p&gt;

&lt;p&gt;The second solution doesn't suffer from the disadvantages of the first; furthermore, you can simply nest calls to the &lt;code&gt;createElement&lt;/code&gt; function to create both the parent and the children nodes at once. The node returned by the top-most call to &lt;code&gt;createElement&lt;/code&gt; can directly be appended to an existing node, inserting the whole sub-tree into the page.&lt;/p&gt;

&lt;h2&gt;
  
  
  How to text
&lt;/h2&gt;

&lt;p&gt;The DOM is a tree structure, meaning that everything is a node. Plain old text is, therefore a node. But it's treated differently from other nodes in the DOM, particularly because of its inability to have children.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Note: Technically, a TextNode is almost nothing like other HTML elements, as a TextNode inherits &lt;code&gt;Node&lt;/code&gt;, whereas &lt;code&gt;HTMLElement&lt;/code&gt; inherits &lt;code&gt;Element&lt;/code&gt; which inherits &lt;code&gt;Node&lt;/code&gt; itself. Therefore, an &lt;code&gt;HTMLElement&lt;/code&gt; ends up being much more "rich" than a TextNode. Read more about &lt;a href="https://developer.mozilla.org/en-US/docs/Web/API/Text" rel="noopener noreferrer"&gt;Text&lt;/a&gt; and &lt;a href="https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement" rel="noopener noreferrer"&gt;HTMLElement&lt;/a&gt;&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;This means we have to make way in our function to treat this special case. We're going to allow strings to be passed in lieu of HTML elements, which will get turned into Text Nodes inside.&lt;/p&gt;

&lt;p&gt;Our function turns into this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="cm"&gt;/**
 * Creates an element and returns it
 * @param tag Tag name, like the HTML tag
 * @param classes List of CSS classes to apply
 * @param children Children nodes to append into the created element
 */&lt;/span&gt;
&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;classes&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;[],&lt;/span&gt;
  &lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;HTMLElement&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)[]&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="c1"&gt;// Append given CSS classes&lt;/span&gt;
  &lt;span class="k"&gt;for &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;classes&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;""&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="nx"&gt;klass&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="kc"&gt;undefined&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;continue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;classList&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;klass&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="c1"&gt;// Insert children&lt;/span&gt;
  &lt;span class="k"&gt;for &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// Text is special in the DOM, we must treat it accordingly&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;typeof&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;string&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createTextNode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We can now recreate the DOM from above, with nested &lt;code&gt;createElement&lt;/code&gt; calls:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;body&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;div&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;foo&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
    &lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;p&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;content&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;This is the tip of the node iceberg&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Which gives us the same results as previously:&lt;/p&gt;

&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/pkc5e"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1d6pcksiv00lmbdxzp80.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/cdn-cgi/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1d6pcksiv00lmbdxzp80.png" alt="Result of the function calls as seen in the Inspect panel of the Firefox DevTools" width="432" height="244"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  What about images?
&lt;/h2&gt;

&lt;p&gt;There is a serious limitation with our current function however, is that we can't include other attributes into the tags. We need to generalize our function so that it accepts an object of attributes to add to the element.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="cm"&gt;/**
 * Creates an element and returns it
 * @param tag Tag name, like the HTML tag
 * @param attrs Object of attributes to add to the node
 * @param children Children nodes to append into the created element
 */&lt;/span&gt;
&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;object&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;HTMLElement&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)[]&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createElement&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;tag&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="c1"&gt;// Append given CSS classes&lt;/span&gt;
  &lt;span class="k"&gt;for &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;key&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;keys&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;setAttribute&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;attrs&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="p"&gt;]);&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="c1"&gt;// Insert children&lt;/span&gt;
  &lt;span class="k"&gt;for &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="k"&gt;of&lt;/span&gt; &lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c1"&gt;// Text is special in the DOM, we must treat it accordingly&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;typeof&lt;/span&gt; &lt;span class="nx"&gt;child&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;string&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createTextNode&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;appendChild&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;child&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;el&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What we have created, more or less, is &lt;strong&gt;hyperscript&lt;/strong&gt;. &lt;a href="https://github.com/hyperhype/hyperscript" rel="noopener noreferrer"&gt;Hyperscript&lt;/a&gt; is a small library which does what we've just done: it encapsulates DOM elements creation into nested function calls. For this reason, and to shorten the name of the function, let's rename it to &lt;code&gt;h&lt;/code&gt;, for &lt;code&gt;hyperscript&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;With that done, let's create and insert some DOM into the page!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;root&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;app&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;app&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;header&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;{},&lt;/span&gt;
    &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;h1&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;My custom-generated web page&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
    &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;h2&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;How neat is that?&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;section&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;{},&lt;/span&gt;
    &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
      &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;div&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;class&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;container&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="nf"&gt;h&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;p&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;class&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;content&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;That's pretty neat.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;// Prepending here because scripts should ideally be at the end of the body&lt;/span&gt;
&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;body&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;prepend&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;root&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;iframe src="https://codesandbox.io/embed/ce6pt"&gt;
&lt;/iframe&gt;
&lt;/p&gt;

&lt;h1&gt;
  
  
  Conclusion
&lt;/h1&gt;

&lt;p&gt;We now have a powerful generic function to construct any DOM tree that we want. There is one last thing to know that applies on top of that &lt;code&gt;h&lt;/code&gt; function, which is used in almost all Preact projects, and which comes back full circle in a way.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>A beginners' tutorial to Preact, without prior React knowledge (Intro)</title>
      <dc:creator>🇨🇵️ Nathan Graule</dc:creator>
      <pubDate>Mon, 10 Jun 2019 15:55:36 +0000</pubDate>
      <link>https://dev.to/solarliner/a-beginners-tutorial-to-preact-without-prior-react-knowledge-intro-go6</link>
      <guid>https://dev.to/solarliner/a-beginners-tutorial-to-preact-without-prior-react-knowledge-intro-go6</guid>
      <description>&lt;p&gt;This series of posts will make up a tutorial for Preact that does not assume knowledge in React, or any other application framework. I found this specific area lacking when it comes to tutorials, as myself someone who has never used React.&lt;/p&gt;

&lt;p&gt;The tutorial assumes that you know the basics of JavaScript, and know how to install npm packages. We'll use the &lt;a href="https://parceljs.org/"&gt;Parcel bundler&lt;/a&gt; to bundle and serve our code during development, though you do not need to know Parcel as I'll explain everything as we go. We'll use &lt;a href="https://babeljs.io/"&gt;Babel&lt;/a&gt; to allow us to actually use JSX in the browser. You don't need to know it either, though I won't spend a lot of time on it. Finally, I'll use TypeScript for the code snippets as I believe static typing offers educational value both reading the code snippets, and also while writing code. You may absolutely want to stick to JavaScript, in which case just strip the types off of the code and be on your way. As with Babel, I will not spend a lot of time on TypeScript either; if you want to dive deeper on any of these, feel free to go learn more about any (or all) of these projects before going back here to follow the tutorial.&lt;/p&gt;

&lt;h2&gt;
  
  
  Contents
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;Introduction&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-2-dom-hyperscript-and-jsx-48op"&gt;DOM Garderning&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dev.to/solarliner/a-beginners-tutorial-to-preact-part-3-jsx-1k68"&gt;JSX, or as it should be called: XML-in-JS&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://dev.to/solarliner/a-beginner-s-tutorial-to-preact-part-4-first-steps-with-preact-4omj"&gt;First steps with Preact&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Components, props, state, and context&lt;/li&gt;
&lt;li&gt;Testing components&lt;/li&gt;
&lt;li&gt;Get hooked, Capt'n!&lt;/li&gt;
&lt;li&gt;To CSS &lt;em&gt;and&lt;/em&gt; not to CSS&lt;/li&gt;
&lt;li&gt;Route it, link it, match it - &lt;em&gt;&lt;a href="https://www.youtube.com/watch?v=D8K90hX4PrE"&gt;technologic&lt;/a&gt;&lt;/em&gt;
&lt;/li&gt;
&lt;li&gt;Manual Server-side Rendering&lt;/li&gt;
&lt;li&gt;Workshop: A music catalog application&lt;/li&gt;
&lt;/ol&gt;

&lt;h1&gt;
  
  
  A dive into modern JavaScript application development
&lt;/h1&gt;

&lt;p&gt;JavaScript was not really designed as the main foundation atop which the modern web would be built. In fact, the web &lt;em&gt;itself&lt;/em&gt; was never designed as an application framework - This is all evident in the way we interact with it: we request and visualize documents, which are described by a particular subset of XML: HTML. They provide the &lt;strong&gt;semantic&lt;/strong&gt; view of the document, that is what the text means and how it is structured. HTML defines hierarchy much like a book can have parts, chapters, headings and paragraphs - because the web was designed to be a digital equivalent to a library, where websites were books you could peek in.&lt;/p&gt;

&lt;p&gt;This is where the "modern" view of the web clashes with its implementation. The modern web of web applications view a website as an application, from which its web pages are the multiple entry points. HTML, then, define the elements which compose the particular application, and how it is structured.&lt;/p&gt;

&lt;h1&gt;
  
  
  Alleviating the pain from the document-centric workflow
&lt;/h1&gt;

&lt;p&gt;There is a way to, if not resolve, at least help bridge the gap between the early design and modern use of the web. By taking a step back from the HTML itself, and focusing instead on composing "elements" which render themselves into HTML. We can then stop thinking about "how will I write HTML in order to build my application?", and start thinking about "How can I break down my application into manageable chunks?", and this is the first step towards building applications that scale while staying maintainable.&lt;/p&gt;

&lt;p&gt;However, this is not a perfect solution, as the technicalities of the document-centric workflow tend to creep up into these elements quite quickly (one being the "cascade" I mentioned earlier, which you'll understand if you have any experience with CSS, however styling is outside the scope of this series).&lt;/p&gt;

&lt;h1&gt;
  
  
  The solution: JS frameworks by the dozen
&lt;/h1&gt;

&lt;p&gt;This very thinking led to the popularization of JS frameworks promising to implement this abstraction of HTML into reusable elements in a way that would benefit the developer. React, Angular, Vue, Elm, Svelte, dozens of frameworks each try to innovate on the above recipe in their own way.&lt;/p&gt;

&lt;h1&gt;
  
  
  Conclusion
&lt;/h1&gt;

&lt;p&gt;This sets the stage and hopefully the mindset towards understanding the thought process behind the design of the technologies we are going to use throughout the series.&lt;/p&gt;

&lt;p&gt;In the next part, we are going to look at the first layer of abstraction over HTML that has become standard for JavaScript application development. I hope you're hyper-excited!&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>jsx</category>
      <category>preact</category>
    </item>
  </channel>
</rss>
