<?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: Amr Yousef</title>
    <description>The latest articles on DEV Community by Amr Yousef (@amrfarid140).</description>
    <link>https://dev.to/amrfarid140</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%2F148866%2F40d30347-53fb-4fb6-85a7-7dcf5dcdc2c8.jpeg</url>
      <title>DEV Community: Amr Yousef</title>
      <link>https://dev.to/amrfarid140</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/amrfarid140"/>
    <language>en</language>
    <item>
      <title>HTTP requests on Android using Ktor</title>
      <dc:creator>Amr Yousef</dc:creator>
      <pubDate>Fri, 03 May 2019 08:56:37 +0000</pubDate>
      <link>https://dev.to/amrfarid140/http-requests-on-android-using-ktor-38nd</link>
      <guid>https://dev.to/amrfarid140/http-requests-on-android-using-ktor-38nd</guid>
      <description>&lt;p&gt;&lt;strong&gt;This blog was originally posted on my website: &lt;a href="https://amryousef.me/android-ktor"&gt;https://amryousef.me/android-ktor&lt;/a&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--QtvahgAe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.amryousef.me/media/screen-shot-2019-05-02-at-17.08.32.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--QtvahgAe--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.amryousef.me/media/screen-shot-2019-05-02-at-17.08.32.png" alt="Ktor logo" title="Ktor Logo"&gt;&lt;/a&gt;&lt;br&gt;
Ktor is a new  framework for building asynchronous servers and clients. It's 100% Kotlin and runs on Coroutines. It supports multiplatform projects which means you can use it for any project targeting Android, iOS or Javascript. In this blog, we will explore using the Ktor client to make HTTP requests in an Android App.&lt;/p&gt;
&lt;h2&gt;
  
  
  Building the client
&lt;/h2&gt;

&lt;p&gt;Ktor client provides you with an interface to make HTTP requests, however, it relies on an engine to perform its duties. For Android, you can work with one of the following engines:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;CIO (Coroutine-based I/O) which has no additional dependencies and uses the power of coroutines to execute requests asynchronously. It's also the only engine compatible with Ktor WebSockets . &lt;strong&gt;Note: HTTP/2 is not supported.&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="c1"&gt;// in build.gradle add&lt;/span&gt;
&lt;span class="n"&gt;implementation&lt;/span&gt; &lt;span class="s"&gt;"io.ktor:ktor-client-cio:$ktor_version"&lt;/span&gt;
&lt;span class="c1"&gt;// in your code, create the client&lt;/span&gt;
&lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;CIO&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;ul&gt;
&lt;li&gt;Android which uses the usual HttpURLConnection and ThreadPool to execute requests.
&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="c1"&gt;// in build.gradle add&lt;/span&gt;
&lt;span class="n"&gt;implementation&lt;/span&gt; &lt;span class="s"&gt;"io.ktor:ktor-client-android:$ktor_version"&lt;/span&gt;
&lt;span class="c1"&gt;// in your code, create the client&lt;/span&gt;
&lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Android&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;


&lt;ul&gt;
&lt;li&gt;OkHttp which depends on Square's OkHttp client.
&lt;/li&gt;
&lt;/ul&gt;
&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="c1"&gt;// in build.gradle add&lt;/span&gt;
&lt;span class="n"&gt;implementation&lt;/span&gt; &lt;span class="s"&gt;"io.ktor:ktor-client-okhttp:$ktor_version"&lt;/span&gt;
&lt;span class="c1"&gt;// in your code, create the client&lt;/span&gt;
&lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Okhttp&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;

&lt;h2&gt;
  
  
  Configuring the client
&lt;/h2&gt;

&lt;p&gt;Configuring Ktor client is super simple. It relies on what's called &lt;code&gt;Features&lt;/code&gt;. All you need is to install the &lt;code&gt;Feature&lt;/code&gt; you want.&lt;br&gt;
For example to add json serialization/de-serialization capabilities using Gson. It becomes as easy as&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="c1"&gt;// You can replace CIO with your engine of choice&lt;/span&gt;
&lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;CIO&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;    
    &lt;span class="n"&gt;install&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;JsonFeature&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;        
        &lt;span class="n"&gt;serializer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;GsonSerializer&lt;/span&gt;&lt;span class="o"&gt;()&lt;/span&gt;    
    &lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Note:&lt;/strong&gt; You will need to include the following dependency&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight groovy"&gt;&lt;code&gt;&lt;span class="n"&gt;implementation&lt;/span&gt; &lt;span class="s2"&gt;"io.ktor:ktor-client-gson:$ktor_version"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h2&gt;
  
  
  Configuring All outbound requests
&lt;/h2&gt;

