<?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: Monaye Win</title>
    <description>The latest articles on DEV Community by Monaye Win (@monaye).</description>
    <link>https://dev.to/monaye</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%2F346013%2F84b939a5-dc20-433e-a875-86dd18624e57.png</url>
      <title>DEV Community: Monaye Win</title>
      <link>https://dev.to/monaye</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/monaye"/>
    <language>en</language>
    <item>
      <title>Laravel Nova Customize Navigation</title>
      <dc:creator>Monaye Win</dc:creator>
      <pubDate>Wed, 31 Mar 2021 00:49:31 +0000</pubDate>
      <link>https://dev.to/monaye/laravel-nova-customize-navigation-7e</link>
      <guid>https://dev.to/monaye/laravel-nova-customize-navigation-7e</guid>
      <description>&lt;p&gt;Laravel Nova is a great tool! There are many packages that will do similar to the customization I will introduce here. &lt;/p&gt;

&lt;p&gt;As a dev, less package is always better if the required customization is simple. &lt;/p&gt;

&lt;p&gt;So, This is what we will customize&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Add an icon to each navigation &lt;/li&gt;
&lt;li&gt;Add method to define return the sort value so we can sort&lt;/li&gt;
&lt;li&gt;Both navigation and group use the defined sort value for sorting&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;If you open a default &lt;code&gt;navigation.blade.php&lt;/code&gt; it looks something like this&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@if (count(\Laravel\Nova\Nova::resourcesForNavigation(request())))
    &amp;lt;h3 class="flex items-center font-normal text-white mb-6 text-base no-underline"&amp;gt;
        &amp;lt;svg class="sidebar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"&amp;gt;
            &amp;lt;path fill="var(--sidebar-icon)" d="M3 1h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3h-4zM3 11h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4h-4z"
            /&amp;gt;
        &amp;lt;/svg&amp;gt;
        &amp;lt;span class="sidebar-label"&amp;gt;{{ __('Resources') }}&amp;lt;/span&amp;gt;
    &amp;lt;/h3&amp;gt;

    @foreach($navigation as $group =&amp;gt; $resources)
        @if (count($groups) &amp;gt; 1)
            &amp;lt;h4 class="ml-8 mb-4 text-xs text-white-50% uppercase tracking-wide"&amp;gt;{{ $group }}&amp;lt;/h4&amp;gt;
        @endif

        &amp;lt;ul class="list-reset mb-8"&amp;gt;
            @foreach($resources as $resource)
                &amp;lt;li class="leading-tight mb-4 ml-8 text-sm"&amp;gt;
                    &amp;lt;router-link :to="{
                        name: 'index',
                        params: {
                            resourceName: '{{ $resource::uriKey() }}'
                        }
                    }" class="text-white text-justify no-underline dim" dusk="{{ $resource::uriKey() }}-resource-link"&amp;gt;
                        {{ $resource::label() }}
                    &amp;lt;/router-link&amp;gt;
                &amp;lt;/li&amp;gt;
            @endforeach
        &amp;lt;/ul&amp;gt;
    @endforeach
