Calculating Distance in Google Maps with React and Typescript

After a long pause, I am back to my Google Maps application. In other words, the 3rd video of the series is out! In this video, our Google Maps application turns out to be something useful. The application lets the user calculate distance between some points on the map. Below is the list of tasks completed in part 3:

  • Create home address marker with center and zoom functionality (panTo and setZoom)
  • Calculate distance between home address marker and custom markers (computeDistanceBetween)
  • Draw a line between home and selected marker (polyline)

Github URL:

This article will point out some of the critical code snippets in the video. I prefer to make up some questions that you may ask along the way.

1. How to create markers with PNG files?

You don’t have to use SVG content to create markers in Google Maps. In some cases, you may prefer to use PNG instead. For example, while creating the home marker of my application, I used a PNG file. Place the image into some folder that is located under your public folder (such as public/assets/images/…) and the icon attribute of your google.maps.Marker constructor receives the url parameter as shown below.

const homeMarkerConst:GoogleMarker = new google.maps.Marker({
    position: location,
    map: map,
    icon: {
        url: window.location.origin + '/assets/images/homeAddressMarker.png'

2. How to create an event for a marker in Google Maps?

You can implement some operations on markers via adding event listeners on them. Preferably, you should add your event listener and the corresponding function right after you create the marker. The code snippet below shows the event listener that I added to my home marker. The arrow function changes the center point of the map with the location of home marker.

homeMarkerConst.addListener('click', () => {

The gif animation below shows how this listener performs in the application. After the user clicks on home marker, the map centers and sets the zoom level to 12.

Homework! 👀

As you see, my zoom operation in the code snippet above is not actually smooth. Clone my repository and create a function called smoothZoom. This function should zoom gradually. I want you to change the zoom level in every 100 milliseconds. (💁 Hint: smoothZoom should be recursive)

3. How to compute distance between two markers in Google Maps?

We so far learnt how to perform some function when a marker is clicked, right? So, if I should calculate the distance when a marker is clicked, what am I supposed to do? The answer is adding another click event listener. Before that, you should add another library to your Api URL. If you’d like to calculate distance in Google Maps, you should use the function computeDistanceBetween(…, …). This function lies under geometry library of Google Maps library. Therefore, your Api URL should be something like this:${your_key}&libraries=geometry,places&language=no...

After making sure that libraries have geometry, now I can add the click event listener which gets the position of two markers and computes the distance between them.

marker.addListener('click', () => {
    const homePos = homeMarker?.getPosition();
    const markerPos = marker.getPosition();
    if (homePos && markerPos) {
        const distanceInMeters = google.maps.geometry.spherical.computeDistanceBetween(homePos, markerPos);

After adding polyline code and few more other things, the code above helped me measure the distance between home marker and custom markers as the gif below shows:

4. How to use React Hooks inside marker event listener?

This is the most challenging part while implementing Google Maps with React. The event listeners are part of vanilla javascript and they have no respect against the render mechanism of React. They only remember the hook values of the moment that you added the listener. Therefore, when you try to perform some setter operation of a hook, its value will not always be updated. I mean the hook value will actually be updated, but your listener functions may still remember the former value of the hook. (I know! This part is a bit complex. So, read this paragraph again and ponder)

To fix this, you should remove your listener function and add it again. So that, your new listener event will keep the updated version of your hook value. Therefore, I keep the listener ids of my events in a hook array and whenever I am supposed to update some hook value inside the event listener, I remove all previous listeners and add them again. I won’t share a code snippet for this part, so you’d better watch the last 20 minutes of the video 😁

Hopefully this blog post will help someone in the future! And again hopefully I will make the 4th video some time soon.

Sercan Leylek

TypeError: Class constructor HTMLElement cannot be invoked without ‘new’

This error message has been a headache for me this week. I noticed that there were no good posts to cover it in the internet, so I decided to write this post. Hopefully, it will help someone in the future.

Technology stack

  • React
  • Typescript
  • testing-library/react
  • Jest

Definition of the problem

This error occurs while running a unit test. The component that you are running has probably some 3rd party code which contains class components and your EcmaScript configuration in tsconfig.json is not able to compile this file. Therefore, your test fails at some random point in the 3rd party code.


Unfortunately, there is no single solution for this error because every environment has its own problem because of similar situation. I will show how I handled it while I was using NRK’s core library.

1) Install custom elements es5 adapter for your project.

npm i custom-elements-es5-adapter

2) Import custom elements adapter to your setupTests file

import '@webcomponents/webcomponentsjs/custom-elements-es5-adapter';

3) Run your test again. It should work 🙂

Sercan Leylek

Highlights of Beyond Design Sytems Meetup

Insurance company Fremtind organised a design system meetup on November 4th. The name of the event is Beyond Design Systems. The text below summarises the purpose of the gathering:

“The digital product industry has been welcoming design systems for a while. Many organizations have been better able to preserve brand guidelines, speed up time-to-market, or improve the user’s experience by establishing and maintaining a functioning design system.

This event will attempt to look beyond: To uncover the good, the bad, and the ugly experiences from inside our design systems. What has thrilled users? Where has it gone wrong? How did we prevail – if at all?”

Because of Corona measures, the event was broadcasted online via company’s youtube channel. The experts who are located in different parts of the globe have been available via a YouTube URL. That was quite comforting. If you are eager to learn about design systems, you can watch the whole session below:

Meetup – Beyond Design System – Fremtind – November 2020

what is a design system?

There are several definitions out there, but I will describe it with my words: A design system is a collection of design rules, patterns and reusable elements which help a web application develop faster and in a correct way.

For example, almost every web application requires a loading animation, footer, date box, etc… Most of these elements are common in every project and they all require time to build, consistent style, accessibility, validation, standard UX, UI guidelines and more. So, the design system assists your project to cover those needs at reusable parts of the final outcome. Therefore, digital product industry has been recently moving towards design systems.


“Design systems should be built on collective culture, not individual achievement.”

Above is a quote from Glenn Brownlee who is the leader of design system, Jøkul. The inclusion of people are needed to make a design system work. If people do not participate, then there would be no progress. Brownlee basically underlines that a design system is actually a living thing. It evolves and the people need to understand why the system is necessary. As the process matures, actors of design system will not follow the rules just because they are told to do so, but they will see these rules as an expected way of doing. In other words, the rules will become their new normal. 

Brownlee also added: “If all you have is a component library, you don’t have a design system. However, once people become part of the movement, that means you have a design system.”

A similar thought was also mentioned by another participant of the meetup, Mike Hall (UX Lead for the Service NSW Transactional Design System). Hall said that if a system was not updated and maintained, it would die very quickly.

I should confess that my favourite presentator of the meetup has been Eirik Fatland (Lead Designer at Fremtind). He mostly shared some of his interesting experiences while expressing his thoughts about design systems. That was truly engaging.

“In Fremtind, we for example have weekly design critique sessions that are important while establishing culture. In design critique session, anyone can bring any design they are working on and they receive feedback on it. Sometimes feedback leads to discussions. The discussions involve everyone in the room and they become wiser.” ~Eirik Fatland

And finally, Morgane Peng had a stunning presentation. She is the director of UX at Societe Generale. I think the Dunning-Kruger effect was a perfect example while she was explaining their design system journey.

The DunningKruger effect is a bias in thinking, usually where a person is unaware of how badly they grasp a subject, not understanding that they are failing at it. Peng says that she and her co-worker thought they built some useful tool in the beginning and afterwards they started to receive feedback and complaints from the users of their design system. Therefore, they fell to the valley of despair because of their mistakes. This experience helped them understand that building design systems is not easy. After putting more work and engagement with additional actors, they started to understand what they were actually building and before they reach to the plateau of sustainability, more partners joined them. As a result, Peng says that a design system is 20% craft and 80% people.

All in all, I hope there would be more interesting meetups soon. And if you are curious about design systems, I recommend you to take a look at this blog post: Everything you need to know about design systems.

Sercan Leylek

Creating Markers on Google Maps with React + Typescript

This is the part two of my Google Maps series. I don’t truly know where we are heading with this app, but I will keep teaching you the secrets of Google Maps programming with React and Typescript. Few days ago, I released the last video. This article serves as a cheatsheet of what I implemented on Youtube.

Creating Markers on Google Maps with React + Typescript (Part 2)

Link to GitHub Respository 

IMarker Interface and marker hook

First, we should create an interface for our marker, right? I want to keep three basic data attributes for a marker. Of course, the label of a marker could be also added here as another string value, but I want to keep things simple. Maybe we do it in the next video.

Based on this interface, I also create the marker hook which will store the content.

const [marker, setMarker] = useState<IMarker>();

Event Listener

While working with Google Maps on React, you should still write some Vanilla JS code as well. I don’t like this, but that’s the way it is. As soon as the map hook is initialised, we add a click listener into this function. This event listener will return us a latLng event object which will be used to get the coordinates from geocoder.


As you notice, I invoke a function called coordinateToAddress() whenever the user clicks somewhere on the map. The click event of google.maps namespace returns us a typical event (e), but this e event has a special attribute called latLng. This is our location value. In this function, I pull three different data types from geocoder. I get the address, latitute and longitude. Just what I need to update with my marker hook.

At this point of the program, our Map component successfully retrieves the coordinates of clicked point and it stores the data in our hook (marker), but we do not illustrate any marker to the user, yet.


I created this function just for convention. If we decide to create an array of IMarker objects (which means storing several markers on the map at the same time), we would create another function called addMultipleMarkers. But let’s see what addSingleMarker() does first. It simply follows the changes on marker hook with a useEffect and whenever it is updated we invoke addMarker function.


So, here is a much more reusable function. This is actually the place where our Map component will create the marker and it will show it to the user.

google.maps.Marker receives a JSON object where the options are almost limitless. There are so many attributes that you can use to customise your marker, but I only used fundamental parts here (position, map and icon). I also created a dummy function called getIconAttributes() which is only used for the output of icon. You may refer to Google Maps manual for further customisation.


The gif animation below shows how I create markers on the map, but there is a problem. As I click a point on the map, the component successfully creates a marker. However, when I create once more, the previous marker is still there although the marker hook changed its value. So, try to create a function which will remove the previous function. Good luck!

I hope you enjoyed this post. I will keep on writing more about Google Maps. Take care!

Sercan Leylek / OSLO

Setting up Google Maps with React + Typescript

Coding with Google Maps is a fun, mysterious and challenging journey. If you do it with Typescript, both joy and pain get doubled.

When I was coding a Google Maps component at Fremtind fremtind logo, I was starving for a comprehensive tutorial on this topic. Unfortunately, the results were a bit disappointing, but like all developers I found a solution for each problem and the job was done. Then I asked to myself: Why not creating a comprehensive project and delivering all the secrets of my journey in one post?

Meanwhile I was working for my map component, I discovered the answers to my questions via different websites. For example:

  • How can I use typescript types from Google for my map project in React?
  • How should I load my Google Maps Api script into my homepage? What could be the best practice?
  • Where should I use “useRef” to point out my Google Maps DOM element?
  • ….

Some of the answers that I found were outdated, some people were not quite sure of what they were advising, etc… You know the drill.

As a result, I created a sample project at my GitHub repository and decided to sail for a new adventure as well. For the first time, I screencast a coding experience like an experienced youtuber. The duration of the video is 55 minutes and I let the audience view the whole process while I am coding the React project.

Link to GitHub Respository github-169-1174970


Setup and Installation

To kick off the project, we need to create a react application with typescript flag. Use the sample command below to start with:

npx create-react-app google-maps --template typescript

After cleaning up default stuff from the project (like deleting logo.svg, App.test.tsx, etc), run the command below to install Google Maps typescript types into your project as a node module element. This will help you access types from google.maps namespace. (Such as google.maps.Map, google.maps.LatLng, google.maps.MapTypeId, …)

npm install --save-dev @types/googlemaps

Bonus Hint: By doing so, you will also obtain google.maps.places.AutocompletePrediction type which can be used to build an address dropdown component.

Now we are ready to give a shape to our React project. I set up the file and folder structure of my src folder as blueprinted below:

├── App.css
├── App.tsx
├── Map
│   ├── Map.scss
│   ├── Map.tsx
│   └── index.ts
├── index.css
├── index.tsx
├── react-app-env.d.ts
└── utils
└── GoogleMapsUtils.ts

Implementing loadMapApi() Utility

While developing a Google Maps component, we need to load the script tag which will download the API library for us. At the end, our webpage should show something like this:

async defer>

Before loading this tag into our DOM structure, we cannot run Google Maps related code pieces. Therefore, we should create a utility function under utils/GoogleMapsUtils.ts.

Screenshot 2020-08-16 at 21.29.09
loadMapApi() Utility Function

This function basically creates the aforementioned script tag and inserts it into the DOM if it is not found. loadMapApi() will be used by the page which calls our Map component. In my example, this page will be the homepage of the project (App.tsx).


In this application, we have two fundamental tasks for App.tsx. First one will handle loading the map utility and latter will call our custom Map component. To do that, I created the React hook below:

const [scriptLoaded, setScriptLoaded] = useState(false);

This hook makes sure that Google Maps script tag is loaded successfully into the page. When scriptLoaded hook is set true, App.tsx renders my custom Map component.

useEffect(() => {
    const googleMapScript = loadMapApi();
    googleMapScript.addEventListener('load', function () {
}, []);

useEffect hook above runs when App component is mounted and when the script is loaded, we are ready to render Map component as shown below:

return (
    <div className="App">
        {scriptLoaded && (


We finally reached to the heart of the application. Map.tsx is my custom map component that I mentioned under the previous title. Let’s create its interface (IMap) first.

interface IMap {
    mapType: google.maps.MapTypeId;
    mapTypeControl?: boolean;

I wanted to receive two basic props. mapType can have ROADMAP, SATELLITE, TERRAIN or HYBRID values. These are specific map types defined by Google.

Screenshot 2020-08-16 at 22.04.24


Screenshot 2020-08-16 at 22.06.29

And we will use mapTypeControl prop to show/hide the control menu on the left-top corner of your map. We may extend the number of props to increase the usability of our map component, but I wanted to use only two props to illustrate my example.

I also use typescript’s custom type definition feature to increase the readability of my source code.

type GoogleLatLng = google.maps.LatLng;
type GoogleMap = google.maps.Map;

Before I explain the initMap, defaultMapStart, and startMap functions, I would like to show you the render part of the Map component.

const ref = useRef<HTMLDivElement>(null);

return (
<div className="map-container">
 <div ref={ref} className="map-container__map"></div>

The inner div element is the reference point for Google Maps. The API will load my map content into this div element and I use the outer div just for styling purposes. On the other hand, the same ref value is used by initMap function where the map is triggered.

Screenshot 2020-08-16 at 22.31.48
initMap function and map hook

As you see above, before implementing the initMap function, I created a hook called map. This hook is used to keep the map object created by google.maps.Map(…) function. The same function takes our div element via ref.current as its first parameter and the second parameter is a json object which keeps the preferences of our map.

initMap receives two inputs: zoomLevel and address. zoomLevel is straightforward to understand, but what address does will be more clear when we take a look at defaultMapStart() function.

Screenshot 2020-08-16 at 22.37.33
defaultMapStart function

So, this function basically calls the initMap, but it also does some critical work as well. It decides where to focus and how much to focus when our map starts.

Screenshot 2020-08-16 at 22.46.40
startMap function

Finally, startMap function calls defaultMapStart() when the map hook is not null anymore. This check is necessary because of rendering delays and typescript will complain if you do not run this check.


This application may not seem so impressive in terms of functionality, but you see that we had to do a lot of things just to start our map. While shooting the video, I had a problem with the API key because I did not want to screencast it via my youtube video, but when I include it, the output is as shown below:

Screenshot 2020-08-16 at 22.04.24
Final output

I am planning to screencast a second video where I will show how to add/remove markers on Google Maps. I hope you enjoyed this tutorial 🙂


Sercan Leylek / OSLO

Is it possible to trigger two DOM events at the same time on React?

Few weeks ago, I found myself desperately googling this question while I was trying to fix a React glitch. The answer is certainly, No! DOM is made to receive one user interaction event at a time, but I wanted to get rid of this error so badly and I was still hoping that there could be a way.

Let me clarify the case with a more elaborative example. I created a simple typeahead component which can be downloaded via

Simple typeahead component demo

As the gif image above declares, there are two basic UI elements in a typical typeahead component: There should be a text box and a list of items that become visible upon user interaction. Component should also have some keyboard navigation where the glitch pops up.

Please take a look at the render part of the typeahead:

Screenshot 2020-05-24 at 18.40.08
Core render of typeahead component

Typeahead basically has the following DOM structure

  • div.typeahead => wrapper
    • input => textbox
    • ul => unordered list
      • li => list item to show a capital
      • li => list item to show a capital

As the code snippet above shows, when the user sets the focus on input, showSuggestions hook is set true. Hence, unordered list becomes visible. I did this by using onFocus and onBlur events. This is quite straightforward thinking. If the user tabs through my text box, dropdown will be shown to user and it will be hidden on the next tab. However, when the user clicks on a list item (to select a capital), onBlur got triggered although I wanted to trigger my onClick event on <li/>. Therefore, I quit using onClick event and used onMouseDown instead. Then, typeahead component worked like a charm 🙂 As a result, I couldn’t trigger two DOM events at the same time, but found a way to orchestrate related events. This should be the approach to solve such problems among UI events.

BONUS MATERIAL => Jøkul’s useKeyListener hookstorksnest_jøkul_bonus_useKeylistener_hook

Aforementioned application (simple-typeahead) can be inspiring for those who are about to develop their own dropdown component. At this point, I would like to introduce you a promising UI library called Jøkul. This library provides you stylish UI components (checkbox, datepicker, progressbar, etc. ) while creating your SPA. In my application, I benefited a custom hook from Jøkul. So, how to use Jøkul’s useKeyListener hook?

Step 1:

Install jkl-react-hooks on your web app:

npm i @fremtind/jkl-react-hooks

Step 2: 

Import useKeyListener under your target component:

import { useKeyListener } from '@fremtind/jkl-react-hooks';

Step 3: 

Identify the set of keys that you will use. In my case, I needed to use following list of keys:

const keys = ['ArrowUp', 'ArrowDown', 'Enter', 'Escape'];

Step 4: 

Create a reference for your input element:

const ref = useRef(null);
<input ref={ref} ...

Step 5:

Program it your way! As the code snippet below indicates, I created a function called onKeyPressed and sent it to Jøkul’s useKeyListener. Besides, my function consists of nothing but a switch case where I implement expected output. For example, if the user presses arrow down key, I increment the value of selectedIndex as long as it is within the length of my suggestions list.

Screenshot 2020-05-24 at 19.09.59

Jøkul’s useKeyListener stops you googling key codes and your source code becomes more readable and neat.

Sercan Leylek / OSLO

Generative Technology

During this year’s spring semester, I followed IT and Management course at University of Oslo. The course content involves IT platforms, how to bootstrap and govern them. While studying through academic network, Wikipedia becomes my best friend. However, Wikipedia or the rest of the internet does not have all the academic definitions for challenging terms. So, this question puzzled my mind for a while: What is generative technology?

Generative technology, as defined by Zittrain, is a technology that allows third parties to innovate upon it without any gate-keeping. The perfect example is the personal computer, which allows any type of third party to develop hardware or software to supplement or modify the original device. Further examples to generative technology are internet, Google Play and App Store.


There is an interesting question at this point: Even though telephony system is over 100 years old, why did it fail to evolve itself as a generative technology like internet did? This is because of the dummy terminal architecture of telephony system. Internet is built on end-to-end principle which lets the nodes of the web to flow data to given address, but the end points of internet has smart devices (computers) which can be developed further. However, telephony system is developed to take care of the management problems via its core components, and its end points are dummy devices. As a result, although both internet and telephony system did not have big changes on their core architecture or how they work in last 50 years, telephony system did not manage to expand itself as a generative technology, but internet is used overall.

Internet has been the major generative technology invention of 20th Century. However, artificial intelligence will surely become the next big generative technology of 21st. Its ultimate power will be unlocked when computers can design and code infrastructures for complex systems.

Sercan Leylek / OSLO

ReferenceError: google is not defined

This error message bugged for two days. I’ve been working on a web application which is written in React+Typescript. My task is to create a Google Maps component without using any node module helper. So, I have to write most of the things from scratch and I had no former experience with Google Maps library. Before I tell more about my other concerns, let me introduce the error.

Description of the error

I experienced this error on Firefox meanwhile my web-app worked just fine on Chrome and Safari. When I tried to get predictions from Google Maps Api, Firefox showed me the following runtime error.

ReferenceError google is not defined firefox
“ReferenceError: google is not defined” occurs on Firefox


The solution is simple! While I was adding my Google Maps API script, I forgot to add async and defer attributes. After adding these attributes, my component did not crash on Firefox. There are two ways of doing this:

1. You may include these attributes inside your index.html

Screenshot 2020-04-30 at 16.27.44

2. Or you can add these values during Dynamic Loading process

ReferenceError google is not defined firefox solution


Do not add Google Maps API script into the head of your html. It should be at the bottom of your body 🙂

Sercan Leylek / OSLO

Squash Your Commits

When I heard this Git term for the first time from a colleague (who is English 💂), I thought it was a British idiom 🇬🇧. I even looked it up on, and I quickly realised that was an actual feature of Git. So, I had to teach this to myself. Then I googled “How to squash commits” and I ended up with a not very useful document on github. (

In very simple words, squashing your commits merges your several commits into a single commit. And there is no such “git squash blah blah” command either. We actually use “git rebase” command to achieve that. See the example case below to squash your commits 🙂

Example case

Assume that you have a development branch (called dev) and a feature branch (called my-pr-branch). The picture below lists my 4 commits which are on my-pr-branch.

how to squash commits sercan leylek

By following the steps below, I will squash those 4 commits into 1 commit.


Make sure that you are on feature branch:

git checkout my-pr-branch


Run the command below:

git rebase -i HEAD~4

In my case, I will squash 4 commits. Therefore, I rebase HEAD~4.


Previous step will open your default text editor. See my case below:

Screenshot 2019-06-29 at 18.04.27


Leave first line as it is and type ‘s’ for the first word of the other lines. As the comments also elaborate, ‘s’ stands for squash.

Screenshot 2019-06-29 at 18.05.51


After you save the editor (:wq), you will be demanded to save the merge request. Just save and move forward:

Screenshot 2019-06-29 at 18.10.04


Push your changes with the command below:

git push origin my-pr-branch --force

Squash commits

And the result will be one commit to rule them all, one commit to find them.


Sercan Leylek / OSLO