&lt;p&gt;Ktor HTTP client allows you to set some default configurations for all outbound requests. For example, adding a header to every request is as easy as&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="c1"&gt;// You can replace CIO with your engine of choice&lt;/span&gt;
&lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;CIO&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;    
    &lt;span class="n"&gt;install&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;DefaultRequest&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;headers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;append&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Accept"&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="s"&gt;"application/xml;q=0.9"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;headers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;append&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Authorization"&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;&lt;span class="s"&gt;"Bearer abc123"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;    
    &lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;h2&gt;
  
  
  Making Requests
&lt;/h2&gt;

&lt;p&gt;Finally, to make a request you can do&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;CIO&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;get&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;String&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;(&lt;/span&gt;&lt;span class="s"&gt;"https://eample.com"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;Here is a full example which call Github API to get a list of public repositories names&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="n"&gt;data&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nf"&gt;Repo&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;
&lt;span class="nd"&gt;@SerializedName&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"full_name"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="nl"&gt;name:&lt;/span&gt; &lt;span class="nc"&gt;String&lt;/span&gt;
&lt;span class="o"&gt;)&lt;/span&gt;

&lt;span class="nc"&gt;CoroutineScope&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;Dispatchers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;IO&lt;/span&gt;&lt;span class="o"&gt;).&lt;/span&gt;&lt;span class="na"&gt;launch&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;    
    &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;HttpClient&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="no"&gt;CIO&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;install&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;DefaultRequest&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;   
        &lt;span class="n"&gt;headers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;append&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Accept"&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"application/vnd.github.v3+json"&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;
    &lt;span class="n"&gt;install&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nc"&gt;JsonFeature&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;serializer&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;GsonSerializer&lt;/span&gt;&lt;span class="o"&gt;()&lt;/span&gt;
    &lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;    
&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;get&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;List&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Repo&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&amp;gt;(&lt;/span&gt;&lt;span class="s"&gt;"https://api.github.com/repositories"&lt;/span&gt;&lt;span class="o"&gt;).&lt;/span&gt;&lt;span class="na"&gt;forEach&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt; 
&lt;span class="n"&gt;repo&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="nc"&gt;Log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;v&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Ktor-Test"&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;repo&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;   
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;close&lt;/span&gt;&lt;span class="o"&gt;()&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



</description>
      <category>android</category>
      <category>kotlin</category>
      <category>ktor</category>
    </item>
    <item>
      <title>Custom Views Lifecycle and handling onMeasure()</title>
      <dc:creator>Amr Yousef</dc:creator>
      <pubDate>Tue, 16 Apr 2019 08:07:39 +0000</pubDate>
      <link>https://dev.to/amrfarid140/custom-views-lifecycle-and-handling-onmeasure-47b0</link>
      <guid>https://dev.to/amrfarid140/custom-views-lifecycle-and-handling-onmeasure-47b0</guid>
      <description>&lt;p&gt;This was originally posted on my &lt;a href="https://www.amryousef.me/custom-view-on-measure"&gt;blog&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;When building your own view, a custom view, there are some items you need to consider. First, let's introduce the lifecycle of a View.&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--6lLE8WZD--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.amryousef.me/media/android_view_lifecycle.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--6lLE8WZD--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://www.amryousef.me/media/android_view_lifecycle.png" alt="View lifecycle" title="View Life Cycle"&gt;&lt;/a&gt;&lt;br&gt;
&lt;em&gt;&lt;a href="https://codentrick.com/android-view-lifecycle/"&gt;Image origin&lt;/a&gt;&lt;/em&gt;&lt;br&gt;
The most important functions you need to worry about are- &lt;code&gt;onMeasure()&lt;/code&gt;- &lt;code&gt;onLayout()&lt;/code&gt;- &lt;code&gt;onDraw()&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  onMeasure
&lt;/h2&gt;

&lt;p&gt;onMeasure provides a way for you to negotiate the width and height of your view. &lt;br&gt;
If you don't override it, your view will behave the same way when &lt;code&gt;match_parent&lt;/code&gt; and &lt;code&gt;wrap_content&lt;/code&gt; is used to define it's size. Your view will also respect the values passed for height and width.&lt;br&gt;
If you choose to have more control on defining the size of the view then you probably need to override it and not call &lt;code&gt;super.onMeasure()&lt;/code&gt;. Instead you would want to call &lt;code&gt;setMeasuredDimension(width,height)&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Overriding onMeasure()
&lt;/h3&gt;