@endif
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Add an icon to each navigation &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Let's look at the part where each link is render&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@foreach($resources as $resource)
                &amp;lt;li class="leading-tight mb-4 ml-8 text-sm"&amp;gt;
                    &amp;lt;router-link :to="{
                        name: 'index',
                        params: {
                            resourceName: '{{ $resource::uriKey() }}'
                        }
                    }" class="text-white text-justify no-underline dim" dusk="{{ $resource::uriKey() }}-resource-link"&amp;gt;
                        {{ $resource::label() }}
                    &amp;lt;/router-link&amp;gt;
                &amp;lt;/li&amp;gt;
            @endforeach
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you &lt;code&gt;dd($resource)&lt;/code&gt; it's a fully FQN of your resources. And this on each, it's calling static method to resource class to get the label&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;{{ $resource::label() }}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We are going to add a new &lt;code&gt;icon()&lt;/code&gt; method to the resource.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    /**
     * The icon of the resource.
     *
     * @return string
     */
    public static function icon()
    {
        return view('nova::icons.icon-customer')-&amp;gt;render();
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;in the &lt;code&gt;icon-customer.blade.php&lt;/code&gt; file we only have an SVG.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;svg width="20" height="20" class="sidebar-icon" fill="var(--sidebar-icon)" viewBox="0 0 25 26"  xmlns="http://www.w3.org/2000/svg"&amp;gt;&amp;lt;path d="M18.501 15.62a7.161 7.161 0 003.409-6.095c0-3.949-3.202-7.161-7.137-7.161-3.935 0-7.137 3.212-7.137 7.161a7.161 7.161 0 003.408 6.095c-4.406.992-7.499 3.702-7.499 6.98 0 2.684 7.058 3.4 11.228 3.4S26 25.284 26 22.6c0-3.278-3.092-5.988-7.499-6.98zM9.106 9.525c0-3.134 2.542-5.684 5.667-5.684 3.124 0 5.666 2.55 5.666 5.684 0 3.135-2.542 5.684-5.666 5.684-3.125 0-5.667-2.55-5.667-5.684zm5.667 14.998c-5.994 0-9.582-1.27-9.757-1.927.005-3.259 4.38-5.91 9.757-5.91 5.376 0 9.75 2.65 9.756 5.909-.17.656-3.758 1.928-9.756 1.928z" /&amp;gt;&amp;lt;path d="M18.501 15.62a7.161 7.161 0 003.409-6.095c0-3.949-3.202-7.161-7.137-7.161-3.935 0-7.137 3.212-7.137 7.161a7.161 7.161 0 003.408 6.095c-4.406.992-7.499 3.702-7.499 6.98 0 2.684 7.058 3.4 11.228 3.4S26 25.284 26 22.6c0-3.278-3.092-5.988-7.499-6.98zM9.106 9.525c0-3.134 2.542-5.684 5.667-5.684 3.124 0 5.666 2.55 5.666 5.684 0 3.135-2.542 5.684-5.666 5.684-3.125 0-5.667-2.55-5.667-5.684zm5.667 14.998c-5.994 0-9.582-1.27-9.757-1.927.005-3.259 4.38-5.91 9.757-5.91 5.376 0 9.75 2.65 9.756 5.909-.17.656-3.758 1.928-9.756 1.928z" /&amp;gt;&amp;lt;path d="M8.169 12.236c-3.92.379-6.927 2.459-6.93 4.961.1.383 1.552 1.01 4.08 1.368a6.948 6.948 0 00-.903 1.134C2.029 19.296 0 18.534 0 17.2c0-2.787 2.604-5.09 6.315-5.933a6.1 6.1 0 01-2.87-5.18C3.444 2.73 6.14 0 9.454 0c1.94 0 3.667.936 4.767 2.385-.49.037-.967.125-1.425.258a4.727 4.727 0 00-3.342-1.387c-2.632 0-4.772 2.167-4.772 4.832a4.839 4.839 0 003.031 4.498 7.09 7.09 0 00.455 1.65zM18.595 15.56l-.094.06.128.03a4.757 4.757 0 00-.034-.09z" /&amp;gt;&amp;lt;/svg&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, update the navigation to render the icon if the method exists or just show the default icon.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  @if(method_exists($resource, 'icon'))
      {!! $resource::icon() !!}
   @else
     &amp;lt;svg class="sidebar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"&amp;gt;
                    &amp;lt;path fill="var(--sidebar-icon)" d="M3 1h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3h-4zM3 11h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4h-4z"/&amp;gt;
      &amp;lt;/svg&amp;gt;
  @endif
  &amp;lt;span class="sidebar-label"&amp;gt;{{ $resource::label() }}&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Add method to define return the sort value 
To sort the navigation, it can be done at the &lt;code&gt;navigation.blade.php&lt;/code&gt; but let's dive a little bit deeper into how Nova got those resources lists from. 
if you open &lt;code&gt;vendor/laravel/nova/src/Tools/ResourceManager.php&lt;/code&gt;, you will find this:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    /**
     * Build the view that renders the navigation links for the tool.
     *
     * @return \Illuminate\View\View
     */
    public function renderNavigation()
    {
        $request = request();
        $groups = Nova::groups($request);
        $navigation = Nova::groupedResourcesForNavigation($request);

        return view('nova::resources.navigation', [
            'navigation' =&amp;gt; $navigation,
            'groups' =&amp;gt; $groups,
        ]);
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;if you start tracing you ended up on the&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    /**
     * Get the sorting strategy to use for Nova resources.
     *
     * @return array
     */
    public static function sortResourcesWith()
    {
        return static::$sortCallback ?? function ($resource) {
            return $resource::label();
        };
    }
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you notice, there is a &lt;code&gt;$sortCallback&lt;/code&gt; function which you can register when Nova boots. So let's do that. &lt;/p&gt;

&lt;p&gt;so in my &lt;code&gt;NovaServiceProvider.php&lt;/code&gt; in the &lt;code&gt;boot()&lt;/code&gt; func, we gonna add:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Nova::sortResourcesBy(function ($resource) {
    return method_exists($resource, 'sortOrder') ? 
         $resource::sortOrder() : $resource::label();
});
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;So, we will look for the &lt;code&gt;sortOrder&lt;/code&gt; method in our resource, if it doesn't it will fall back to the original &lt;code&gt;label&lt;/code&gt; based sort.&lt;/p&gt;

&lt;p&gt;That's all!! &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Both navigation and group use the defined sort value &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;For the group to order, I just utilize the &lt;code&gt;sortorder&lt;/code&gt; of resource.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@php
        // dump($navigation);
        $orderNav = $navigation-&amp;gt;sortBy(function($resources){
            // dump($resources-&amp;gt;first());
            return $resources-&amp;gt;first()::sortOrder();
        });
    @endphp
    @foreach($orderNav as $group =&amp;gt; $resources)
       ... 
    @endforeach
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I ended up only showing the icon for the group and here is my &lt;code&gt;navigation.blade.php&lt;/code&gt;. just FYI: not cleaned up/optimized&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7ldvhfpwtihujscvzcbf.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F7ldvhfpwtihujscvzcbf.png" alt="image"&gt;&lt;/a&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@if (count(Nova::availableResources(request())))
&amp;lt;ul class="sidemenu"&amp;gt;
    @php
        $orderNav = $navigation-&amp;gt;sortBy(function($resources){
            return $resources-&amp;gt;first()::sortOrder();
        });
    @endphp
    @foreach($orderNav as $group =&amp;gt; $resources)
      @if (count($groups) &amp;gt; 1)
      &amp;lt;li class="sidebar-dropdown mb-2"&amp;gt;
        &amp;lt;input id="{{$group}}" class="toogle-group" type="checkbox" /&amp;gt;
        &amp;lt;label for="{{$group}}" data-toggle="dropdown" class="flex items-center font-normal text-white mb-4 text-base no-underline dim"&amp;gt;
            @if(method_exists($resources-&amp;gt;first(), 'icon'))
                {!! $resources-&amp;gt;first()::icon() !!}
            @endif
            {{ $group }}
            &amp;lt;svg class="text-gray-300 ml-auto h-5 w-5 transform group-hover:text-gray-400 transition-transform ease-in-out duration-150 focus:ring-indigo-500" viewBox="0 0 20 20" aria-hidden="true"&amp;gt;
                &amp;lt;path d="M6 6L14 10L6 14V6Z" fill="currentColor" /&amp;gt;
              &amp;lt;/svg&amp;gt;
        &amp;lt;/label&amp;gt;

        &amp;lt;ul class="dropdown-menu"&amp;gt;
          @foreach($resources as $resource)
          &amp;lt;li&amp;gt;
            &amp;lt;router-link :to="{
                name: 'index',
                params: {
                    resourceName: '{{ $resource::uriKey() }}'
                }
            }" class="flex items-center font-normal text-white mb-4 text-base no-underline dim"&amp;gt;

                &amp;lt;span class="sidebar-label"&amp;gt;{{ $resource::label() }}&amp;lt;/span&amp;gt;
            &amp;lt;/router-link&amp;gt;
          &amp;lt;/li&amp;gt;
          @endforeach
        &amp;lt;/ul&amp;gt;
      &amp;lt;/li&amp;gt;

      @else
        @foreach($resources as $resource)
        &amp;lt;li class="sidebar-dropdown"&amp;gt;
            &amp;lt;router-link :to="{
                name: 'index',
                params: {
                    resourceName: '{{ $resource::uriKey() }}'
                }
            }" class="flex items-center font-normal text-white mb-6 text-base no-underline dim"&amp;gt;
                @if(property_exists($resource, 'icon'))
                    {!! $resource::$icon !!}
                @elseif(method_exists($resource, 'icon'))
                    {!! $resource::icon() !!}
                @else
                &amp;lt;svg class="sidebar-icon" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 20 20"&amp;gt;
                    &amp;lt;path fill="var(--sidebar-icon)" d="M3 1h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2V3c0-1.1045695.8954305-2 2-2zm0 2v4h4V3h-4zM3 11h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2H3c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4H3zm10-2h4c1.1045695 0 2 .8954305 2 2v4c0 1.1045695-.8954305 2-2 2h-4c-1.1045695 0-2-.8954305-2-2v-4c0-1.1045695.8954305-2 2-2zm0 2v4h4v-4h-4z"
                    /&amp;gt;
                &amp;lt;/svg&amp;gt;
                @endif
                &amp;lt;span class="sidebar-label"&amp;gt;{{ $resource::label() }}&amp;lt;/span&amp;gt;
            &amp;lt;/router-link&amp;gt;
        &amp;lt;/li&amp;gt;
        @endforeach
      @endif
    @endforeach
