DEV Community

Cover image for Write less with Intellij Live Templates
Mahendran
Mahendran

Posted on • Originally published at mahendranv.github.io on

Write less with Intellij Live Templates

LiveTemplate is a feature in Intellij based IDEs where you can expand a code snippet by typing an abbreviation and the IDE guide your cursor through the parts that need your attention (a variable name).

Intellij has a complete set of live templates at your disposal. Few of them you might’ve been using it in day-to-day basis. Check this list blow.

  1. sout
  2. logi
  3. soutf
  4. soutm
  5. appNs
  6. psvm and goes on…

If you haven’t used them before, for items 1-4 open a kotlin file ⇨ type the abbreviation and press tab to expand.

Within five minutes, you can also write a template.


Know your template

Template is special kind of macro that allows you to enter your input in between / place cursor for you. It is located in Preferences ⇨ Editor ⇨ Live templates section. Let’s have a look at soutf and analyze what cooks the live template.


// soutf : Prints current class and function name to System.out

println("$CLASS$.$METHOD$")

Enter fullscreen mode Exit fullscreen mode

It’s just a one-liner where class and method wrapped inside $. IDE reads thesee variables and fill in when expanding it.


Cursor context

One major thing to design a better template is Cursor context. It tells the IDE, when is a Live template is applicable. Expanding a kotlin code inside a xml file is totally useless.

For soutf, the context is set to work inside Kotlin files, and it can expand inside a function. Try to expand it outside a function. Check the below templates to know various contexts.

abbreviation scope
main top-level
sout statement
fun0 class
ifn expression

The Best way understand the scope is to expand all these templates in their destined place in code. That’s all about the context, on to the fun part where we edit the sout template.


Placing cursor in template

The sout template is great, it autofills classname and function name for us. But it places cursor outside the quotes after expanding it. Let’s fix it. Add an $END$ to the template and try it now.


println("$CLASS$.$METHOD$ $END$")

Enter fullscreen mode Exit fullscreen mode

That’s a bit about scopes and cursor. Let’s create our live template for LiveData.


What is LiveData?

An android class that connects UI to the Presenter/VieweModel.

If you’re not familiar with LiveData, think of it as an Observable. Any consumer class can attach to it and get updates when the underlying value change. It has two variants, LiveData(observe only model) and MutableLiveData(Superset of LiveData — where you can publish values).

Let me draw out the target code and inline why each line is needed.


    // A mutable backing property which is set to private.
    private val _email = MutableLiveData<String>()

    // Frontface to field, the observers will be able to read
    // but, cannot modify
    val emailLiveData : LiveData<String> = _email

    // Syntactic sugar — to validate the data in later part 
    // of the application — use this
    private val email: String?
            get() = emailLiveData.value

    // A setter method that updates our mutable property
    // write code to trigger validation in here. This is why
    // we don't expose the mutable version of livedata outside.
    fun updateEmail(value: String?) {
      _email.value = value
      // start your validation flow here
    }

Enter fullscreen mode Exit fullscreen mode

Scanning though the live template window in IDE, you might’ve already figured out how to duplicate/create new live template. Ours will be called ld. I’ll use the same name going further. Notice that ld is scoped to Kotlin — Class.

Live Template for LiveData


Placeholders

In sout, we didn’t need user input on anything as cursor context can give us the function and class names. That’s not the case with ld (LD), here we need two inputs from the user. Property name $PROP_NAME$ and Type $PROP_TYPE$ — rest can be filled by live template.


private val _$PROP_NAME$ = MutableLiveData<$PROP_TYPE$>()
val $PROP_NAME$LiveData : LiveData<$PROP_TYPE$> = _$PROP_NAME$
private val $PROP_NAME$: $PROP_TYPE$?
        get() = $PROP_NAME$LiveData.value

fun update$PROP_NAME_IN_FUNCTION$(value: $PROP_TYPE$?) {
  _$PROP_NAME$.value = value
}

Enter fullscreen mode Exit fullscreen mode

By mentioning these placeholders in different places, we tell the IDE to fill-in the variable wherever we it inside the template. So, when you type email for the PROP_NAME, it is filled in for LiveData, MutableLiveData, in the field so on. Same for PROP_TYPE.

We have another placeholder called PROP_NAME_IN_FUNCTION, which is a capitalized version of our PROP_NAME. So, that’s about template content, now we have to tell the IDE, what each placeholder is.

Click on Edit Variables and input the values as in below table.

Name Expression
PROP_NAME
PROP_TYPE className()
PROP_NAME_IN_FUNCTION capitalize(PROP_NAME)

The property name is left to our choice, there is not much IDE can do about it. When filling in PROP_TYPE, IDE will suggest classes. And PROP_NAME_IN_FUNCTION is a derived property that capitalizes the PROP_NAME(email ⇨ Email). Now we have a live template setup for future use. Create as many as you want and focus on what matters the most.

Happy coding ⌨️.

Top comments (0)