&lt;p&gt;When onMeasure is called you get &lt;code&gt;widthMeasureSpec&lt;/code&gt; and &lt;code&gt;heightMeasureSpec&lt;/code&gt;. This &lt;em&gt;Spec&lt;/em&gt; is a way for the parent view to inform you about the requested size and size mode for your view. A size mode is a constraint the parent view sets for its child. It's either- &lt;code&gt;UNSPECIFIED&lt;/code&gt; : The parent has not imposed any constraint on the child. It can be whatever size it wants.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;EXACTLY&lt;/code&gt; : The parent has determined an exact size for the child. The child is going to be given those bounds regardless of how big it wants to be.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;AT_MOST&lt;/code&gt; : The child can be as large as it wants up to the specified size.
With that in  mind, here's an example on how to implement &lt;code&gt;onMeasure()&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight"&gt;&lt;pre class="highlight java"&gt;&lt;code&gt;&lt;span class="n"&gt;override&lt;/span&gt; &lt;span class="n"&gt;fun&lt;/span&gt; &lt;span class="nf"&gt;onMeasure&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="nl"&gt;widthMeasureSpec:&lt;/span&gt; &lt;span class="nc"&gt;Int&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="nl"&gt;heightMeasureSpec:&lt;/span&gt; &lt;span class="nc"&gt;Int&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;requestedWidth&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getSize&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;widthMeasureSpec&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;        
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;requestedWidthMode&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getMode&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;widthMeasureSpec&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;requestedHeight&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getSize&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;heightMeasureSpec&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;        
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;requestedHeightMode&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;getMode&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;heightMeasureSpec&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="nl"&gt;desiredWidth:&lt;/span&gt; &lt;span class="nc"&gt;Int&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="c1"&gt;//TODO("Define your desired width")        &lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="nl"&gt;desiredHeight:&lt;/span&gt; &lt;span class="nc"&gt;Int&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="c1"&gt;//TODO("Define your desired height")&lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;width&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;when&lt;/span&gt; &lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedWidthMode&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;            
               &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;EXACTLY&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;requestedWidth&lt;/span&gt;                        
               &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;UNSPECIFIED&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;desiredWidth&lt;/span&gt;
               &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="nc"&gt;Math&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;min&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedWidth&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;desiredWidth&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;        
        &lt;span class="o"&gt;}&lt;/span&gt;
        &lt;span class="n"&gt;val&lt;/span&gt; &lt;span class="n"&gt;height&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;when&lt;/span&gt; &lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedHeightMode&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt; &lt;span class="o"&gt;{&lt;/span&gt;            
                &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;EXACTLY&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;requestedHeight&lt;/span&gt; 
                &lt;span class="nc"&gt;MeasureSpec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;UNSPECIFIED&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;desiredHeight&lt;/span&gt;
                &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="o"&gt;-&amp;gt;&lt;/span&gt; &lt;span class="nc"&gt;Math&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="na"&gt;min&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedHeight&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;desiredHeight&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;        
        &lt;span class="o"&gt;}&lt;/span&gt;
        &lt;span class="n"&gt;setMeasuredDimension&lt;/span&gt;&lt;span class="o"&gt;(&lt;/span&gt;&lt;span class="n"&gt;width&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt; &lt;span class="n"&gt;height&lt;/span&gt;&lt;span class="o"&gt;)&lt;/span&gt;
&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;



&lt;p&gt;This is setting the size to the requested size if the mode is &lt;code&gt;EXACTLY&lt;/code&gt; as we have to respect the parent's requested mode. If the mode is &lt;code&gt;UNSPECIFIED&lt;/code&gt; then we are free to use whatever size we want, which is usually the case with &lt;code&gt;wrap_content&lt;/code&gt;. If the mode is &lt;code&gt;AT_MOST&lt;/code&gt; then we compare &lt;code&gt;desired&lt;/code&gt; and &lt;code&gt;requested&lt;/code&gt; sizes and use the lowest of value.&lt;/p&gt;

&lt;h2&gt;
  
  
  onLayout
&lt;/h2&gt;

&lt;p&gt;The parent uses &lt;code&gt;onLayout()&lt;/code&gt; to notify your view of its position. You get to know if the position has changed and left, top, right and bottom position of your view. You should use to calculate your drawing width and height.&lt;br&gt;
Remember that what happens in &lt;code&gt;onMeasure()&lt;/code&gt; affects the positions you will get from your parent. You should always calculate your drawing size here before proceeding to draw your view.&lt;/p&gt;

&lt;h2&gt;
  
  
  onDraw
&lt;/h2&gt;

&lt;p&gt;This is where all the drawing happens. It's as simple as you get an instance of &lt;code&gt;Canvas&lt;/code&gt; object and you are free to draw what you want.&lt;/p&gt;

&lt;h2&gt;
  
  
  Performance considerations
&lt;/h2&gt;

&lt;p&gt;Your &lt;code&gt;onDraw()&lt;/code&gt; implementation should be efficient. You should avoid any long loops or creating new instances. Google's official documentation says "your app should render frames in under 16ms to achieve 60 frames per second".&lt;br&gt;
Checkout &lt;a href="https://developer.android.com/topic/performance/vitals/render.html"&gt;this piece of documentation&lt;/a&gt; to know more on tackling slow rendering.&lt;/p&gt;

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