&amp;lt;/ul&amp;gt;
@endif
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



</description>
      <category>laravel</category>
      <category>nova</category>
      <category>navigation</category>
    </item>
    <item>
      <title>Refactor davidwalsh's debounce function using ES6 arrow and more</title>
      <dc:creator>Monaye Win</dc:creator>
      <pubDate>Fri, 13 Mar 2020 05:58:47 +0000</pubDate>
      <link>https://dev.to/monaye/refactor-davidwalsh-s-debounce-function-5afc</link>
      <guid>https://dev.to/monaye/refactor-davidwalsh-s-debounce-function-5afc</guid>
      <description>&lt;p&gt;We all know Davidwalsh's debounce function. The post is from 2014 but even now many developers use this and most of the Youtube tutorials are based on this. &lt;br&gt;
If you are not familiar with Davidwalsh debounce function take a look at it here: &lt;br&gt;
&lt;a href="https://davidwalsh.name/javascript-debounce-function"&gt;https://davidwalsh.name/javascript-debounce-function&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When I looked at this, it didn't strike me. I have to bang my head many times to understand why he ended up writing the way it is. &lt;/p&gt;

&lt;p&gt;So I ended up refactoring the code using a new ES6 arrow function. &lt;/p&gt;

&lt;p&gt;Our brains are not made the same way, so some people may get my function better and others don't. Important thing is, you understand what you are writing and your team agrees.&lt;/p&gt;

&lt;p&gt;That being said. here we go&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const debounce = (func, delay) =&amp;gt; {
  let timerId; 
  return () =&amp;gt; {
    clearTimeout(timerId);
    timerId = setTimeout(func, delay); // start the timer
  };
};
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it??!! Yes! this is the bare minimum version of the debounce. It utilize the &lt;a href="https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures"&gt;closures&lt;/a&gt; to store the &lt;code&gt;timerId&lt;/code&gt; in the parent scope.&lt;br&gt;
You can try it on the sandbox here: &lt;a href="https://codesandbox.io/s/es6-debounce-example-llgu7?file=/src/index.js"&gt;https://codesandbox.io/s/es6-debounce-example-llgu7?file=/src/index.js&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Davidwalsh's debounce function has more features built in. &lt;br&gt;
Now, instead of adding all features to make the function complex, let's isolate the features, so we can better understand how each feature effects the function. At the end we combine both features into single function. &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;pass arguments to the function&lt;/li&gt;
&lt;li&gt;execute function immediately then delay&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;
  
  
  Argument Version
&lt;/h2&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const debounce = (func, delay) =&amp;gt; {
  let timerId; // keep track of current timer

  // return the function
  return (...args) =&amp;gt; {
    const boundFunc = func.bind(this, ...args);
    clearTimeout(timerId);
    timerId = setTimeout(boundFunc, delay); // start the timer
  };
};
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;This was easy to add. We just needed to bind the arguments to the function.&lt;br&gt;
&lt;a href="https://codesandbox.io/s/es6-debounce-arguments-example-2p4bp?file=/src/index.js"&gt;https://codesandbox.io/s/es6-debounce-arguments-example-2p4bp?file=/src/index.js&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Immediate Version
&lt;/h2&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const debounce = (func, delay) =&amp;gt; {
  let timerId;
  return () =&amp;gt; {
    if (!timerId) {
      func();
    }
    clearTimeout(timerId);
    timerId = setTimeout(() =&amp;gt; {
      timerId = null; 
    }, delay);
  };
};
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;As you can see, on the initial call, we execute the function immediately then set the timerId with the callback function that will null the timerId after the delay. &lt;br&gt;
Here is the immediate version of the sandbox: &lt;br&gt;
&lt;a href="https://codesandbox.io/s/es6-debounce-immediate-example-737vm?file=/src/index.js"&gt;https://codesandbox.io/s/es6-debounce-immediate-example-737vm?file=/src/index.js&lt;/a&gt;&lt;/p&gt;
&lt;h2&gt;
  
  
  Combined all
&lt;/h2&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const debounce = (func, delay, immediate) =&amp;gt; {
  let timerId;
  return (...args) =&amp;gt; {
    const boundFunc = func.bind(this, ...args);
    clearTimeout(timerId);
    if (immediate &amp;amp;&amp;amp; !timerId) {
      boundFunc();
    }
    const calleeFunc = immediate ? () =&amp;gt; { timerId = null } : boundFunc;
    timerId = setTimeout(calleeFunc, delay);
  }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;for the bonus, we can change this to throttle as well. Only differences is, timing of resetting the &lt;code&gt;timerId&lt;/code&gt;. For throttle, we don't &lt;code&gt;clearTimeout&lt;/code&gt;, we just &lt;code&gt;null&lt;/code&gt; the &lt;code&gt;timerId&lt;/code&gt; after the execution of the function.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const throttle = (func, delay, immediate) =&amp;gt; {
  let timerId;
  return (...args) =&amp;gt; {
    const boundFunc = func.bind(this, ...args);
    if (timerId) {
      return;
    }
    if (immediate &amp;amp;&amp;amp; !timerId) {
      boundFunc();
    }
    timerId = setTimeout(() =&amp;gt; {
      if(!immediate) {
        boundFunc(); 
      }
      timerId = null; // reset the timer so next call will be excuted
    }, delay);
  }
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://codesandbox.io/s/es6-throttle-example-2702s?file=/src/index.js"&gt;https://codesandbox.io/s/es6-throttle-example-2702s?file=/src/index.js&lt;/a&gt;&lt;/p&gt;

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